mirror of
https://github.com/ziglang/zig.git
synced 2026-01-20 14:25:16 +00:00
AstGen: make pointless discard error more strict
The error should only happen as a result of `_ = <expr>` not for an operand of a break expression that is discarded. Closes #13212
This commit is contained in:
parent
d2cc55109a
commit
0a188190b3
@ -339,6 +339,8 @@ pub const ResultInfo = struct {
|
||||
fn_arg,
|
||||
/// The expression is the right-hand side of an initializer for a `const` variable
|
||||
const_init,
|
||||
/// The expression is the right-hand side of an assignment expression.
|
||||
assignment,
|
||||
/// No specific operator in particular.
|
||||
none,
|
||||
};
|
||||
@ -3216,7 +3218,7 @@ fn assign(gz: *GenZir, scope: *Scope, infix_node: Ast.Node.Index) InnerError!voi
|
||||
// This intentionally does not support `@"_"` syntax.
|
||||
const ident_name = tree.tokenSlice(main_tokens[lhs]);
|
||||
if (mem.eql(u8, ident_name, "_")) {
|
||||
_ = try expr(gz, scope, .{ .rl = .discard }, rhs);
|
||||
_ = try expr(gz, scope, .{ .rl = .discard, .ctx = .assignment }, rhs);
|
||||
return;
|
||||
}
|
||||
}
|
||||
@ -7088,7 +7090,7 @@ fn localVarRef(
|
||||
if (local_val.name == name_str_index) {
|
||||
// Locals cannot shadow anything, so we do not need to look for ambiguous
|
||||
// references in this case.
|
||||
if (ri.rl == .discard) {
|
||||
if (ri.rl == .discard and ri.ctx == .assignment) {
|
||||
local_val.discarded = ident_token;
|
||||
} else {
|
||||
local_val.used = ident_token;
|
||||
@ -7111,7 +7113,7 @@ fn localVarRef(
|
||||
.local_ptr => {
|
||||
const local_ptr = s.cast(Scope.LocalPtr).?;
|
||||
if (local_ptr.name == name_str_index) {
|
||||
if (ri.rl == .discard) {
|
||||
if (ri.rl == .discard and ri.ctx == .assignment) {
|
||||
local_ptr.discarded = ident_token;
|
||||
} else {
|
||||
local_ptr.used = ident_token;
|
||||
@ -10672,14 +10674,19 @@ const GenZir = struct {
|
||||
gz.break_result_info = parent_ri;
|
||||
},
|
||||
|
||||
.discard, .none, .ref => {
|
||||
.none, .ref => {
|
||||
gz.rl_ty_inst = .none;
|
||||
gz.break_result_info = parent_ri;
|
||||
},
|
||||
|
||||
.discard => {
|
||||
gz.rl_ty_inst = .none;
|
||||
gz.break_result_info = .{ .rl = .discard };
|
||||
},
|
||||
|
||||
.ptr => |ptr_res| {
|
||||
gz.rl_ty_inst = .none;
|
||||
gz.break_result_info = .{ .rl = .{ .ptr = .{ .inst = ptr_res.inst } } };
|
||||
gz.break_result_info = .{ .rl = .{ .ptr = .{ .inst = ptr_res.inst } }, .ctx = parent_ri.ctx };
|
||||
},
|
||||
|
||||
.inferred_ptr => |ptr| {
|
||||
|
||||
@ -3,6 +3,14 @@ export fn foo() void {
|
||||
x += 1;
|
||||
_ = x;
|
||||
}
|
||||
export fn bar() void {
|
||||
var b: u32 = 1;
|
||||
_ = blk: {
|
||||
const a = 1;
|
||||
b = a;
|
||||
break :blk a;
|
||||
};
|
||||
}
|
||||
|
||||
// error
|
||||
// backend=stage2
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user