From f4bd723d929e53475f7990374dca7b7dfcbbdc42 Mon Sep 17 00:00:00 2001 From: Cliff Click Date: Sun, 1 Nov 2026 10:33:55 -0800 Subject: Add Chapter 29 for tech debt cleanup with the parser split Keep Chapter 28b intact and carry the grammar-oriented parser package, Var move, IterPeeps move, and parser regression tests into Chapter 29. Defer privacy and exclude its experimental tests and fixture changes. Register the chapter in the indexes, IntelliJ modules and run configurations, Maven reactor, roadmap, and linear-history publisher. Windows and Linux each pass 573 tests, release builds, 199 allocation replays, and 29 native checks. --- .../java/com/seaofnodes/simple/Chapter17aTest.java | 109 +++++++++++++++++++++ 1 file changed, 109 insertions(+) create mode 100644 chapter29/src/test/java/com/seaofnodes/simple/Chapter17aTest.java (limited to 'chapter29/src/test/java/com/seaofnodes/simple/Chapter17aTest.java') diff --git a/chapter29/src/test/java/com/seaofnodes/simple/Chapter17aTest.java b/chapter29/src/test/java/com/seaofnodes/simple/Chapter17aTest.java new file mode 100644 index 00000000..ea7afe56 --- /dev/null +++ b/chapter29/src/test/java/com/seaofnodes/simple/Chapter17aTest.java @@ -0,0 +1,109 @@ +package com.seaofnodes.simple; + +import com.seaofnodes.simple.codegen.CodeGen; +import org.junit.Test; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.fail; + +public class Chapter17aTest { + + @Test + public void testFinal1() { + CodeGen code = new CodeGen( +""" +int x=2, y=3; +if( arg ) { int x = y; x = x*x; y=x; } // Shadow final x +return y; +"""); + code.driver(CodeGen.Phase.FinalizeIR); + assertEquals("return Phi(Region,9,3);", code.print()); + assertEquals("3", Eval2.eval(code, 0)); + assertEquals("9", Eval2.eval(code, 1)); + } + + @Test + public void testConstruct1() { + CodeGen code = new CodeGen(""" +struct _X { int ~x; new _X = { int xx -> x=xx; }; }; +_X z = new _X(3); +return z.x; +"""); + code.driver(CodeGen.Phase.FinalizeIR); + assertEquals("return 3;", code.print()); + assertEquals("3", Eval2.eval(code, 0)); + } + + @Test + public void testStructFinal0() { + CodeGen code = new CodeGen(""" +struct _Point { int ~x, ~y; new _Point = { int xx, int yy -> x=xx; y=yy; }; }; +_Point p = new _Point(3,4); +return p; +"""); + code.driver(CodeGen.Phase.FinalizeIR); + assertEquals("return (const)Test._Point;", code.print()); + assertEquals("Test._Point{x=3,y=4}", Eval2.eval(code, 0)); + } + + @Test + public void testStructFinal1() { + CodeGen code = new CodeGen(""" +struct _Point { int x=3, y=4; new _Point = { int xx, int yy -> x=xx; y=yy; }; }; +~_Point p = new _Point(5,6); +p.x++; +return p; +"""); + try { code.driver(CodeGen.Phase.TypeCheck); fail(); } + catch( Exception e ) { assertEquals("Cannot modify final field 'x'",e.getMessage()); } + } + + @Test + public void testStructFinal2() { + CodeGen code = new CodeGen(""" +struct _Point { int x=3, y=4; }; +~_Point p = new _Point; +p.x++; +return p; +"""); + try { code.driver(CodeGen.Phase.TypeCheck); fail(); } + catch( Exception e ) { assertEquals("Cannot modify final field 'x'",e.getMessage()); } + } + + @Test + public void testStructFinal3() { + CodeGen code = new CodeGen(""" +struct _Point { var x; var y; }; +_Point p = new _Point; +p.x++; +return p; +"""); + try { code.driver(CodeGen.Phase.FinalizeIR); fail(); } + catch( Exception e ) { assertEquals("'Test._Point' is not fully initialized, field 'x' needs to be set in a constructor",e.getMessage()); } + } + + @Test + public void testStructFinal4() { + CodeGen code = new CodeGen(""" +struct _Point { val x=2; val y=4; }; +_Point p = new _Point; +p.x++; +return p; +"""); + try { code.driver(CodeGen.Phase.TypeCheck); fail(); } + catch( Exception e ) { assertEquals("Cannot modify final field 'x'",e.getMessage()); } + } + + @Test + public void testStructFinal5() { + CodeGen code = new CodeGen(""" +struct _Point { var x=3; var y=4; }; +!_Point !p = new _Point; +p.x++; +return p; +"""); + code.driver(CodeGen.Phase.FinalizeIR); + assertEquals("return Test._Point;", code.print()); + assertEquals("Test._Point{x=4,y=4}", Eval2.eval(code, 0)); + } + +} -- cgit v1.2.3