diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump.asm b/src/test/java/dk/camelot64/kickc/test/ref/longjump.asm new file mode 100644 index 000000000..8ad42fcd9 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump.asm @@ -0,0 +1,273 @@ +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" + jsr main +main: { + .label SCREEN = $400 + ldx #0 + b1: + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + txa + sta SCREEN,x + inx + cpx #$b + beq !b+ + jmp b1 + !b: + rts +} diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump.cfg b/src/test/java/dk/camelot64/kickc/test/ref/longjump.cfg new file mode 100644 index 000000000..846fe3e46 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump.cfg @@ -0,0 +1,22 @@ +@begin: scope:[] from + [0] phi() [ ] ( ) + to:@1 +@1: scope:[] from @begin + [1] phi() [ ] ( ) + [2] call main param-assignment [ ] ( ) + to:@end +@end: scope:[] from @1 + [3] phi() [ ] ( ) +main: scope:[main] from @1 + [4] phi() [ ] ( main:2 [ ] ) + to:main::@1 +main::@1: scope:[main] from main main::@1 + [5] (byte) main::i#2 ← phi( main/(byte/signed byte/word/signed word/dword/signed dword) 0 main::@1/(byte) main::i#1 ) [ main::i#2 ] ( main:2 [ main::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [7] *((const byte*) main::SCREEN#0 + (byte) main::i#2) ← (byte) main::i#2 [ main::i#2 ] ( main:2 [ main::i#2 ] ) + [8] (byte) main::i#1 ← ++ (byte) main::i#2 [ main::i#1 ] ( main:2 [ main::i#1 ] ) + [9] if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 [ main::i#1 ] ( main:2 [ main::i#1 ] ) + to:main::@return +main::@return: scope:[main] from main::@1 + [10] return [ ] ( main:2 [ ] ) + to:@return diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump.log b/src/test/java/dk/camelot64/kickc/test/ref/longjump.log new file mode 100644 index 000000000..112f06930 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump.log @@ -0,0 +1,1433 @@ +PARSING src/test/java/dk/camelot64/kickc/test/kc/longjump.kc +// Minimal example program generating a long jump + +void main() { + byte* SCREEN = $0400; + for(byte i : 0..10) { + asm { + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + } + SCREEN[i] = i; + } +} + + +STATEMENTS +proc (void()) main() + (byte*) main::SCREEN ← (word/signed word/dword/signed dword) 1024 + (byte) main::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 +main::@1: + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) main::SCREEN + (byte) main::i) ← (byte) main::i + (byte) main::i ← ++ (byte) main::i + (boolean~) main::$0 ← (byte) main::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) main::$0) goto main::@1 +main::@return: + return +endproc // main() + call main + +SYMBOLS +(void()) main() +(boolean~) main::$0 +(label) main::@1 +(label) main::@return +(byte*) main::SCREEN +(byte) main::i + +Promoting word/signed word/dword/signed dword to byte* in main::SCREEN ← ((byte*)) 1024 +INITIAL CONTROL FLOW GRAPH +@begin: scope:[] from + to:@1 +main: scope:[main] from + (byte*) main::SCREEN ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) main::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:main::@1 +main::@1: scope:[main] from main main::@1 + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) main::SCREEN + (byte) main::i) ← (byte) main::i + (byte) main::i ← ++ (byte) main::i + (boolean~) main::$0 ← (byte) main::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) main::$0) goto main::@1 + to:main::@2 +main::@2: scope:[main] from main::@1 + to:main::@return +main::@return: scope:[main] from main::@2 + return + to:@return +@1: scope:[] from @begin + call main + to:@end +@end: scope:[] from @1 + +Removing empty block main::@2 +PROCEDURE MODIFY VARIABLE ANALYSIS + +Completing Phi functions... + +CONTROL FLOW GRAPH SSA WITH ASSIGNMENT CALL & RETURN +@begin: scope:[] from + to:@1 +main: scope:[main] from @1 + (byte*) main::SCREEN#0 ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) main::i#0 ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:main::@1 +main::@1: scope:[main] from main main::@1 + (byte*) main::SCREEN#1 ← phi( main/(byte*) main::SCREEN#0 main::@1/(byte*) main::SCREEN#1 ) + (byte) main::i#2 ← phi( main/(byte) main::i#0 main::@1/(byte) main::i#1 ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) main::SCREEN#1 + (byte) main::i#2) ← (byte) main::i#2 + (byte) main::i#1 ← ++ (byte) main::i#2 + (boolean~) main::$0 ← (byte) main::i#1 != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) main::$0) goto main::@1 + to:main::@return +main::@return: scope:[main] from main::@1 + return + to:@return +@1: scope:[] from @begin + call main param-assignment + to:@2 +@2: scope:[] from @1 + to:@end +@end: scope:[] from @2 + +SYMBOL TABLE SSA +(label) @1 +(label) @2 +(label) @begin +(label) @end +(void()) main() +(boolean~) main::$0 +(label) main::@1 +(label) main::@return +(byte*) main::SCREEN +(byte*) main::SCREEN#0 +(byte*) main::SCREEN#1 +(byte) main::i +(byte) main::i#0 +(byte) main::i#1 +(byte) main::i#2 + +OPTIMIZING CONTROL FLOW GRAPH +Culled Empty Block (label) @2 +Succesful SSA optimization Pass2CullEmptyBlocks +Self Phi Eliminated (byte*) main::SCREEN#1 +Succesful SSA optimization Pass2SelfPhiElimination +Redundant Phi (byte*) main::SCREEN#1 (byte*) main::SCREEN#0 +Succesful SSA optimization Pass2RedundantPhiElimination +Simple Condition (boolean~) main::$0 if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 +Succesful SSA optimization Pass2ConditionalJumpSimplification +Constant (const byte*) main::SCREEN#0 = ((byte*))1024 +Constant (const byte) main::i#0 = 0 +Succesful SSA optimization Pass2ConstantIdentification +Multiple usages for variable. Not optimizing sub-constant (byte) main::i#2 +Multiple usages for variable. Not optimizing sub-constant (byte) main::i#2 +OPTIMIZING CONTROL FLOW GRAPH +Inlining constant with var siblings (const byte) main::i#0 +Inlining constant with var siblings (const byte) main::i#0 +Constant inlined main::i#0 = (byte/signed byte/word/signed word/dword/signed dword) 0 +Succesful SSA optimization Pass2ConstantInlining +Block Sequence Planned @begin @1 @end main main::@1 main::@return +Added new block during phi lifting main::@3(between main::@1 and main::@1) +Block Sequence Planned @begin @1 @end main main::@1 main::@return main::@3 +Adding NOP phi() at start of @begin +Adding NOP phi() at start of @1 +Adding NOP phi() at start of @end +Adding NOP phi() at start of main +CALL GRAPH +Calls in [] to main:2 + +Propagating live ranges... +Propagating live ranges... +Propagating live ranges... +Created 1 initial phi equivalence classes +Coalesced [11] main::i#3 ← main::i#1 +Coalesced down to 1 phi equivalence classes +Culled Empty Block (label) main::@3 +Block Sequence Planned @begin @1 @end main main::@1 main::@return +Adding NOP phi() at start of @begin +Adding NOP phi() at start of @1 +Adding NOP phi() at start of @end +Adding NOP phi() at start of main +Propagating live ranges... +Propagating live ranges... +Propagating live ranges... + +FINAL CONTROL FLOW GRAPH +@begin: scope:[] from + [0] phi() [ ] ( ) + to:@1 +@1: scope:[] from @begin + [1] phi() [ ] ( ) + [2] call main param-assignment [ ] ( ) + to:@end +@end: scope:[] from @1 + [3] phi() [ ] ( ) +main: scope:[main] from @1 + [4] phi() [ ] ( main:2 [ ] ) + to:main::@1 +main::@1: scope:[main] from main main::@1 + [5] (byte) main::i#2 ← phi( main/(byte/signed byte/word/signed word/dword/signed dword) 0 main::@1/(byte) main::i#1 ) [ main::i#2 ] ( main:2 [ main::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [7] *((const byte*) main::SCREEN#0 + (byte) main::i#2) ← (byte) main::i#2 [ main::i#2 ] ( main:2 [ main::i#2 ] ) + [8] (byte) main::i#1 ← ++ (byte) main::i#2 [ main::i#1 ] ( main:2 [ main::i#1 ] ) + [9] if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 [ main::i#1 ] ( main:2 [ main::i#1 ] ) + to:main::@return +main::@return: scope:[main] from main::@1 + [10] return [ ] ( main:2 [ ] ) + to:@return + +DOMINATORS +@begin dominated by @begin +@1 dominated by @1 @begin +@end dominated by @1 @begin @end +main dominated by @1 @begin main +main::@1 dominated by @1 @begin main::@1 main +main::@return dominated by main::@return @1 @begin main::@1 main + +NATURAL LOOPS +Found back edge: Loop head: main::@1 tails: main::@1 blocks: null +Populated: Loop head: main::@1 tails: main::@1 blocks: main::@1 +Loop head: main::@1 tails: main::@1 blocks: main::@1 + +NATURAL LOOPS WITH DEPTH +Found 0 loops in scope [] +Found 1 loops in scope [main] + Loop head: main::@1 tails: main::@1 blocks: main::@1 +Loop head: main::@1 tails: main::@1 blocks: main::@1 depth: 1 + + +VARIABLE REGISTER WEIGHTS +(void()) main() +(byte*) main::SCREEN +(byte) main::i +(byte) main::i#1 16.5 +(byte) main::i#2 14.666666666666666 + +Initial phi equivalence classes +[ main::i#2 main::i#1 ] +Complete equivalence classes +[ main::i#2 main::i#1 ] +Allocated zp ZP_BYTE:2 [ main::i#2 main::i#1 ] + +INITIAL ASM +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +bbegin: +//SEG3 [1] phi from @begin to @1 [phi:@begin->@1] +b1_from_bbegin: + jmp b1 +//SEG4 @1 +b1: +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @1 to main [phi:@1->main] +main_from_b1: + jsr main +//SEG7 [3] phi from @1 to @end [phi:@1->@end] +bend_from_b1: + jmp bend +//SEG8 @end +bend: +//SEG9 main +main: { + .label SCREEN = $400 + .label i = 2 + //SEG10 [5] phi from main to main::@1 [phi:main->main::@1] + b1_from_main: + //SEG11 [5] phi (byte) main::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:main->main::@1#0] -- vbuz1=vbuc1 + lda #0 + sta i + jmp b1 + //SEG12 [5] phi from main::@1 to main::@1 [phi:main::@1->main::@1] + b1_from_b1: + //SEG13 [5] phi (byte) main::i#2 = (byte) main::i#1 [phi:main::@1->main::@1#0] -- register_copy + jmp b1 + //SEG14 main::@1 + b1: + //SEG15 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG16 [7] *((const byte*) main::SCREEN#0 + (byte) main::i#2) ← (byte) main::i#2 [ main::i#2 ] ( main:2 [ main::i#2 ] ) -- pbuc1_derefidx_vbuz1=vbuz1 + ldy i + tya + sta SCREEN,y + //SEG17 [8] (byte) main::i#1 ← ++ (byte) main::i#2 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuz1=_inc_vbuz1 + inc i + //SEG18 [9] if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuz1_neq_vbuc1_then_la1 + lda i + cmp #$b + bne b1_from_b1 + jmp breturn + //SEG19 main::@return + breturn: + //SEG20 [10] return [ ] ( main:2 [ ] ) + rts +} + +REGISTER UPLIFT POTENTIAL REGISTERS +Potential registers zp ZP_BYTE:2 [ main::i#2 main::i#1 ] : zp ZP_BYTE:2 , reg byte a , reg byte x , reg byte y , + +REGISTER UPLIFT SCOPES +Uplift Scope [main] 31.17: zp ZP_BYTE:2 [ main::i#2 main::i#1 ] +Uplift Scope [] + +Uplifting [main] best 5383 combination reg byte x [ main::i#2 main::i#1 ] +Uplifting [] best 5383 combination + +ASSEMBLER BEFORE OPTIMIZATION +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +bbegin: +//SEG3 [1] phi from @begin to @1 [phi:@begin->@1] +b1_from_bbegin: + jmp b1 +//SEG4 @1 +b1: +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @1 to main [phi:@1->main] +main_from_b1: + jsr main +//SEG7 [3] phi from @1 to @end [phi:@1->@end] +bend_from_b1: + jmp bend +//SEG8 @end +bend: +//SEG9 main +main: { + .label SCREEN = $400 + //SEG10 [5] phi from main to main::@1 [phi:main->main::@1] + b1_from_main: + //SEG11 [5] phi (byte) main::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:main->main::@1#0] -- vbuxx=vbuc1 + ldx #0 + jmp b1 + //SEG12 [5] phi from main::@1 to main::@1 [phi:main::@1->main::@1] + b1_from_b1: + //SEG13 [5] phi (byte) main::i#2 = (byte) main::i#1 [phi:main::@1->main::@1#0] -- register_copy + jmp b1 + //SEG14 main::@1 + b1: + //SEG15 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG16 [7] *((const byte*) main::SCREEN#0 + (byte) main::i#2) ← (byte) main::i#2 [ main::i#2 ] ( main:2 [ main::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG17 [8] (byte) main::i#1 ← ++ (byte) main::i#2 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG18 [9] if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + bne b1_from_b1 + jmp breturn + //SEG19 main::@return + breturn: + //SEG20 [10] return [ ] ( main:2 [ ] ) + rts +} + +ASSEMBLER OPTIMIZATIONS +Removing instruction jmp b1 +Removing instruction jmp bend +Removing instruction jmp b1 +Removing instruction jmp breturn +Succesful ASM optimization Pass5NextJumpElimination +Replacing label b1_from_b1 with b1 +Removing instruction bbegin: +Removing instruction b1_from_bbegin: +Removing instruction main_from_b1: +Removing instruction bend_from_b1: +Removing instruction b1_from_b1: +Succesful ASM optimization Pass5RedundantLabelElimination +Removing instruction b1: +Removing instruction bend: +Removing instruction b1_from_main: +Removing instruction breturn: +Succesful ASM optimization Pass5UnusedLabelElimination +Removing instruction jmp b1 +Succesful ASM optimization Pass5NextJumpElimination +Fixing long branch [268] bne b1 to beq + +FINAL SYMBOL TABLE +(label) @1 +(label) @begin +(label) @end +(void()) main() +(label) main::@1 +(label) main::@return +(byte*) main::SCREEN +(const byte*) main::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) main::i +(byte) main::i#1 reg byte x 16.5 +(byte) main::i#2 reg byte x 14.666666666666666 + +reg byte x [ main::i#2 main::i#1 ] + + +FINAL ASSEMBLER +Score: 5317 + +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +//SEG3 [1] phi from @begin to @1 [phi:@begin->@1] +//SEG4 @1 +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @1 to main [phi:@1->main] + jsr main +//SEG7 [3] phi from @1 to @end [phi:@1->@end] +//SEG8 @end +//SEG9 main +main: { + .label SCREEN = $400 + //SEG10 [5] phi from main to main::@1 [phi:main->main::@1] + //SEG11 [5] phi (byte) main::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:main->main::@1#0] -- vbuxx=vbuc1 + ldx #0 + //SEG12 [5] phi from main::@1 to main::@1 [phi:main::@1->main::@1] + //SEG13 [5] phi (byte) main::i#2 = (byte) main::i#1 [phi:main::@1->main::@1#0] -- register_copy + //SEG14 main::@1 + b1: + //SEG15 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG16 [7] *((const byte*) main::SCREEN#0 + (byte) main::i#2) ← (byte) main::i#2 [ main::i#2 ] ( main:2 [ main::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG17 [8] (byte) main::i#1 ← ++ (byte) main::i#2 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG18 [9] if((byte) main::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto main::@1 [ main::i#1 ] ( main:2 [ main::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + beq !b+ + jmp b1 + !b: + //SEG19 main::@return + //SEG20 [10] return [ ] ( main:2 [ ] ) + rts +} + diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump.sym b/src/test/java/dk/camelot64/kickc/test/ref/longjump.sym new file mode 100644 index 000000000..ee7917c2e --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump.sym @@ -0,0 +1,13 @@ +(label) @1 +(label) @begin +(label) @end +(void()) main() +(label) main::@1 +(label) main::@return +(byte*) main::SCREEN +(const byte*) main::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) main::i +(byte) main::i#1 reg byte x 16.5 +(byte) main::i#2 reg byte x 14.666666666666666 + +reg byte x [ main::i#2 main::i#1 ] diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump2.asm b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.asm new file mode 100644 index 000000000..25c678d03 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.asm @@ -0,0 +1,547 @@ +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" + jsr main +main: { + jsr long1 + jsr long2 + rts +} +long2: { + .label SCREEN = $400 + ldx #0 + b1: + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + txa + sta SCREEN,x + inx + cpx #$b + beq !b+ + jmp b1 + !b: + rts +} +long1: { + .label SCREEN = $400 + ldx #0 + b1: + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + txa + sta SCREEN,x + inx + cpx #$b + beq !b+ + jmp b1 + !b: + rts +} diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump2.cfg b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.cfg new file mode 100644 index 000000000..107cfea42 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.cfg @@ -0,0 +1,46 @@ +@begin: scope:[] from + [0] phi() [ ] ( ) + to:@3 +@3: scope:[] from @begin + [1] phi() [ ] ( ) + [2] call main param-assignment [ ] ( ) + to:@end +@end: scope:[] from @3 + [3] phi() [ ] ( ) +main: scope:[main] from @3 + [4] phi() [ ] ( main:2 [ ] ) + [5] call long1 param-assignment [ ] ( main:2 [ ] ) + to:main::@1 +main::@1: scope:[main] from main + [6] phi() [ ] ( main:2 [ ] ) + [7] call long2 param-assignment [ ] ( main:2 [ ] ) + to:main::@return +main::@return: scope:[main] from main::@1 + [8] return [ ] ( main:2 [ ] ) + to:@return +long2: scope:[long2] from main::@1 + [9] phi() [ ] ( main:2::long2:7 [ ] ) + to:long2::@1 +long2::@1: scope:[long2] from long2 long2::@1 + [10] (byte) long2::i#2 ← phi( long2/(byte/signed byte/word/signed word/dword/signed dword) 0 long2::@1/(byte) long2::i#1 ) [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [12] *((const byte*) long2::SCREEN#0 + (byte) long2::i#2) ← (byte) long2::i#2 [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) + [13] (byte) long2::i#1 ← ++ (byte) long2::i#2 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) + [14] if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) + to:long2::@return +long2::@return: scope:[long2] from long2::@1 + [15] return [ ] ( main:2::long2:7 [ ] ) + to:@return +long1: scope:[long1] from main + [16] phi() [ ] ( main:2::long1:5 [ ] ) + to:long1::@1 +long1::@1: scope:[long1] from long1 long1::@1 + [17] (byte) long1::i#2 ← phi( long1/(byte/signed byte/word/signed word/dword/signed dword) 0 long1::@1/(byte) long1::i#1 ) [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [19] *((const byte*) long1::SCREEN#0 + (byte) long1::i#2) ← (byte) long1::i#2 [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) + [20] (byte) long1::i#1 ← ++ (byte) long1::i#2 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) + [21] if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) + to:long1::@return +long1::@return: scope:[long1] from long1::@1 + [22] return [ ] ( main:2::long1:5 [ ] ) + to:@return diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump2.log b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.log new file mode 100644 index 000000000..66338cd46 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.log @@ -0,0 +1,2817 @@ +PARSING src/test/java/dk/camelot64/kickc/test/kc/longjump2.kc +// Minimal example program generating two long jumps + +void main() { + long1(); + long2(); +} + + +void long1() { + byte* SCREEN = $0400; + for(byte i : 0..10) { + asm { + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + } + SCREEN[i] = i; + } +} + +void long2() { + byte* SCREEN = $0400; + for(byte i : 0..10) { + asm { + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + } + SCREEN[i] = i; + } + +} + +STATEMENTS +proc (void()) main() + (void~) main::$0 ← call long1 + (void~) main::$1 ← call long2 +main::@return: + return +endproc // main() +proc (void()) long1() + (byte*) long1::SCREEN ← (word/signed word/dword/signed dword) 1024 + (byte) long1::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 +long1::@1: + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long1::SCREEN + (byte) long1::i) ← (byte) long1::i + (byte) long1::i ← ++ (byte) long1::i + (boolean~) long1::$0 ← (byte) long1::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long1::$0) goto long1::@1 +long1::@return: + return +endproc // long1() +proc (void()) long2() + (byte*) long2::SCREEN ← (word/signed word/dword/signed dword) 1024 + (byte) long2::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 +long2::@1: + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long2::SCREEN + (byte) long2::i) ← (byte) long2::i + (byte) long2::i ← ++ (byte) long2::i + (boolean~) long2::$0 ← (byte) long2::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long2::$0) goto long2::@1 +long2::@return: + return +endproc // long2() + call main + +SYMBOLS +(void()) long1() +(boolean~) long1::$0 +(label) long1::@1 +(label) long1::@return +(byte*) long1::SCREEN +(byte) long1::i +(void()) long2() +(boolean~) long2::$0 +(label) long2::@1 +(label) long2::@return +(byte*) long2::SCREEN +(byte) long2::i +(void()) main() +(void~) main::$0 +(void~) main::$1 +(label) main::@return + +Promoting word/signed word/dword/signed dword to byte* in long1::SCREEN ← ((byte*)) 1024 +Promoting word/signed word/dword/signed dword to byte* in long2::SCREEN ← ((byte*)) 1024 +INITIAL CONTROL FLOW GRAPH +@begin: scope:[] from + to:@1 +main: scope:[main] from + (void~) main::$0 ← call long1 + (void~) main::$1 ← call long2 + to:main::@return +main::@return: scope:[main] from main + return + to:@return +@1: scope:[] from @begin + to:@2 +long1: scope:[long1] from + (byte*) long1::SCREEN ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) long1::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:long1::@1 +long1::@1: scope:[long1] from long1 long1::@1 + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long1::SCREEN + (byte) long1::i) ← (byte) long1::i + (byte) long1::i ← ++ (byte) long1::i + (boolean~) long1::$0 ← (byte) long1::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long1::$0) goto long1::@1 + to:long1::@2 +long1::@2: scope:[long1] from long1::@1 + to:long1::@return +long1::@return: scope:[long1] from long1::@2 + return + to:@return +@2: scope:[] from @1 + to:@3 +long2: scope:[long2] from + (byte*) long2::SCREEN ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) long2::i ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:long2::@1 +long2::@1: scope:[long2] from long2 long2::@1 + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long2::SCREEN + (byte) long2::i) ← (byte) long2::i + (byte) long2::i ← ++ (byte) long2::i + (boolean~) long2::$0 ← (byte) long2::i != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long2::$0) goto long2::@1 + to:long2::@2 +long2::@2: scope:[long2] from long2::@1 + to:long2::@return +long2::@return: scope:[long2] from long2::@2 + return + to:@return +@3: scope:[] from @2 + call main + to:@end +@end: scope:[] from @3 + +Eliminating unused variable - keeping the call (void~) main::$0 +Eliminating unused variable - keeping the call (void~) main::$1 +Removing empty block @1 +Removing empty block long1::@2 +Removing empty block @2 +Removing empty block long2::@2 +PROCEDURE MODIFY VARIABLE ANALYSIS + +Completing Phi functions... + +CONTROL FLOW GRAPH SSA WITH ASSIGNMENT CALL & RETURN +@begin: scope:[] from + to:@3 +main: scope:[main] from @3 + call long1 param-assignment + to:main::@1 +main::@1: scope:[main] from main + call long2 param-assignment + to:main::@2 +main::@2: scope:[main] from main::@1 + to:main::@return +main::@return: scope:[main] from main::@2 + return + to:@return +long1: scope:[long1] from main + (byte*) long1::SCREEN#0 ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) long1::i#0 ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:long1::@1 +long1::@1: scope:[long1] from long1 long1::@1 + (byte*) long1::SCREEN#1 ← phi( long1/(byte*) long1::SCREEN#0 long1::@1/(byte*) long1::SCREEN#1 ) + (byte) long1::i#2 ← phi( long1/(byte) long1::i#0 long1::@1/(byte) long1::i#1 ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long1::SCREEN#1 + (byte) long1::i#2) ← (byte) long1::i#2 + (byte) long1::i#1 ← ++ (byte) long1::i#2 + (boolean~) long1::$0 ← (byte) long1::i#1 != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long1::$0) goto long1::@1 + to:long1::@return +long1::@return: scope:[long1] from long1::@1 + return + to:@return +long2: scope:[long2] from main::@1 + (byte*) long2::SCREEN#0 ← ((byte*)) (word/signed word/dword/signed dword) 1024 + (byte) long2::i#0 ← (byte/signed byte/word/signed word/dword/signed dword) 0 + to:long2::@1 +long2::@1: scope:[long2] from long2 long2::@1 + (byte*) long2::SCREEN#1 ← phi( long2/(byte*) long2::SCREEN#0 long2::@1/(byte*) long2::SCREEN#1 ) + (byte) long2::i#2 ← phi( long2/(byte) long2::i#0 long2::@1/(byte) long2::i#1 ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + *((byte*) long2::SCREEN#1 + (byte) long2::i#2) ← (byte) long2::i#2 + (byte) long2::i#1 ← ++ (byte) long2::i#2 + (boolean~) long2::$0 ← (byte) long2::i#1 != (byte/signed byte/word/signed word/dword/signed dword) 11 + if((boolean~) long2::$0) goto long2::@1 + to:long2::@return +long2::@return: scope:[long2] from long2::@1 + return + to:@return +@3: scope:[] from @begin + call main param-assignment + to:@4 +@4: scope:[] from @3 + to:@end +@end: scope:[] from @4 + +SYMBOL TABLE SSA +(label) @3 +(label) @4 +(label) @begin +(label) @end +(void()) long1() +(boolean~) long1::$0 +(label) long1::@1 +(label) long1::@return +(byte*) long1::SCREEN +(byte*) long1::SCREEN#0 +(byte*) long1::SCREEN#1 +(byte) long1::i +(byte) long1::i#0 +(byte) long1::i#1 +(byte) long1::i#2 +(void()) long2() +(boolean~) long2::$0 +(label) long2::@1 +(label) long2::@return +(byte*) long2::SCREEN +(byte*) long2::SCREEN#0 +(byte*) long2::SCREEN#1 +(byte) long2::i +(byte) long2::i#0 +(byte) long2::i#1 +(byte) long2::i#2 +(void()) main() +(label) main::@1 +(label) main::@2 +(label) main::@return + +OPTIMIZING CONTROL FLOW GRAPH +Culled Empty Block (label) main::@2 +Culled Empty Block (label) @4 +Succesful SSA optimization Pass2CullEmptyBlocks +Self Phi Eliminated (byte*) long1::SCREEN#1 +Self Phi Eliminated (byte*) long2::SCREEN#1 +Succesful SSA optimization Pass2SelfPhiElimination +Redundant Phi (byte*) long1::SCREEN#1 (byte*) long1::SCREEN#0 +Redundant Phi (byte*) long2::SCREEN#1 (byte*) long2::SCREEN#0 +Succesful SSA optimization Pass2RedundantPhiElimination +Simple Condition (boolean~) long1::$0 if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 +Simple Condition (boolean~) long2::$0 if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 +Succesful SSA optimization Pass2ConditionalJumpSimplification +Constant (const byte*) long1::SCREEN#0 = ((byte*))1024 +Constant (const byte) long1::i#0 = 0 +Constant (const byte*) long2::SCREEN#0 = ((byte*))1024 +Constant (const byte) long2::i#0 = 0 +Succesful SSA optimization Pass2ConstantIdentification +Multiple usages for variable. Not optimizing sub-constant (byte) long1::i#2 +Multiple usages for variable. Not optimizing sub-constant (byte) long2::i#2 +Multiple usages for variable. Not optimizing sub-constant (byte) long1::i#2 +Multiple usages for variable. Not optimizing sub-constant (byte) long2::i#2 +OPTIMIZING CONTROL FLOW GRAPH +Inlining constant with var siblings (const byte) long1::i#0 +Inlining constant with var siblings (const byte) long1::i#0 +Inlining constant with var siblings (const byte) long2::i#0 +Inlining constant with var siblings (const byte) long2::i#0 +Constant inlined long1::i#0 = (byte/signed byte/word/signed word/dword/signed dword) 0 +Constant inlined long2::i#0 = (byte/signed byte/word/signed word/dword/signed dword) 0 +Succesful SSA optimization Pass2ConstantInlining +Block Sequence Planned @begin @3 @end main main::@1 main::@return long2 long2::@1 long2::@return long1 long1::@1 long1::@return +Added new block during phi lifting long2::@3(between long2::@1 and long2::@1) +Added new block during phi lifting long1::@3(between long1::@1 and long1::@1) +Block Sequence Planned @begin @3 @end main main::@1 main::@return long2 long2::@1 long2::@return long2::@3 long1 long1::@1 long1::@return long1::@3 +Adding NOP phi() at start of @begin +Adding NOP phi() at start of @3 +Adding NOP phi() at start of @end +Adding NOP phi() at start of main +Adding NOP phi() at start of main::@1 +Adding NOP phi() at start of long2 +Adding NOP phi() at start of long1 +CALL GRAPH +Calls in [] to main:2 +Calls in [main] to long1:5 long2:7 + +Propagating live ranges... +Propagating live ranges... +Propagating live ranges... +Created 2 initial phi equivalence classes +Coalesced [16] long2::i#3 ← long2::i#1 +Coalesced [24] long1::i#3 ← long1::i#1 +Coalesced down to 2 phi equivalence classes +Culled Empty Block (label) long2::@3 +Culled Empty Block (label) long1::@3 +Block Sequence Planned @begin @3 @end main main::@1 main::@return long2 long2::@1 long2::@return long1 long1::@1 long1::@return +Adding NOP phi() at start of @begin +Adding NOP phi() at start of @3 +Adding NOP phi() at start of @end +Adding NOP phi() at start of main +Adding NOP phi() at start of main::@1 +Adding NOP phi() at start of long2 +Adding NOP phi() at start of long1 +Propagating live ranges... +Propagating live ranges... +Propagating live ranges... + +FINAL CONTROL FLOW GRAPH +@begin: scope:[] from + [0] phi() [ ] ( ) + to:@3 +@3: scope:[] from @begin + [1] phi() [ ] ( ) + [2] call main param-assignment [ ] ( ) + to:@end +@end: scope:[] from @3 + [3] phi() [ ] ( ) +main: scope:[main] from @3 + [4] phi() [ ] ( main:2 [ ] ) + [5] call long1 param-assignment [ ] ( main:2 [ ] ) + to:main::@1 +main::@1: scope:[main] from main + [6] phi() [ ] ( main:2 [ ] ) + [7] call long2 param-assignment [ ] ( main:2 [ ] ) + to:main::@return +main::@return: scope:[main] from main::@1 + [8] return [ ] ( main:2 [ ] ) + to:@return +long2: scope:[long2] from main::@1 + [9] phi() [ ] ( main:2::long2:7 [ ] ) + to:long2::@1 +long2::@1: scope:[long2] from long2 long2::@1 + [10] (byte) long2::i#2 ← phi( long2/(byte/signed byte/word/signed word/dword/signed dword) 0 long2::@1/(byte) long2::i#1 ) [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [12] *((const byte*) long2::SCREEN#0 + (byte) long2::i#2) ← (byte) long2::i#2 [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) + [13] (byte) long2::i#1 ← ++ (byte) long2::i#2 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) + [14] if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) + to:long2::@return +long2::@return: scope:[long2] from long2::@1 + [15] return [ ] ( main:2::long2:7 [ ] ) + to:@return +long1: scope:[long1] from main + [16] phi() [ ] ( main:2::long1:5 [ ] ) + to:long1::@1 +long1::@1: scope:[long1] from long1 long1::@1 + [17] (byte) long1::i#2 ← phi( long1/(byte/signed byte/word/signed word/dword/signed dword) 0 long1::@1/(byte) long1::i#1 ) [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) + asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + [19] *((const byte*) long1::SCREEN#0 + (byte) long1::i#2) ← (byte) long1::i#2 [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) + [20] (byte) long1::i#1 ← ++ (byte) long1::i#2 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) + [21] if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) + to:long1::@return +long1::@return: scope:[long1] from long1::@1 + [22] return [ ] ( main:2::long1:5 [ ] ) + to:@return + +DOMINATORS +@begin dominated by @begin +@3 dominated by @begin @3 +@end dominated by @begin @3 @end +main dominated by @begin @3 main +main::@1 dominated by @begin @3 main::@1 main +main::@return dominated by main::@return @begin @3 main::@1 main +long2 dominated by long2 @begin @3 main::@1 main +long2::@1 dominated by long2 @begin @3 main::@1 main long2::@1 +long2::@return dominated by long2 @begin @3 main::@1 main long2::@1 long2::@return +long1 dominated by @begin @3 long1 main +long1::@1 dominated by @begin @3 long1 long1::@1 main +long1::@return dominated by long1::@return @begin @3 long1 long1::@1 main + +NATURAL LOOPS +Found back edge: Loop head: long2::@1 tails: long2::@1 blocks: null +Found back edge: Loop head: long1::@1 tails: long1::@1 blocks: null +Populated: Loop head: long2::@1 tails: long2::@1 blocks: long2::@1 +Populated: Loop head: long1::@1 tails: long1::@1 blocks: long1::@1 +Loop head: long2::@1 tails: long2::@1 blocks: long2::@1 +Loop head: long1::@1 tails: long1::@1 blocks: long1::@1 + +NATURAL LOOPS WITH DEPTH +Found 0 loops in scope [] +Found 0 loops in scope [main] +Found 1 loops in scope [long1] + Loop head: long1::@1 tails: long1::@1 blocks: long1::@1 +Found 1 loops in scope [long2] + Loop head: long2::@1 tails: long2::@1 blocks: long2::@1 +Loop head: long2::@1 tails: long2::@1 blocks: long2::@1 depth: 1 +Loop head: long1::@1 tails: long1::@1 blocks: long1::@1 depth: 1 + + +VARIABLE REGISTER WEIGHTS +(void()) long1() +(byte*) long1::SCREEN +(byte) long1::i +(byte) long1::i#1 16.5 +(byte) long1::i#2 14.666666666666666 +(void()) long2() +(byte*) long2::SCREEN +(byte) long2::i +(byte) long2::i#1 16.5 +(byte) long2::i#2 14.666666666666666 +(void()) main() + +Initial phi equivalence classes +[ long2::i#2 long2::i#1 ] +[ long1::i#2 long1::i#1 ] +Complete equivalence classes +[ long2::i#2 long2::i#1 ] +[ long1::i#2 long1::i#1 ] +Allocated zp ZP_BYTE:2 [ long2::i#2 long2::i#1 ] +Allocated zp ZP_BYTE:3 [ long1::i#2 long1::i#1 ] + +INITIAL ASM +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +bbegin: +//SEG3 [1] phi from @begin to @3 [phi:@begin->@3] +b3_from_bbegin: + jmp b3 +//SEG4 @3 +b3: +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @3 to main [phi:@3->main] +main_from_b3: + jsr main +//SEG7 [3] phi from @3 to @end [phi:@3->@end] +bend_from_b3: + jmp bend +//SEG8 @end +bend: +//SEG9 main +main: { + //SEG10 [5] call long1 param-assignment [ ] ( main:2 [ ] ) + //SEG11 [16] phi from main to long1 [phi:main->long1] + long1_from_main: + jsr long1 + //SEG12 [6] phi from main to main::@1 [phi:main->main::@1] + b1_from_main: + jmp b1 + //SEG13 main::@1 + b1: + //SEG14 [7] call long2 param-assignment [ ] ( main:2 [ ] ) + //SEG15 [9] phi from main::@1 to long2 [phi:main::@1->long2] + long2_from_b1: + jsr long2 + jmp breturn + //SEG16 main::@return + breturn: + //SEG17 [8] return [ ] ( main:2 [ ] ) + rts +} +//SEG18 long2 +long2: { + .label SCREEN = $400 + .label i = 2 + //SEG19 [10] phi from long2 to long2::@1 [phi:long2->long2::@1] + b1_from_long2: + //SEG20 [10] phi (byte) long2::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long2->long2::@1#0] -- vbuz1=vbuc1 + lda #0 + sta i + jmp b1 + //SEG21 [10] phi from long2::@1 to long2::@1 [phi:long2::@1->long2::@1] + b1_from_b1: + //SEG22 [10] phi (byte) long2::i#2 = (byte) long2::i#1 [phi:long2::@1->long2::@1#0] -- register_copy + jmp b1 + //SEG23 long2::@1 + b1: + //SEG24 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG25 [12] *((const byte*) long2::SCREEN#0 + (byte) long2::i#2) ← (byte) long2::i#2 [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) -- pbuc1_derefidx_vbuz1=vbuz1 + ldy i + tya + sta SCREEN,y + //SEG26 [13] (byte) long2::i#1 ← ++ (byte) long2::i#2 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuz1=_inc_vbuz1 + inc i + //SEG27 [14] if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuz1_neq_vbuc1_then_la1 + lda i + cmp #$b + bne b1_from_b1 + jmp breturn + //SEG28 long2::@return + breturn: + //SEG29 [15] return [ ] ( main:2::long2:7 [ ] ) + rts +} +//SEG30 long1 +long1: { + .label SCREEN = $400 + .label i = 3 + //SEG31 [17] phi from long1 to long1::@1 [phi:long1->long1::@1] + b1_from_long1: + //SEG32 [17] phi (byte) long1::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long1->long1::@1#0] -- vbuz1=vbuc1 + lda #0 + sta i + jmp b1 + //SEG33 [17] phi from long1::@1 to long1::@1 [phi:long1::@1->long1::@1] + b1_from_b1: + //SEG34 [17] phi (byte) long1::i#2 = (byte) long1::i#1 [phi:long1::@1->long1::@1#0] -- register_copy + jmp b1 + //SEG35 long1::@1 + b1: + //SEG36 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG37 [19] *((const byte*) long1::SCREEN#0 + (byte) long1::i#2) ← (byte) long1::i#2 [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) -- pbuc1_derefidx_vbuz1=vbuz1 + ldy i + tya + sta SCREEN,y + //SEG38 [20] (byte) long1::i#1 ← ++ (byte) long1::i#2 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuz1=_inc_vbuz1 + inc i + //SEG39 [21] if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuz1_neq_vbuc1_then_la1 + lda i + cmp #$b + bne b1_from_b1 + jmp breturn + //SEG40 long1::@return + breturn: + //SEG41 [22] return [ ] ( main:2::long1:5 [ ] ) + rts +} + +REGISTER UPLIFT POTENTIAL REGISTERS +Potential registers zp ZP_BYTE:2 [ long2::i#2 long2::i#1 ] : zp ZP_BYTE:2 , reg byte a , reg byte x , reg byte y , +Potential registers zp ZP_BYTE:3 [ long1::i#2 long1::i#1 ] : zp ZP_BYTE:3 , reg byte a , reg byte x , reg byte y , + +REGISTER UPLIFT SCOPES +Uplift Scope [long1] 31.17: zp ZP_BYTE:3 [ long1::i#2 long1::i#1 ] +Uplift Scope [long2] 31.17: zp ZP_BYTE:2 [ long2::i#2 long2::i#1 ] +Uplift Scope [main] +Uplift Scope [] + +Uplifting [long1] best 10898 combination reg byte x [ long1::i#2 long1::i#1 ] +Uplifting [long2] best 10778 combination reg byte x [ long2::i#2 long2::i#1 ] +Uplifting [main] best 10778 combination +Uplifting [] best 10778 combination + +ASSEMBLER BEFORE OPTIMIZATION +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +bbegin: +//SEG3 [1] phi from @begin to @3 [phi:@begin->@3] +b3_from_bbegin: + jmp b3 +//SEG4 @3 +b3: +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @3 to main [phi:@3->main] +main_from_b3: + jsr main +//SEG7 [3] phi from @3 to @end [phi:@3->@end] +bend_from_b3: + jmp bend +//SEG8 @end +bend: +//SEG9 main +main: { + //SEG10 [5] call long1 param-assignment [ ] ( main:2 [ ] ) + //SEG11 [16] phi from main to long1 [phi:main->long1] + long1_from_main: + jsr long1 + //SEG12 [6] phi from main to main::@1 [phi:main->main::@1] + b1_from_main: + jmp b1 + //SEG13 main::@1 + b1: + //SEG14 [7] call long2 param-assignment [ ] ( main:2 [ ] ) + //SEG15 [9] phi from main::@1 to long2 [phi:main::@1->long2] + long2_from_b1: + jsr long2 + jmp breturn + //SEG16 main::@return + breturn: + //SEG17 [8] return [ ] ( main:2 [ ] ) + rts +} +//SEG18 long2 +long2: { + .label SCREEN = $400 + //SEG19 [10] phi from long2 to long2::@1 [phi:long2->long2::@1] + b1_from_long2: + //SEG20 [10] phi (byte) long2::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long2->long2::@1#0] -- vbuxx=vbuc1 + ldx #0 + jmp b1 + //SEG21 [10] phi from long2::@1 to long2::@1 [phi:long2::@1->long2::@1] + b1_from_b1: + //SEG22 [10] phi (byte) long2::i#2 = (byte) long2::i#1 [phi:long2::@1->long2::@1#0] -- register_copy + jmp b1 + //SEG23 long2::@1 + b1: + //SEG24 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG25 [12] *((const byte*) long2::SCREEN#0 + (byte) long2::i#2) ← (byte) long2::i#2 [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG26 [13] (byte) long2::i#1 ← ++ (byte) long2::i#2 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG27 [14] if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + bne b1_from_b1 + jmp breturn + //SEG28 long2::@return + breturn: + //SEG29 [15] return [ ] ( main:2::long2:7 [ ] ) + rts +} +//SEG30 long1 +long1: { + .label SCREEN = $400 + //SEG31 [17] phi from long1 to long1::@1 [phi:long1->long1::@1] + b1_from_long1: + //SEG32 [17] phi (byte) long1::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long1->long1::@1#0] -- vbuxx=vbuc1 + ldx #0 + jmp b1 + //SEG33 [17] phi from long1::@1 to long1::@1 [phi:long1::@1->long1::@1] + b1_from_b1: + //SEG34 [17] phi (byte) long1::i#2 = (byte) long1::i#1 [phi:long1::@1->long1::@1#0] -- register_copy + jmp b1 + //SEG35 long1::@1 + b1: + //SEG36 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG37 [19] *((const byte*) long1::SCREEN#0 + (byte) long1::i#2) ← (byte) long1::i#2 [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG38 [20] (byte) long1::i#1 ← ++ (byte) long1::i#2 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG39 [21] if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + bne b1_from_b1 + jmp breturn + //SEG40 long1::@return + breturn: + //SEG41 [22] return [ ] ( main:2::long1:5 [ ] ) + rts +} + +ASSEMBLER OPTIMIZATIONS +Removing instruction jmp b3 +Removing instruction jmp bend +Removing instruction jmp b1 +Removing instruction jmp breturn +Removing instruction jmp b1 +Removing instruction jmp breturn +Removing instruction jmp b1 +Removing instruction jmp breturn +Succesful ASM optimization Pass5NextJumpElimination +Replacing label b1_from_b1 with b1 +Replacing label b1_from_b1 with b1 +Removing instruction bbegin: +Removing instruction b3_from_bbegin: +Removing instruction main_from_b3: +Removing instruction bend_from_b3: +Removing instruction b1_from_main: +Removing instruction long2_from_b1: +Removing instruction b1_from_b1: +Removing instruction b1_from_b1: +Succesful ASM optimization Pass5RedundantLabelElimination +Removing instruction b3: +Removing instruction bend: +Removing instruction long1_from_main: +Removing instruction b1: +Removing instruction breturn: +Removing instruction b1_from_long2: +Removing instruction breturn: +Removing instruction b1_from_long1: +Removing instruction breturn: +Succesful ASM optimization Pass5UnusedLabelElimination +Removing instruction jmp b1 +Removing instruction jmp b1 +Succesful ASM optimization Pass5NextJumpElimination +Fixing long branch [273] bne b1 to beq +Fixing long branch [542] bne b1 to beq + +FINAL SYMBOL TABLE +(label) @3 +(label) @begin +(label) @end +(void()) long1() +(label) long1::@1 +(label) long1::@return +(byte*) long1::SCREEN +(const byte*) long1::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) long1::i +(byte) long1::i#1 reg byte x 16.5 +(byte) long1::i#2 reg byte x 14.666666666666666 +(void()) long2() +(label) long2::@1 +(label) long2::@return +(byte*) long2::SCREEN +(const byte*) long2::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) long2::i +(byte) long2::i#1 reg byte x 16.5 +(byte) long2::i#2 reg byte x 14.666666666666666 +(void()) main() +(label) main::@1 +(label) main::@return + +reg byte x [ long2::i#2 long2::i#1 ] +reg byte x [ long1::i#2 long1::i#1 ] + + +FINAL ASSEMBLER +Score: 10646 + +//SEG0 Basic Upstart +.pc = $801 "Basic" +:BasicUpstart(main) +.pc = $80d "Program" +//SEG1 Global Constants & labels +//SEG2 @begin +//SEG3 [1] phi from @begin to @3 [phi:@begin->@3] +//SEG4 @3 +//SEG5 [2] call main param-assignment [ ] ( ) +//SEG6 [4] phi from @3 to main [phi:@3->main] + jsr main +//SEG7 [3] phi from @3 to @end [phi:@3->@end] +//SEG8 @end +//SEG9 main +main: { + //SEG10 [5] call long1 param-assignment [ ] ( main:2 [ ] ) + //SEG11 [16] phi from main to long1 [phi:main->long1] + jsr long1 + //SEG12 [6] phi from main to main::@1 [phi:main->main::@1] + //SEG13 main::@1 + //SEG14 [7] call long2 param-assignment [ ] ( main:2 [ ] ) + //SEG15 [9] phi from main::@1 to long2 [phi:main::@1->long2] + jsr long2 + //SEG16 main::@return + //SEG17 [8] return [ ] ( main:2 [ ] ) + rts +} +//SEG18 long2 +long2: { + .label SCREEN = $400 + //SEG19 [10] phi from long2 to long2::@1 [phi:long2->long2::@1] + //SEG20 [10] phi (byte) long2::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long2->long2::@1#0] -- vbuxx=vbuc1 + ldx #0 + //SEG21 [10] phi from long2::@1 to long2::@1 [phi:long2::@1->long2::@1] + //SEG22 [10] phi (byte) long2::i#2 = (byte) long2::i#1 [phi:long2::@1->long2::@1#0] -- register_copy + //SEG23 long2::@1 + b1: + //SEG24 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG25 [12] *((const byte*) long2::SCREEN#0 + (byte) long2::i#2) ← (byte) long2::i#2 [ long2::i#2 ] ( main:2::long2:7 [ long2::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG26 [13] (byte) long2::i#1 ← ++ (byte) long2::i#2 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG27 [14] if((byte) long2::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long2::@1 [ long2::i#1 ] ( main:2::long2:7 [ long2::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + beq !b+ + jmp b1 + !b: + //SEG28 long2::@return + //SEG29 [15] return [ ] ( main:2::long2:7 [ ] ) + rts +} +//SEG30 long1 +long1: { + .label SCREEN = $400 + //SEG31 [17] phi from long1 to long1::@1 [phi:long1->long1::@1] + //SEG32 [17] phi (byte) long1::i#2 = (byte/signed byte/word/signed word/dword/signed dword) 0 [phi:long1->long1::@1#0] -- vbuxx=vbuc1 + ldx #0 + //SEG33 [17] phi from long1::@1 to long1::@1 [phi:long1::@1->long1::@1] + //SEG34 [17] phi (byte) long1::i#2 = (byte) long1::i#1 [phi:long1::@1->long1::@1#0] -- register_copy + //SEG35 long1::@1 + b1: + //SEG36 asm { nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop nop } + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + nop + //SEG37 [19] *((const byte*) long1::SCREEN#0 + (byte) long1::i#2) ← (byte) long1::i#2 [ long1::i#2 ] ( main:2::long1:5 [ long1::i#2 ] ) -- pbuc1_derefidx_vbuxx=vbuxx + txa + sta SCREEN,x + //SEG38 [20] (byte) long1::i#1 ← ++ (byte) long1::i#2 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuxx=_inc_vbuxx + inx + //SEG39 [21] if((byte) long1::i#1!=(byte/signed byte/word/signed word/dword/signed dword) 11) goto long1::@1 [ long1::i#1 ] ( main:2::long1:5 [ long1::i#1 ] ) -- vbuxx_neq_vbuc1_then_la1 + cpx #$b + beq !b+ + jmp b1 + !b: + //SEG40 long1::@return + //SEG41 [22] return [ ] ( main:2::long1:5 [ ] ) + rts +} + diff --git a/src/test/java/dk/camelot64/kickc/test/ref/longjump2.sym b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.sym new file mode 100644 index 000000000..198792fc5 --- /dev/null +++ b/src/test/java/dk/camelot64/kickc/test/ref/longjump2.sym @@ -0,0 +1,25 @@ +(label) @3 +(label) @begin +(label) @end +(void()) long1() +(label) long1::@1 +(label) long1::@return +(byte*) long1::SCREEN +(const byte*) long1::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) long1::i +(byte) long1::i#1 reg byte x 16.5 +(byte) long1::i#2 reg byte x 14.666666666666666 +(void()) long2() +(label) long2::@1 +(label) long2::@return +(byte*) long2::SCREEN +(const byte*) long2::SCREEN#0 SCREEN = ((byte*))(word/signed word/dword/signed dword) 1024 +(byte) long2::i +(byte) long2::i#1 reg byte x 16.5 +(byte) long2::i#2 reg byte x 14.666666666666666 +(void()) main() +(label) main::@1 +(label) main::@return + +reg byte x [ long2::i#2 long2::i#1 ] +reg byte x [ long1::i#2 long1::i#1 ]