Commit 14aa08fcd3
Changed files (4)
src-self-hosted
test
stage2
src-self-hosted/main.zig
@@ -504,7 +504,7 @@ fn updateModule(gpa: *Allocator, module: *Module, zir_out_path: ?[]const u8) !vo
});
}
} else {
- std.debug.print("Update completed in {} ms\n", .{update_nanos / std.time.ns_per_ms});
+ std.log.info(.compiler, "Update completed in {} ms\n", .{update_nanos / std.time.ns_per_ms});
}
if (zir_out_path) |zop| {
src-self-hosted/Module.zig
@@ -1060,21 +1060,24 @@ fn ensureDeclAnalyzed(self: *Module, decl: *Decl) InnerError!void {
.unreferenced => false,
};
- const type_changed = self.astGenAndAnalyzeDecl(decl) catch |err| switch (err) {
- error.OutOfMemory => return error.OutOfMemory,
- error.AnalysisFail => return error.AnalysisFail,
- else => {
- try self.failed_decls.ensureCapacity(self.failed_decls.size + 1);
- self.failed_decls.putAssumeCapacityNoClobber(decl, try ErrorMsg.create(
- self.allocator,
- decl.src(),
- "unable to analyze: {}",
- .{@errorName(err)},
- ));
- decl.analysis = .sema_failure_retryable;
- return error.AnalysisFail;
- },
- };
+ const type_changed = if (self.root_scope.cast(Scope.ZIRModule)) |zir_module|
+ try self.analyzeZirDecl(decl, zir_module.contents.module.decls[decl.src_index])
+ else
+ self.astGenAndAnalyzeDecl(decl) catch |err| switch (err) {
+ error.OutOfMemory => return error.OutOfMemory,
+ error.AnalysisFail => return error.AnalysisFail,
+ else => {
+ try self.failed_decls.ensureCapacity(self.failed_decls.size + 1);
+ self.failed_decls.putAssumeCapacityNoClobber(decl, try ErrorMsg.create(
+ self.allocator,
+ decl.src(),
+ "unable to analyze: {}",
+ .{@errorName(err)},
+ ));
+ decl.analysis = .sema_failure_retryable;
+ return error.AnalysisFail;
+ },
+ };
if (subsequent_analysis) {
// We may need to chase the dependants and re-analyze them.
@@ -1724,71 +1727,63 @@ fn analyzeRootSrcFile(self: *Module, root_scope: *Scope.File) !void {
}
fn analyzeRootZIRModule(self: *Module, root_scope: *Scope.ZIRModule) !void {
- switch (root_scope.status) {
- .never_loaded => {
- const src_module = try self.getSrcModule(root_scope);
+ // We may be analyzing it for the first time, or this may be
+ // an incremental update. This code handles both cases.
+ const src_module = try self.getSrcModule(root_scope);
- // Here we ensure enough queue capacity to store all the decls, so that later we can use
- // appendAssumeCapacity.
- try self.work_queue.ensureUnusedCapacity(src_module.decls.len);
+ try self.work_queue.ensureUnusedCapacity(src_module.decls.len);
+ try root_scope.decls.ensureCapacity(self.allocator, src_module.decls.len);
- for (src_module.decls) |src_decl| {
- if (src_decl.inst.cast(zir.Inst.Export)) |export_inst| {
- _ = try self.resolveDecl(&root_scope.base, src_decl);
- }
- }
- },
+ var exports_to_resolve = std.ArrayList(*zir.Decl).init(self.allocator);
+ defer exports_to_resolve.deinit();
- .unloaded_parse_failure,
- .unloaded_sema_failure,
- .unloaded_success,
- .loaded_sema_failure,
- .loaded_success,
- => {
- const src_module = try self.getSrcModule(root_scope);
-
- var exports_to_resolve = std.ArrayList(*zir.Decl).init(self.allocator);
- defer exports_to_resolve.deinit();
-
- // Keep track of the decls that we expect to see in this file so that
- // we know which ones have been deleted.
- var deleted_decls = std.AutoHashMap(*Decl, void).init(self.allocator);
- defer deleted_decls.deinit();
- try deleted_decls.ensureCapacity(self.decl_table.size);
- {
- var it = self.decl_table.iterator();
- while (it.next()) |kv| {
- deleted_decls.putAssumeCapacityNoClobber(kv.value, {});
- }
- }
+ // Keep track of the decls that we expect to see in this file so that
+ // we know which ones have been deleted.
+ var deleted_decls = std.AutoHashMap(*Decl, void).init(self.allocator);
+ defer deleted_decls.deinit();
+ try deleted_decls.ensureCapacity(self.decl_table.size);
+ {
+ var it = self.decl_table.iterator();
+ while (it.next()) |kv| {
+ deleted_decls.putAssumeCapacityNoClobber(kv.value, {});
+ }
+ }
- for (src_module.decls) |src_decl| {
- const name_hash = root_scope.fullyQualifiedNameHash(src_decl.name);
- if (self.decl_table.get(name_hash)) |kv| {
- const decl = kv.value;
- deleted_decls.removeAssertDiscard(decl);
- //std.debug.warn("'{}' contents: '{}'\n", .{ src_decl.name, src_decl.contents });
- if (!srcHashEql(src_decl.contents_hash, decl.contents_hash)) {
- try self.markOutdatedDecl(decl);
- decl.contents_hash = src_decl.contents_hash;
- }
- } else if (src_decl.inst.cast(zir.Inst.Export)) |export_inst| {
- try exports_to_resolve.append(src_decl);
- }
+ for (src_module.decls) |src_decl, decl_i| {
+ const name_hash = root_scope.fullyQualifiedNameHash(src_decl.name);
+ if (self.decl_table.get(name_hash)) |kv| {
+ const decl = kv.value;
+ deleted_decls.removeAssertDiscard(decl);
+ //std.debug.warn("'{}' contents: '{}'\n", .{ src_decl.name, src_decl.contents });
+ if (!srcHashEql(src_decl.contents_hash, decl.contents_hash)) {
+ try self.markOutdatedDecl(decl);
+ decl.contents_hash = src_decl.contents_hash;
}
- {
- // Handle explicitly deleted decls from the source code. Not to be confused
- // with when we delete decls because they are no longer referenced.
- var it = deleted_decls.iterator();
- while (it.next()) |kv| {
- //std.debug.warn("noticed '{}' deleted from source\n", .{kv.key.name});
- try self.deleteDecl(kv.key);
- }
- }
- for (exports_to_resolve.items) |export_decl| {
- _ = try self.resolveDecl(&root_scope.base, export_decl);
+ } else {
+ const new_decl = try self.createNewDecl(
+ &root_scope.base,
+ src_decl.name,
+ decl_i,
+ name_hash,
+ src_decl.contents_hash,
+ );
+ root_scope.decls.appendAssumeCapacity(new_decl);
+ if (src_decl.inst.cast(zir.Inst.Export)) |export_inst| {
+ try exports_to_resolve.append(src_decl);
}
- },
+ }
+ }
+ {
+ // Handle explicitly deleted decls from the source code. Not to be confused
+ // with when we delete decls because they are no longer referenced.
+ var it = deleted_decls.iterator();
+ while (it.next()) |kv| {
+ //std.debug.warn("noticed '{}' deleted from source\n", .{kv.key.name});
+ try self.deleteDecl(kv.key);
+ }
+ }
+ for (exports_to_resolve.items) |export_decl| {
+ _ = try self.resolveZirDecl(&root_scope.base, export_decl);
}
}
@@ -1933,73 +1928,67 @@ fn createNewDecl(
return new_decl;
}
-fn analyzeNewDecl(self: *Module, new_decl: *Decl, src_decl: *zir.Decl) InnerError!void {
+fn analyzeZirDecl(self: *Module, decl: *Decl, src_decl: *zir.Decl) InnerError!bool {
var decl_scope: Scope.DeclAnalysis = .{
- .decl = new_decl,
+ .decl = decl,
.arena = std.heap.ArenaAllocator.init(self.allocator),
};
errdefer decl_scope.arena.deinit();
- new_decl.analysis = .in_progress;
+ decl.analysis = .in_progress;
- const typed_value = self.analyzeConstInst(&decl_scope.base, src_decl.inst) catch |err| switch (err) {
- error.OutOfMemory => return error.OutOfMemory,
- error.AnalysisFail => {
- switch (new_decl.analysis) {
- .in_progress => new_decl.analysis = .dependency_failure,
- else => {},
- }
- new_decl.generation = self.generation;
- return error.AnalysisFail;
- },
- };
+ const typed_value = try self.analyzeConstInst(&decl_scope.base, src_decl.inst);
const arena_state = try decl_scope.arena.allocator.create(std.heap.ArenaAllocator.State);
- arena_state.* = decl_scope.arena.state;
+ var prev_type_has_bits = false;
+ var type_changed = true;
- new_decl.typed_value = .{
+ if (decl.typedValueManaged()) |tvm| {
+ prev_type_has_bits = tvm.typed_value.ty.hasCodeGenBits();
+ type_changed = !tvm.typed_value.ty.eql(typed_value.ty);
+
+ tvm.deinit(self.allocator);
+ }
+
+ arena_state.* = decl_scope.arena.state;
+ decl.typed_value = .{
.most_recent = .{
.typed_value = typed_value,
.arena = arena_state,
},
};
- new_decl.analysis = .complete;
- new_decl.generation = self.generation;
+ decl.analysis = .complete;
+ decl.generation = self.generation;
if (typed_value.ty.hasCodeGenBits()) {
// We don't fully codegen the decl until later, but we do need to reserve a global
// offset table index for it. This allows us to codegen decls out of dependency order,
// increasing how many computations can be done in parallel.
- try self.bin_file.allocateDeclIndexes(new_decl);
- try self.work_queue.writeItem(.{ .codegen_decl = new_decl });
+ try self.bin_file.allocateDeclIndexes(decl);
+ try self.work_queue.writeItem(.{ .codegen_decl = decl });
+ } else if (prev_type_has_bits) {
+ self.bin_file.freeDecl(decl);
}
+
+ return type_changed;
}
-fn resolveDecl(self: *Module, scope: *Scope, src_decl: *zir.Decl) InnerError!*Decl {
- // If the name is empty, then we make this an anonymous Decl.
- const scope_decl = scope.decl().?;
- const new_decl = try self.allocateNewDecl(scope, scope_decl.src_index, src_decl.contents_hash);
- try self.analyzeNewDecl(new_decl, src_decl);
- return new_decl;
- //const name_hash = Decl.hashSimpleName(src_decl.name);
- //if (self.decl_table.get(name_hash)) |kv| {
- // const decl = kv.value;
- // decl.src = src_decl.src;
- // try self.reAnalyzeDecl(decl, src_decl);
- // return decl;
- //} else if (src_decl.cast(zir.Inst.DeclVal)) |decl_val| {
- // // This is just a named reference to another decl.
- // return self.analyzeDeclVal(scope, decl_val);
- //} else {
- // const new_decl = try self.createNewDecl(scope, src_decl.name, src_decl.src, name_hash, src_decl.contents_hash);
- // try self.analyzeNewDecl(new_decl, src_decl);
-
- // return new_decl;
- //}
+fn resolveZirDecl(self: *Module, scope: *Scope, src_decl: *zir.Decl) InnerError!*Decl {
+ const zir_module = self.root_scope.cast(Scope.ZIRModule).?;
+ const entry = zir_module.contents.module.findDecl(src_decl.name).?;
+ return self.resolveZirDeclHavingIndex(scope, src_decl, entry.index);
+}
+
+fn resolveZirDeclHavingIndex(self: *Module, scope: *Scope, src_decl: *zir.Decl, src_index: usize) InnerError!*Decl {
+ const name_hash = scope.namespace().fullyQualifiedNameHash(src_decl.name);
+ const decl = self.decl_table.getValue(name_hash).?;
+ decl.src_index = src_index;
+ try self.ensureDeclAnalyzed(decl);
+ return decl;
}
/// Declares a dependency on the decl.
-fn resolveCompleteDecl(self: *Module, scope: *Scope, src_decl: *zir.Decl) InnerError!*Decl {
- const decl = try self.resolveDecl(scope, src_decl);
+fn resolveCompleteZirDecl(self: *Module, scope: *Scope, src_decl: *zir.Decl) InnerError!*Decl {
+ const decl = try self.resolveZirDecl(scope, src_decl);
switch (decl.analysis) {
.unreferenced => unreachable,
.in_progress => unreachable,
@@ -2014,15 +2003,32 @@ fn resolveCompleteDecl(self: *Module, scope: *Scope, src_decl: *zir.Decl) InnerE
.complete => {},
}
- if (scope.decl()) |scope_decl| {
- try self.declareDeclDependency(scope_decl, decl);
- }
return decl;
}
-/// TODO look into removing this function
+/// TODO Look into removing this function. The body is only needed for .zir files, not .zig files.
fn resolveInst(self: *Module, scope: *Scope, old_inst: *zir.Inst) InnerError!*Inst {
- return old_inst.analyzed_inst;
+ if (old_inst.analyzed_inst) |inst| return inst;
+
+ // If this assert trips, the instruction that was referenced did not get properly
+ // analyzed before it was referenced.
+ const zir_module = scope.namespace().cast(Scope.ZIRModule).?;
+ const entry = if (old_inst.cast(zir.Inst.DeclVal)) |declval| blk: {
+ const decl_name = declval.positionals.name;
+ const entry = zir_module.contents.module.findDecl(decl_name) orelse
+ return self.fail(scope, old_inst.src, "decl '{}' not found", .{decl_name});
+ break :blk entry;
+ } else blk: {
+ // If this assert trips, the instruction that was referenced did not get
+ // properly analyzed by a previous instruction analysis before it was
+ // referenced by the current one.
+ break :blk zir_module.contents.module.findInstDecl(old_inst).?;
+ };
+ const decl = try self.resolveCompleteZirDecl(scope, entry.decl);
+ const decl_ref = try self.analyzeDeclRef(scope, old_inst.src, decl);
+ const result = try self.analyzeDeref(scope, old_inst.src, decl_ref, old_inst.src);
+ old_inst.analyzed_inst = result;
+ return result;
}
fn requireRuntimeBlock(self: *Module, scope: *Scope, src: usize) !*Scope.Block {
@@ -2071,6 +2077,7 @@ fn resolveType(self: *Module, scope: *Scope, old_inst: *zir.Inst) !Type {
}
fn analyzeExport(self: *Module, scope: *Scope, src: usize, symbol_name: []const u8, exported_decl: *Decl) !void {
+ try self.ensureDeclAnalyzed(exported_decl);
const typed_value = exported_decl.typed_value.most_recent.typed_value;
switch (typed_value.ty.zigTypeTag()) {
.Fn => {},
@@ -2439,7 +2446,7 @@ fn analyzeDeclVal(self: *Module, scope: *Scope, inst: *zir.Inst.DeclVal) InnerEr
const src_decl = zir_module.contents.module.findDecl(decl_name) orelse
return self.fail(scope, inst.base.src, "use of undeclared identifier '{}'", .{decl_name});
- const decl = try self.resolveCompleteDecl(scope, src_decl.decl);
+ const decl = try self.resolveCompleteZirDecl(scope, src_decl.decl);
return decl;
}
@@ -2555,19 +2562,31 @@ fn analyzeInstCall(self: *Module, scope: *Scope, inst: *zir.Inst.Call) InnerErro
}
fn analyzeInstFn(self: *Module, scope: *Scope, fn_inst: *zir.Inst.Fn) InnerError!*Inst {
- return self.fail(scope, fn_inst.base.src, "TODO implement ZIR fn inst", .{});
- //const fn_type = try self.resolveType(scope, fn_inst.positionals.fn_type);
- //const new_func = try scope.arena().create(Fn);
- //new_func.* = .{
- // .analysis = .{ .queued = fn_inst },
- // .owner_decl = scope.decl().?,
- //};
- //const fn_payload = try scope.arena().create(Value.Payload.Function);
- //fn_payload.* = .{ .func = new_func };
- //return self.constInst(scope, fn_inst.base.src, .{
- // .ty = fn_type,
- // .val = Value.initPayload(&fn_payload.base),
- //});
+ const fn_type = try self.resolveType(scope, fn_inst.positionals.fn_type);
+ const fn_zir = blk: {
+ var fn_arena = std.heap.ArenaAllocator.init(self.allocator);
+ errdefer fn_arena.deinit();
+
+ const fn_zir = try scope.arena().create(Fn.ZIR);
+ fn_zir.* = .{
+ .body = .{
+ .instructions = fn_inst.positionals.body.instructions,
+ },
+ .arena = fn_arena.state,
+ };
+ break :blk fn_zir;
+ };
+ const new_func = try scope.arena().create(Fn);
+ new_func.* = .{
+ .analysis = .{ .queued = fn_zir },
+ .owner_decl = scope.decl().?,
+ };
+ const fn_payload = try scope.arena().create(Value.Payload.Function);
+ fn_payload.* = .{ .func = new_func };
+ return self.constInst(scope, fn_inst.base.src, .{
+ .ty = fn_type,
+ .val = Value.initPayload(&fn_payload.base),
+ });
}
fn analyzeInstFnType(self: *Module, scope: *Scope, fntype: *zir.Inst.FnType) InnerError!*Inst {
@@ -3277,6 +3296,7 @@ fn failWithOwnedErrorMsg(self: *Module, scope: *Scope, src: usize, err_msg: *Err
.decl => {
const decl = scope.cast(Scope.DeclAnalysis).?.decl;
decl.analysis = .sema_failure;
+ decl.generation = self.generation;
self.failed_decls.putAssumeCapacityNoClobber(decl, err_msg);
},
.block => {
@@ -3285,12 +3305,14 @@ fn failWithOwnedErrorMsg(self: *Module, scope: *Scope, src: usize, err_msg: *Err
func.analysis = .sema_failure;
} else {
block.decl.analysis = .sema_failure;
+ block.decl.generation = self.generation;
}
self.failed_decls.putAssumeCapacityNoClobber(block.decl, err_msg);
},
.gen_zir => {
const gen_zir = scope.cast(Scope.GenZIR).?;
gen_zir.decl.analysis = .sema_failure;
+ gen_zir.decl.generation = self.generation;
self.failed_decls.putAssumeCapacityNoClobber(gen_zir.decl, err_msg);
},
.zir_module => {
src-self-hosted/zir.zig
@@ -30,7 +30,7 @@ pub const Inst = struct {
/// Byte offset into the source.
src: usize,
/// Pre-allocated field for mapping ZIR text instructions to post-analysis instructions.
- analyzed_inst: *ir.Inst = undefined,
+ analyzed_inst: ?*ir.Inst = null,
/// These names are used directly as the instruction names in the text format.
pub const Tag = enum {
@@ -545,6 +545,18 @@ pub const Module = struct {
return null;
}
+ pub fn findInstDecl(self: Module, inst: *Inst) ?DeclAndIndex {
+ for (self.decls) |decl, i| {
+ if (decl.inst == inst) {
+ return DeclAndIndex{
+ .decl = decl,
+ .index = i,
+ };
+ }
+ }
+ return null;
+ }
+
/// The allocator is used for temporary storage, but this function always returns
/// with no resources allocated.
pub fn writeToStream(self: Module, allocator: *Allocator, stream: var) !void {
test/stage2/zir.zig
@@ -228,17 +228,6 @@ pub fn addCases(ctx: *TestContext) void {
\\@2 = int(2)
\\@3 = int(3)
\\
- \\@syscall_array = str("syscall")
- \\@sysoutreg_array = str("={rax}")
- \\@rax_array = str("{rax}")
- \\@rdi_array = str("{rdi}")
- \\@rcx_array = str("rcx")
- \\@r11_array = str("r11")
- \\@rdx_array = str("{rdx}")
- \\@rsi_array = str("{rsi}")
- \\@memory_array = str("memory")
- \\@len_array = str("len")
- \\
\\@msg = str("Hello, world!\n")
\\
\\@start_fnty = fntype([], @noreturn, cc=Naked)
@@ -246,24 +235,23 @@ pub fn addCases(ctx: *TestContext) void {
\\ %SYS_exit_group = int(231)
\\ %exit_code = as(@usize, @0)
\\
- \\ %syscall = ref(@syscall_array)
- \\ %sysoutreg = ref(@sysoutreg_array)
- \\ %rax = ref(@rax_array)
- \\ %rdi = ref(@rdi_array)
- \\ %rcx = ref(@rcx_array)
- \\ %rdx = ref(@rdx_array)
- \\ %rsi = ref(@rsi_array)
- \\ %r11 = ref(@r11_array)
- \\ %memory = ref(@memory_array)
+ \\ %syscall = str("syscall")
+ \\ %sysoutreg = str("={rax}")
+ \\ %rax = str("{rax}")
+ \\ %rdi = str("{rdi}")
+ \\ %rcx = str("rcx")
+ \\ %rdx = str("{rdx}")
+ \\ %rsi = str("{rsi}")
+ \\ %r11 = str("r11")
+ \\ %memory = str("memory")
\\
\\ %SYS_write = as(@usize, @1)
\\ %STDOUT_FILENO = as(@usize, @1)
\\
- \\ %msg_ptr = ref(@msg)
- \\ %msg_addr = ptrtoint(%msg_ptr)
+ \\ %msg_addr = ptrtoint(@msg)
\\
- \\ %len_name = ref(@len_array)
- \\ %msg_len_ptr = fieldptr(%msg_ptr, %len_name)
+ \\ %len_name = str("len")
+ \\ %msg_len_ptr = fieldptr(@msg, %len_name)
\\ %msg_len = deref(%msg_len_ptr)
\\ %rc_write = asm(%syscall, @usize,
\\ volatile=1,
@@ -283,8 +271,7 @@ pub fn addCases(ctx: *TestContext) void {
\\});
\\
\\@9 = str("_start")
- \\@10 = ref(@9)
- \\@11 = export(@10, @start)
+ \\@11 = export(@9, "start")
,
\\@noreturn = primitive(noreturn)
\\@void = primitive(void)
@@ -294,17 +281,6 @@ pub fn addCases(ctx: *TestContext) void {
\\@2 = int(2)
\\@3 = int(3)
\\
- \\@syscall_array = str("syscall")
- \\@sysoutreg_array = str("={rax}")
- \\@rax_array = str("{rax}")
- \\@rdi_array = str("{rdi}")
- \\@rcx_array = str("rcx")
- \\@r11_array = str("r11")
- \\@rdx_array = str("{rdx}")
- \\@rsi_array = str("{rsi}")
- \\@memory_array = str("memory")
- \\@len_array = str("len")
- \\
\\@msg = str("Hello, world!\n")
\\@msg2 = str("HELL WORLD\n")
\\
@@ -313,24 +289,23 @@ pub fn addCases(ctx: *TestContext) void {
\\ %SYS_exit_group = int(231)
\\ %exit_code = as(@usize, @0)
\\
- \\ %syscall = ref(@syscall_array)
- \\ %sysoutreg = ref(@sysoutreg_array)
- \\ %rax = ref(@rax_array)
- \\ %rdi = ref(@rdi_array)
- \\ %rcx = ref(@rcx_array)
- \\ %rdx = ref(@rdx_array)
- \\ %rsi = ref(@rsi_array)
- \\ %r11 = ref(@r11_array)
- \\ %memory = ref(@memory_array)
+ \\ %syscall = str("syscall")
+ \\ %sysoutreg = str("={rax}")
+ \\ %rax = str("{rax}")
+ \\ %rdi = str("{rdi}")
+ \\ %rcx = str("rcx")
+ \\ %rdx = str("{rdx}")
+ \\ %rsi = str("{rsi}")
+ \\ %r11 = str("r11")
+ \\ %memory = str("memory")
\\
\\ %SYS_write = as(@usize, @1)
\\ %STDOUT_FILENO = as(@usize, @1)
\\
- \\ %msg_ptr = ref(@msg2)
- \\ %msg_addr = ptrtoint(%msg_ptr)
+ \\ %msg_addr = ptrtoint(@msg2)
\\
- \\ %len_name = ref(@len_array)
- \\ %msg_len_ptr = fieldptr(%msg_ptr, %len_name)
+ \\ %len_name = str("len")
+ \\ %msg_len_ptr = fieldptr(@msg2, %len_name)
\\ %msg_len = deref(%msg_len_ptr)
\\ %rc_write = asm(%syscall, @usize,
\\ volatile=1,
@@ -350,8 +325,7 @@ pub fn addCases(ctx: *TestContext) void {
\\});
\\
\\@9 = str("_start")
- \\@10 = ref(@9)
- \\@11 = export(@10, @start)
+ \\@11 = export(@9, "start")
,
\\@noreturn = primitive(noreturn)
\\@void = primitive(void)
@@ -361,17 +335,6 @@ pub fn addCases(ctx: *TestContext) void {
\\@2 = int(2)
\\@3 = int(3)
\\
- \\@syscall_array = str("syscall")
- \\@sysoutreg_array = str("={rax}")
- \\@rax_array = str("{rax}")
- \\@rdi_array = str("{rdi}")
- \\@rcx_array = str("rcx")
- \\@r11_array = str("r11")
- \\@rdx_array = str("{rdx}")
- \\@rsi_array = str("{rsi}")
- \\@memory_array = str("memory")
- \\@len_array = str("len")
- \\
\\@msg = str("Hello, world!\n")
\\@msg2 = str("Editing the same msg2 decl but this time with a much longer message which will\ncause the data to need to be relocated in virtual address space.\n")
\\
@@ -380,24 +343,23 @@ pub fn addCases(ctx: *TestContext) void {
\\ %SYS_exit_group = int(231)
\\ %exit_code = as(@usize, @0)
\\
- \\ %syscall = ref(@syscall_array)
- \\ %sysoutreg = ref(@sysoutreg_array)
- \\ %rax = ref(@rax_array)
- \\ %rdi = ref(@rdi_array)
- \\ %rcx = ref(@rcx_array)
- \\ %rdx = ref(@rdx_array)
- \\ %rsi = ref(@rsi_array)
- \\ %r11 = ref(@r11_array)
- \\ %memory = ref(@memory_array)
+ \\ %syscall = str("syscall")
+ \\ %sysoutreg = str("={rax}")
+ \\ %rax = str("{rax}")
+ \\ %rdi = str("{rdi}")
+ \\ %rcx = str("rcx")
+ \\ %rdx = str("{rdx}")
+ \\ %rsi = str("{rsi}")
+ \\ %r11 = str("r11")
+ \\ %memory = str("memory")
\\
\\ %SYS_write = as(@usize, @1)
\\ %STDOUT_FILENO = as(@usize, @1)
\\
- \\ %msg_ptr = ref(@msg2)
- \\ %msg_addr = ptrtoint(%msg_ptr)
+ \\ %msg_addr = ptrtoint(@msg2)
\\
- \\ %len_name = ref(@len_array)
- \\ %msg_len_ptr = fieldptr(%msg_ptr, %len_name)
+ \\ %len_name = str("len")
+ \\ %msg_len_ptr = fieldptr(@msg2, %len_name)
\\ %msg_len = deref(%msg_len_ptr)
\\ %rc_write = asm(%syscall, @usize,
\\ volatile=1,
@@ -417,8 +379,7 @@ pub fn addCases(ctx: *TestContext) void {
\\});
\\
\\@9 = str("_start")
- \\@10 = ref(@9)
- \\@11 = export(@10, @start)
+ \\@11 = export(@9, "start")
},
&[_][]const u8{
\\Hello, world!