| author | |
| committer | |
| log | da7fcfd1586fa93c3d00815f60030e00ea583701 |
| tree | d1f9b47a50df7ebff0b43a5ca98a406149821ddf |
| parent | e851d89113a57064c38ed85722edc7f686d0c11a |
4 files changed, 35 insertions(+), 5 deletions(-)
src/Sema.zig+10-5| ... | @@ -11048,11 +11048,16 @@ fn elemVal( | ... | @@ -11048,11 +11048,16 @@ fn elemVal( |
| 11048 | switch (maybe_ptr_ty.zigTypeTag()) { | 11048 | switch (maybe_ptr_ty.zigTypeTag()) { |
| 11049 | .Pointer => switch (maybe_ptr_ty.ptrSize()) { | 11049 | .Pointer => switch (maybe_ptr_ty.ptrSize()) { |
| 11050 | .Slice => { | 11050 | .Slice => { |
| 11051 | if (try sema.resolveDefinedValue(block, src, array_maybe_ptr)) |slice_val| { | 11051 | const maybe_slice_val = try sema.resolveDefinedValue(block, array_ptr_src, array_maybe_ptr); |
| 11052 | _ = slice_val; | 11052 | const maybe_index_val = try sema.resolveDefinedValue(block, elem_index_src, elem_index); |
| 11053 | return sema.fail(block, src, "TODO implement Sema for elemVal for comptime known slice", .{}); | 11053 | const runtime_src = if (maybe_slice_val) |slice_val| rs: { |
| 11054 | } | 11054 | const index_val = maybe_index_val orelse break :rs elem_index_src; |
| 11055 | try sema.requireRuntimeBlock(block, src); | 11055 | const index = @intCast(usize, index_val.toUnsignedInt()); |
| 11056 | const elem_val = try slice_val.elemValue(sema.arena, index); | ||
| 11057 | return sema.addConstant(maybe_ptr_ty.elemType2(), elem_val); | ||
| 11058 | } else array_ptr_src; | ||
| 11059 | |||
| 11060 | try sema.requireRuntimeBlock(block, runtime_src); | ||
| 11056 | return block.addBinOp(.slice_elem_val, array_maybe_ptr, elem_index); | 11061 | return block.addBinOp(.slice_elem_val, array_maybe_ptr, elem_index); |
| 11057 | }, | 11062 | }, |
| 11058 | .Many, .C => { | 11063 | .Many, .C => { |
src/type.zig+1| ... | @@ -2448,6 +2448,7 @@ pub const Type = extern union { | ... | @@ -2448,6 +2448,7 @@ pub const Type = extern union { |
| 2448 | /// For ?[*]T, returns T. | 2448 | /// For ?[*]T, returns T. |
| 2449 | /// For *T, returns T. | 2449 | /// For *T, returns T. |
| 2450 | /// For [*]T, returns T. | 2450 | /// For [*]T, returns T. |
| 2451 | /// For []T, returns T. | ||
| 2451 | pub fn elemType2(ty: Type) Type { | 2452 | pub fn elemType2(ty: Type) Type { |
| 2452 | return switch (ty.tag()) { | 2453 | return switch (ty.tag()) { |
| 2453 | .vector => ty.castTag(.vector).?.data.elem_type, | 2454 | .vector => ty.castTag(.vector).?.data.elem_type, |
src/value.zig+3| ... | @@ -1651,6 +1651,9 @@ pub const Value = extern union { | ... | @@ -1651,6 +1651,9 @@ pub const Value = extern union { |
| 1651 | .array => return val.castTag(.array).?.data[index], | 1651 | .array => return val.castTag(.array).?.data[index], |
| 1652 | .slice => return val.castTag(.slice).?.data.ptr.elemValue(arena, index), | 1652 | .slice => return val.castTag(.slice).?.data.ptr.elemValue(arena, index), |
| 1653 | 1653 | ||
| 1654 | .decl_ref => return val.castTag(.decl_ref).?.data.val.elemValue(arena, index), | ||
| 1655 | .decl_ref_mut => return val.castTag(.decl_ref_mut).?.data.decl.val.elemValue(arena, index), | ||
| 1656 | |||
| 1654 | else => unreachable, | 1657 | else => unreachable, |
| 1655 | } | 1658 | } |
| 1656 | } | 1659 | } |
test/behavior/slice.zig+21| ... | @@ -3,3 +3,24 @@ const expect = std.testing.expect; | ... | @@ -3,3 +3,24 @@ const expect = std.testing.expect; |
| 3 | const expectEqualSlices = std.testing.expectEqualSlices; | 3 | const expectEqualSlices = std.testing.expectEqualSlices; |
| 4 | const expectEqual = std.testing.expectEqual; | 4 | const expectEqual = std.testing.expectEqual; |
| 5 | const mem = std.mem; | 5 | const mem = std.mem; |
| 6 | |||
| 7 | // comptime array passed as slice argument | ||
| 8 | comptime { | ||
| 9 | const S = struct { | ||
| 10 | fn indexOfScalarPos(comptime T: type, slice: []const T, start_index: usize, value: T) ?usize { | ||
| 11 | var i: usize = start_index; | ||
| 12 | while (i < slice.len) : (i += 1) { | ||
| 13 | if (slice[i] == value) return i; | ||
| 14 | } | ||
| 15 | return null; | ||
| 16 | } | ||
| 17 | |||
| 18 | fn indexOfScalar(comptime T: type, slice: []const T, value: T) ?usize { | ||
| 19 | return indexOfScalarPos(T, slice, 0, value); | ||
| 20 | } | ||
| 21 | }; | ||
| 22 | const unsigned = [_]type{ c_uint, c_ulong, c_ulonglong }; | ||
| 23 | const list: []const type = &unsigned; | ||
| 24 | var pos = S.indexOfScalar(type, list, c_ulong).?; | ||
| 25 | if (pos != 1) @compileError("bad pos"); | ||
| 26 | } |