public function passStatementBlock(array $statements)
{
foreach ($statements as $statement) {
switch ($statement['type']) {
case 'let':
$this->passLetStatement($statement);
break;
case 'echo':
if (isset($statement['expressions'])) {
foreach ($statement['expressions'] as $expr) {
$this->passExpression($expr);
}
}
break;
case 'declare':
$this->declareVariables($statement);
break;
case 'if':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
if (isset($statement['statements'])) {
$this->passStatementBlock($statement['statements']);
}
if (isset($statement['else_statements'])) {
$this->passStatementBlock($statement['else_statements']);
}
break;
case 'switch':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
if (isset($statement['clauses'])) {
foreach ($statement['clauses'] as $clause) {
if (isset($clause['expr'])) {
$this->passExpression($clause['expr']);
}
if (isset($clause['statements'])) {
$this->passStatementBlock($clause['statements']);
}
}
}
break;
case 'while':
case 'do-while':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
if (isset($statement['statements'])) {
$this->passStatementBlock($statement['statements']);
}
break;
case 'for':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
if (isset($statement['value'])) {
$this->markLastUse($statement['value'], $statement);
$this->markVariableNoLocal($statement['value']);
$this->increaseMutations($statement['value']);
}
if (isset($statement['key'])) {
$this->markLastUse($statement['key'], $statement);
$this->markVariableNoLocal($statement['key']);
$this->increaseMutations($statement['key']);
}
if (isset($statement['statements'])) {
$this->passStatementBlock($statement['statements']);
}
break;
case 'return':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
break;
case 'loop':
if (isset($statement['statements'])) {
$this->passStatementBlock($statement['statements']);
}
break;
case 'try-catch':
if (isset($statement['statements'])) {
$this->passStatementBlock($statement['statements']);
}
if (isset($statement['catches'])) {
foreach ($statement['catches'] as $catch) {
if (isset($catch['variable'])) {
$this->markVariableNoLocal($catch['variable']['value']);
$this->increaseMutations($catch['variable']['value']);
}
if (isset($catch['statements'])) {
$this->passStatementBlock($catch['statements']);
}
}
}
break;
case 'throw':
if (isset($statement['expr'])) {
$this->passExpression($statement['expr']);
}
$this->lastCallLine = $statement['line'];
break;
case 'fetch':
$this->passExpression($statement['expr']);
break;
case 'mcall':
case 'scall':
case 'fcall':
case 'require':
if ($statement['expr']['type'] == 'mcall') {
if (isset($statement['expr']['variable'])) {
if ($statement['expr']['variable']['type'] == 'variable') {
$this->markVariableNoLocal($statement['expr']['variable']['value']);
}
}
}
$this->passCall($statement['expr']);
$this->lastCallLine = $statement['line'];
break;
case 'unset':
if ($statement['expr']['type'] == "array-access") {
if ($statement['expr']['left']['type'] == 'variable') {
$this->markVariableNoLocal($statement['expr']['left']['value']);
$this->increaseMutations($statement['expr']['left']['value']);
}
} else {
if ($statement['expr']['type'] == "list") {
if ($statement['expr']['left']['type'] == 'array-access') {
if ($statement['expr']['left']['left']['type'] == 'variable') {
$this->markVariableNoLocal($statement['expr']['left']['left']['value']);
$this->increaseMutations($statement['expr']['left']['left']['value']);
}
}
}
}
$this->lastUnsetLine = $statement['line'];
break;
case 'break':
case 'continue':
case 'empty':
case 'cblock':
case 'comment':
break;
default:
echo 'Statement=', $statement['type'], PHP_EOL;
}
}
}