@@ -176,6 +176,52 @@ macro_rules! isle_common_prelude_methods {
176176 Imm64 :: new( ( x >> y) & ty_mask)
177177 }
178178
179+ #[ inline]
180+ fn imm64_rotl( & mut self , ty: Type , x: Imm64 , y: Imm64 ) -> Imm64 {
181+ let bits = ty. bits( ) ;
182+ assert!( bits <= 64 ) ;
183+ // This holds for all Cranelift types ({u/i}{8,16,32,64})
184+ debug_assert!( bits. is_power_of_two( ) ) ;
185+
186+ let ty_mask = self . ty_mask( ty) ;
187+ let x = ( x. bits( ) as u64 ) & ty_mask;
188+
189+ // Mask off any excess rotate bits so the rotate stays within `ty`.
190+ let shift_mask = bits - 1 ;
191+ let y = ( ( y. bits( ) as u64 ) & u64 :: from( shift_mask) ) as u32 ;
192+
193+ // In Rust, x >> 64 or x << 64 panics.
194+ let result = if y == 0 {
195+ x
196+ } else {
197+ ( x << y) | ( x >> ( u32 :: from( bits) - y) )
198+ } ;
199+
200+ Imm64 :: new( ( result & ty_mask) as i64 )
201+ }
202+
203+ #[ inline]
204+ fn imm64_rotr( & mut self , ty: Type , x: Imm64 , y: Imm64 ) -> Imm64 {
205+ let bits = ty. bits( ) ;
206+ assert!( bits <= 64 ) ;
207+ debug_assert!( bits. is_power_of_two( ) ) ;
208+
209+ let ty_mask = self . ty_mask( ty) ;
210+ let x = ( x. bits( ) as u64 ) & ty_mask;
211+
212+ // Mask off any excess rotate bits so the rotate stays within `ty`.
213+ let shift_mask = bits - 1 ;
214+ let y = ( ( y. bits( ) as u64 ) & u64 :: from( shift_mask) ) as u32 ;
215+
216+ let result = if y == 0 {
217+ x
218+ } else {
219+ ( x >> y) | ( x << ( u32 :: from( bits) - y) )
220+ } ;
221+
222+ Imm64 :: new( ( result & ty_mask) as i64 )
223+ }
224+
179225 #[ inline]
180226 fn i64_sextend_u64( & mut self , ty: Type , x: u64 ) -> i64 {
181227 let shift_amt = core:: cmp:: max( 0 , 64 - ty. bits( ) ) ;
0 commit comments