diff options
| author | bjorn3 <17426603+bjorn3@users.noreply.github.com> | 2023-06-23 09:17:02 +0000 |
|---|---|---|
| committer | bjorn3 <17426603+bjorn3@users.noreply.github.com> | 2023-06-23 09:17:02 +0000 |
| commit | 0311202fd49615ddeb41879eff2a87e4faaa25ab (patch) | |
| tree | 3c76086019db95dfd590e724244e0deb8810f551 /src | |
| parent | 6b141f39d210907c8f7e50b082addb92b00235d4 (diff) | |
| download | rust-0311202fd49615ddeb41879eff2a87e4faaa25ab.tar.gz rust-0311202fd49615ddeb41879eff2a87e4faaa25ab.zip | |
Implement _addcarry_u32 and _subborrow_u32
Diffstat (limited to 'src')
| -rw-r--r-- | src/intrinsics/llvm_x86.rs | 24 |
1 files changed, 8 insertions, 16 deletions
diff --git a/src/intrinsics/llvm_x86.rs b/src/intrinsics/llvm_x86.rs index bbd5f4be783..a48ef7348d1 100644 --- a/src/intrinsics/llvm_x86.rs +++ b/src/intrinsics/llvm_x86.rs @@ -321,13 +321,13 @@ pub(crate) fn codegen_x86_llvm_intrinsic_call<'tcx>( let dest = CPlace::for_ptr(Pointer::new(mem_addr), a.layout()); dest.write_cvalue(fx, a); } - "llvm.x86.addcarry.64" => { + "llvm.x86.addcarry.32" | "llvm.x86.addcarry.64" => { intrinsic_args!(fx, args => (c_in, a, b); intrinsic); let c_in = c_in.load_scalar(fx); llvm_add_sub(fx, BinOp::Add, ret, c_in, a, b); } - "llvm.x86.subborrow.64" => { + "llvm.x86.subborrow.32" | "llvm.x86.subborrow.64" => { intrinsic_args!(fx, args => (b_in, a, b); intrinsic); let b_in = b_in.load_scalar(fx); @@ -361,16 +361,7 @@ fn llvm_add_sub<'tcx>( a: CValue<'tcx>, b: CValue<'tcx>, ) { - assert_eq!( - a.layout().ty, - fx.tcx.types.u64, - "llvm.x86.addcarry.64/llvm.x86.subborrow.64 second operand must be u64" - ); - assert_eq!( - b.layout().ty, - fx.tcx.types.u64, - "llvm.x86.addcarry.64/llvm.x86.subborrow.64 third operand must be u64" - ); + assert_eq!(a.layout().ty, b.layout().ty); // c + carry -> c + first intermediate carry or borrow respectively let int0 = crate::num::codegen_checked_int_binop(fx, bin_op, a, b); @@ -378,15 +369,16 @@ fn llvm_add_sub<'tcx>( let cb0 = int0.value_field(fx, FieldIdx::new(1)).load_scalar(fx); // c + carry -> c + second intermediate carry or borrow respectively - let cb_in_as_u64 = fx.bcx.ins().uextend(types::I64, cb_in); - let cb_in_as_u64 = CValue::by_val(cb_in_as_u64, fx.layout_of(fx.tcx.types.u64)); - let int1 = crate::num::codegen_checked_int_binop(fx, bin_op, c, cb_in_as_u64); + let clif_ty = fx.clif_type(a.layout().ty).unwrap(); + let cb_in_as_int = fx.bcx.ins().uextend(clif_ty, cb_in); + let cb_in_as_int = CValue::by_val(cb_in_as_int, fx.layout_of(a.layout().ty)); + let int1 = crate::num::codegen_checked_int_binop(fx, bin_op, c, cb_in_as_int); let (c, cb1) = int1.load_scalar_pair(fx); // carry0 | carry1 -> carry or borrow respectively let cb_out = fx.bcx.ins().bor(cb0, cb1); - let layout = fx.layout_of(fx.tcx.mk_tup(&[fx.tcx.types.u8, fx.tcx.types.u64])); + let layout = fx.layout_of(fx.tcx.mk_tup(&[fx.tcx.types.u8, a.layout().ty])); let val = CValue::by_val_pair(cb_out, c, layout); ret.write_cvalue(fx, val); } |
