1
0
mirror of https://gitlab.com/camelot/kickc.git synced 2024-11-07 23:07:29 +00:00

Merge branch 'master' into address_with_expression_value

This commit is contained in:
Andrzej Sliwa 2020-12-10 18:37:56 +01:00
commit 6116709c7e
3 changed files with 26 additions and 4 deletions

View File

@ -6,6 +6,8 @@ import dk.camelot64.kickc.model.Program;
import dk.camelot64.kickc.model.statements.Statement; import dk.camelot64.kickc.model.statements.Statement;
import dk.camelot64.kickc.model.statements.StatementCall; import dk.camelot64.kickc.model.statements.StatementCall;
import dk.camelot64.kickc.model.symbols.Procedure; import dk.camelot64.kickc.model.symbols.Procedure;
import dk.camelot64.kickc.model.symbols.Scope;
import dk.camelot64.kickc.model.symbols.Symbol;
/** /**
* Updates procedure calls to point to the actual procedure called. * Updates procedure calls to point to the actual procedure called.
@ -23,10 +25,13 @@ public class Pass1Procedures extends Pass2SsaOptimization {
if(statement instanceof StatementCall) { if(statement instanceof StatementCall) {
StatementCall call = (StatementCall) statement; StatementCall call = (StatementCall) statement;
String procedureName = call.getProcedureName(); String procedureName = call.getProcedureName();
Procedure procedure = getScope().getLocalProcedure(procedureName); Scope localScope = (Scope) getScope().getSymbol(block.getScope());
if(procedure == null) { final Symbol procedureSymbol = localScope.findSymbol(procedureName);
throw new CompileError("Called procedure not found. " + call.toString(getProgram(), false), statement.getSource()); if(procedureSymbol == null)
} throw new CompileError("Called procedure not found. " + procedureName, statement.getSource());
if(!(procedureSymbol instanceof Procedure))
throw new CompileError("Called symbol is not a procedure. " + procedureSymbol.toString(), statement.getSource());
Procedure procedure = (Procedure) procedureSymbol;
call.setProcedure(procedure.getRef()); call.setProcedure(procedure.getRef());
if(procedure.isVariableLengthParameterList() && procedure.getParameters().size() > call.getParameters().size()) { if(procedure.isVariableLengthParameterList() && procedure.getParameters().size() > call.getParameters().size()) {
throw new CompileError("Wrong number of parameters in call. Expected " + procedure.getParameters().size() + " or more. " + statement.toString(), statement.getSource()); throw new CompileError("Wrong number of parameters in call. Expected " + procedure.getParameters().size() + " or more. " + statement.toString(), statement.getSource());

View File

@ -42,6 +42,11 @@ public class TestPrograms {
public TestPrograms() { public TestPrograms() {
} }
@Test
public void testLocalVarShadowingProcedure() throws IOException, URISyntaxException {
assertError("local-var-shadowing-procedure.c", "Called symbol is not a procedure. main::doit");
}
@Test @Test
public void testAdventOfCode04() throws IOException, URISyntaxException { public void testAdventOfCode04() throws IOException, URISyntaxException {
compileAndCompare("adventofcode/2020-04.c"); compileAndCompare("adventofcode/2020-04.c");

View File

@ -0,0 +1,12 @@
// Demonstrate that local variable shadowing a global procedure causes an error
void main() {
char doit = 7;
doit();
}
char * const SCREEN = 0x0400;
void doit() {
SCREEN[0] = '*';
}