diff --git a/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValue.java b/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValue.java index 44f25436f..16e4dc247 100644 --- a/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValue.java +++ b/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValue.java @@ -410,7 +410,7 @@ public interface ProgramValue { @Override public void set(Value value) { - statementAsm.getReferenced().put(label, (SymbolVariableRef) value); + statementAsm.getReferenced().put(label, (SymbolRef) value); } } diff --git a/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValueIterator.java b/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValueIterator.java index e1d38aecd..3164722b7 100644 --- a/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValueIterator.java +++ b/src/main/java/dk/camelot64/kickc/model/iterator/ProgramValueIterator.java @@ -151,7 +151,7 @@ public class ProgramValueIterator { } } else if(statement instanceof StatementAsm) { StatementAsm statementAsm = (StatementAsm) statement; - Map referenced = statementAsm.getReferenced(); + Map referenced = statementAsm.getReferenced(); for(String label : referenced.keySet()) { execute(new ProgramValue.ProgramValueAsmReferenced(statementAsm, label), handler, statement, statementsIt, block); } diff --git a/src/main/java/dk/camelot64/kickc/model/statements/StatementAsm.java b/src/main/java/dk/camelot64/kickc/model/statements/StatementAsm.java index 71b4c731b..aec9d66e5 100644 --- a/src/main/java/dk/camelot64/kickc/model/statements/StatementAsm.java +++ b/src/main/java/dk/camelot64/kickc/model/statements/StatementAsm.java @@ -4,6 +4,7 @@ import dk.camelot64.kickc.AsmParser; import dk.camelot64.kickc.asm.AsmClobber; import dk.camelot64.kickc.model.Comment; import dk.camelot64.kickc.model.Program; +import dk.camelot64.kickc.model.values.SymbolRef; import dk.camelot64.kickc.model.values.SymbolVariableRef; import dk.camelot64.kickc.parser.KickCParser; @@ -20,12 +21,12 @@ public class StatementAsm extends StatementBase { private transient KickCParser.AsmLinesContext asmLines; /** All variables/constants referenced in the inline assembler. */ - private Map referenced; + private Map referenced; /** Declared clobber for the inline ASM. */ private AsmClobber declaredClobber; - public StatementAsm(String asmBody, Map referenced, AsmClobber declaredClobber, StatementSource source, List comments) { + public StatementAsm(String asmBody, Map referenced, AsmClobber declaredClobber, StatementSource source, List comments) { super(null, source, comments); this.asmBody = asmBody; this.referenced = referenced; @@ -54,11 +55,11 @@ public class StatementAsm extends StatementBase { return asmLines; } - public void setReferenced(Map referenced) { + public void setReferenced(Map referenced) { this.referenced = referenced; } - public Map getReferenced() { + public Map getReferenced() { return referenced; } diff --git a/src/main/java/dk/camelot64/kickc/passes/Pass0GenerateStatementSequence.java b/src/main/java/dk/camelot64/kickc/passes/Pass0GenerateStatementSequence.java index e9bcb271e..6386f39f0 100644 --- a/src/main/java/dk/camelot64/kickc/passes/Pass0GenerateStatementSequence.java +++ b/src/main/java/dk/camelot64/kickc/passes/Pass0GenerateStatementSequence.java @@ -1157,7 +1157,7 @@ public class Pass0GenerateStatementSequence extends KickCBaseVisitor { // Find all defined labels in the ASM List definedLabels = getAsmDefinedLabels(ctx); // Find all referenced symbols in the ASM - Map referenced = getAsmReferencedSymbolVariables(ctx, definedLabels); + Map referenced = getAsmReferencedSymbolVariables(ctx, definedLabels); List comments = ensureUnusedComments(getCommentsSymbol(ctx)); AsmClobber declaredClobber = null; @@ -1199,8 +1199,8 @@ public class Pass0GenerateStatementSequence extends KickCBaseVisitor { * @param definedLabels All labels defined in the ASM * @return All variables/constants referenced in the ASM. Some may be ForwardVariableRefs to be resolved later. */ - private Map getAsmReferencedSymbolVariables(KickCParser.StmtAsmContext ctx, List definedLabels) { - Map referenced = new LinkedHashMap<>(); + private Map getAsmReferencedSymbolVariables(KickCParser.StmtAsmContext ctx, List definedLabels) { + Map referenced = new LinkedHashMap<>(); KickCBaseVisitor findReferenced = new KickCBaseVisitor() { @Override @@ -1221,9 +1221,8 @@ public class Pass0GenerateStatementSequence extends KickCBaseVisitor { if(!definedLabels.contains(label)) { // Look for the symbol Symbol symbol = getCurrentScope().getSymbol(ctxLabel.NAME().getText()); - if(symbol instanceof Variable) { - Variable variable = (Variable) symbol; - referenced.put(label, variable.getRef()); + if(symbol!=null) { + referenced.put(label, symbol.getRef()); } else { // Either forward reference or a non-existing variable. Create a forward reference for later resolving. referenced.put(label, new ForwardVariableRef(ctxLabel.NAME().getText())); diff --git a/src/main/java/dk/camelot64/kickc/passes/Pass3AssertConstants.java b/src/main/java/dk/camelot64/kickc/passes/Pass3AssertConstants.java index ea0b79628..1faef40c6 100644 --- a/src/main/java/dk/camelot64/kickc/passes/Pass3AssertConstants.java +++ b/src/main/java/dk/camelot64/kickc/passes/Pass3AssertConstants.java @@ -44,10 +44,10 @@ public class Pass3AssertConstants extends Pass2SsaAssertion { } } else if(statement instanceof StatementAsm) { StatementAsm statementAsm = (StatementAsm) statement; - Map referenced = statementAsm.getReferenced(); + Map referenced = statementAsm.getReferenced(); for(String label : referenced.keySet()) { - SymbolVariableRef symbolRef = referenced.get(label); - if(!(symbolRef instanceof ConstantRef)) { + SymbolRef symbolRef = referenced.get(label); + if(!(symbolRef instanceof ConstantRef) && !(symbolRef instanceof ProcedureRef)) { throw new CompileError("Error! Inline ASM reference is not constant " + label, statement); } } diff --git a/src/test/kc/complex/xmega65/xmega65.kc b/src/test/kc/complex/xmega65/xmega65.kc index 1603c9451..771f3738d 100644 --- a/src/test/kc/complex/xmega65/xmega65.kc +++ b/src/test/kc/complex/xmega65/xmega65.kc @@ -20,7 +20,6 @@ char[] MESSAGE = "hello world!"; void main() { // Initialize screen memory *VIC_MEMORY = 0x14; - *BGCOL = 0x0f; // Init screen/colors memset(SCREEN, ' ', 40*25); memset(COLS, WHITE, 40*25); @@ -40,15 +39,12 @@ void main() { } } - void syscall1() { - const char* BORDERCOL = $d020; - (*BORDERCOL)++; + *(SCREEN+79) = '>'; } void syscall2() { - const char* BGCOL = $d021; - (*BGCOL)++; + *(SCREEN+78) = '<'; } #pragma data_seg(Syscall) diff --git a/src/test/ref/complex/xmega65/xmega65.asm b/src/test/ref/complex/xmega65/xmega65.asm index bb1ea5d7f..ef79d949b 100644 --- a/src/test/ref/complex/xmega65/xmega65.asm +++ b/src/test/ref/complex/xmega65/xmega65.asm @@ -24,8 +24,6 @@ main: { // Initialize screen memory lda #$14 sta VIC_MEMORY - lda #$f - sta BGCOL ldx #' ' lda #' + sta SCREEN+$4f rts } .segment Data diff --git a/src/test/ref/complex/xmega65/xmega65.cfg b/src/test/ref/complex/xmega65/xmega65.cfg index 421e0937f..32c382581 100644 --- a/src/test/ref/complex/xmega65/xmega65.cfg +++ b/src/test/ref/complex/xmega65/xmega65.cfg @@ -9,65 +9,64 @@ [3] phi() main: scope:[main] from @1 [4] *((const byte*) VIC_MEMORY#0) ← (byte) $14 - [5] *((const byte*) BGCOL#0) ← (byte) $f - [6] call memset + [5] call memset to:main::@6 main::@6: scope:[main] from main - [7] phi() - [8] call memset + [6] phi() + [7] call memset to:main::@1 main::@1: scope:[main] from main::@2 main::@6 - [9] (byte*) main::sc#2 ← phi( main::@6/(const byte*) SCREEN#0+(byte) $28 main::@2/(byte*) main::sc#1 ) - [9] (byte*) main::msg#2 ← phi( main::@6/(const byte[]) MESSAGE#0 main::@2/(byte*) main::msg#1 ) - [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 + [8] (byte*) main::sc#2 ← phi( main::@6/(const byte*) SCREEN#0+(byte) $28 main::@2/(byte*) main::sc#1 ) + [8] (byte*) main::msg#2 ← phi( main::@6/(const byte[]) MESSAGE#0 main::@2/(byte*) main::msg#1 ) + [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 to:main::@3 main::@3: scope:[main] from main::@1 main::@4 main::@5 - [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 + [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 to:main::@7 main::@7: scope:[main] from main::@3 - [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 + [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 to:main::@5 main::@5: scope:[main] from main::@7 - [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 + [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 to:main::@3 main::@4: scope:[main] from main::@3 main::@7 - [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 + [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 to:main::@3 main::@2: scope:[main] from main::@1 - [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) - [16] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 - [17] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 + [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) + [15] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 + [16] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 to:main::@1 memset: scope:[memset] from main main::@6 - [18] (byte) memset::c#4 ← phi( main/(byte) ' ' main::@6/(const byte) WHITE#0 ) - [18] (void*) memset::str#3 ← phi( main/(void*)(const byte*) SCREEN#0 main::@6/(void*)(const byte*) COLS#0 ) - [18] (word) memset::num#2 ← phi( main/(word)(number) $28*(number) $19 main::@6/(word)(number) $28*(number) $19 ) - [19] if((word) memset::num#2<=(byte) 0) goto memset::@return + [17] (byte) memset::c#4 ← phi( main/(byte) ' ' main::@6/(const byte) WHITE#0 ) + [17] (void*) memset::str#3 ← phi( main/(void*)(const byte*) SCREEN#0 main::@6/(void*)(const byte*) COLS#0 ) + [17] (word) memset::num#2 ← phi( main/(word)(number) $28*(number) $19 main::@6/(word)(number) $28*(number) $19 ) + [18] if((word) memset::num#2<=(byte) 0) goto memset::@return to:memset::@1 memset::@1: scope:[memset] from memset - [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 - [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 + [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 + [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 to:memset::@2 memset::@2: scope:[memset] from memset::@1 memset::@3 - [22] (byte*) memset::dst#2 ← phi( memset::@1/(byte*~) memset::dst#4 memset::@3/(byte*) memset::dst#1 ) - [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 + [21] (byte*) memset::dst#2 ← phi( memset::@1/(byte*~) memset::dst#4 memset::@3/(byte*) memset::dst#1 ) + [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 to:memset::@return memset::@return: scope:[memset] from memset memset::@2 - [24] return + [23] return to:@return memset::@3: scope:[memset] from memset::@2 - [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 - [26] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 + [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 + [25] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 to:memset::@2 syscall2: scope:[syscall2] from - [27] *((const byte*) syscall2::BGCOL#0) ← ++ *((const byte*) syscall2::BGCOL#0) + [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' to:syscall2::@return syscall2::@return: scope:[syscall2] from syscall2 - [28] return + [27] return to:@return syscall1: scope:[syscall1] from - [29] *((const byte*) syscall1::BORDERCOL#0) ← ++ *((const byte*) syscall1::BORDERCOL#0) + [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' to:syscall1::@return syscall1::@return: scope:[syscall1] from syscall1 - [30] return + [29] return to:@return diff --git a/src/test/ref/complex/xmega65/xmega65.log b/src/test/ref/complex/xmega65/xmega65.log index 89013b5ab..194e41d90 100644 --- a/src/test/ref/complex/xmega65/xmega65.log +++ b/src/test/ref/complex/xmega65/xmega65.log @@ -79,7 +79,6 @@ memset::@return: scope:[memset] from memset::@1 to:@7 main: scope:[main] from @7 *((byte*) VIC_MEMORY#0) ← (number) $14 - *((byte*) BGCOL#0) ← (number) $f (void*) memset::str#0 ← (void*)(byte*) SCREEN#0 (byte) memset::c#0 ← (byte) ' ' (word) memset::num#0 ← (number) $28*(number) $19 @@ -130,15 +129,15 @@ main::@return: scope:[main] from main::@7 return to:@return syscall1: scope:[syscall1] from - (byte*) syscall1::BORDERCOL#0 ← ((byte*)) (number) $d020 - *((byte*) syscall1::BORDERCOL#0) ← ++ *((byte*) syscall1::BORDERCOL#0) + (byte*~) syscall1::$0 ← (byte*) SCREEN#0 + (number) $4f + *((byte*~) syscall1::$0) ← (byte) '>' to:syscall1::@return syscall1::@return: scope:[syscall1] from syscall1 return to:@return syscall2: scope:[syscall2] from - (byte*) syscall2::BGCOL#0 ← ((byte*)) (number) $d021 - *((byte*) syscall2::BGCOL#0) ← ++ *((byte*) syscall2::BGCOL#0) + (byte*~) syscall2::$0 ← (byte*) SCREEN#0 + (number) $4e + *((byte*~) syscall2::$0) ← (byte) '<' to:syscall2::@return syscall2::@return: scope:[syscall2] from syscall2 return @@ -266,25 +265,24 @@ SYMBOL TABLE SSA (void*) memset::str#5 (void*) memset::str#6 (void()) syscall1() +(byte*~) syscall1::$0 (label) syscall1::@return -(byte*) syscall1::BORDERCOL -(byte*) syscall1::BORDERCOL#0 (void()) syscall2() +(byte*~) syscall2::$0 (label) syscall2::@return -(byte*) syscall2::BGCOL -(byte*) syscall2::BGCOL#0 Adding number conversion cast (unumber) 0 in (bool~) memset::$0 ← (word) memset::num#2 > (number) 0 Adding number conversion cast (unumber) 0 in (byte) BLACK#0 ← (number) 0 Adding number conversion cast (unumber) 1 in (byte) WHITE#0 ← (number) 1 Adding number conversion cast (unumber) $14 in *((byte*) VIC_MEMORY#0) ← (number) $14 -Adding number conversion cast (unumber) $f in *((byte*) BGCOL#0) ← (number) $f Adding number conversion cast (unumber) $28*$19 in (word) memset::num#0 ← (number) $28*(number) $19 Adding number conversion cast (unumber) $28*$19 in (word) memset::num#1 ← (number) $28*(number) $19 Adding number conversion cast (unumber) $28 in (byte*~) main::$2 ← (byte*) SCREEN#0 + (number) $28 Adding number conversion cast (unumber) 0 in (bool~) main::$6 ← (number) 0 != *((byte*) main::msg#2) Adding number conversion cast (unumber) $36 in (bool~) main::$3 ← *((byte*) RASTER#0) == (number) $36 Adding number conversion cast (unumber) $42 in (bool~) main::$4 ← *((byte*) RASTER#0) == (number) $42 +Adding number conversion cast (unumber) $4f in (byte*~) syscall1::$0 ← (byte*) SCREEN#0 + (number) $4f +Adding number conversion cast (unumber) $4e in (byte*~) syscall2::$0 ← (byte*) SCREEN#0 + (number) $4e Adding number conversion cast (unumber) $4c in (byte) JMP#0 ← (number) $4c Adding number conversion cast (unumber) $ea in (byte) NOP#0 ← (number) $ea Successful SSA optimization PassNAddNumberTypeConversions @@ -298,11 +296,8 @@ Inlining cast (byte*) COLS#0 ← (byte*)(number) $d800 Inlining cast (byte) BLACK#0 ← (unumber)(number) 0 Inlining cast (byte) WHITE#0 ← (unumber)(number) 1 Inlining cast *((byte*) VIC_MEMORY#0) ← (unumber)(number) $14 -Inlining cast *((byte*) BGCOL#0) ← (unumber)(number) $f Inlining cast (word) memset::num#0 ← (unumber)(number) $28*(number) $19 Inlining cast (word) memset::num#1 ← (unumber)(number) $28*(number) $19 -Inlining cast (byte*) syscall1::BORDERCOL#0 ← (byte*)(number) $d020 -Inlining cast (byte*) syscall2::BGCOL#0 ← (byte*)(number) $d021 Inlining cast (byte) JMP#0 ← (unumber)(number) $4c Inlining cast (byte) NOP#0 ← (unumber)(number) $ea Successful SSA optimization Pass2InlineCast @@ -315,13 +310,12 @@ Simplifying constant pointer cast (byte*) 55296 Simplifying constant integer cast 0 Simplifying constant integer cast 1 Simplifying constant integer cast $14 -Simplifying constant integer cast $f Simplifying constant integer cast $28 Simplifying constant integer cast 0 Simplifying constant integer cast $36 Simplifying constant integer cast $42 -Simplifying constant pointer cast (byte*) 53280 -Simplifying constant pointer cast (byte*) 53281 +Simplifying constant integer cast $4f +Simplifying constant integer cast $4e Simplifying constant integer cast $4c Simplifying constant integer cast $ea Successful SSA optimization PassNCastSimplification @@ -329,11 +323,12 @@ Finalized unsigned number type (byte) 0 Finalized unsigned number type (byte) 0 Finalized unsigned number type (byte) 1 Finalized unsigned number type (byte) $14 -Finalized unsigned number type (byte) $f Finalized unsigned number type (byte) $28 Finalized unsigned number type (byte) 0 Finalized unsigned number type (byte) $36 Finalized unsigned number type (byte) $42 +Finalized unsigned number type (byte) $4f +Finalized unsigned number type (byte) $4e Finalized unsigned number type (byte) $4c Finalized unsigned number type (byte) $ea Successful SSA optimization PassNFinalizeNumberTypeConversions @@ -360,15 +355,15 @@ Identical Phi Values (void*) memset::return#0 (void*) memset::str#3 Successful SSA optimization Pass2IdenticalPhiElimination Simple Condition (bool~) memset::$1 [3] if((word) memset::num#2<=(byte) 0) goto memset::@1 Simple Condition (bool~) memset::$4 [13] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@5 -Simple Condition (bool~) main::$6 [45] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 +Simple Condition (bool~) main::$6 [44] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 Successful SSA optimization Pass2ConditionalJumpSimplification -Rewriting || if()-condition to two if()s [53] (bool~) main::$5 ← (bool~) main::$3 || (bool~) main::$4 +Rewriting || if()-condition to two if()s [52] (bool~) main::$5 ← (bool~) main::$3 || (bool~) main::$4 Successful SSA optimization Pass2ConditionalAndOrRewriting -Constant right-side identified [32] (word) memset::num#0 ← (unumber)(number) $28*(number) $19 -Constant right-side identified [37] (word) memset::num#1 ← (unumber)(number) $28*(number) $19 -Constant right-side identified [66] (void()*~) $0 ← & (void()) syscall1() -Constant right-side identified [67] (void()*~) $1 ← & (void()) syscall2() -Constant right-side identified [69] (void()*~) $2 ← & (void()) main() +Constant right-side identified [31] (word) memset::num#0 ← (unumber)(number) $28*(number) $19 +Constant right-side identified [36] (word) memset::num#1 ← (unumber)(number) $28*(number) $19 +Constant right-side identified [65] (void()*~) $0 ← & (void()) syscall1() +Constant right-side identified [66] (void()*~) $1 ← & (void()) syscall2() +Constant right-side identified [68] (void()*~) $2 ← & (void()) main() Successful SSA optimization Pass2ConstantRValueConsolidation Constant (const byte*) RASTER#0 = (byte*) 53266 Constant (const byte*) VIC_MEMORY#0 = (byte*) 53272 @@ -381,8 +376,6 @@ Constant (const byte[]) MESSAGE#0 = $3 Constant (const byte) memset::c#0 = ' ' Constant (const word) memset::num#0 = (unumber)$28*$19 Constant (const word) memset::num#1 = (unumber)$28*$19 -Constant (const byte*) syscall1::BORDERCOL#0 = (byte*) 53280 -Constant (const byte*) syscall2::BGCOL#0 = (byte*) 53281 Constant (const byte) JMP#0 = $4c Constant (const byte) NOP#0 = $ea Constant (const void()*) $0 = &syscall1 @@ -392,20 +385,25 @@ Successful SSA optimization Pass2ConstantIdentification Constant (const byte) memset::c#1 = WHITE#0 Constant (const byte*) main::msg#0 = MESSAGE#0 Successful SSA optimization Pass2ConstantIdentification -Constant value identified (void*)SCREEN#0 in [30] (void*) memset::str#0 ← (void*)(const byte*) SCREEN#0 -Constant value identified (void*)COLS#0 in [35] (void*) memset::str#1 ← (void*)(const byte*) COLS#0 +Constant value identified (void*)SCREEN#0 in [29] (void*) memset::str#0 ← (void*)(const byte*) SCREEN#0 +Constant value identified (void*)COLS#0 in [34] (void*) memset::str#1 ← (void*)(const byte*) COLS#0 Successful SSA optimization Pass2ConstantValues -if() condition always true - replacing block destination [50] if(true) goto main::@8 +if() condition always true - replacing block destination [49] if(true) goto main::@8 Successful SSA optimization Pass2ConstantIfs -Eliminating unused variable (void*) memset::return#2 and assignment [14] (void*) memset::return#2 ← (void*) memset::str#3 -Eliminating unused variable (void*) memset::return#3 and assignment [17] (void*) memset::return#3 ← (void*) memset::str#3 +Converting *(pointer+n) to pointer[n] [58] *((byte*~) syscall1::$0) ← (byte) '>' -- *(SCREEN#0 + $4f) +Converting *(pointer+n) to pointer[n] [61] *((byte*~) syscall2::$0) ← (byte) '<' -- *(SCREEN#0 + $4e) +Successful SSA optimization Pass2InlineDerefIdx +Eliminating unused variable (void*) memset::return#2 and assignment [13] (void*) memset::return#2 ← (void*) memset::str#3 +Eliminating unused variable (void*) memset::return#3 and assignment [16] (void*) memset::return#3 ← (void*) memset::str#3 +Eliminating unused variable (byte*~) syscall1::$0 and assignment [29] (byte*~) syscall1::$0 ← (const byte*) SCREEN#0 + (byte) $4f +Eliminating unused variable (byte*~) syscall2::$0 and assignment [32] (byte*~) syscall2::$0 ← (const byte*) SCREEN#0 + (byte) $4e Successful SSA optimization PassNEliminateUnusedVars Removing unused block main::@return Successful SSA optimization Pass2EliminateUnusedBlocks -Simple Condition (bool~) main::$3 [24] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@10 -Simple Condition (bool~) main::$4 [34] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@10 +Simple Condition (bool~) main::$3 [23] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@10 +Simple Condition (bool~) main::$4 [33] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@10 Successful SSA optimization Pass2ConditionalJumpSimplification -Constant right-side identified [16] (byte*) main::sc#0 ← (const byte*) SCREEN#0 + (byte) $28 +Constant right-side identified [15] (byte*) main::sc#0 ← (const byte*) SCREEN#0 + (byte) $28 Successful SSA optimization Pass2ConstantRValueConsolidation Identified constant from value list (struct SysCall) { xjmp: (const byte) JMP#0, syscall: (const void()*) $0, xnop: (const byte) NOP#0 } Identified constant from value list (struct SysCall) { xjmp: (const byte) JMP#0, syscall: (const void()*) $1, xnop: (const byte) NOP#0 } @@ -444,6 +442,9 @@ Constant inlined $1 = &(void()) syscall2() Constant inlined $2 = &(void()) main() Constant inlined $3 = (const byte[]) MESSAGE#0 Successful SSA optimization Pass2ConstantInlining +Consolidated array index constant in *(SCREEN#0+$4f) +Consolidated array index constant in *(SCREEN#0+$4e) +Successful SSA optimization Pass2ConstantAdditionElimination Adding NOP phi() at start of @begin Adding NOP phi() at start of @4 Adding NOP phi() at start of @7 @@ -455,12 +456,12 @@ Adding NOP phi() at start of main::@7 Adding NOP phi() at start of memset::@1 CALL GRAPH Calls in [] to main:3 -Calls in [main] to memset:8 memset:10 +Calls in [main] to memset:7 memset:9 Created 6 initial phi equivalence classes -Coalesced [22] main::msg#4 ← main::msg#1 -Coalesced [23] main::sc#4 ← main::sc#1 -Coalesced [34] memset::dst#5 ← memset::dst#1 +Coalesced [21] main::msg#4 ← main::msg#1 +Coalesced [22] main::sc#4 ← main::sc#1 +Coalesced [33] memset::dst#5 ← memset::dst#1 Coalesced down to 6 phi equivalence classes Culled Empty Block (label) @4 Culled Empty Block (label) @8 @@ -493,67 +494,66 @@ FINAL CONTROL FLOW GRAPH [3] phi() main: scope:[main] from @1 [4] *((const byte*) VIC_MEMORY#0) ← (byte) $14 - [5] *((const byte*) BGCOL#0) ← (byte) $f - [6] call memset + [5] call memset to:main::@6 main::@6: scope:[main] from main - [7] phi() - [8] call memset + [6] phi() + [7] call memset to:main::@1 main::@1: scope:[main] from main::@2 main::@6 - [9] (byte*) main::sc#2 ← phi( main::@6/(const byte*) SCREEN#0+(byte) $28 main::@2/(byte*) main::sc#1 ) - [9] (byte*) main::msg#2 ← phi( main::@6/(const byte[]) MESSAGE#0 main::@2/(byte*) main::msg#1 ) - [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 + [8] (byte*) main::sc#2 ← phi( main::@6/(const byte*) SCREEN#0+(byte) $28 main::@2/(byte*) main::sc#1 ) + [8] (byte*) main::msg#2 ← phi( main::@6/(const byte[]) MESSAGE#0 main::@2/(byte*) main::msg#1 ) + [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 to:main::@3 main::@3: scope:[main] from main::@1 main::@4 main::@5 - [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 + [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 to:main::@7 main::@7: scope:[main] from main::@3 - [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 + [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 to:main::@5 main::@5: scope:[main] from main::@7 - [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 + [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 to:main::@3 main::@4: scope:[main] from main::@3 main::@7 - [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 + [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 to:main::@3 main::@2: scope:[main] from main::@1 - [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) - [16] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 - [17] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 + [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) + [15] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 + [16] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 to:main::@1 memset: scope:[memset] from main main::@6 - [18] (byte) memset::c#4 ← phi( main/(byte) ' ' main::@6/(const byte) WHITE#0 ) - [18] (void*) memset::str#3 ← phi( main/(void*)(const byte*) SCREEN#0 main::@6/(void*)(const byte*) COLS#0 ) - [18] (word) memset::num#2 ← phi( main/(word)(number) $28*(number) $19 main::@6/(word)(number) $28*(number) $19 ) - [19] if((word) memset::num#2<=(byte) 0) goto memset::@return + [17] (byte) memset::c#4 ← phi( main/(byte) ' ' main::@6/(const byte) WHITE#0 ) + [17] (void*) memset::str#3 ← phi( main/(void*)(const byte*) SCREEN#0 main::@6/(void*)(const byte*) COLS#0 ) + [17] (word) memset::num#2 ← phi( main/(word)(number) $28*(number) $19 main::@6/(word)(number) $28*(number) $19 ) + [18] if((word) memset::num#2<=(byte) 0) goto memset::@return to:memset::@1 memset::@1: scope:[memset] from memset - [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 - [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 + [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 + [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 to:memset::@2 memset::@2: scope:[memset] from memset::@1 memset::@3 - [22] (byte*) memset::dst#2 ← phi( memset::@1/(byte*~) memset::dst#4 memset::@3/(byte*) memset::dst#1 ) - [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 + [21] (byte*) memset::dst#2 ← phi( memset::@1/(byte*~) memset::dst#4 memset::@3/(byte*) memset::dst#1 ) + [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 to:memset::@return memset::@return: scope:[memset] from memset memset::@2 - [24] return + [23] return to:@return memset::@3: scope:[memset] from memset::@2 - [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 - [26] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 + [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 + [25] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 to:memset::@2 syscall2: scope:[syscall2] from - [27] *((const byte*) syscall2::BGCOL#0) ← ++ *((const byte*) syscall2::BGCOL#0) + [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' to:syscall2::@return syscall2::@return: scope:[syscall2] from syscall2 - [28] return + [27] return to:@return syscall1: scope:[syscall1] from - [29] *((const byte*) syscall1::BORDERCOL#0) ← ++ *((const byte*) syscall1::BORDERCOL#0) + [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' to:syscall1::@return syscall1::@return: scope:[syscall1] from syscall1 - [30] return + [29] return to:@return @@ -595,9 +595,7 @@ VARIABLE REGISTER WEIGHTS (void*) memset::str (void*) memset::str#3 (void()) syscall1() -(byte*) syscall1::BORDERCOL (void()) syscall2() -(byte*) syscall2::BGCOL Initial phi equivalence classes [ main::msg#2 main::msg#1 ] @@ -670,56 +668,53 @@ main: { // Initialize screen memory lda #$14 sta VIC_MEMORY - // [5] *((const byte*) BGCOL#0) ← (byte) $f -- _deref_pbuc1=vbuc2 - lda #$f - sta BGCOL - // [6] call memset - // [18] phi from main to memset [phi:main->memset] + // [5] call memset + // [17] phi from main to memset [phi:main->memset] memset_from_main: - // [18] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuz1=vbuc1 + // [17] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuz1=vbuc1 lda #' ' sta.z memset.c - // [18] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 lda #SCREEN sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [7] phi from main to main::@6 [phi:main->main::@6] + // [6] phi from main to main::@6 [phi:main->main::@6] b6_from_main: jmp b6 // main::@6 b6: - // [8] call memset - // [18] phi from main::@6 to memset [phi:main::@6->memset] + // [7] call memset + // [17] phi from main::@6 to memset [phi:main::@6->memset] memset_from_b6: - // [18] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuz1=vbuc1 + // [17] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuz1=vbuc1 lda #WHITE sta.z memset.c - // [18] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 lda #COLS sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [9] phi from main::@6 to main::@1 [phi:main::@6->main::@1] + // [8] phi from main::@6 to main::@1 [phi:main::@6->main::@1] b1_from_b6: - // [9] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 + // [8] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 lda #SCREEN+$28 sta.z sc+1 - // [9] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 + // [8] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 lda #MESSAGE @@ -727,7 +722,7 @@ main: { jmp b1 // main::@1 b1: - // [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 + // [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 ldy #0 lda (msg),y cmp #0 @@ -735,51 +730,51 @@ main: { jmp b3 // main::@3 b3: - // [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$36 cmp RASTER beq b4 jmp b7 // main::@7 b7: - // [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$42 cmp RASTER beq b4 jmp b5 // main::@5 b5: - // [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 + // [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 lda #BLACK sta BGCOL jmp b3 // main::@4 b4: - // [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 + // [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 lda #WHITE sta BGCOL jmp b3 // main::@2 b2: - // [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 + // [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 ldy #0 lda (msg),y ldy #0 sta (sc),y - // [16] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 + // [15] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 inc.z sc bne !+ inc.z sc+1 !: - // [17] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 + // [16] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 inc.z msg bne !+ inc.z msg+1 !: - // [9] phi from main::@2 to main::@1 [phi:main::@2->main::@1] + // [8] phi from main::@2 to main::@1 [phi:main::@2->main::@1] b1_from_b2: - // [9] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy - // [9] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy + // [8] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy + // [8] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy jmp b1 } // memset @@ -791,7 +786,7 @@ memset: { .label num = 6 .label str = 8 .label c = $a - // [19] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 + // [18] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 lda.z num bne !+ lda.z num+1 @@ -800,7 +795,7 @@ memset: { jmp b1 // memset::@1 b1: - // [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz3 + // [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz3 lda.z str clc adc.z num @@ -808,19 +803,19 @@ memset: { lda.z str+1 adc.z num+1 sta.z end+1 - // [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 -- pbuz1=pbuz2 + // [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 -- pbuz1=pbuz2 lda.z str sta.z dst lda.z str+1 sta.z dst+1 - // [22] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] + // [21] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] b2_from_b1: b2_from_b3: - // [22] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy + // [21] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy jmp b2 // memset::@2 b2: - // [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 + // [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 lda.z dst+1 cmp.z end+1 bne b3 @@ -830,15 +825,15 @@ memset: { jmp breturn // memset::@return breturn: - // [24] return + // [23] return rts // memset::@3 b3: - // [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuz2 + // [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuz2 lda.z c ldy #0 sta (dst),y - // [26] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 + // [25] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 inc.z dst bne !+ inc.z dst+1 @@ -847,24 +842,24 @@ memset: { } // syscall2 syscall2: { - .label BGCOL = $d021 - // [27] *((const byte*) syscall2::BGCOL#0) ← ++ *((const byte*) syscall2::BGCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BGCOL + // [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' -- _deref_pbuc1=vbuc2 + lda #'<' + sta SCREEN+$4e jmp breturn // syscall2::@return breturn: - // [28] return + // [27] return rts } // syscall1 syscall1: { - .label BORDERCOL = $d020 - // [29] *((const byte*) syscall1::BORDERCOL#0) ← ++ *((const byte*) syscall1::BORDERCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BORDERCOL + // [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' -- _deref_pbuc1=vbuc2 + lda #'>' + sta SCREEN+$4f jmp breturn // syscall1::@return breturn: - // [30] return + // [29] return rts } // File Data @@ -887,33 +882,35 @@ SYSCALL_RESET: REGISTER UPLIFT POTENTIAL REGISTERS Statement [4] *((const byte*) VIC_MEMORY#0) ← (byte) $14 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [5] *((const byte*) BGCOL#0) ← (byte) $f [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y -Statement [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y -Statement [19] if((word) memset::num#2<=(byte) 0) goto memset::@return [ memset::num#2 memset::str#3 memset::c#4 ] ( memset:6 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:6 [ memset::num#2 memset::str#3 memset::c#4 ] memset:8 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:8 [ memset::num#2 memset::str#3 memset::c#4 ] ) always clobbers reg byte a +Statement [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y +Statement [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y +Statement [18] if((word) memset::num#2<=(byte) 0) goto memset::@return [ memset::num#2 memset::str#3 memset::c#4 ] ( memset:5 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:5 [ memset::num#2 memset::str#3 memset::c#4 ] memset:7 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:7 [ memset::num#2 memset::str#3 memset::c#4 ] ) always clobbers reg byte a Removing always clobbered register reg byte a as potential for zp ZP_BYTE:10 [ memset::c#4 ] -Statement [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 [ memset::str#3 memset::c#4 memset::end#0 ] ( memset:6 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:6 [ memset::str#3 memset::c#4 memset::end#0 ] memset:8 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:8 [ memset::str#3 memset::c#4 memset::end#0 ] ) always clobbers reg byte a -Statement [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 [ memset::c#4 memset::end#0 memset::dst#4 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#4 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#4 ] ) always clobbers reg byte a -Statement [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a -Statement [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a reg byte y +Statement [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 [ memset::str#3 memset::c#4 memset::end#0 ] ( memset:5 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:5 [ memset::str#3 memset::c#4 memset::end#0 ] memset:7 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:7 [ memset::str#3 memset::c#4 memset::end#0 ] ) always clobbers reg byte a +Statement [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 [ memset::c#4 memset::end#0 memset::dst#4 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#4 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#4 ] ) always clobbers reg byte a +Statement [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a +Statement [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a reg byte y Removing always clobbered register reg byte y as potential for zp ZP_BYTE:10 [ memset::c#4 ] +Statement [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' [ ] ( [ ] ) always clobbers reg byte a +Statement [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' [ ] ( [ ] ) always clobbers reg byte a Statement [4] *((const byte*) VIC_MEMORY#0) ← (byte) $14 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [5] *((const byte*) BGCOL#0) ← (byte) $f [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y -Statement [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a -Statement [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y -Statement [19] if((word) memset::num#2<=(byte) 0) goto memset::@return [ memset::num#2 memset::str#3 memset::c#4 ] ( memset:6 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:6 [ memset::num#2 memset::str#3 memset::c#4 ] memset:8 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:8 [ memset::num#2 memset::str#3 memset::c#4 ] ) always clobbers reg byte a -Statement [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 [ memset::str#3 memset::c#4 memset::end#0 ] ( memset:6 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:6 [ memset::str#3 memset::c#4 memset::end#0 ] memset:8 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:8 [ memset::str#3 memset::c#4 memset::end#0 ] ) always clobbers reg byte a -Statement [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 [ memset::c#4 memset::end#0 memset::dst#4 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#4 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#4 ] ) always clobbers reg byte a -Statement [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a -Statement [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:6 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:8 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a reg byte y +Statement [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y +Statement [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 [ ] ( [ ] main:2 [ ] ) always clobbers reg byte a +Statement [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) [ main::msg#2 main::sc#2 ] ( [ main::msg#2 main::sc#2 ] main:2 [ main::msg#2 main::sc#2 ] ) always clobbers reg byte a reg byte y +Statement [18] if((word) memset::num#2<=(byte) 0) goto memset::@return [ memset::num#2 memset::str#3 memset::c#4 ] ( memset:5 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:5 [ memset::num#2 memset::str#3 memset::c#4 ] memset:7 [ memset::num#2 memset::str#3 memset::c#4 ] main:2::memset:7 [ memset::num#2 memset::str#3 memset::c#4 ] ) always clobbers reg byte a +Statement [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 [ memset::str#3 memset::c#4 memset::end#0 ] ( memset:5 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:5 [ memset::str#3 memset::c#4 memset::end#0 ] memset:7 [ memset::str#3 memset::c#4 memset::end#0 ] main:2::memset:7 [ memset::str#3 memset::c#4 memset::end#0 ] ) always clobbers reg byte a +Statement [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 [ memset::c#4 memset::end#0 memset::dst#4 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#4 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#4 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#4 ] ) always clobbers reg byte a +Statement [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a +Statement [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 [ memset::c#4 memset::end#0 memset::dst#2 ] ( memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:5 [ memset::c#4 memset::end#0 memset::dst#2 ] memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] main:2::memset:7 [ memset::c#4 memset::end#0 memset::dst#2 ] ) always clobbers reg byte a reg byte y +Statement [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' [ ] ( [ ] ) always clobbers reg byte a +Statement [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' [ ] ( [ ] ) always clobbers reg byte a Potential registers zp ZP_WORD:2 [ main::msg#2 main::msg#1 ] : zp ZP_WORD:2 , Potential registers zp ZP_WORD:4 [ main::sc#2 main::sc#1 ] : zp ZP_WORD:4 , Potential registers zp ZP_WORD:6 [ memset::num#2 ] : zp ZP_WORD:6 , @@ -930,12 +927,12 @@ Uplift Scope [syscall2] Uplift Scope [SysCall] Uplift Scope [] -Uplifting [main] best 1891 combination zp ZP_WORD:2 [ main::msg#2 main::msg#1 ] zp ZP_WORD:4 [ main::sc#2 main::sc#1 ] -Uplifting [memset] best 1875 combination zp ZP_WORD:11 [ memset::dst#2 memset::dst#4 memset::dst#1 ] zp ZP_WORD:13 [ memset::end#0 ] zp ZP_WORD:6 [ memset::num#2 ] reg byte x [ memset::c#4 ] zp ZP_WORD:8 [ memset::str#3 ] -Uplifting [syscall1] best 1875 combination -Uplifting [syscall2] best 1875 combination -Uplifting [SysCall] best 1875 combination -Uplifting [] best 1875 combination +Uplifting [main] best 1885 combination zp ZP_WORD:2 [ main::msg#2 main::msg#1 ] zp ZP_WORD:4 [ main::sc#2 main::sc#1 ] +Uplifting [memset] best 1869 combination zp ZP_WORD:11 [ memset::dst#2 memset::dst#4 memset::dst#1 ] zp ZP_WORD:13 [ memset::end#0 ] zp ZP_WORD:6 [ memset::num#2 ] reg byte x [ memset::c#4 ] zp ZP_WORD:8 [ memset::str#3 ] +Uplifting [syscall1] best 1869 combination +Uplifting [syscall2] best 1869 combination +Uplifting [SysCall] best 1869 combination +Uplifting [] best 1869 combination Coalescing zero page register [ zp ZP_WORD:6 [ memset::num#2 ] ] with [ zp ZP_WORD:13 [ memset::end#0 ] ] - score: 1 Coalescing zero page register [ zp ZP_WORD:8 [ memset::str#3 ] ] with [ zp ZP_WORD:11 [ memset::dst#2 memset::dst#4 memset::dst#1 ] ] - score: 1 Coalescing zero page register [ zp ZP_WORD:6 [ memset::num#2 memset::end#0 ] ] with [ zp ZP_WORD:2 [ main::msg#2 main::msg#1 ] ] @@ -989,54 +986,51 @@ main: { // Initialize screen memory lda #$14 sta VIC_MEMORY - // [5] *((const byte*) BGCOL#0) ← (byte) $f -- _deref_pbuc1=vbuc2 - lda #$f - sta BGCOL - // [6] call memset - // [18] phi from main to memset [phi:main->memset] + // [5] call memset + // [17] phi from main to memset [phi:main->memset] memset_from_main: - // [18] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuxx=vbuc1 + // [17] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuxx=vbuc1 ldx #' ' - // [18] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 lda #SCREEN sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [7] phi from main to main::@6 [phi:main->main::@6] + // [6] phi from main to main::@6 [phi:main->main::@6] b6_from_main: jmp b6 // main::@6 b6: - // [8] call memset - // [18] phi from main::@6 to memset [phi:main::@6->memset] + // [7] call memset + // [17] phi from main::@6 to memset [phi:main::@6->memset] memset_from_b6: - // [18] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuxx=vbuc1 + // [17] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuxx=vbuc1 ldx #WHITE - // [18] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 lda #COLS sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [9] phi from main::@6 to main::@1 [phi:main::@6->main::@1] + // [8] phi from main::@6 to main::@1 [phi:main::@6->main::@1] b1_from_b6: - // [9] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 + // [8] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 lda #SCREEN+$28 sta.z sc+1 - // [9] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 + // [8] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 lda #MESSAGE @@ -1044,7 +1038,7 @@ main: { jmp b1 // main::@1 b1: - // [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 + // [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 ldy #0 lda (msg),y cmp #0 @@ -1052,51 +1046,51 @@ main: { jmp b3 // main::@3 b3: - // [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$36 cmp RASTER beq b4 jmp b7 // main::@7 b7: - // [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$42 cmp RASTER beq b4 jmp b5 // main::@5 b5: - // [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 + // [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 lda #BLACK sta BGCOL jmp b3 // main::@4 b4: - // [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 + // [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 lda #WHITE sta BGCOL jmp b3 // main::@2 b2: - // [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 + // [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 ldy #0 lda (msg),y ldy #0 sta (sc),y - // [16] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 + // [15] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 inc.z sc bne !+ inc.z sc+1 !: - // [17] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 + // [16] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 inc.z msg bne !+ inc.z msg+1 !: - // [9] phi from main::@2 to main::@1 [phi:main::@2->main::@1] + // [8] phi from main::@2 to main::@1 [phi:main::@2->main::@1] b1_from_b2: - // [9] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy - // [9] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy + // [8] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy + // [8] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy jmp b1 } // memset @@ -1107,7 +1101,7 @@ memset: { .label dst = 4 .label num = 2 .label str = 4 - // [19] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 + // [18] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 lda.z num bne !+ lda.z num+1 @@ -1116,7 +1110,7 @@ memset: { jmp b1 // memset::@1 b1: - // [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz1 + // [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz1 lda.z end clc adc.z str @@ -1124,15 +1118,15 @@ memset: { lda.z end+1 adc.z str+1 sta.z end+1 - // [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 - // [22] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] + // [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 + // [21] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] b2_from_b1: b2_from_b3: - // [22] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy + // [21] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy jmp b2 // memset::@2 b2: - // [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 + // [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 lda.z dst+1 cmp.z end+1 bne b3 @@ -1142,15 +1136,15 @@ memset: { jmp breturn // memset::@return breturn: - // [24] return + // [23] return rts // memset::@3 b3: - // [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuxx + // [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuxx txa ldy #0 sta (dst),y - // [26] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 + // [25] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 inc.z dst bne !+ inc.z dst+1 @@ -1159,24 +1153,24 @@ memset: { } // syscall2 syscall2: { - .label BGCOL = $d021 - // [27] *((const byte*) syscall2::BGCOL#0) ← ++ *((const byte*) syscall2::BGCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BGCOL + // [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' -- _deref_pbuc1=vbuc2 + lda #'<' + sta SCREEN+$4e jmp breturn // syscall2::@return breturn: - // [28] return + // [27] return rts } // syscall1 syscall1: { - .label BORDERCOL = $d020 - // [29] *((const byte*) syscall1::BORDERCOL#0) ← ++ *((const byte*) syscall1::BORDERCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BORDERCOL + // [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' -- _deref_pbuc1=vbuc2 + lda #'>' + sta SCREEN+$4f jmp breturn // syscall1::@return breturn: - // [30] return + // [29] return rts } // File Data @@ -1302,12 +1296,8 @@ FINAL SYMBOL TABLE (void*) memset::str#3 str zp ZP_WORD:4 (void()) syscall1() (label) syscall1::@return -(byte*) syscall1::BORDERCOL -(const byte*) syscall1::BORDERCOL#0 BORDERCOL = (byte*) 53280 (void()) syscall2() (label) syscall2::@return -(byte*) syscall2::BGCOL -(const byte*) syscall2::BGCOL#0 BGCOL = (byte*) 53281 zp ZP_WORD:2 [ memset::num#2 memset::end#0 main::msg#2 main::msg#1 ] zp ZP_WORD:4 [ memset::str#3 memset::dst#2 memset::dst#4 memset::dst#1 main::sc#2 main::sc#1 ] @@ -1315,7 +1305,7 @@ reg byte x [ memset::c#4 ] FINAL ASSEMBLER -Score: 1639 +Score: 1633 // File Comments // XMega65 Kernal Development Template @@ -1355,51 +1345,47 @@ main: { // Initialize screen memory lda #$14 sta VIC_MEMORY - // *BGCOL = 0x0f - // [5] *((const byte*) BGCOL#0) ← (byte) $f -- _deref_pbuc1=vbuc2 - lda #$f - sta BGCOL // memset(SCREEN, ' ', 40*25) - // [6] call memset - // [18] phi from main to memset [phi:main->memset] - // [18] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuxx=vbuc1 + // [5] call memset + // [17] phi from main to memset [phi:main->memset] + // [17] phi (byte) memset::c#4 = (byte) ' ' [phi:main->memset#0] -- vbuxx=vbuc1 ldx #' ' - // [18] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) SCREEN#0 [phi:main->memset#1] -- pvoz1=pvoc1 lda #SCREEN sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [7] phi from main to main::@6 [phi:main->main::@6] + // [6] phi from main to main::@6 [phi:main->main::@6] // main::@6 // memset(COLS, WHITE, 40*25) - // [8] call memset - // [18] phi from main::@6 to memset [phi:main::@6->memset] - // [18] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuxx=vbuc1 + // [7] call memset + // [17] phi from main::@6 to memset [phi:main::@6->memset] + // [17] phi (byte) memset::c#4 = (const byte) WHITE#0 [phi:main::@6->memset#0] -- vbuxx=vbuc1 ldx #WHITE - // [18] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 + // [17] phi (void*) memset::str#3 = (void*)(const byte*) COLS#0 [phi:main::@6->memset#1] -- pvoz1=pvoc1 lda #COLS sta.z memset.str+1 - // [18] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 + // [17] phi (word) memset::num#2 = (word)(number) $28*(number) $19 [phi:main::@6->memset#2] -- vwuz1=vwuc1 lda #<$28*$19 sta.z memset.num lda #>$28*$19 sta.z memset.num+1 jsr memset - // [9] phi from main::@6 to main::@1 [phi:main::@6->main::@1] - // [9] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 + // [8] phi from main::@6 to main::@1 [phi:main::@6->main::@1] + // [8] phi (byte*) main::sc#2 = (const byte*) SCREEN#0+(byte) $28 [phi:main::@6->main::@1#0] -- pbuz1=pbuc1 lda #SCREEN+$28 sta.z sc+1 - // [9] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 + // [8] phi (byte*) main::msg#2 = (const byte[]) MESSAGE#0 [phi:main::@6->main::@1#1] -- pbuz1=pbuc1 lda #MESSAGE @@ -1407,7 +1393,7 @@ main: { // main::@1 b1: // while(*msg) - // [10] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 + // [9] if((byte) 0!=*((byte*) main::msg#2)) goto main::@2 -- vbuc1_neq__deref_pbuz1_then_la1 ldy #0 lda (msg),y cmp #0 @@ -1415,49 +1401,49 @@ main: { // main::@3 b3: // if(*RASTER==54 || *RASTER==66) - // [11] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [10] if(*((const byte*) RASTER#0)==(byte) $36) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$36 cmp RASTER beq b4 // main::@7 - // [12] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 + // [11] if(*((const byte*) RASTER#0)==(byte) $42) goto main::@4 -- _deref_pbuc1_eq_vbuc2_then_la1 lda #$42 cmp RASTER beq b4 // main::@5 // *BGCOL = BLACK - // [13] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 + // [12] *((const byte*) BGCOL#0) ← (const byte) BLACK#0 -- _deref_pbuc1=vbuc2 lda #BLACK sta BGCOL jmp b3 // main::@4 b4: // *BGCOL = WHITE - // [14] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 + // [13] *((const byte*) BGCOL#0) ← (const byte) WHITE#0 -- _deref_pbuc1=vbuc2 lda #WHITE sta BGCOL jmp b3 // main::@2 b2: // *sc++ = *msg++ - // [15] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 + // [14] *((byte*) main::sc#2) ← *((byte*) main::msg#2) -- _deref_pbuz1=_deref_pbuz2 ldy #0 lda (msg),y sta (sc),y // *sc++ = *msg++; - // [16] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 + // [15] (byte*) main::sc#1 ← ++ (byte*) main::sc#2 -- pbuz1=_inc_pbuz1 inc.z sc bne !+ inc.z sc+1 !: - // [17] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 + // [16] (byte*) main::msg#1 ← ++ (byte*) main::msg#2 -- pbuz1=_inc_pbuz1 inc.z msg bne !+ inc.z msg+1 !: - // [9] phi from main::@2 to main::@1 [phi:main::@2->main::@1] - // [9] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy - // [9] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy + // [8] phi from main::@2 to main::@1 [phi:main::@2->main::@1] + // [8] phi (byte*) main::sc#2 = (byte*) main::sc#1 [phi:main::@2->main::@1#0] -- register_copy + // [8] phi (byte*) main::msg#2 = (byte*) main::msg#1 [phi:main::@2->main::@1#1] -- register_copy jmp b1 } // memset @@ -1469,7 +1455,7 @@ memset: { .label num = 2 .label str = 4 // if(num>0) - // [19] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 + // [18] if((word) memset::num#2<=(byte) 0) goto memset::@return -- vwuz1_le_0_then_la1 lda.z num bne !+ lda.z num+1 @@ -1477,7 +1463,7 @@ memset: { !: // memset::@1 // end = (char*)str + num - // [20] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz1 + // [19] (byte*) memset::end#0 ← (byte*)(void*) memset::str#3 + (word) memset::num#2 -- pbuz1=pbuz2_plus_vwuz1 lda.z end clc adc.z str @@ -1485,13 +1471,13 @@ memset: { lda.z end+1 adc.z str+1 sta.z end+1 - // [21] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 - // [22] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] - // [22] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy + // [20] (byte*~) memset::dst#4 ← (byte*)(void*) memset::str#3 + // [21] phi from memset::@1 memset::@3 to memset::@2 [phi:memset::@1/memset::@3->memset::@2] + // [21] phi (byte*) memset::dst#2 = (byte*~) memset::dst#4 [phi:memset::@1/memset::@3->memset::@2#0] -- register_copy // memset::@2 b2: // for(char* dst = str; dst!=end; dst++) - // [23] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 + // [22] if((byte*) memset::dst#2!=(byte*) memset::end#0) goto memset::@3 -- pbuz1_neq_pbuz2_then_la1 lda.z dst+1 cmp.z end+1 bne b3 @@ -1501,17 +1487,17 @@ memset: { // memset::@return breturn: // } - // [24] return + // [23] return rts // memset::@3 b3: // *dst = c - // [25] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuxx + // [24] *((byte*) memset::dst#2) ← (byte) memset::c#4 -- _deref_pbuz1=vbuxx txa ldy #0 sta (dst),y // for(char* dst = str; dst!=end; dst++) - // [26] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 + // [25] (byte*) memset::dst#1 ← ++ (byte*) memset::dst#2 -- pbuz1=_inc_pbuz1 inc.z dst bne !+ inc.z dst+1 @@ -1520,24 +1506,24 @@ memset: { } // syscall2 syscall2: { - .label BGCOL = $d021 - // (*BGCOL)++; - // [27] *((const byte*) syscall2::BGCOL#0) ← ++ *((const byte*) syscall2::BGCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BGCOL + // *(SCREEN+78) = '<' + // [26] *((const byte*) SCREEN#0+(byte) $4e) ← (byte) '<' -- _deref_pbuc1=vbuc2 + lda #'<' + sta SCREEN+$4e // syscall2::@return // } - // [28] return + // [27] return rts } // syscall1 syscall1: { - .label BORDERCOL = $d020 - // (*BORDERCOL)++; - // [29] *((const byte*) syscall1::BORDERCOL#0) ← ++ *((const byte*) syscall1::BORDERCOL#0) -- _deref_pbuc1=_inc__deref_pbuc1 - inc BORDERCOL + // *(SCREEN+79) = '>' + // [28] *((const byte*) SCREEN#0+(byte) $4f) ← (byte) '>' -- _deref_pbuc1=vbuc2 + lda #'>' + sta SCREEN+$4f // syscall1::@return // } - // [30] return + // [29] return rts } // File Data diff --git a/src/test/ref/complex/xmega65/xmega65.sym b/src/test/ref/complex/xmega65/xmega65.sym index 32329e713..7f5880b79 100644 --- a/src/test/ref/complex/xmega65/xmega65.sym +++ b/src/test/ref/complex/xmega65/xmega65.sym @@ -62,12 +62,8 @@ (void*) memset::str#3 str zp ZP_WORD:4 (void()) syscall1() (label) syscall1::@return -(byte*) syscall1::BORDERCOL -(const byte*) syscall1::BORDERCOL#0 BORDERCOL = (byte*) 53280 (void()) syscall2() (label) syscall2::@return -(byte*) syscall2::BGCOL -(const byte*) syscall2::BGCOL#0 BGCOL = (byte*) 53281 zp ZP_WORD:2 [ memset::num#2 memset::end#0 main::msg#2 main::msg#1 ] zp ZP_WORD:4 [ memset::str#3 memset::dst#2 memset::dst#4 memset::dst#1 main::sc#2 main::sc#1 ]