@@ -4309,10 +4309,10 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index, op: Op) InnerError!W
4309
4309
// for signed integers, we first apply signed shifts by the difference in bits
4310
4310
// to get the signed value, as we store it internally as 2's complement.
4311
4311
const lhs = if (wasm_bits != int_info .bits and is_signed ) blk : {
4312
- break :blk try self .signAbsValue (lhs_op , lhs_ty );
4312
+ break :blk try ( try self .signAbsValue (lhs_op , lhs_ty )). toLocal ( self , lhs_ty );
4313
4313
} else lhs_op ;
4314
4314
const rhs = if (wasm_bits != int_info .bits and is_signed ) blk : {
4315
- break :blk try self .signAbsValue (rhs_op , lhs_ty );
4315
+ break :blk try ( try self .signAbsValue (rhs_op , lhs_ty )). toLocal ( self , lhs_ty );
4316
4316
} else rhs_op ;
4317
4317
4318
4318
const bin_op = try (try self .binOp (lhs , rhs , lhs_ty , op )).toLocal (self , lhs_ty );
@@ -4420,9 +4420,9 @@ fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) InnerError!WValue {
4420
4420
} else shl ;
4421
4421
4422
4422
const overflow_bit = if (wasm_bits != int_info .bits and is_signed ) blk : {
4423
- const abs = try self .signAbsValue (shl , lhs_ty );
4424
4423
// emit lhs to stack to we can keep 'wrapped' on the stack also
4425
4424
try self .emitWValue (lhs );
4425
+ const abs = try self .signAbsValue (shl , lhs_ty );
4426
4426
const wrapped = try self .wrapBinOp (abs , rhs , lhs_ty , .shr );
4427
4427
break :blk try self .cmp (.{ .stack = {} }, wrapped , lhs_ty , .neq );
4428
4428
} else blk : {
@@ -4909,10 +4909,10 @@ fn airDivFloor(self: *Self, inst: Air.Inst.Index) InnerError!WValue {
4909
4909
return self .fail ("TODO: `@divFloor` for signed integers larger than '{d}' bits" , .{int_bits });
4910
4910
};
4911
4911
const lhs_res = if (wasm_bits != int_bits ) blk : {
4912
- break :blk try self .signAbsValue (lhs , ty );
4912
+ break :blk try ( try self .signAbsValue (lhs , ty )). toLocal ( self , ty );
4913
4913
} else lhs ;
4914
4914
const rhs_res = if (wasm_bits != int_bits ) blk : {
4915
- break :blk try self .signAbsValue (rhs , ty );
4915
+ break :blk try ( try self .signAbsValue (rhs , ty )). toLocal ( self , ty );
4916
4916
} else rhs ;
4917
4917
4918
4918
const zero = switch (wasm_bits ) {
@@ -4994,10 +4994,9 @@ fn divSigned(self: *Self, lhs: WValue, rhs: WValue, ty: Type) InnerError!WValue
4994
4994
}
4995
4995
4996
4996
if (wasm_bits != int_bits ) {
4997
- const lhs_abs = try self .signAbsValue (lhs , ty );
4998
- const rhs_abs = try self .signAbsValue (rhs , ty );
4999
- try self .emitWValue (lhs_abs );
5000
- try self .emitWValue (rhs_abs );
4997
+ // Leave both values on the stack
4998
+ _ = try self .signAbsValue (lhs , ty );
4999
+ _ = try self .signAbsValue (rhs , ty );
5001
5000
} else {
5002
5001
try self .emitWValue (lhs );
5003
5002
try self .emitWValue (rhs );
@@ -5009,6 +5008,8 @@ fn divSigned(self: *Self, lhs: WValue, rhs: WValue, ty: Type) InnerError!WValue
5009
5008
return result ;
5010
5009
}
5011
5010
5011
+ /// Retrieves the absolute value of a signed integer
5012
+ /// NOTE: Leaves the result value on the stack.
5012
5013
fn signAbsValue (self : * Self , operand : WValue , ty : Type ) InnerError ! WValue {
5013
5014
const int_bits = ty .intInfo (self .target ).bits ;
5014
5015
const wasm_bits = toWasmBits (int_bits ) orelse {
@@ -5037,9 +5038,8 @@ fn signAbsValue(self: *Self, operand: WValue, ty: Type) InnerError!WValue {
5037
5038
},
5038
5039
else = > unreachable ,
5039
5040
}
5040
- const result = try self .allocLocal (ty );
5041
- try self .addLabel (.local_set , result .local );
5042
- return result ;
5041
+
5042
+ return WValue { .stack = {} };
5043
5043
}
5044
5044
5045
5045
fn airCeilFloorTrunc (self : * Self , inst : Air.Inst.Index , op : Op ) InnerError ! WValue {
@@ -5130,8 +5130,12 @@ fn signedSat(self: *Self, lhs_operand: WValue, rhs_operand: WValue, ty: Type, op
5130
5130
const wasm_bits = toWasmBits (int_info .bits ).? ;
5131
5131
const is_wasm_bits = wasm_bits == int_info .bits ;
5132
5132
5133
- const lhs = if (! is_wasm_bits ) try self .signAbsValue (lhs_operand , ty ) else lhs_operand ;
5134
- const rhs = if (! is_wasm_bits ) try self .signAbsValue (rhs_operand , ty ) else rhs_operand ;
5133
+ const lhs = if (! is_wasm_bits ) lhs : {
5134
+ break :lhs try (try self .signAbsValue (lhs_operand , ty )).toLocal (self , ty );
5135
+ } else lhs_operand ;
5136
+ const rhs = if (! is_wasm_bits ) rhs : {
5137
+ break :rhs try (try self .signAbsValue (rhs_operand , ty )).toLocal (self , ty );
5138
+ } else rhs_operand ;
5135
5139
5136
5140
const max_val : u64 = @intCast (u64 , (@as (u65 , 1 ) << @intCast (u7 , int_info .bits - 1 )) - 1 );
5137
5141
const min_val : i64 = (- @intCast (i64 , @intCast (u63 , max_val ))) - 1 ;
0 commit comments