compiler_builtins/float/
pow.rs

1use crate::float::Float;
2use crate::int::Int;
3
4/// Returns `a` raised to the power `b`
5fn pow<F: Float>(a: F, b: i32) -> F {
6    let mut a = a;
7    let recip = b < 0;
8    let mut pow = Int::abs_diff(b, 0);
9    let mut mul = F::ONE;
10    loop {
11        if (pow & 1) != 0 {
12            mul *= a;
13        }
14        pow >>= 1;
15        if pow == 0 {
16            break;
17        }
18        a *= a;
19    }
20
21    if recip { F::ONE / mul } else { mul }
22}
23
24intrinsics! {
25    pub extern "C" fn __powisf2(a: f32, b: i32) -> f32 {
26        pow(a, b)
27    }
28
29    pub extern "C" fn __powidf2(a: f64, b: i32) -> f64 {
30        pow(a, b)
31    }
32
33    #[ppc_alias = __powikf2]
34    #[cfg(f128_enabled)]
35    // FIXME(f16_f128): MSVC cannot build these until `__divtf3` is available in nightly.
36    #[cfg(not(target_env = "msvc"))]
37    pub extern "C" fn __powitf2(a: f128, b: i32) -> f128 {
38        pow(a, b)
39    }
40}