diff --git a/src/main/java/dk/camelot64/kickc/Compiler.java b/src/main/java/dk/camelot64/kickc/Compiler.java index 1ec80b3d6..317c50605 100644 --- a/src/main/java/dk/camelot64/kickc/Compiler.java +++ b/src/main/java/dk/camelot64/kickc/Compiler.java @@ -18,7 +18,6 @@ import java.io.File; import java.nio.file.Path; import java.util.ArrayList; import java.util.List; -import java.util.Locale; import java.util.Map; /** @@ -277,6 +276,7 @@ public class Compiler { new PassNAddTypeConversionAssignment(program, true).execute(); new Pass1EarlyConstantIdentification(program).execute(); + // new Pass1AsmUsesHandling(program).execute(); new PassNAssertConstantModification(program).execute(); new PassNAssertTypeDeref(program).check(); diff --git a/src/main/java/dk/camelot64/kickc/passes/Pass1AddressOfHandling.java b/src/main/java/dk/camelot64/kickc/passes/Pass1AddressOfHandling.java index 16ef3d7ac..514dbf8b4 100644 --- a/src/main/java/dk/camelot64/kickc/passes/Pass1AddressOfHandling.java +++ b/src/main/java/dk/camelot64/kickc/passes/Pass1AddressOfHandling.java @@ -8,7 +8,10 @@ import dk.camelot64.kickc.model.operators.Operators; import dk.camelot64.kickc.model.symbols.Symbol; import dk.camelot64.kickc.model.symbols.Variable; import dk.camelot64.kickc.model.types.SymbolTypeStruct; -import dk.camelot64.kickc.model.values.*; +import dk.camelot64.kickc.model.values.ConstantSymbolPointer; +import dk.camelot64.kickc.model.values.RValue; +import dk.camelot64.kickc.model.values.SymbolVariableRef; +import dk.camelot64.kickc.model.values.Value; /** * Update variables properly if address-of is used @@ -21,6 +24,7 @@ public class Pass1AddressOfHandling extends Pass2SsaOptimization { @Override public boolean step() { + // Expressions using & operator ProgramExpressionIterator.execute(getProgram(), (programExpression, currentStmt, stmtIt, currentBlock) -> { if(Operators.ADDRESS_OF.equals(programExpression.getOperator())) { RValue rValue = ((ProgramExpressionUnary) programExpression).getOperand(); @@ -36,13 +40,16 @@ public class Pass1AddressOfHandling extends Pass2SsaOptimization { }); ProgramValueIterator.execute(getProgram(), (programValue, currentStmt, stmtIt, currentBlock) -> { if(programValue.get() instanceof ConstantSymbolPointer) { + // Values containing constant pointers Value value = ((ConstantSymbolPointer) programValue.get()).getToSymbol(); if(value instanceof SymbolVariableRef) { Symbol toSymbol = getScope().getSymbol((SymbolVariableRef) value); if(toSymbol instanceof Variable) { final Variable variable = (Variable) toSymbol; - final String stmtStr = currentStmt==null?toSymbol.toString(getProgram()):currentStmt.toString(getProgram(), false); - updateAddressOfVariable(variable, stmtStr); + if(!variable.isNoModify() && !variable.isVolatile()) { + final String stmtStr = currentStmt == null ? toSymbol.toString(getProgram()) : currentStmt.toString(getProgram(), false); + updateAddressOfVariable(variable, stmtStr); + } } } } @@ -54,10 +61,12 @@ public class Pass1AddressOfHandling extends Pass2SsaOptimization { if(variable.getType() instanceof SymbolTypeStruct) { variable.setKind(Variable.Kind.LOAD_STORE); getLog().append("Setting struct to load/store in variable affected by address-of " + stmtStr); + //getLog().append("Setting struct to load/store in variable affected by address-of: " + variable.toString() + " in " + stmtStr); } else { variable.setKind(Variable.Kind.LOAD_STORE); variable.setVolatile(true); getLog().append("Setting inferred volatile on symbol affected by address-of " + stmtStr); + //getLog().append("Setting inferred volatile on symbol affected by address-of: " + variable.toString() + " in " + stmtStr); } } diff --git a/src/main/java/dk/camelot64/kickc/passes/Pass1AsmUsesHandling.java b/src/main/java/dk/camelot64/kickc/passes/Pass1AsmUsesHandling.java new file mode 100644 index 000000000..be1c8f65f --- /dev/null +++ b/src/main/java/dk/camelot64/kickc/passes/Pass1AsmUsesHandling.java @@ -0,0 +1,51 @@ +package dk.camelot64.kickc.passes; + +import dk.camelot64.kickc.model.Program; +import dk.camelot64.kickc.model.iterator.ProgramValue; +import dk.camelot64.kickc.model.iterator.ProgramValueIterator; +import dk.camelot64.kickc.model.symbols.Variable; +import dk.camelot64.kickc.model.types.SymbolTypeStruct; +import dk.camelot64.kickc.model.values.SymbolVariableRef; +import dk.camelot64.kickc.model.values.Value; + +/** + * Update variables properly if address-of is used + */ +public class Pass1AsmUsesHandling extends Pass2SsaOptimization { + + public Pass1AsmUsesHandling(Program program) { + super(program); + } + + @Override + public boolean step() { + + ProgramValueIterator.execute(getProgram(), (programValue, currentStmt, stmtIt, currentBlock) -> { + if(programValue instanceof ProgramValue.ProgramValueAsmReferenced || programValue instanceof ProgramValue.KickAsmUses || programValue instanceof ProgramValue.ProgramValueConstantArrayKickAsmUses) { + // Symbol used in inline ASM or KickAsm + final Value value = programValue.get(); + if(value instanceof SymbolVariableRef) { + Variable variable = getScope().getVariable((SymbolVariableRef) value); + if(!variable.isKindConstant() && !variable.isVolatile()) { + final String stmtStr = currentStmt == null ? value.toString(getProgram()) : currentStmt.toString(getProgram(), false); + updateAddressOfVariable(variable, stmtStr); + } + } + } + }); + return false; + } + + private void updateAddressOfVariable(Variable variable, String stmtStr) { + if(variable.getType() instanceof SymbolTypeStruct) { + variable.setKind(Variable.Kind.LOAD_STORE); + getLog().append("Setting struct to load/store in variable affected by address-of: " + variable.toString() + " in " + stmtStr); + } else { + variable.setKind(Variable.Kind.LOAD_STORE); + variable.setVolatile(true); + getLog().append("Setting inferred volatile on symbol affected by address-of: " + variable.toString() + " in " + stmtStr); + } + } + + +} diff --git a/src/test/ref/hex2dec-ptrptr.log b/src/test/ref/hex2dec-ptrptr.log index eb385aed1..664976182 100644 --- a/src/test/ref/hex2dec-ptrptr.log +++ b/src/test/ref/hex2dec-ptrptr.log @@ -1,7 +1,4 @@ Setting inferred volatile on symbol affected by address-of utoa16w::$2 = call utoa16n utoa16w::$1 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$5 = call utoa16n utoa16w::$4 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$8 = call utoa16n utoa16w::$7 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$11 = call utoa16n utoa16w::$10 &utoa16w::dst 1 CONTROL FLOW GRAPH SSA diff --git a/src/test/ref/hex2dec.log b/src/test/ref/hex2dec.log index 20f91448b..e1102a876 100644 --- a/src/test/ref/hex2dec.log +++ b/src/test/ref/hex2dec.log @@ -1,7 +1,4 @@ Setting inferred volatile on symbol affected by address-of utoa16w::$2 = call utoa16n utoa16w::$1 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$5 = call utoa16n utoa16w::$4 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$8 = call utoa16n utoa16w::$7 &utoa16w::dst utoa16w::started -Setting inferred volatile on symbol affected by address-of utoa16w::$11 = call utoa16n utoa16w::$10 &utoa16w::dst 1 CONTROL FLOW GRAPH SSA diff --git a/src/test/ref/pointer-pointer-3.log b/src/test/ref/pointer-pointer-3.log index 9c3fbd0a6..61e9b69a6 100644 --- a/src/test/ref/pointer-pointer-3.log +++ b/src/test/ref/pointer-pointer-3.log @@ -1,5 +1,4 @@ Setting inferred volatile on symbol affected by address-of main::$0 = call setscreen &screen screen1 -Setting inferred volatile on symbol affected by address-of main::$1 = call setscreen &screen screen2 Inlined call call __init CONTROL FLOW GRAPH SSA diff --git a/src/test/ref/ptrptr-optimize-2.log b/src/test/ref/ptrptr-optimize-2.log index d453b28e7..9f5e56294 100644 --- a/src/test/ref/ptrptr-optimize-2.log +++ b/src/test/ref/ptrptr-optimize-2.log @@ -1,5 +1,4 @@ Setting inferred volatile on symbol affected by address-of main::$0 = call sub 'a' &main::screen -Setting inferred volatile on symbol affected by address-of main::$1 = call sub 'b' &main::screen CONTROL FLOW GRAPH SSA diff --git a/src/test/ref/sizeof-expr.log b/src/test/ref/sizeof-expr.log index c152efe23..93070d1bd 100644 --- a/src/test/ref/sizeof-expr.log +++ b/src/test/ref/sizeof-expr.log @@ -1,4 +1,3 @@ -Setting inferred volatile on symbol affected by address-of main::wp = &main::w Resolving sizeof() main::$2 = sizeof main::idx Resolving sizeof() main::$4 = sizeof main::b Resolving sizeof() main::$7 = sizeof main::$6 diff --git a/src/test/ref/struct-ptr-12.log b/src/test/ref/struct-ptr-12.log index 2d686c2cd..4fccf7e8c 100644 --- a/src/test/ref/struct-ptr-12.log +++ b/src/test/ref/struct-ptr-12.log @@ -1,4 +1,3 @@ -Setting struct to load/store in variable affected by address-of main::q = &main::p CONTROL FLOW GRAPH SSA diff --git a/src/test/ref/struct-ptr-14.log b/src/test/ref/struct-ptr-14.log index 600f79348..8ecfab8da 100644 --- a/src/test/ref/struct-ptr-14.log +++ b/src/test/ref/struct-ptr-14.log @@ -1,4 +1,3 @@ -Setting struct to load/store in variable affected by address-of main::q = &main::p CONTROL FLOW GRAPH SSA