| author | |
| committer | |
| log | bee19572c83c77995ca9a1206a6b08606f65eaa7 |
| tree | d5f98142584f04be404c35a338008d0f0528f8dc |
| parent | b5c22777f839f926ff3e272c9285d4d3e6402c0d |
| signature |
* Indexing zero-bit types should not produce AIR indexing instructions
* Getting a runtime-known element pointer from a many-pointer should
check that the many-pointer is not comptime-only
Resolves: #234053 files changed, 47 insertions(+), 0 deletions(-)
src/Sema.zig+13| ... | @@ -29037,6 +29037,14 @@ fn elemPtrOneLayerOnly( | ... | @@ -29037,6 +29037,14 @@ fn elemPtrOneLayerOnly( |
| 29037 | } | 29037 | } |
| 29038 | const result_ty = try indexable_ty.elemPtrType(null, pt); | 29038 | const result_ty = try indexable_ty.elemPtrType(null, pt); |
| 29039 | 29039 | ||
| 29040 | try sema.validateRuntimeElemAccess(block, elem_index_src, result_ty, indexable_ty, indexable_src); | ||
| 29041 | try sema.validateRuntimeValue(block, indexable_src, indexable); | ||
| 29042 | |||
| 29043 | if (!try result_ty.childType(zcu).hasRuntimeBitsIgnoreComptimeSema(pt)) { | ||
| 29044 | // zero-bit child type; just bitcast the pointer | ||
| 29045 | return block.addBitCast(result_ty, indexable); | ||
| 29046 | } | ||
| 29047 | |||
| 29040 | return block.addPtrElemPtr(indexable, elem_index, result_ty); | 29048 | return block.addPtrElemPtr(indexable, elem_index, result_ty); |
| 29041 | }, | 29049 | }, |
| 29042 | .one => { | 29050 | .one => { |
| ... | @@ -29497,6 +29505,11 @@ fn elemPtrSlice( | ... | @@ -29497,6 +29505,11 @@ fn elemPtrSlice( |
| 29497 | const cmp_op: Air.Inst.Tag = if (slice_sent) .cmp_lte else .cmp_lt; | 29505 | const cmp_op: Air.Inst.Tag = if (slice_sent) .cmp_lte else .cmp_lt; |
| 29498 | try sema.addSafetyCheckIndexOob(block, src, elem_index, len_inst, cmp_op); | 29506 | try sema.addSafetyCheckIndexOob(block, src, elem_index, len_inst, cmp_op); |
| 29499 | } | 29507 | } |
| 29508 | if (!try slice_ty.childType(zcu).hasRuntimeBitsIgnoreComptimeSema(pt)) { | ||
| 29509 | // zero-bit child type; just extract the pointer and bitcast it | ||
| 29510 | const slice_ptr = try block.addTyOp(.slice_ptr, slice_ty.slicePtrFieldType(zcu), slice); | ||
| 29511 | return block.addBitCast(elem_ptr_ty, slice_ptr); | ||
| 29512 | } | ||
| 29500 | return block.addSliceElemPtr(slice, elem_index, elem_ptr_ty); | 29513 | return block.addSliceElemPtr(slice, elem_index, elem_ptr_ty); |
| 29501 | } | 29514 | } |
| 29502 | 29515 |
test/behavior/pointers.zig+24| ... | @@ -760,3 +760,27 @@ test "comptime pointer equality through distinct elements with well-defined layo | ... | @@ -760,3 +760,27 @@ test "comptime pointer equality through distinct elements with well-defined layo |
| 760 | comptime assert(buf[1] == 456); | 760 | comptime assert(buf[1] == 456); |
| 761 | comptime assert(second_elem.* == 456); | 761 | comptime assert(second_elem.* == 456); |
| 762 | } | 762 | } |
| 763 | |||
| 764 | test "pointers to elements of slice of zero-bit type" { | ||
| 765 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 766 | |||
| 767 | var slice: []const u0 = undefined; | ||
| 768 | slice = &.{ 0, 0 }; | ||
| 769 | |||
| 770 | const a = &slice[0]; | ||
| 771 | const b = &slice[1]; | ||
| 772 | |||
| 773 | try expect(a == b); | ||
| 774 | } | ||
| 775 | |||
| 776 | test "pointers to elements of many-ptr to zero-bit type" { | ||
| 777 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 778 | |||
| 779 | var many_ptr: [*]const u0 = undefined; | ||
| 780 | many_ptr = &.{ 0, 0 }; | ||
| 781 | |||
| 782 | const a = &many_ptr[0]; | ||
| 783 | const b = &many_ptr[1]; | ||
| 784 | |||
| 785 | try expect(a == b); | ||
| 786 | } |
test/cases/compile_errors/runtime_index_into_comptime_only_many_ptr.zig created+10| ... | @@ -0,0 +1,10 @@ | ||
| 1 | var rt: usize = 0; | ||
| 2 | export fn foo() void { | ||
| 3 | const x: [*]const type = &.{ u8, u16 }; | ||
| 4 | _ = &x[rt]; | ||
| 5 | } | ||
| 6 | |||
| 7 | // error | ||
| 8 | // | ||
| 9 | // :4:12: error: values of type '[*]const type' must be comptime-known, but index value is runtime-known | ||
| 10 | // :4:11: note: types are not available at runtime | ||