aboutsummaryrefslogtreecommitdiff
path: root/src/Sema.zig
diff options
context:
space:
mode:
authorMatthew Lugg <mlugg@mlugg.co.uk>2025-11-12 23:14:02 +0000
committerGitHub <noreply@github.com>2025-11-12 23:14:02 +0000
commit181b25ce4fcebc32f6fdc7498148c0f5e131dda9 (patch)
treef5cfe981b1b158e8bac17cc3a3bc909ffb7b1aa1 /src/Sema.zig
parentdfd7b7f2337d84ce660253a37079489f7780b055 (diff)
parent532aa3c5758f110eb7cf0992eb394088ab563899 (diff)
downloadzig-181b25ce4fcebc32f6fdc7498148c0f5e131dda9.tar.gz
zig-181b25ce4fcebc32f6fdc7498148c0f5e131dda9.zip
Merge pull request #25772 from mlugg/kill-dead-code
compiler: rewrite some legalizations, and remove a bunch of dead code
Diffstat (limited to 'src/Sema.zig')
-rw-r--r--src/Sema.zig125
1 files changed, 31 insertions, 94 deletions
diff --git a/src/Sema.zig b/src/Sema.zig
index 27c1716c2b..191ab34070 100644
--- a/src/Sema.zig
+++ b/src/Sema.zig
@@ -15919,24 +15919,30 @@ fn zirOverflowArithmetic(
},
.mul_with_overflow => {
// If either of the arguments is zero, the result is zero and no overflow occured.
- // If either of the arguments is one, the result is the other and no overflow occured.
- // Otherwise, if either of the arguments is undefined, both results are undefined.
- const scalar_one = try pt.intValue(dest_ty.scalarType(zcu), 1);
if (maybe_lhs_val) |lhs_val| {
- if (!lhs_val.isUndef(zcu)) {
- if (try lhs_val.compareAllWithZeroSema(.eq, pt)) {
- break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = lhs };
- } else if (try sema.compareAll(lhs_val, .eq, try sema.splat(dest_ty, scalar_one), dest_ty)) {
- break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = rhs };
- }
+ if (!lhs_val.isUndef(zcu) and try lhs_val.compareAllWithZeroSema(.eq, pt)) {
+ break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = lhs };
}
}
-
if (maybe_rhs_val) |rhs_val| {
- if (!rhs_val.isUndef(zcu)) {
- if (try rhs_val.compareAllWithZeroSema(.eq, pt)) {
+ if (!rhs_val.isUndef(zcu) and try rhs_val.compareAllWithZeroSema(.eq, pt)) {
+ break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = rhs };
+ }
+ }
+ // If either of the arguments is one, the result is the other and no overflow occured.
+ const dest_scalar_ty = dest_ty.scalarType(zcu);
+ const dest_scalar_int = dest_scalar_ty.intInfo(zcu);
+ // We could still be working with i1, where '1' is not a legal value!
+ if (!(dest_scalar_int.bits == 1 and dest_scalar_int.signedness == .signed)) {
+ const scalar_one = try pt.intValue(dest_scalar_ty, 1);
+ const vec_one = try sema.splat(dest_ty, scalar_one);
+ if (maybe_lhs_val) |lhs_val| {
+ if (!lhs_val.isUndef(zcu) and try sema.compareAll(lhs_val, .eq, vec_one, dest_ty)) {
break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = rhs };
- } else if (try sema.compareAll(rhs_val, .eq, try sema.splat(dest_ty, scalar_one), dest_ty)) {
+ }
+ }
+ if (maybe_rhs_val) |rhs_val| {
+ if (!rhs_val.isUndef(zcu) and try sema.compareAll(rhs_val, .eq, vec_one, dest_ty)) {
break :result .{ .overflow_bit = try sema.splat(overflow_ty, .zero_u1), .inst = lhs };
}
}
@@ -15947,7 +15953,6 @@ fn zirOverflowArithmetic(
if (lhs_val.isUndef(zcu) or rhs_val.isUndef(zcu)) {
break :result .{ .overflow_bit = .undef, .wrapped = .undef };
}
-
const result = try arith.mulWithOverflow(sema, dest_ty, lhs_val, rhs_val);
break :result .{ .overflow_bit = result.overflow_bit, .wrapped = result.wrapped_result };
}
@@ -17751,10 +17756,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai
try ty.resolveStructFieldInits(pt);
for (struct_field_vals, 0..) |*field_val, field_index| {
- const field_name = if (struct_type.fieldName(ip, field_index).unwrap()) |field_name|
- field_name
- else
- try ip.getOrPutStringFmt(gpa, pt.tid, "{d}", .{field_index}, .no_embedded_nulls);
+ const field_name = struct_type.fieldName(ip, field_index);
const field_name_len = field_name.length(ip);
const field_ty: Type = .fromInterned(struct_type.field_types.get(ip)[field_index]);
const field_init = struct_type.fieldInit(ip, field_index);
@@ -28345,6 +28347,10 @@ fn elemPtrArray(
break :o index;
} else null;
+ if (offset == null and array_ty.zigTypeTag(zcu) == .vector) {
+ return sema.fail(block, elem_index_src, "vector index not comptime known", .{});
+ }
+
const elem_ptr_ty = try array_ptr_ty.elemPtrType(offset, pt);
if (maybe_undef_array_ptr_val) |array_ptr_val| {
@@ -28362,10 +28368,6 @@ fn elemPtrArray(
try sema.validateRuntimeValue(block, array_ptr_src, array_ptr);
}
- if (offset == null and array_ty.zigTypeTag(zcu) == .vector) {
- return sema.fail(block, elem_index_src, "vector index not comptime known", .{});
- }
-
// Runtime check is only needed if unable to comptime check.
if (oob_safety and block.wantSafety() and offset == null) {
const len_inst = try pt.intRef(.usize, array_len);
@@ -30397,22 +30399,6 @@ fn storePtr2(
const is_ret = air_tag == .ret_ptr;
- // Detect if we are storing an array operand to a bitcasted vector pointer.
- // If so, we instead reach through the bitcasted pointer to the vector pointer,
- // bitcast the array operand to a vector, and then lower this as a store of
- // a vector value to a vector pointer. This generally results in better code,
- // as well as working around an LLVM bug:
- // https://github.com/ziglang/zig/issues/11154
- if (sema.obtainBitCastedVectorPtr(ptr)) |vector_ptr| {
- const vector_ty = sema.typeOf(vector_ptr).childType(zcu);
- const vector = sema.coerceExtra(block, vector_ty, uncasted_operand, operand_src, .{ .is_ret = is_ret }) catch |err| switch (err) {
- error.NotCoercible => unreachable,
- else => |e| return e,
- };
- try sema.storePtr2(block, src, vector_ptr, ptr_src, vector, operand_src, .store);
- return;
- }
-
const operand = sema.coerceExtra(block, elem_ty, uncasted_operand, operand_src, .{ .is_ret = is_ret }) catch |err| switch (err) {
error.NotCoercible => unreachable,
else => |e| return e,
@@ -30445,29 +30431,6 @@ fn storePtr2(
try sema.requireRuntimeBlock(block, src, runtime_src);
- if (ptr_ty.ptrInfo(zcu).flags.vector_index == .runtime) {
- const ptr_inst = ptr.toIndex().?;
- const air_tags = sema.air_instructions.items(.tag);
- if (air_tags[@intFromEnum(ptr_inst)] == .ptr_elem_ptr) {
- const ty_pl = sema.air_instructions.items(.data)[@intFromEnum(ptr_inst)].ty_pl;
- const bin_op = sema.getTmpAir().extraData(Air.Bin, ty_pl.payload).data;
- _ = try block.addInst(.{
- .tag = .vector_store_elem,
- .data = .{ .vector_store_elem = .{
- .vector_ptr = bin_op.lhs,
- .payload = try block.sema.addExtra(Air.Bin{
- .lhs = bin_op.rhs,
- .rhs = operand,
- }),
- } },
- });
- return;
- }
- return sema.fail(block, ptr_src, "unable to determine vector element index of type '{f}'", .{
- ptr_ty.fmt(pt),
- });
- }
-
const store_inst = if (is_ret)
try block.addBinOp(.store, ptr, operand)
else
@@ -30567,37 +30530,6 @@ fn markMaybeComptimeAllocRuntime(sema: *Sema, block: *Block, alloc_inst: Air.Ins
}
}
-/// Traverse an arbitrary number of bitcasted pointers and return the underyling vector
-/// pointer. Only if the final element type matches the vector element type, and the
-/// lengths match.
-fn obtainBitCastedVectorPtr(sema: *Sema, ptr: Air.Inst.Ref) ?Air.Inst.Ref {
- const pt = sema.pt;
- const zcu = pt.zcu;
- const array_ty = sema.typeOf(ptr).childType(zcu);
- if (array_ty.zigTypeTag(zcu) != .array) return null;
- var ptr_ref = ptr;
- var ptr_inst = ptr_ref.toIndex() orelse return null;
- const air_datas = sema.air_instructions.items(.data);
- const air_tags = sema.air_instructions.items(.tag);
- const vector_ty = while (air_tags[@intFromEnum(ptr_inst)] == .bitcast) {
- ptr_ref = air_datas[@intFromEnum(ptr_inst)].ty_op.operand;
- if (!sema.isKnownZigType(ptr_ref, .pointer)) return null;
- const child_ty = sema.typeOf(ptr_ref).childType(zcu);
- if (child_ty.zigTypeTag(zcu) == .vector) break child_ty;
- ptr_inst = ptr_ref.toIndex() orelse return null;
- } else return null;
-
- // We have a pointer-to-array and a pointer-to-vector. If the elements and
- // lengths match, return the result.
- if (array_ty.childType(zcu).eql(vector_ty.childType(zcu), zcu) and
- array_ty.arrayLen(zcu) == vector_ty.vectorLen(zcu))
- {
- return ptr_ref;
- } else {
- return null;
- }
-}
-
/// Call when you have Value objects rather than Air instructions, and you want to
/// assert the store must be done at comptime.
fn storePtrVal(
@@ -35577,8 +35509,13 @@ fn structFieldInits(
const default_val = try sema.resolveConstValue(&block_scope, init_src, coerced, null);
if (default_val.canMutateComptimeVarState(zcu)) {
- const field_name = struct_type.fieldName(ip, field_i).unwrap().?;
- return sema.failWithContainsReferenceToComptimeVar(&block_scope, init_src, field_name, "field default value", default_val);
+ return sema.failWithContainsReferenceToComptimeVar(
+ &block_scope,
+ init_src,
+ struct_type.fieldName(ip, field_i),
+ "field default value",
+ default_val,
+ );
}
struct_type.field_inits.get(ip)[field_i] = default_val.toIntern();
}