diff options
| author | Cliff Click <cliffc@acm.org> | 2025-04-06 16:22:38 -0700 |
|---|---|---|
| committer | Cliff Click <cliffc@acm.org> | 2025-04-06 16:22:38 -0700 |
| commit | a81794df00369f6adf4a06e2f0247d309a196e27 (patch) | |
| tree | 667c1fd370acb05c21dda87baa7552822cd9841a /chapter21/src | |
| parent | 4c4778f8cc3dd4fd354832bfb0ba1a8c03ee744d (diff) | |
| download | Simple-a81794df00369f6adf4a06e2f0247d309a196e27.tar.gz Simple-a81794df00369f6adf4a06e2f0247d309a196e27.zip | |
Fix sieve
RA returns maxSlot+1
FunX86 prints as `subi`, uses Sub; Ret uses Add
X86 knows that always RPC is passed on stack "as if" a stack arg.
sieve uses unsigned ints.
Driver expects an array pointer
Diffstat (limited to 'chapter21/src')
10 files changed, 30 insertions, 34 deletions
diff --git a/chapter21/src/main/java/com/seaofnodes/simple/codegen/RegAlloc.java b/chapter21/src/main/java/com/seaofnodes/simple/codegen/RegAlloc.java index 9042de3b..c84e6011 100644 --- a/chapter21/src/main/java/com/seaofnodes/simple/codegen/RegAlloc.java +++ b/chapter21/src/main/java/com/seaofnodes/simple/codegen/RegAlloc.java @@ -550,7 +550,7 @@ public class RegAlloc { Node n = bb.out(j); if( lrg(n)!=null ) { int slot = _code._mach.stackSlot(lrg(n)._reg); - maxSlot = Math.max(maxSlot,slot); + maxSlot = Math.max(maxSlot,slot+1); } if( !(n instanceof SplitNode lo) ) continue; diff --git a/chapter21/src/main/java/com/seaofnodes/simple/node/FunNode.java b/chapter21/src/main/java/com/seaofnodes/simple/node/FunNode.java index 8db30e7d..2e32b75e 100644 --- a/chapter21/src/main/java/com/seaofnodes/simple/node/FunNode.java +++ b/chapter21/src/main/java/com/seaofnodes/simple/node/FunNode.java @@ -184,7 +184,7 @@ public class FunNode extends RegionNode { public short _maxSlot = -1; // Max argument slot, set during early Encoding. public short _maxArgSlot = -1; - // Frame adjust, including padding, st during early Encoding + // Frame adjust, including padding, set during early Encoding public short _frameAdjust; diff --git a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/FunX86.java b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/FunX86.java index 923fa362..15805fee 100644 --- a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/FunX86.java +++ b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/FunX86.java @@ -7,7 +7,7 @@ import com.seaofnodes.simple.node.MachNode; public class FunX86 extends FunNode implements MachNode { FunX86( FunNode fun ) { super(fun); } - @Override public String op() { return "addi"; } + @Override public String op() { return "subi"; } @Override public RegMask regmap(int i) { return null; } @Override public RegMask outregmap() { return null; } @Override public void postSelect(CodeGen code) { code.link(this); } @@ -16,15 +16,16 @@ public class FunX86 extends FunNode implements MachNode { // X86, with too many args & spills: // | CALLER | // | argN | // slot 1, required by callER - // +--------+ + // +--------+ // Old frame // | RPC | // slot 0, required by callER + // +--------+ // New frame top + // | PAD16 | // | callee | // slot 3, callEE // | callee | // slot 2, callEE - // | PAD16 | // +--------+ @Override public void encoding( Encoding enc ) { // Stack frame size: _maxSlot - max(arg), padded to 16. - _maxArgSlot = x86_64_v2.maxSlot(enc._fun.sig()); + _maxArgSlot = x86_64_v2.maxArgSlot(enc._fun.sig()); int sz = _maxSlot - _maxArgSlot; // If non-leaf function, pad to 16b if( _hasCalls ) sz = ((sz+1) & -2)+1; @@ -34,11 +35,11 @@ public class FunX86 extends FunNode implements MachNode { // opcode: 0x83, addi rsp with immediate 8 enc.add1( x86_64_v2.REX_W ).add1( 0x83 ); - enc.add1( x86_64_v2.modrm(x86_64_v2.MOD.DIRECT, 0, x86_64_v2.RSP) ); + enc.add1( x86_64_v2.modrm(x86_64_v2.MOD.DIRECT, 0b101, x86_64_v2.RSP) ); enc.add1(sz*8); } @Override public void asm(CodeGen code, SB sb) { - sb.p("rsp += #").p(_frameAdjust*8); + sb.p("rsp -= #").p(_frameAdjust*8); } } diff --git a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/RetX86.java b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/RetX86.java index a9da15c6..4faf7cb4 100644 --- a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/RetX86.java +++ b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/RetX86.java @@ -22,7 +22,7 @@ public class RetX86 extends ReturnNode implements MachNode { if( frameAdjust > 0 ) { enc.add1( x86_64_v2.REX_W ).add1( 0x83 ); enc.add1( x86_64_v2.modrm(x86_64_v2.MOD.DIRECT, 0, x86_64_v2.RSP) ); - enc.add1(frameAdjust*-8); + enc.add1(frameAdjust*8); } enc.add1(0xC3); } diff --git a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/x86_64_v2.java b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/x86_64_v2.java index d9bca291..4770bfbb 100644 --- a/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/x86_64_v2.java +++ b/chapter21/src/main/java/com/seaofnodes/simple/node/cpus/x86_64_v2/x86_64_v2.java @@ -59,10 +59,10 @@ public class x86_64_v2 extends Machine { public static int REX_WB = 0x49; public enum MOD { - INDIRECT, // [mem] - INDIRECT_disp8, // [mem + 0x12] - INDIRECT_disp32,// [mem + 0x12345678] - DIRECT, // mem + INDIRECT, // [mem] + INDIRECT_disp8, // [mem + 0x12] + INDIRECT_disp32, // [mem + 0x12345678] + DIRECT, // mem }; // opcode included here @@ -249,8 +249,8 @@ public class x86_64_v2 extends Machine { throw Utils.TODO(); // Pass on stack slot } - // Return the max stack slot used by this signature, or 0 - static short maxSlot( TypeFunPtr tfp ) { + // Return the max stack slot used by this signature, or 1 (for RPC) + static short maxArgSlot( TypeFunPtr tfp ) { // Count floats in signature up to index int fcnt=0; for( int i=0; i<tfp.nargs(); i++ ) @@ -265,12 +265,7 @@ public class x86_64_v2 extends Machine { }; if( tfp.nargs()-fcnt >= cargs.length ) throw Utils.TODO(); - return 0; // No stack args - } - - // Return single int/ptr register. Used by CallEnd output and Return input. - static RegMask retMask( TypeFunPtr tfp ) { - return tfp.ret() instanceof TypeFloat ? XMM0_MASK : RAX_MASK; + return 1; // No stack args, plus RPC } diff --git a/chapter21/src/test/java/com/seaofnodes/simple/Chapter15Test.java b/chapter21/src/test/java/com/seaofnodes/simple/Chapter15Test.java index a850b1b8..8da5cf96 100644 --- a/chapter21/src/test/java/com/seaofnodes/simple/Chapter15Test.java +++ b/chapter21/src/test/java/com/seaofnodes/simple/Chapter15Test.java @@ -217,8 +217,8 @@ return ary[1] * 1000 + ary[3]; // 1 * 1000 + 6 String src = Files.readString(Path.of("src/test/java/com/seaofnodes/simple/progs/sieve.smp")); CodeGen code = new CodeGen(src+"return sieve(arg);"); code.parse().opto(); - assertEquals("return [int];", code.print()); - assertEquals("int[ 2,3,5,7,11,13,17,19]",Eval2.eval(code, 20)); + assertEquals("return [u32];", code.print()); + assertEquals("u32[ 2,3,5,7,11,13,17,19]",Eval2.eval(code, 20)); } @Test diff --git a/chapter21/src/test/java/com/seaofnodes/simple/Chapter19Test.java b/chapter21/src/test/java/com/seaofnodes/simple/Chapter19Test.java index 6425fb80..9ba8e972 100644 --- a/chapter21/src/test/java/com/seaofnodes/simple/Chapter19Test.java +++ b/chapter21/src/test/java/com/seaofnodes/simple/Chapter19Test.java @@ -303,8 +303,8 @@ return A[1]; public void sieveOfEratosthenes() throws IOException { String src = Files.readString(Path.of("src/test/java/com/seaofnodes/simple/progs/sieve.smp")); CodeGen code = new CodeGen(src).parse().opto().typeCheck().instSelect("x86_64_v2", "SystemV").GCM().localSched(); - assertEquals("return [int];", code.print()); - //assertEquals("int[ 2,3,5,7,11,13,17,19]",Eval2.eval(code, 20)); + assertEquals("return [u32];", code.print()); + //assertEquals("u32[ 2,3,5,7,11,13,17,19]",Eval2.eval(code, 20)); } diff --git a/chapter21/src/test/java/com/seaofnodes/simple/Chapter21Test.java b/chapter21/src/test/java/com/seaofnodes/simple/Chapter21Test.java index 3f764a4c..170a7674 100644 --- a/chapter21/src/test/java/com/seaofnodes/simple/Chapter21Test.java +++ b/chapter21/src/test/java/com/seaofnodes/simple/Chapter21Test.java @@ -89,7 +89,7 @@ public class Chapter21Test { @Test public void testStringExport() throws IOException { TestC.run("stringHash"); } @Test public void testSieve() throws IOException { - String primes = "[2, 3, ]"; + String primes = "25[2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97, ]"; TestC.run("sieve",primes); } diff --git a/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.c b/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.c index 8c28aea8..b0e85dba 100644 --- a/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.c +++ b/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.c @@ -3,16 +3,16 @@ typedef struct AryInt { unsigned int len; - unsigned int data[]; + int data[]; } AryInt; -extern AryInt sieve(int N); +extern AryInt *sieve(int N); int main() { - AryInt ps = sieve(10); - printf("["); - for( int i=0; i<ps.len; i++ ) - printf("%d, ",ps.data[i]); + AryInt* ps = sieve(100); + printf("%d[",ps->len); + for( int i=0; i<ps->len; i++ ) + printf("%d, ",ps->data[i]); printf("]"); return 0; } diff --git a/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.smp b/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.smp index c5c3824a..6d160b1e 100644 --- a/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.smp +++ b/chapter21/src/test/java/com/seaofnodes/simple/progs/sieve.smp @@ -3,7 +3,7 @@ val sieve = { int N -> bool[] !ary = new bool[N]; // The primes less than N - int[] !primes = new int[N>>1]; + u32[] !primes = new u32[N>>1]; // Number of primes so far, searching at index p int nprimes = 0, p=2; // Find primes while p^2 < N @@ -24,7 +24,7 @@ val sieve = { int N -> primes[nprimes++] = p; // Copy/shrink the result array - int[] !rez = new int[nprimes]; + u32[] !rez = new u32[nprimes]; for( int j=0; j < nprimes; j++ ) rez[j] = primes[j]; return rez; |
