diff options
Diffstat (limited to 'src/compile.zig')
-rw-r--r-- | src/compile.zig | 29 |
1 files changed, 25 insertions, 4 deletions
diff --git a/src/compile.zig b/src/compile.zig index 80a9a17..636cf01 100644 --- a/src/compile.zig +++ b/src/compile.zig @@ -56,14 +56,26 @@ pub const Procedure = struct { name: []const u8, blocks: []BasicBlock, param_reg: ?VReg, - - fn init(allocator: Allocator, name: []const u8, blocks: []BasicBlock, param_reg: ?VReg) !Procedure { + locals: std.AutoHashMap(LVar, void), + + fn init( + allocator: Allocator, + name: []const u8, + blocks: []BasicBlock, + param_reg: ?VReg, + locals: std.AutoHashMap(LVar, void), + ) !Procedure { for (blocks) |*block| { try block.finalize(allocator); if (param_reg) |p| _ = block.vreg_last_use.remove(p); } - return .{ .name = name, .blocks = blocks, .param_reg = param_reg }; + return .{ + .name = name, + .blocks = blocks, + .param_reg = param_reg, + .locals = locals, + }; } pub fn format(self: Procedure, comptime fmt: []const u8, options: std.fmt.FormatOptions, writer: anytype) !void { @@ -352,6 +364,7 @@ fn compileProcedure( .vreg_ctr = .init, .lvar_ctr = .init, .scope = .{ .locals = .empty, .parent = null }, + .locals = .empty, .param = .{ .name = "", .reg = undefined }, .blocks = try .init(ctx.allocator, &.{first_block}, &.{.{ .ref = first_block }}), .current_block = first_block, @@ -379,7 +392,13 @@ fn compileProcedure( std.debug.assert(kv.key_ptr.* == kv.value_ptr.ref); blocks[i] = kv.value_ptr.*; } - return try .init(ctx.allocator, name.getIdent(ctx.source), blocks, param_reg); + return try .init( + ctx.allocator, + name.getIdent(ctx.source), + blocks, + param_reg, + pctx.locals.promote(ctx.allocator), + ); } const ProcedureContext = struct { @@ -389,6 +408,7 @@ const ProcedureContext = struct { lvar_ctr: IdCounter(LVar), scope: Scope, + locals: std.AutoHashMapUnmanaged(LVar, void), param: struct { name: []const u8, reg: VReg }, blocks: std.AutoArrayHashMapUnmanaged(BlockRef, BasicBlock), @@ -420,6 +440,7 @@ const ProcedureContext = struct { const local = self.lvar_ctr.get(); const name = assign_var.ident.getIdent(self.ctx.source); try self.scope.locals.put(self.ctx.allocator, name, local); + try self.locals.put(self.ctx.allocator, local, {}); break :blk local; } else blk: { var scope: ?*Scope = &self.scope; |