mirror of
https://github.com/ziglang/zig.git
synced 2026-01-21 06:45:24 +00:00
Sema: catch runtime stores to comptime variables through calls
This commit is contained in:
parent
32f30399e5
commit
731ff120d0
25
src/Sema.zig
25
src/Sema.zig
@ -341,8 +341,8 @@ pub const Block = struct {
|
||||
label: ?*Label = null,
|
||||
inlining: ?*Inlining,
|
||||
/// If runtime_index is not 0 then one of these is guaranteed to be non null.
|
||||
runtime_cond: ?LazySrcLoc = null,
|
||||
runtime_loop: ?LazySrcLoc = null,
|
||||
runtime_cond: ?Module.SrcLoc = null,
|
||||
runtime_loop: ?Module.SrcLoc = null,
|
||||
/// This Decl is the Decl according to the Zig source code corresponding to this Block.
|
||||
/// This can vary during inline or comptime function calls. See `Sema.owner_decl`
|
||||
/// for the one that will be the same for all Block instances.
|
||||
@ -1504,7 +1504,7 @@ fn analyzeBodyInner(
|
||||
const msg = try sema.errMsg(block, src, "comptime control flow inside runtime block", .{});
|
||||
errdefer msg.destroy(sema.gpa);
|
||||
|
||||
try sema.errNote(block, runtime_src, msg, "runtime control flow here", .{});
|
||||
try mod.errNoteNonLazy(runtime_src, msg, "runtime control flow here", .{});
|
||||
break :msg msg;
|
||||
};
|
||||
return sema.failWithOwnedErrorMsg(block, msg);
|
||||
@ -5761,7 +5761,7 @@ fn zirLoop(sema: *Sema, parent_block: *Block, inst: Zir.Inst.Index) CompileError
|
||||
var child_block = parent_block.makeSubBlock();
|
||||
child_block.label = &label;
|
||||
child_block.runtime_cond = null;
|
||||
child_block.runtime_loop = src;
|
||||
child_block.runtime_loop = src.toSrcLoc(mod.declPtr(child_block.src_decl), mod);
|
||||
child_block.runtime_index.increment();
|
||||
const merges = &child_block.label.?.merges;
|
||||
|
||||
@ -6049,7 +6049,7 @@ fn analyzeBlockBody(
|
||||
errdefer msg.destroy(sema.gpa);
|
||||
|
||||
const runtime_src = child_block.runtime_cond orelse child_block.runtime_loop.?;
|
||||
try sema.errNote(child_block, runtime_src, msg, "runtime control flow here", .{});
|
||||
try mod.errNoteNonLazy(runtime_src, msg, "runtime control flow here", .{});
|
||||
|
||||
const child_src_decl = mod.declPtr(child_block.src_decl);
|
||||
try sema.explainWhyTypeIsComptime(msg, type_src.toSrcLoc(child_src_decl, mod), resolved_ty);
|
||||
@ -7458,6 +7458,9 @@ fn analyzeCall(
|
||||
.is_comptime = is_comptime_call,
|
||||
.comptime_reason = comptime_reason,
|
||||
.error_return_trace_index = block.error_return_trace_index,
|
||||
.runtime_cond = block.runtime_cond,
|
||||
.runtime_loop = block.runtime_loop,
|
||||
.runtime_index = block.runtime_index,
|
||||
};
|
||||
|
||||
const merges = &child_block.inlining.?.merges;
|
||||
@ -11533,7 +11536,7 @@ fn zirSwitchBlockErrUnion(sema: *Sema, block: *Block, inst: Zir.Inst.Index) Comp
|
||||
|
||||
var sub_block = child_block.makeSubBlock();
|
||||
sub_block.runtime_loop = null;
|
||||
sub_block.runtime_cond = main_operand_src;
|
||||
sub_block.runtime_cond = main_operand_src.toSrcLoc(mod.declPtr(child_block.src_decl), mod);
|
||||
sub_block.runtime_index.increment();
|
||||
defer sub_block.instructions.deinit(gpa);
|
||||
|
||||
@ -12268,7 +12271,7 @@ fn analyzeSwitchRuntimeBlock(
|
||||
|
||||
var case_block = child_block.makeSubBlock();
|
||||
case_block.runtime_loop = null;
|
||||
case_block.runtime_cond = operand_src;
|
||||
case_block.runtime_cond = operand_src.toSrcLoc(mod.declPtr(child_block.src_decl), mod);
|
||||
case_block.runtime_index.increment();
|
||||
defer case_block.instructions.deinit(gpa);
|
||||
|
||||
@ -18810,7 +18813,7 @@ fn zirBoolBr(
|
||||
|
||||
var child_block = parent_block.makeSubBlock();
|
||||
child_block.runtime_loop = null;
|
||||
child_block.runtime_cond = lhs_src;
|
||||
child_block.runtime_cond = lhs_src.toSrcLoc(mod.declPtr(child_block.src_decl), mod);
|
||||
child_block.runtime_index.increment();
|
||||
defer child_block.instructions.deinit(gpa);
|
||||
|
||||
@ -19004,7 +19007,7 @@ fn zirCondbr(
|
||||
// instructions array in between using it for the then block and else block.
|
||||
var sub_block = parent_block.makeSubBlock();
|
||||
sub_block.runtime_loop = null;
|
||||
sub_block.runtime_cond = cond_src;
|
||||
sub_block.runtime_cond = cond_src.toSrcLoc(mod.declPtr(parent_block.src_decl), mod);
|
||||
sub_block.runtime_index.increment();
|
||||
defer sub_block.instructions.deinit(gpa);
|
||||
|
||||
@ -23543,7 +23546,7 @@ fn checkComptimeVarStore(
|
||||
const msg = msg: {
|
||||
const msg = try sema.errMsg(block, src, "store to comptime variable depends on runtime condition", .{});
|
||||
errdefer msg.destroy(sema.gpa);
|
||||
try sema.errNote(block, cond_src, msg, "runtime condition here", .{});
|
||||
try sema.mod.errNoteNonLazy(cond_src, msg, "runtime condition here", .{});
|
||||
break :msg msg;
|
||||
};
|
||||
return sema.failWithOwnedErrorMsg(block, msg);
|
||||
@ -23552,7 +23555,7 @@ fn checkComptimeVarStore(
|
||||
const msg = msg: {
|
||||
const msg = try sema.errMsg(block, src, "cannot store to comptime variable in non-inline loop", .{});
|
||||
errdefer msg.destroy(sema.gpa);
|
||||
try sema.errNote(block, loop_src, msg, "non-inline loop here", .{});
|
||||
try sema.mod.errNoteNonLazy(loop_src, msg, "non-inline loop here", .{});
|
||||
break :msg msg;
|
||||
};
|
||||
return sema.failWithOwnedErrorMsg(block, msg);
|
||||
|
||||
@ -0,0 +1,15 @@
|
||||
export fn entry(b: bool) void {
|
||||
comptime var int = 0;
|
||||
if (b) {
|
||||
comptime incr(&int);
|
||||
}
|
||||
}
|
||||
fn incr(x: *comptime_int) void {
|
||||
x.* += 1;
|
||||
}
|
||||
|
||||
// error
|
||||
//
|
||||
// :8:9: error: store to comptime variable depends on runtime condition
|
||||
// :3:9: note: runtime condition here
|
||||
// :4:22: note: called from here
|
||||
Loading…
x
Reference in New Issue
Block a user