Skip to content

Commit 42d9017

Browse files
wrongnullVexu
andauthored
Sema: fix OOB access in coerceTupleToStruct (#19620)
Co-authored-by: Veikka Tuominen <[email protected]>
1 parent 08cddaf commit 42d9017

File tree

2 files changed

+18
-23
lines changed

2 files changed

+18
-23
lines changed

src/Sema.zig

Lines changed: 5 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -31867,14 +31867,9 @@ fn coerceTupleToStruct(
3186731867
};
3186831868
for (0..field_count) |tuple_field_index| {
3186931869
const field_src = inst_src; // TODO better source location
31870-
const field_name: InternPool.NullTerminatedString = switch (ip.indexToKey(inst_ty.toIntern())) {
31871-
.anon_struct_type => |anon_struct_type| if (anon_struct_type.names.len > 0)
31872-
anon_struct_type.names.get(ip)[tuple_field_index]
31873-
else
31874-
try ip.getOrPutStringFmt(sema.gpa, pt.tid, "{d}", .{tuple_field_index}, .no_embedded_nulls),
31875-
.struct_type => ip.loadStructType(inst_ty.toIntern()).field_names.get(ip)[tuple_field_index],
31876-
else => unreachable,
31877-
};
31870+
const field_name = inst_ty.structFieldName(tuple_field_index, mod).unwrap() orelse
31871+
try ip.getOrPutStringFmt(sema.gpa, pt.tid, "{d}", .{tuple_field_index}, .no_embedded_nulls);
31872+
3187831873
const struct_field_index = try sema.structFieldIndex(block, struct_ty, field_name, field_src);
3187931874
const struct_field_ty = Type.fromInterned(struct_type.field_types.get(ip)[struct_field_index]);
3188031875
const elem_ref = try sema.tupleField(block, inst_src, inst, field_src, @intCast(tuple_field_index));
@@ -31980,21 +31975,8 @@ fn coerceTupleToTuple(
3198031975
for (0..dest_field_count) |field_index_usize| {
3198131976
const field_i: u32 = @intCast(field_index_usize);
3198231977
const field_src = inst_src; // TODO better source location
31983-
const field_name: InternPool.NullTerminatedString = switch (ip.indexToKey(inst_ty.toIntern())) {
31984-
.anon_struct_type => |anon_struct_type| if (anon_struct_type.names.len > 0)
31985-
anon_struct_type.names.get(ip)[field_i]
31986-
else
31987-
try ip.getOrPutStringFmt(sema.gpa, pt.tid, "{d}", .{field_i}, .no_embedded_nulls),
31988-
.struct_type => s: {
31989-
const struct_type = ip.loadStructType(inst_ty.toIntern());
31990-
if (struct_type.field_names.len > 0) {
31991-
break :s struct_type.field_names.get(ip)[field_i];
31992-
} else {
31993-
break :s try ip.getOrPutStringFmt(sema.gpa, pt.tid, "{d}", .{field_i}, .no_embedded_nulls);
31994-
}
31995-
},
31996-
else => unreachable,
31997-
};
31978+
const field_name = inst_ty.structFieldName(field_index_usize, mod).unwrap() orelse
31979+
try ip.getOrPutStringFmt(sema.gpa, pt.tid, "{d}", .{field_index_usize}, .no_embedded_nulls);
3199831980

3199931981
if (field_name.eqlSlice("len", ip))
3200031982
return sema.fail(block, field_src, "cannot assign to 'len' field of tuple", .{});
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
const S = struct {
2+
fizz: void,
3+
};
4+
5+
export fn entry() void {
6+
_ = @as(S, struct { void }{{}});
7+
}
8+
9+
// error
10+
// target=native
11+
//
12+
// :6:31: error: no field named '0' in struct 'tmp.S'
13+
// :1:11: note: struct declared here

0 commit comments

Comments
 (0)