]> git.lizzy.rs Git - rust.git/blob - compiler/rustc_codegen_cranelift/src/intrinsics/llvm.rs
Auto merge of #107843 - bjorn3:sync_cg_clif-2023-02-09, r=bjorn3
[rust.git] / compiler / rustc_codegen_cranelift / src / intrinsics / llvm.rs
1 //! Emulate LLVM intrinsics
2
3 use crate::intrinsics::*;
4 use crate::prelude::*;
5
6 use rustc_middle::ty::subst::SubstsRef;
7
8 pub(crate) fn codegen_llvm_intrinsic_call<'tcx>(
9     fx: &mut FunctionCx<'_, '_, 'tcx>,
10     intrinsic: &str,
11     substs: SubstsRef<'tcx>,
12     args: &[mir::Operand<'tcx>],
13     ret: CPlace<'tcx>,
14     target: Option<BasicBlock>,
15 ) {
16     if intrinsic.starts_with("llvm.aarch64") {
17         return llvm_aarch64::codegen_aarch64_llvm_intrinsic_call(
18             fx, intrinsic, substs, args, ret, target,
19         );
20     }
21     if intrinsic.starts_with("llvm.x86") {
22         return llvm_x86::codegen_x86_llvm_intrinsic_call(fx, intrinsic, substs, args, ret, target);
23     }
24
25     match intrinsic {
26         _ if intrinsic.starts_with("llvm.ctlz.v") => {
27             intrinsic_args!(fx, args => (a); intrinsic);
28
29             simd_for_each_lane(fx, a, ret, &|fx, _lane_ty, _res_lane_ty, lane| {
30                 fx.bcx.ins().clz(lane)
31             });
32         }
33
34         _ if intrinsic.starts_with("llvm.ctpop.v") => {
35             intrinsic_args!(fx, args => (a); intrinsic);
36
37             simd_for_each_lane(fx, a, ret, &|fx, _lane_ty, _res_lane_ty, lane| {
38                 fx.bcx.ins().popcnt(lane)
39             });
40         }
41
42         _ => {
43             fx.tcx
44                 .sess
45                 .warn(&format!("unsupported llvm intrinsic {}; replacing with trap", intrinsic));
46             crate::trap::trap_unimplemented(fx, intrinsic);
47             return;
48         }
49     }
50
51     let dest = target.expect("all llvm intrinsics used by stdlib should return");
52     let ret_block = fx.get_block(dest);
53     fx.bcx.ins().jump(ret_block, &[]);
54 }