From 6532fdd00288356d5a0f96cf3a46226ffbf40bd9 Mon Sep 17 00:00:00 2001 From: jespergravgaard Date: Thu, 28 Dec 2017 00:17:39 +0100 Subject: [PATCH] Added array length mismatch error in Pass1. --- .../java/dk/camelot64/kickc/Compiler.java | 1 + .../kickc/passes/Pass1AssertArrayLengths.java | 47 +++++++++++++++++++ .../dk/camelot64/kickc/test/TestPrograms.java | 8 ++++ .../kickc/test/array-length-mismatch.kc | 3 ++ .../kickc/test/string-length-mismatch.kc | 3 ++ 5 files changed, 62 insertions(+) create mode 100644 src/main/java/dk/camelot64/kickc/passes/Pass1AssertArrayLengths.java create mode 100644 src/main/java/dk/camelot64/kickc/test/array-length-mismatch.kc create mode 100644 src/main/java/dk/camelot64/kickc/test/string-length-mismatch.kc diff --git a/src/main/java/dk/camelot64/kickc/Compiler.java b/src/main/java/dk/camelot64/kickc/Compiler.java index 594218b1c..381595633 100644 --- a/src/main/java/dk/camelot64/kickc/Compiler.java +++ b/src/main/java/dk/camelot64/kickc/Compiler.java @@ -116,6 +116,7 @@ public class Compiler { new Pass1FixLValuesLoHi(program).execute(); new Pass1AssertNoLValueIntermediate(program).execute(); new Pass1AddTypePromotions(program).execute(); + new Pass1AssertArrayLengths(program).execute(); getLog().append("INITIAL CONTROL FLOW GRAPH"); getLog().append(program.getGraph().toString(program)); diff --git a/src/main/java/dk/camelot64/kickc/passes/Pass1AssertArrayLengths.java b/src/main/java/dk/camelot64/kickc/passes/Pass1AssertArrayLengths.java new file mode 100644 index 000000000..42f23bcf9 --- /dev/null +++ b/src/main/java/dk/camelot64/kickc/passes/Pass1AssertArrayLengths.java @@ -0,0 +1,47 @@ +package dk.camelot64.kickc.passes; + +import dk.camelot64.kickc.model.*; + +/** + * Asserts that all arrays with lengths and initializers have matching lengths. + */ +public class Pass1AssertArrayLengths extends Pass1Base { + + public Pass1AssertArrayLengths(Program program) { + super(program); + } + + @Override + public boolean step() { + for(ControlFlowBlock block : getGraph().getAllBlocks()) { + for(Statement statement : block.getStatements()) { + if(statement instanceof StatementAssignment) { + StatementAssignment assignment = (StatementAssignment) statement; + LValue lValue = assignment.getlValue(); + if(lValue instanceof VariableRef) { + Variable variable = getScope().getVariable((VariableRef) lValue); + if(variable.getType() instanceof SymbolTypeArray) { + Integer declaredSize = ((SymbolTypeArray) variable.getType()).getSize(); + if(declaredSize != null) { + if(assignment.getrValue1() == null && assignment.getOperator() == null) { + RValue value = assignment.getrValue2(); + if(value instanceof ValueList) { + if(((ValueList) value).getList().size()!=declaredSize) { + throw new CompileError("Error! Array length mismatch "+statement.toString(getProgram(), false)); + } + } else if(value instanceof ConstantString) { + if(((ConstantString) value).getValue().length()!=declaredSize) { + throw new CompileError("Error! Array length mismatch "+statement.toString(getProgram(), false)); + } + } + } + } + } + } + } + } + } + return false; + } + +} diff --git a/src/main/java/dk/camelot64/kickc/test/TestPrograms.java b/src/main/java/dk/camelot64/kickc/test/TestPrograms.java index 9f08cf848..2aaf3eb49 100644 --- a/src/main/java/dk/camelot64/kickc/test/TestPrograms.java +++ b/src/main/java/dk/camelot64/kickc/test/TestPrograms.java @@ -351,6 +351,14 @@ public class TestPrograms extends TestCase { assertError("array-uninitialized", "Cannot determine array size."); } + public void testArrayLengthMismatch() throws IOException, URISyntaxException { + assertError("array-length-mismatch", "Array length mismatch"); + } + + public void testStringLengthMismatch() throws IOException, URISyntaxException { + assertError("string-length-mismatch", "Array length mismatch"); + } + private void assertError(String kcFile, String expectError) throws IOException, URISyntaxException { try { compileAndCompare(kcFile); diff --git a/src/main/java/dk/camelot64/kickc/test/array-length-mismatch.kc b/src/main/java/dk/camelot64/kickc/test/array-length-mismatch.kc new file mode 100644 index 000000000..5fb4b39c2 --- /dev/null +++ b/src/main/java/dk/camelot64/kickc/test/array-length-mismatch.kc @@ -0,0 +1,3 @@ +byte[3] b = { 1, 2 }; + +void main() {} \ No newline at end of file diff --git a/src/main/java/dk/camelot64/kickc/test/string-length-mismatch.kc b/src/main/java/dk/camelot64/kickc/test/string-length-mismatch.kc new file mode 100644 index 000000000..bbc6a0943 --- /dev/null +++ b/src/main/java/dk/camelot64/kickc/test/string-length-mismatch.kc @@ -0,0 +1,3 @@ +byte[3] b = "qwe!"; + +void main() {} \ No newline at end of file