compiler_builtins/int/
shift.rs1use crate::int::{DInt, HInt, Int, MinInt};
2
3trait Ashl: DInt {
4 fn ashl(self, shl: u32) -> Self {
6 let n_h = Self::H::BITS;
7 if shl & n_h != 0 {
8 self.lo().wrapping_shl(shl - n_h).widen_hi()
10 } else if shl == 0 {
11 self
12 } else {
13 Self::from_lo_hi(
14 self.lo().wrapping_shl(shl),
15 self.lo().logical_shr(n_h.wrapping_sub(shl)) | self.hi().wrapping_shl(shl),
16 )
17 }
18 }
19}
20
21impl Ashl for u32 {}
22impl Ashl for u64 {}
23impl Ashl for u128 {}
24
25trait Ashr: DInt {
26 fn ashr(self, shr: u32) -> Self {
28 let n_h = Self::H::BITS;
29 if shr & n_h != 0 {
30 Self::from_lo_hi(
31 self.hi().wrapping_shr(shr - n_h),
32 self.hi().wrapping_shr(n_h - 1),
34 )
35 } else if shr == 0 {
36 self
37 } else {
38 Self::from_lo_hi(
39 self.lo().logical_shr(shr) | self.hi().wrapping_shl(n_h.wrapping_sub(shr)),
40 self.hi().wrapping_shr(shr),
41 )
42 }
43 }
44}
45
46impl Ashr for i32 {}
47impl Ashr for i64 {}
48impl Ashr for i128 {}
49
50trait Lshr: DInt {
51 fn lshr(self, shr: u32) -> Self {
53 let n_h = Self::H::BITS;
54 if shr & n_h != 0 {
55 self.hi().logical_shr(shr - n_h).zero_widen()
56 } else if shr == 0 {
57 self
58 } else {
59 Self::from_lo_hi(
60 self.lo().logical_shr(shr) | self.hi().wrapping_shl(n_h.wrapping_sub(shr)),
61 self.hi().logical_shr(shr),
62 )
63 }
64 }
65}
66
67impl Lshr for u32 {}
68impl Lshr for u64 {}
69impl Lshr for u128 {}
70
71intrinsics! {
72 #[maybe_use_optimized_c_shim]
73 pub extern "C" fn __ashlsi3(a: u32, b: u32) -> u32 {
74 a.ashl(b)
75 }
76
77 #[maybe_use_optimized_c_shim]
78 #[arm_aeabi_alias = __aeabi_llsl]
79 pub extern "C" fn __ashldi3(a: u64, b: core::ffi::c_uint) -> u64 {
80 a.ashl(b as u32)
81 }
82
83 pub extern "C" fn __ashlti3(a: u128, b: u32) -> u128 {
84 a.ashl(b)
85 }
86
87 #[maybe_use_optimized_c_shim]
88 pub extern "C" fn __ashrsi3(a: i32, b: u32) -> i32 {
89 a.ashr(b)
90 }
91
92 #[maybe_use_optimized_c_shim]
93 #[arm_aeabi_alias = __aeabi_lasr]
94 pub extern "C" fn __ashrdi3(a: i64, b: core::ffi::c_uint) -> i64 {
95 a.ashr(b as u32)
96 }
97
98 pub extern "C" fn __ashrti3(a: i128, b: u32) -> i128 {
99 a.ashr(b)
100 }
101
102 #[maybe_use_optimized_c_shim]
103 pub extern "C" fn __lshrsi3(a: u32, b: u32) -> u32 {
104 a.lshr(b)
105 }
106
107 #[maybe_use_optimized_c_shim]
108 #[arm_aeabi_alias = __aeabi_llsr]
109 pub extern "C" fn __lshrdi3(a: u64, b: core::ffi::c_uint) -> u64 {
110 a.lshr(b as u32)
111 }
112
113 pub extern "C" fn __lshrti3(a: u128, b: u32) -> u128 {
114 a.lshr(b)
115 }
116}