patchIfBlock method
Patches up all the branches for a single open if block. That includes the last "else" block, as well as one or more "end if" jumps.
Implementation
void patchIfBlock(bool singleLineIf) {
ValNumber target = ValNumber(code.length.toDouble());
int idx = backpatches.length - 1;
while (idx >= 0) {
BackPatch bp = backpatches[idx];
if (bp.waitingFor == "if:MARK") {
// There's the special marker that indicates the true start of this if block.
backpatches.removeAt(idx);
return;
} else if (bp.waitingFor == "end if" || bp.waitingFor == "else") {
code[bp.lineNum].rhsA = target;
backpatches.removeAt(idx);
} else if (backpatches[idx].waitingFor == "break") {
// Not the expected keyword, but "break"; this is always OK.
} else {
// Not the expected patch, and not "break"; we have a mismatched block start/end.
String msg;
if (singleLineIf) {
if (bp.waitingFor == "end for" || bp.waitingFor == "end while") {
msg = "loop is invalid within single-line 'if'";
} else {
msg = "invalid control structure within single-line 'if'";
}
} else {
msg = "'end if' without matching 'if'";
}
throw CompilerException(msg);
}
idx--;
}
// If we get here, we never found the expected if:MARK. That's an error.
throw CompilerException("'end if' without matching 'if'");
}