aboutsummaryrefslogtreecommitdiff
path: root/src/codegen/c.zig
diff options
context:
space:
mode:
authorAndrew Kelley <andrew@ziglang.org>2021-03-31 23:11:15 -0700
committerGitHub <noreply@github.com>2021-03-31 23:11:15 -0700
commit070a28e493c6994197b2e52f42f3d0020b7395aa (patch)
tree495bf07a61916906a7f1b1d13019be91426ebbdc /src/codegen/c.zig
parent1b657e6e41bcaf362d1cc9455c17e06e57973554 (diff)
parentc9e31febf811286580792265efe20ccfa76c0fcf (diff)
downloadzig-070a28e493c6994197b2e52f42f3d0020b7395aa.tar.gz
zig-070a28e493c6994197b2e52f42f3d0020b7395aa.zip
Merge pull request #8266 from ziglang/zir-memory-layout
rework ZIR memory layout; overhaul source locations
Diffstat (limited to 'src/codegen/c.zig')
-rw-r--r--src/codegen/c.zig44
1 files changed, 27 insertions, 17 deletions
diff --git a/src/codegen/c.zig b/src/codegen/c.zig
index af8d2d272d..6e68a43607 100644
--- a/src/codegen/c.zig
+++ b/src/codegen/c.zig
@@ -14,6 +14,7 @@ const TypedValue = @import("../TypedValue.zig");
const C = link.File.C;
const Decl = Module.Decl;
const trace = @import("../tracy.zig").trace;
+const LazySrcLoc = Module.LazySrcLoc;
const Mutability = enum { Const, Mut };
@@ -145,11 +146,10 @@ pub const DeclGen = struct {
error_msg: ?*Module.ErrorMsg,
typedefs: TypedefMap,
- fn fail(dg: *DeclGen, src: usize, comptime format: []const u8, args: anytype) error{ AnalysisFail, OutOfMemory } {
- dg.error_msg = try Module.ErrorMsg.create(dg.module.gpa, .{
- .file_scope = dg.decl.getFileScope(),
- .byte_offset = src,
- }, format, args);
+ fn fail(dg: *DeclGen, src: LazySrcLoc, comptime format: []const u8, args: anytype) error{ AnalysisFail, OutOfMemory } {
+ @setCold(true);
+ const src_loc = src.toSrcLocWithDecl(dg.decl);
+ dg.error_msg = try Module.ErrorMsg.create(dg.module.gpa, src_loc, format, args);
return error.AnalysisFail;
}
@@ -160,7 +160,7 @@ pub const DeclGen = struct {
val: Value,
) error{ OutOfMemory, AnalysisFail }!void {
if (val.isUndef()) {
- return dg.fail(dg.decl.src(), "TODO: C backend: properly handle undefined in all cases (with debug safety?)", .{});
+ return dg.fail(.{ .node_offset = 0 }, "TODO: C backend: properly handle undefined in all cases (with debug safety?)", .{});
}
switch (t.zigTypeTag()) {
.Int => {
@@ -193,7 +193,7 @@ pub const DeclGen = struct {
try writer.print("{s}", .{decl.name});
},
else => |e| return dg.fail(
- dg.decl.src(),
+ .{ .node_offset = 0 },
"TODO: C backend: implement Pointer value {s}",
.{@tagName(e)},
),
@@ -276,7 +276,7 @@ pub const DeclGen = struct {
try writer.writeAll(", .error = 0 }");
}
},
- else => |e| return dg.fail(dg.decl.src(), "TODO: C backend: implement value {s}", .{
+ else => |e| return dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement value {s}", .{
@tagName(e),
}),
}
@@ -350,7 +350,7 @@ pub const DeclGen = struct {
break;
}
} else {
- return dg.fail(dg.decl.src(), "TODO: C backend: implement integer types larger than 128 bits", .{});
+ return dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement integer types larger than 128 bits", .{});
}
},
else => unreachable,
@@ -358,7 +358,7 @@ pub const DeclGen = struct {
},
.Pointer => {
if (t.isSlice()) {
- return dg.fail(dg.decl.src(), "TODO: C backend: implement slices", .{});
+ return dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement slices", .{});
} else {
try dg.renderType(w, t.elemType());
try w.writeAll(" *");
@@ -431,7 +431,7 @@ pub const DeclGen = struct {
dg.typedefs.putAssumeCapacityNoClobber(t, .{ .name = name, .rendered = rendered });
},
.Null, .Undefined => unreachable, // must be const or comptime
- else => |e| return dg.fail(dg.decl.src(), "TODO: C backend: implement type {s}", .{
+ else => |e| return dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement type {s}", .{
@tagName(e),
}),
}
@@ -569,13 +569,15 @@ pub fn genBody(o: *Object, body: ir.Body) error{ AnalysisFail, OutOfMemory }!voi
.optional_payload_ptr => try genOptionalPayload(o, inst.castTag(.optional_payload_ptr).?),
.is_err => try genIsErr(o, inst.castTag(.is_err).?),
.is_err_ptr => try genIsErr(o, inst.castTag(.is_err_ptr).?),
+ .error_to_int => try genErrorToInt(o, inst.castTag(.error_to_int).?),
+ .int_to_error => try genIntToError(o, inst.castTag(.int_to_error).?),
.unwrap_errunion_payload => try genUnwrapErrUnionPay(o, inst.castTag(.unwrap_errunion_payload).?),
.unwrap_errunion_err => try genUnwrapErrUnionErr(o, inst.castTag(.unwrap_errunion_err).?),
.unwrap_errunion_payload_ptr => try genUnwrapErrUnionPay(o, inst.castTag(.unwrap_errunion_payload_ptr).?),
.unwrap_errunion_err_ptr => try genUnwrapErrUnionErr(o, inst.castTag(.unwrap_errunion_err_ptr).?),
.wrap_errunion_payload => try genWrapErrUnionPay(o, inst.castTag(.wrap_errunion_payload).?),
.wrap_errunion_err => try genWrapErrUnionErr(o, inst.castTag(.wrap_errunion_err).?),
- else => |e| return o.dg.fail(o.dg.decl.src(), "TODO: C backend: implement codegen for {}", .{e}),
+ else => |e| return o.dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement codegen for {}", .{e}),
};
switch (result_value) {
.none => {},
@@ -756,11 +758,11 @@ fn genCall(o: *Object, inst: *Inst.Call) !CValue {
try writer.writeAll(");\n");
return result_local;
} else {
- return o.dg.fail(o.dg.decl.src(), "TODO: C backend: implement function pointers", .{});
+ return o.dg.fail(.{ .node_offset = 0 }, "TODO: C backend: implement function pointers", .{});
}
}
-fn genDbgStmt(o: *Object, inst: *Inst.NoOp) !CValue {
+fn genDbgStmt(o: *Object, inst: *Inst.DbgStmt) !CValue {
// TODO emit #line directive here with line number and filename
return CValue.none;
}
@@ -913,13 +915,13 @@ fn genAsm(o: *Object, as: *Inst.Assembly) !CValue {
try o.writeCValue(writer, arg_c_value);
try writer.writeAll(";\n");
} else {
- return o.dg.fail(o.dg.decl.src(), "TODO non-explicit inline asm regs", .{});
+ return o.dg.fail(.{ .node_offset = 0 }, "TODO non-explicit inline asm regs", .{});
}
}
const volatile_string: []const u8 = if (as.is_volatile) "volatile " else "";
try writer.print("__asm {s}(\"{s}\"", .{ volatile_string, as.asm_source });
if (as.output) |_| {
- return o.dg.fail(o.dg.decl.src(), "TODO inline asm output", .{});
+ return o.dg.fail(.{ .node_offset = 0 }, "TODO inline asm output", .{});
}
if (as.inputs.len > 0) {
if (as.output == null) {
@@ -945,7 +947,7 @@ fn genAsm(o: *Object, as: *Inst.Assembly) !CValue {
if (as.base.isUnused())
return CValue.none;
- return o.dg.fail(o.dg.decl.src(), "TODO: C backend: inline asm expression result used", .{});
+ return o.dg.fail(.{ .node_offset = 0 }, "TODO: C backend: inline asm expression result used", .{});
}
fn genIsNull(o: *Object, inst: *Inst.UnOp) !CValue {
@@ -1072,6 +1074,14 @@ fn genIsErr(o: *Object, inst: *Inst.UnOp) !CValue {
return local;
}
+fn genIntToError(o: *Object, inst: *Inst.UnOp) !CValue {
+ return o.resolveInst(inst.operand);
+}
+
+fn genErrorToInt(o: *Object, inst: *Inst.UnOp) !CValue {
+ return o.resolveInst(inst.operand);
+}
+
fn IndentWriter(comptime UnderlyingWriter: type) type {
return struct {
const Self = @This();