authorgravatar for luuk@degram.devLuuk de Gram <luuk@degram.dev> 2022-03-06 16:52:10+01:00
committergravatar for luuk@degram.devLuuk de Gram <luuk@degram.dev> 2022-03-06 19:38:53+01:00
log70fc6e37766c3c0b7d75854055fa3f862d4025f7
treeb9ad100bee4c13f53a1618fcbe0c030e24b2bc36
parent5a45fe2dba12e1440fabe0b4b594d69703640e17
signaturelock-open Commit is signed but in an unrecognized format.

wasm: call into `generateSymbol` when lowering

This also unifies the wasm backend to use `generateSymbol` when lowering a constant that cannot be lowered to an immediate value. As both decls and constants are now refactored, the old `genTypedValue` is removed.

5 files changed, 31 insertions(+), 22 deletions(-)

src/link/Wasm.zig+22-21
...@@ -503,7 +503,7 @@ pub fn updateFunc(self: *Wasm, module: *Module, func: *Module.Fn, air: Air, live...@@ -503,7 +503,7 @@ pub fn updateFunc(self: *Wasm, module: *Module, func: *Module.Fn, air: Air, live
503 const decl = func.owner_decl;503 const decl = func.owner_decl;
504 assert(decl.link.wasm.sym_index != 0); // Must call allocateDeclIndexes()504 assert(decl.link.wasm.sym_index != 0); // Must call allocateDeclIndexes()
505505
506 decl.link.wasm.clear();506 decl.link.wasm.clear(self.base.allocator);
507507
508 var codegen_: CodeGen = .{508 var codegen_: CodeGen = .{
509 .gpa = self.base.allocator,509 .gpa = self.base.allocator,
...@@ -544,7 +544,7 @@ pub fn updateDecl(self: *Wasm, module: *Module, decl: *Module.Decl) !void {...@@ -544,7 +544,7 @@ pub fn updateDecl(self: *Wasm, module: *Module, decl: *Module.Decl) !void {
544544
545 assert(decl.link.wasm.sym_index != 0); // Must call allocateDeclIndexes()545 assert(decl.link.wasm.sym_index != 0); // Must call allocateDeclIndexes()
546546
547 decl.link.wasm.clear();547 decl.link.wasm.clear(self.base.allocator);
548548
549 if (decl.isExtern()) {549 if (decl.isExtern()) {
550 return self.addOrUpdateImport(decl);550 return self.addOrUpdateImport(decl);
...@@ -607,7 +607,9 @@ pub fn lowerUnnamedConst(self: *Wasm, decl: *Module.Decl, tv: TypedValue) !u32 {...@@ -607,7 +607,9 @@ pub fn lowerUnnamedConst(self: *Wasm, decl: *Module.Decl, tv: TypedValue) !u32 {
607607
608 // Create and initialize a new local symbol and atom608 // Create and initialize a new local symbol and atom
609 const local_index = decl.link.wasm.locals.items.len;609 const local_index = decl.link.wasm.locals.items.len;
610 const name = try std.fmt.allocPrintZ(self.base.allocator, "__unnamed_{s}_{d}", .{ decl.name, local_index });610 const fqdn = try decl.getFullyQualifiedName(self.base.allocator);
611 defer self.base.allocator.free(fqdn);
612 const name = try std.fmt.allocPrintZ(self.base.allocator, "__unnamed_{s}_{d}", .{ fqdn, local_index });
611 defer self.base.allocator.free(name);613 defer self.base.allocator.free(name);
612 var symbol: Symbol = .{614 var symbol: Symbol = .{
613 .name = try self.string_table.put(self.base.allocator, name),615 .name = try self.string_table.put(self.base.allocator, name),
...@@ -636,27 +638,25 @@ pub fn lowerUnnamedConst(self: *Wasm, decl: *Module.Decl, tv: TypedValue) !u32 {...@@ -636,27 +638,25 @@ pub fn lowerUnnamedConst(self: *Wasm, decl: *Module.Decl, tv: TypedValue) !u32 {
636 defer value_bytes.deinit();638 defer value_bytes.deinit();
637639
638 const module = self.base.options.module.?;640 const module = self.base.options.module.?;
639 var decl_gen: CodeGen.DeclGen = .{641 const result = try codegen.generateSymbol(
640 .bin_file = self,642 &self.base,
641 .decl = decl,643 decl.srcLoc(),
642 .err_msg = undefined,644 tv,
643 .gpa = self.base.allocator,645 &value_bytes,
644 .module = module,646 .none,
645 .code = &value_bytes,647 .{
646 .symbol_index = atom.sym_index,648 .parent_atom_index = atom.sym_index,
647 };649 .addend = null,
648
649 const result = decl_gen.genTypedValue(tv.ty, tv.val) catch |err| switch (err) {
650 error.CodegenFail => {
651 decl.analysis = .codegen_failure;
652 try module.failed_decls.put(module.gpa, decl, decl_gen.err_msg);
653 return error.AnalysisFail;
654 },650 },
655 else => |e| return e,651 );
656 };
657 const code = switch (result) {652 const code = switch (result) {
653 .externally_managed => |x| x,
658 .appended => value_bytes.items,654 .appended => value_bytes.items,
659 .externally_managed => |data| data,655 .fail => |em| {
656 decl.analysis = .codegen_failure;
657 try module.failed_decls.put(module.gpa, decl, em);
658 return error.AnalysisFail;
659 },
660 };660 };
661661
662 atom.size = @intCast(u32, code.len);662 atom.size = @intCast(u32, code.len);
...@@ -989,6 +989,7 @@ fn allocateAtoms(self: *Wasm) !void {...@@ -989,6 +989,7 @@ fn allocateAtoms(self: *Wasm) !void {
989 atom.size,989 atom.size,
990 });990 });
991 offset += atom.size;991 offset += atom.size;
992 self.symbol_atom.putAssumeCapacity(atom.symbolLoc(), atom); // Update atom pointers
992 atom = atom.next orelse break;993 atom = atom.next orelse break;
993 }994 }
994 }995 }
src/link/Wasm/Atom.zig+6-1
...@@ -62,9 +62,14 @@ pub fn deinit(self: *Atom, gpa: Allocator) void {...@@ -62,9 +62,14 @@ pub fn deinit(self: *Atom, gpa: Allocator) void {
6262
63/// Sets the length of relocations and code to '0',63/// Sets the length of relocations and code to '0',
64/// effectively resetting them and allowing them to be re-populated.64/// effectively resetting them and allowing them to be re-populated.
65pub fn clear(self: *Atom) void {65pub fn clear(self: *Atom, gpa: Allocator) void {
66 self.relocs.clearRetainingCapacity();66 self.relocs.clearRetainingCapacity();
67 self.code.clearRetainingCapacity();67 self.code.clearRetainingCapacity();
68
69 // locals will be re-generated
70 for (self.locals.items) |*local| {
71 local.deinit(gpa);
72 }
68}73}
6974
70pub fn format(self: Atom, comptime fmt: []const u8, options: std.fmt.FormatOptions, writer: anytype) !void {75pub fn format(self: Atom, comptime fmt: []const u8, options: std.fmt.FormatOptions, writer: anytype) !void {
test/behavior/align.zig+1
...@@ -149,6 +149,7 @@ test "return error union with 128-bit integer" {...@@ -149,6 +149,7 @@ test "return error union with 128-bit integer" {
149 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest;149 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest;
150 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest;150 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest;
151 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest;151 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest;
152 if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest;
152153
153 try expect(3 == try give());154 try expect(3 == try give());
154}155}
test/behavior/cast.zig+1
...@@ -1142,6 +1142,7 @@ test "cast u128 to f128 and back" {...@@ -1142,6 +1142,7 @@ test "cast u128 to f128 and back" {
1142 if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO1142 if (builtin.zig_backend == .stage2_c) return error.SkipZigTest; // TODO
1143 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO1143 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
1144 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO1144 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
1145 if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
11451146
1146 comptime try testCast128();1147 comptime try testCast128();
1147 try testCast128();1148 try testCast128();
test/behavior/struct.zig+1
...@@ -856,6 +856,7 @@ test "non-packed struct with u128 entry in union" {...@@ -856,6 +856,7 @@ test "non-packed struct with u128 entry in union" {
856 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO856 if (builtin.zig_backend == .stage2_x86_64) return error.SkipZigTest; // TODO
857 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO857 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
858 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO858 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
859 if (builtin.zig_backend == .stage2_wasm) return error.SkipZigTest; // TODO
859860
860 const U = union(enum) {861 const U = union(enum) {
861 Num: u128,862 Num: u128,