From c039fa81f7aa09a033444a94fd4ff44ca57b556b Mon Sep 17 00:00:00 2001 From: Will Medrano Date: Mon, 26 Aug 2024 08:24:25 -0700 Subject: [PATCH] Replace main.zig with a golden test. Fizz is a library so it makes sense to remove any non-example binaries. --- build.zig | 33 ++------ src/golden_test.zig | 89 ++++++++++++++++++++++ src/main.zig | 69 ----------------- main.fizz => test_scripts/golden_test.fizz | 0 4 files changed, 94 insertions(+), 97 deletions(-) create mode 100644 src/golden_test.zig delete mode 100644 src/main.zig rename main.fizz => test_scripts/golden_test.fizz (100%) diff --git a/build.zig b/build.zig index 825f7dc..9d12823 100644 --- a/build.zig +++ b/build.zig @@ -4,51 +4,28 @@ pub fn build(b: *std.Build) void { const target = b.standardTargetOptions(.{}); const optimize = b.standardOptimizeOption(.{}); - // Command: zig build install - const exe = b.addExecutable(.{ - .name = "fizz", - .root_source_file = b.path("src/main.zig"), + // Module: fizz + _ = b.addModule("fizz", .{ + .root_source_file = b.path("src/root.zig"), .target = target, .optimize = optimize, }); - b.installArtifact(exe); // Command: zig build check // // Run a build without completing the fool exe_build. This is a workaround, a more stable // solution is tracked at https://github.com/ziglang/zig/issues/18877 - const check_exe = b.addExecutable(.{ - .name = "fizz", - .root_source_file = b.path("src/main.zig"), - .target = target, - .optimize = optimize, - }); const check_test = b.addTest(.{ - .root_source_file = b.path("src/main.zig"), + .root_source_file = b.path("src/golden_test.zig"), .target = target, .optimize = optimize, }); const check_step = b.step("check", "Check for compile errors"); - check_step.dependOn(&check_exe.step); check_step.dependOn(&check_test.step); - // Module: fizz - _ = b.addModule("fizz", .{ - .root_source_file = b.path("src/root.zig"), - .target = target, - .optimize = optimize, - }); - - // Command: zig build run - const run_cmd = b.addRunArtifact(exe); - run_cmd.step.dependOn(b.getInstallStep()); - if (b.args) |args| run_cmd.addArgs(args); - const run_step = b.step("run", "Run the app"); - run_step.dependOn(&run_cmd.step); - // Command: zig build test const exe_unit_tests = b.addTest(.{ - .root_source_file = b.path("src/main.zig"), + .root_source_file = b.path("src/golden_test.zig"), .target = target, .optimize = optimize, }); diff --git a/src/golden_test.zig b/src/golden_test.zig new file mode 100644 index 0000000..72feeb1 --- /dev/null +++ b/src/golden_test.zig @@ -0,0 +1,89 @@ +const std = @import("std"); +const Ast = @import("Ast.zig"); +const Vm = @import("Vm.zig"); +const Ir = @import("ir.zig").Ir; +const Compiler = @import("Compiler.zig"); + +test "golden test" { + const input = try std.fs.cwd().readFileAlloc(std.testing.allocator, "./test_scripts/golden_test.fizz", 4096); + defer std.testing.allocator.free(input); + + var writer_buffer = std.ArrayList(u8).init(std.testing.allocator); + var writer = writer_buffer.writer(); + defer writer_buffer.deinit(); + + var base_allocator = std.heap.GeneralPurposeAllocator(.{}){}; + const allocator = base_allocator.allocator(); + var vm = try Vm.init(allocator); + defer vm.deinit(); + + var ast = try Ast.initWithStr(std.testing.allocator, input); + defer ast.deinit(); + var expr_number: usize = 1; + for (ast.asts) |node| { + try runAst(std.testing.allocator, &writer, &vm, &expr_number, &node); + } + + const actual = writer_buffer.items; + const expected = + \\$1: "------------------------------------------------------------" + \\$2: "test define" + \\$3: "defined once" + \\$4: "redefined" + \\$5: "------------------------------------------------------------" + \\$6: "test functions" + \\$7: 31400 + \\$8: 31400 + \\$9: "------------------------------------------------------------" + \\$10: "test strings" + \\$11: "0123" + \\$12: 4 + \\$13: "" + \\$14: "01" + \\$15: "" + \\$16: "3" + \\$17: "------------------------------------------------------------" + \\$18: "test lists" + \\$19: 1 + \\$20: (2 3 4) + \\$21: (3 4) + \\$22: 4 + \\$23: "------------------------------------------------------------" + \\$24: "test structs" + \\$25: (struct 'id 0 'hello "world") + \\$26: (struct 'id 100 'hello "world") + \\$27: "world" + \\$28: "------------------------------------------------------------" + \\$29: "test fib" + \\$30: + \\$31: 75025 + \\$32: "------------------------------------------------------------" + \\$33: "test equal" + \\$34: true + \\$35: true + \\$36: "------------------------------------------------------------" + \\$37: "test modules" + \\$38: ("*global*" "*test*" "/dev/null") + \\$39: "------------------------------------------------------------" + \\ + ; + try std.testing.expectEqualStrings(expected, actual); +} + +fn runAst(allocator: std.mem.Allocator, writer: anytype, vm: *Vm, expr_number: *usize, ast: *const Ast.Node) !void { + var compiler = try Compiler.initModule( + allocator, + &vm.env, + try vm.env.getOrCreateModule(.{ .name = "*test*" }), + ); + defer compiler.deinit(); + const ir = try Ir.init(allocator, &[1]Ast.Node{ast.*}); + defer ir.deinit(allocator); + const bytecode = try compiler.compile(ir); + const res = try vm.eval(bytecode, &.{}); + if (res.tag() != .none) { + try writer.print("${d}: {any}\n", .{ expr_number.*, res }); + expr_number.* += 1; + } + try vm.env.runGc(); +} diff --git a/src/main.zig b/src/main.zig deleted file mode 100644 index bf996db..0000000 --- a/src/main.zig +++ /dev/null @@ -1,69 +0,0 @@ -const std = @import("std"); -const Ast = @import("Ast.zig"); -const Vm = @import("Vm.zig"); -const Ir = @import("ir.zig").Ir; -const Compiler = @import("Compiler.zig"); - -pub fn main() !void { - const input = try std.fs.cwd().readFileAlloc(std.heap.page_allocator, "main.fizz", 1024 * 1024); - defer std.heap.page_allocator.free(input); - const stdout = std.io.getStdOut(); - try runScript(stdout.writer(), input, false); -} - -fn runScript( - writer: anytype, - script_contents: []const u8, - require_determinism: bool, -) !void { - var base_allocator = std.heap.GeneralPurposeAllocator(.{}){}; - const allocator = base_allocator.allocator(); - var vm = try Vm.init(allocator); - defer vm.deinit(); - - var ast_arena = std.heap.ArenaAllocator.init(std.heap.page_allocator); - defer ast_arena.deinit(); - const ast = try Ast.initWithStr(ast_arena.allocator(), script_contents); - var ir_arena = std.heap.ArenaAllocator.init(std.heap.page_allocator); - defer ir_arena.deinit(); - var expr_number: usize = 1; - for (ast.asts) |node| { - try runAst(ir_arena.allocator(), writer, &vm, &expr_number, &node); - _ = ir_arena.reset(.retain_capacity); - } - if (!require_determinism) { - try writer.print("gc_duration: {d}ns\n", .{vm.env.runtime_stats.gc_duration_nanos}); - } -} - -fn runAst(allocator: std.mem.Allocator, writer: anytype, vm: *Vm, expr_number: *usize, ast: *const Ast.Node) !void { - var compiler = try Compiler.initModule( - allocator, - &vm.env, - try vm.env.getOrCreateModule(.{ .name = "*test*" }), - ); - defer compiler.deinit(); - const ir = try Ir.init(allocator, &[1]Ast.Node{ast.*}); - defer ir.deinit(allocator); - const bytecode = try compiler.compile(ir); - const res = try vm.eval(bytecode, &.{}); - if (res.tag() != .none) { - try writer.print("${d}: {any}\n", .{ expr_number.*, res }); - expr_number.* += 1; - } - try vm.env.runGc(); -} - -test "simple input" { - var actual = std.ArrayList(u8).init(std.testing.allocator); - defer actual.deinit(); - try runScript(actual.writer(), "(+ 1 2) (- 3.0 4.0) (< 1 2) (list \"hello\" 42) (*modules*)", true); - try std.testing.expectEqualStrings( - \\$1: 3 - \\$2: -1 - \\$3: true - \\$4: ("hello" 42) - \\$5: ("*global*" "*test*") - \\ - , actual.items); -} diff --git a/main.fizz b/test_scripts/golden_test.fizz similarity index 100% rename from main.fizz rename to test_scripts/golden_test.fizz