xref: /freebsd/contrib/llvm-project/clang/lib/Headers/ia32intrin.h (revision 7a6dacaca14b62ca4b74406814becb87a3fefac0)
10b57cec5SDimitry Andric /* ===-------- ia32intrin.h ---------------------------------------------------===
20b57cec5SDimitry Andric  *
30b57cec5SDimitry Andric  * Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric  * See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric  * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric  *
70b57cec5SDimitry Andric  *===-----------------------------------------------------------------------===
80b57cec5SDimitry Andric  */
90b57cec5SDimitry Andric 
100b57cec5SDimitry Andric #ifndef __X86INTRIN_H
110b57cec5SDimitry Andric #error "Never use <ia32intrin.h> directly; include <x86intrin.h> instead."
120b57cec5SDimitry Andric #endif
130b57cec5SDimitry Andric 
140b57cec5SDimitry Andric #ifndef __IA32INTRIN_H
150b57cec5SDimitry Andric #define __IA32INTRIN_H
160b57cec5SDimitry Andric 
17e8d8bef9SDimitry Andric /* Define the default attributes for the functions in this file. */
18e8d8bef9SDimitry Andric #define __DEFAULT_FN_ATTRS __attribute__((__always_inline__, __nodebug__))
19349cc55cSDimitry Andric #define __DEFAULT_FN_ATTRS_CRC32 __attribute__((__always_inline__, __nodebug__, __target__("crc32")))
20e8d8bef9SDimitry Andric 
21e8d8bef9SDimitry Andric #if defined(__cplusplus) && (__cplusplus >= 201103L)
22e8d8bef9SDimitry Andric #define __DEFAULT_FN_ATTRS_CAST __attribute__((__always_inline__)) constexpr
23e8d8bef9SDimitry Andric #define __DEFAULT_FN_ATTRS_CONSTEXPR __DEFAULT_FN_ATTRS constexpr
24e8d8bef9SDimitry Andric #else
25e8d8bef9SDimitry Andric #define __DEFAULT_FN_ATTRS_CAST __attribute__((__always_inline__))
26e8d8bef9SDimitry Andric #define __DEFAULT_FN_ATTRS_CONSTEXPR __DEFAULT_FN_ATTRS
27e8d8bef9SDimitry Andric #endif
28e8d8bef9SDimitry Andric 
29297eecfbSDimitry Andric /// Find the first set bit starting from the lsb. Result is undefined if
30297eecfbSDimitry Andric ///    input is 0.
31297eecfbSDimitry Andric ///
32297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
33297eecfbSDimitry Andric ///
34297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSF instruction or the
35297eecfbSDimitry Andric ///    \c TZCNT instruction.
36297eecfbSDimitry Andric ///
37297eecfbSDimitry Andric /// \param __A
38297eecfbSDimitry Andric ///    A 32-bit integer operand.
39297eecfbSDimitry Andric /// \returns A 32-bit integer containing the bit number.
40*7a6dacacSDimitry Andric /// \see _bit_scan_forward
41e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
420b57cec5SDimitry Andric __bsfd(int __A) {
4381ad6265SDimitry Andric   return __builtin_ctz((unsigned int)__A);
440b57cec5SDimitry Andric }
450b57cec5SDimitry Andric 
46297eecfbSDimitry Andric /// Find the first set bit starting from the msb. Result is undefined if
47297eecfbSDimitry Andric ///    input is 0.
48297eecfbSDimitry Andric ///
49297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
50297eecfbSDimitry Andric ///
51297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSR instruction or the
52297eecfbSDimitry Andric ///    \c LZCNT instruction and an \c XOR.
53297eecfbSDimitry Andric ///
54297eecfbSDimitry Andric /// \param __A
55297eecfbSDimitry Andric ///    A 32-bit integer operand.
56297eecfbSDimitry Andric /// \returns A 32-bit integer containing the bit number.
57*7a6dacacSDimitry Andric /// \see _bit_scan_reverse
58e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
590b57cec5SDimitry Andric __bsrd(int __A) {
6081ad6265SDimitry Andric   return 31 - __builtin_clz((unsigned int)__A);
610b57cec5SDimitry Andric }
620b57cec5SDimitry Andric 
63*7a6dacacSDimitry Andric /// Swaps the bytes in the input, converting little endian to big endian or
64297eecfbSDimitry Andric ///    vice versa.
65297eecfbSDimitry Andric ///
66297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
67297eecfbSDimitry Andric ///
68297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSWAP instruction.
69297eecfbSDimitry Andric ///
70297eecfbSDimitry Andric /// \param __A
71297eecfbSDimitry Andric ///    A 32-bit integer operand.
72297eecfbSDimitry Andric /// \returns A 32-bit integer containing the swapped bytes.
73e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
740b57cec5SDimitry Andric __bswapd(int __A) {
7581ad6265SDimitry Andric   return (int)__builtin_bswap32((unsigned int)__A);
760b57cec5SDimitry Andric }
770b57cec5SDimitry Andric 
78*7a6dacacSDimitry Andric /// Swaps the bytes in the input, converting little endian to big endian or
79*7a6dacacSDimitry Andric ///    vice versa.
80*7a6dacacSDimitry Andric ///
81*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
82*7a6dacacSDimitry Andric ///
83*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c BSWAP instruction.
84*7a6dacacSDimitry Andric ///
85*7a6dacacSDimitry Andric /// \param __A
86*7a6dacacSDimitry Andric ///    A 32-bit integer operand.
87*7a6dacacSDimitry Andric /// \returns A 32-bit integer containing the swapped bytes.
88e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
890b57cec5SDimitry Andric _bswap(int __A) {
9081ad6265SDimitry Andric   return (int)__builtin_bswap32((unsigned int)__A);
910b57cec5SDimitry Andric }
920b57cec5SDimitry Andric 
93*7a6dacacSDimitry Andric /// Find the first set bit starting from the lsb. Result is undefined if
94*7a6dacacSDimitry Andric ///    input is 0.
95*7a6dacacSDimitry Andric ///
96*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
97*7a6dacacSDimitry Andric ///
98*7a6dacacSDimitry Andric /// \code
99*7a6dacacSDimitry Andric /// int _bit_scan_forward(int A);
100*7a6dacacSDimitry Andric /// \endcode
101*7a6dacacSDimitry Andric ///
102*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c BSF instruction or the
103*7a6dacacSDimitry Andric ///    \c TZCNT instruction.
104*7a6dacacSDimitry Andric ///
105*7a6dacacSDimitry Andric /// \param A
106*7a6dacacSDimitry Andric ///    A 32-bit integer operand.
107*7a6dacacSDimitry Andric /// \returns A 32-bit integer containing the bit number.
108*7a6dacacSDimitry Andric /// \see __bsfd
1090b57cec5SDimitry Andric #define _bit_scan_forward(A) __bsfd((A))
110*7a6dacacSDimitry Andric 
111*7a6dacacSDimitry Andric /// Find the first set bit starting from the msb. Result is undefined if
112*7a6dacacSDimitry Andric ///    input is 0.
113*7a6dacacSDimitry Andric ///
114*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
115*7a6dacacSDimitry Andric ///
116*7a6dacacSDimitry Andric /// \code
117*7a6dacacSDimitry Andric /// int _bit_scan_reverse(int A);
118*7a6dacacSDimitry Andric /// \endcode
119*7a6dacacSDimitry Andric ///
120*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c BSR instruction or the
121*7a6dacacSDimitry Andric ///    \c LZCNT instruction and an \c XOR.
122*7a6dacacSDimitry Andric ///
123*7a6dacacSDimitry Andric /// \param A
124*7a6dacacSDimitry Andric ///    A 32-bit integer operand.
125*7a6dacacSDimitry Andric /// \returns A 32-bit integer containing the bit number.
126*7a6dacacSDimitry Andric /// \see __bsrd
1270b57cec5SDimitry Andric #define _bit_scan_reverse(A) __bsrd((A))
1280b57cec5SDimitry Andric 
1290b57cec5SDimitry Andric #ifdef __x86_64__
130297eecfbSDimitry Andric /// Find the first set bit starting from the lsb. Result is undefined if
131297eecfbSDimitry Andric ///    input is 0.
132297eecfbSDimitry Andric ///
133297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
134297eecfbSDimitry Andric ///
135297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSF instruction or the
136297eecfbSDimitry Andric ///    \c TZCNT instruction.
137297eecfbSDimitry Andric ///
138297eecfbSDimitry Andric /// \param __A
139297eecfbSDimitry Andric ///    A 64-bit integer operand.
140297eecfbSDimitry Andric /// \returns A 32-bit integer containing the bit number.
141e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
1420b57cec5SDimitry Andric __bsfq(long long __A) {
14381ad6265SDimitry Andric   return (long long)__builtin_ctzll((unsigned long long)__A);
1440b57cec5SDimitry Andric }
1450b57cec5SDimitry Andric 
146297eecfbSDimitry Andric /// Find the first set bit starting from the msb. Result is undefined if
147297eecfbSDimitry Andric ///    input is 0.
148297eecfbSDimitry Andric ///
149297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
150297eecfbSDimitry Andric ///
151297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSR instruction or the
152297eecfbSDimitry Andric ///    \c LZCNT instruction and an \c XOR.
153297eecfbSDimitry Andric ///
154297eecfbSDimitry Andric /// \param __A
155297eecfbSDimitry Andric ///    A 64-bit integer operand.
156297eecfbSDimitry Andric /// \returns A 32-bit integer containing the bit number.
157e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
1580b57cec5SDimitry Andric __bsrq(long long __A) {
15981ad6265SDimitry Andric   return 63 - __builtin_clzll((unsigned long long)__A);
1600b57cec5SDimitry Andric }
1610b57cec5SDimitry Andric 
162297eecfbSDimitry Andric /// Swaps the bytes in the input. Converting little endian to big endian or
163297eecfbSDimitry Andric ///    vice versa.
164297eecfbSDimitry Andric ///
165297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
166297eecfbSDimitry Andric ///
167297eecfbSDimitry Andric /// This intrinsic corresponds to the \c BSWAP instruction.
168297eecfbSDimitry Andric ///
169297eecfbSDimitry Andric /// \param __A
170297eecfbSDimitry Andric ///    A 64-bit integer operand.
171297eecfbSDimitry Andric /// \returns A 64-bit integer containing the swapped bytes.
172*7a6dacacSDimitry Andric /// \see _bswap64
173e8d8bef9SDimitry Andric static __inline__ long long __DEFAULT_FN_ATTRS_CONSTEXPR
1740b57cec5SDimitry Andric __bswapq(long long __A) {
17581ad6265SDimitry Andric   return (long long)__builtin_bswap64((unsigned long long)__A);
1760b57cec5SDimitry Andric }
1770b57cec5SDimitry Andric 
178*7a6dacacSDimitry Andric /// Swaps the bytes in the input. Converting little endian to big endian or
179*7a6dacacSDimitry Andric ///    vice versa.
180*7a6dacacSDimitry Andric ///
181*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
182*7a6dacacSDimitry Andric ///
183*7a6dacacSDimitry Andric /// \code
184*7a6dacacSDimitry Andric /// long long _bswap64(long long A);
185*7a6dacacSDimitry Andric /// \endcode
186*7a6dacacSDimitry Andric ///
187*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c BSWAP instruction.
188*7a6dacacSDimitry Andric ///
189*7a6dacacSDimitry Andric /// \param A
190*7a6dacacSDimitry Andric ///    A 64-bit integer operand.
191*7a6dacacSDimitry Andric /// \returns A 64-bit integer containing the swapped bytes.
192*7a6dacacSDimitry Andric /// \see __bswapq
1930b57cec5SDimitry Andric #define _bswap64(A) __bswapq((A))
194*7a6dacacSDimitry Andric #endif /* __x86_64__ */
1950b57cec5SDimitry Andric 
196297eecfbSDimitry Andric /// Counts the number of bits in the source operand having a value of 1.
197297eecfbSDimitry Andric ///
198297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
199297eecfbSDimitry Andric ///
200297eecfbSDimitry Andric /// This intrinsic corresponds to the \c POPCNT instruction or a
201297eecfbSDimitry Andric ///    a sequence of arithmetic and logic ops to calculate it.
202297eecfbSDimitry Andric ///
203297eecfbSDimitry Andric /// \param __A
204297eecfbSDimitry Andric ///    An unsigned 32-bit integer operand.
205297eecfbSDimitry Andric /// \returns A 32-bit integer containing the number of bits with value 1 in the
206297eecfbSDimitry Andric ///    source operand.
207*7a6dacacSDimitry Andric /// \see _popcnt32
208e8d8bef9SDimitry Andric static __inline__ int __DEFAULT_FN_ATTRS_CONSTEXPR
2090b57cec5SDimitry Andric __popcntd(unsigned int __A)
2100b57cec5SDimitry Andric {
2110b57cec5SDimitry Andric   return __builtin_popcount(__A);
2120b57cec5SDimitry Andric }
2130b57cec5SDimitry Andric 
214*7a6dacacSDimitry Andric /// Counts the number of bits in the source operand having a value of 1.
215*7a6dacacSDimitry Andric ///
216*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
217*7a6dacacSDimitry Andric ///
218*7a6dacacSDimitry Andric /// \code
219*7a6dacacSDimitry Andric /// int _popcnt32(int A);
220*7a6dacacSDimitry Andric /// \endcode
221*7a6dacacSDimitry Andric ///
222*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c POPCNT instruction or a
223*7a6dacacSDimitry Andric ///    a sequence of arithmetic and logic ops to calculate it.
224*7a6dacacSDimitry Andric ///
225*7a6dacacSDimitry Andric /// \param A
226*7a6dacacSDimitry Andric ///    An unsigned 32-bit integer operand.
227*7a6dacacSDimitry Andric /// \returns A 32-bit integer containing the number of bits with value 1 in the
228*7a6dacacSDimitry Andric ///    source operand.
229*7a6dacacSDimitry Andric /// \see __popcntd
2300b57cec5SDimitry Andric #define _popcnt32(A) __popcntd((A))
2310b57cec5SDimitry Andric 
2320b57cec5SDimitry Andric #ifdef __x86_64__
233297eecfbSDimitry Andric /// Counts the number of bits in the source operand having a value of 1.
234297eecfbSDimitry Andric ///
235297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
236297eecfbSDimitry Andric ///
237297eecfbSDimitry Andric /// This intrinsic corresponds to the \c POPCNT instruction or a
238297eecfbSDimitry Andric ///    a sequence of arithmetic and logic ops to calculate it.
239297eecfbSDimitry Andric ///
240297eecfbSDimitry Andric /// \param __A
241297eecfbSDimitry Andric ///    An unsigned 64-bit integer operand.
242297eecfbSDimitry Andric /// \returns A 64-bit integer containing the number of bits with value 1 in the
243297eecfbSDimitry Andric ///    source operand.
244*7a6dacacSDimitry Andric /// \see _popcnt64
245e8d8bef9SDimitry Andric static __inline__ long long __DEFAULT_FN_ATTRS_CONSTEXPR
2460b57cec5SDimitry Andric __popcntq(unsigned long long __A)
2470b57cec5SDimitry Andric {
2480b57cec5SDimitry Andric   return __builtin_popcountll(__A);
2490b57cec5SDimitry Andric }
2500b57cec5SDimitry Andric 
251*7a6dacacSDimitry Andric /// Counts the number of bits in the source operand having a value of 1.
252*7a6dacacSDimitry Andric ///
253*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
254*7a6dacacSDimitry Andric ///
255*7a6dacacSDimitry Andric /// \code
256*7a6dacacSDimitry Andric /// long long _popcnt64(unsigned long long A);
257*7a6dacacSDimitry Andric /// \endcode
258*7a6dacacSDimitry Andric ///
259*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c POPCNT instruction or a
260*7a6dacacSDimitry Andric ///    a sequence of arithmetic and logic ops to calculate it.
261*7a6dacacSDimitry Andric ///
262*7a6dacacSDimitry Andric /// \param A
263*7a6dacacSDimitry Andric ///    An unsigned 64-bit integer operand.
264*7a6dacacSDimitry Andric /// \returns A 64-bit integer containing the number of bits with value 1 in the
265*7a6dacacSDimitry Andric ///    source operand.
266*7a6dacacSDimitry Andric /// \see __popcntq
2670b57cec5SDimitry Andric #define _popcnt64(A) __popcntq((A))
2680b57cec5SDimitry Andric #endif /* __x86_64__ */
2690b57cec5SDimitry Andric 
2700b57cec5SDimitry Andric #ifdef __x86_64__
271*7a6dacacSDimitry Andric /// Returns the program status and control \c RFLAGS register with the \c VM
272*7a6dacacSDimitry Andric ///    and \c RF flags cleared.
273*7a6dacacSDimitry Andric ///
274*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
275*7a6dacacSDimitry Andric ///
276*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c PUSHFQ + \c POP instruction sequence.
277*7a6dacacSDimitry Andric ///
278*7a6dacacSDimitry Andric /// \returns The 64-bit value of the RFLAGS register.
279e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS
2800b57cec5SDimitry Andric __readeflags(void)
2810b57cec5SDimitry Andric {
2820b57cec5SDimitry Andric   return __builtin_ia32_readeflags_u64();
2830b57cec5SDimitry Andric }
2840b57cec5SDimitry Andric 
285*7a6dacacSDimitry Andric /// Writes the specified value to the program status and control \c RFLAGS
286*7a6dacacSDimitry Andric ///    register. Reserved bits are not affected.
287*7a6dacacSDimitry Andric ///
288*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
289*7a6dacacSDimitry Andric ///
290*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c PUSH + \c POPFQ instruction sequence.
291*7a6dacacSDimitry Andric ///
292*7a6dacacSDimitry Andric /// \param __f
293*7a6dacacSDimitry Andric ///    The 64-bit value to write to \c RFLAGS.
294e8d8bef9SDimitry Andric static __inline__ void __DEFAULT_FN_ATTRS
2950b57cec5SDimitry Andric __writeeflags(unsigned long long __f)
2960b57cec5SDimitry Andric {
2970b57cec5SDimitry Andric   __builtin_ia32_writeeflags_u64(__f);
2980b57cec5SDimitry Andric }
2990b57cec5SDimitry Andric 
3000b57cec5SDimitry Andric #else /* !__x86_64__ */
301*7a6dacacSDimitry Andric /// Returns the program status and control \c EFLAGS register with the \c VM
302*7a6dacacSDimitry Andric ///    and \c RF flags cleared.
303*7a6dacacSDimitry Andric ///
304*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
305*7a6dacacSDimitry Andric ///
306*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c PUSHFD + \c POP instruction sequence.
307*7a6dacacSDimitry Andric ///
308*7a6dacacSDimitry Andric /// \returns The 32-bit value of the EFLAGS register.
309e8d8bef9SDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS
3100b57cec5SDimitry Andric __readeflags(void)
3110b57cec5SDimitry Andric {
3120b57cec5SDimitry Andric   return __builtin_ia32_readeflags_u32();
3130b57cec5SDimitry Andric }
3140b57cec5SDimitry Andric 
315*7a6dacacSDimitry Andric /// Writes the specified value to the program status and control \c EFLAGS
316*7a6dacacSDimitry Andric ///    register. Reserved bits are not affected.
317*7a6dacacSDimitry Andric ///
318*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
319*7a6dacacSDimitry Andric ///
320*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c PUSH + \c POPFD instruction sequence.
321*7a6dacacSDimitry Andric ///
322*7a6dacacSDimitry Andric /// \param __f
323*7a6dacacSDimitry Andric ///    The 32-bit value to write to \c EFLAGS.
324e8d8bef9SDimitry Andric static __inline__ void __DEFAULT_FN_ATTRS
3250b57cec5SDimitry Andric __writeeflags(unsigned int __f)
3260b57cec5SDimitry Andric {
3270b57cec5SDimitry Andric   __builtin_ia32_writeeflags_u32(__f);
3280b57cec5SDimitry Andric }
3290b57cec5SDimitry Andric #endif /* !__x86_64__ */
3300b57cec5SDimitry Andric 
331297eecfbSDimitry Andric /// Cast a 32-bit float value to a 32-bit unsigned integer value.
332297eecfbSDimitry Andric ///
333297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
334297eecfbSDimitry Andric ///
335297eecfbSDimitry Andric /// This intrinsic corresponds to the \c VMOVD / \c MOVD instruction in x86_64,
336297eecfbSDimitry Andric ///    and corresponds to the \c VMOVL / \c MOVL instruction in ia32.
337297eecfbSDimitry Andric ///
338297eecfbSDimitry Andric /// \param __A
339297eecfbSDimitry Andric ///    A 32-bit float value.
340297eecfbSDimitry Andric /// \returns a 32-bit unsigned integer containing the converted value.
341e8d8bef9SDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CAST
342a7dea167SDimitry Andric _castf32_u32(float __A) {
343e8d8bef9SDimitry Andric   return __builtin_bit_cast(unsigned int, __A);
344a7dea167SDimitry Andric }
345a7dea167SDimitry Andric 
346297eecfbSDimitry Andric /// Cast a 64-bit float value to a 64-bit unsigned integer value.
347297eecfbSDimitry Andric ///
348297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
349297eecfbSDimitry Andric ///
350297eecfbSDimitry Andric /// This intrinsic corresponds to the \c VMOVQ / \c MOVQ instruction in x86_64,
351297eecfbSDimitry Andric ///    and corresponds to the \c VMOVL / \c MOVL instruction in ia32.
352297eecfbSDimitry Andric ///
353297eecfbSDimitry Andric /// \param __A
354297eecfbSDimitry Andric ///    A 64-bit float value.
355297eecfbSDimitry Andric /// \returns a 64-bit unsigned integer containing the converted value.
356e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS_CAST
357a7dea167SDimitry Andric _castf64_u64(double __A) {
358e8d8bef9SDimitry Andric   return __builtin_bit_cast(unsigned long long, __A);
359a7dea167SDimitry Andric }
360a7dea167SDimitry Andric 
361297eecfbSDimitry Andric /// Cast a 32-bit unsigned integer value to a 32-bit float value.
362297eecfbSDimitry Andric ///
363297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
364297eecfbSDimitry Andric ///
365297eecfbSDimitry Andric /// This intrinsic corresponds to the \c VMOVQ / \c MOVQ instruction in x86_64,
366297eecfbSDimitry Andric ///    and corresponds to the \c FLDS instruction in ia32.
367297eecfbSDimitry Andric ///
368297eecfbSDimitry Andric /// \param __A
369297eecfbSDimitry Andric ///    A 32-bit unsigned integer value.
370297eecfbSDimitry Andric /// \returns a 32-bit float value containing the converted value.
371e8d8bef9SDimitry Andric static __inline__ float __DEFAULT_FN_ATTRS_CAST
372a7dea167SDimitry Andric _castu32_f32(unsigned int __A) {
373e8d8bef9SDimitry Andric   return __builtin_bit_cast(float, __A);
374a7dea167SDimitry Andric }
375a7dea167SDimitry Andric 
376297eecfbSDimitry Andric /// Cast a 64-bit unsigned integer value to a 64-bit float value.
377297eecfbSDimitry Andric ///
378297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
379297eecfbSDimitry Andric ///
380297eecfbSDimitry Andric /// This intrinsic corresponds to the \c VMOVQ / \c MOVQ instruction in x86_64,
381297eecfbSDimitry Andric ///    and corresponds to the \c FLDL instruction in ia32.
382297eecfbSDimitry Andric ///
383297eecfbSDimitry Andric /// \param __A
384297eecfbSDimitry Andric ///    A 64-bit unsigned integer value.
385297eecfbSDimitry Andric /// \returns a 64-bit float value containing the converted value.
386e8d8bef9SDimitry Andric static __inline__ double __DEFAULT_FN_ATTRS_CAST
387a7dea167SDimitry Andric _castu64_f64(unsigned long long __A) {
388e8d8bef9SDimitry Andric   return __builtin_bit_cast(double, __A);
389a7dea167SDimitry Andric }
390a7dea167SDimitry Andric 
391297eecfbSDimitry Andric /// Adds the unsigned integer operand to the CRC-32C checksum of the
392297eecfbSDimitry Andric ///     unsigned char operand.
393297eecfbSDimitry Andric ///
394297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
395297eecfbSDimitry Andric ///
396297eecfbSDimitry Andric /// This intrinsic corresponds to the \c CRC32B instruction.
397297eecfbSDimitry Andric ///
398297eecfbSDimitry Andric /// \param __C
399297eecfbSDimitry Andric ///    An unsigned integer operand to add to the CRC-32C checksum of operand
400297eecfbSDimitry Andric ///    \a  __D.
401297eecfbSDimitry Andric /// \param __D
402297eecfbSDimitry Andric ///    An unsigned 8-bit integer operand used to compute the CRC-32C checksum.
403297eecfbSDimitry Andric /// \returns The result of adding operand \a __C to the CRC-32C checksum of
404297eecfbSDimitry Andric ///    operand \a __D.
405349cc55cSDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CRC32
4060b57cec5SDimitry Andric __crc32b(unsigned int __C, unsigned char __D)
4070b57cec5SDimitry Andric {
4080b57cec5SDimitry Andric   return __builtin_ia32_crc32qi(__C, __D);
4090b57cec5SDimitry Andric }
4100b57cec5SDimitry Andric 
411297eecfbSDimitry Andric /// Adds the unsigned integer operand to the CRC-32C checksum of the
412297eecfbSDimitry Andric ///    unsigned short operand.
413297eecfbSDimitry Andric ///
414297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
415297eecfbSDimitry Andric ///
416297eecfbSDimitry Andric /// This intrinsic corresponds to the \c CRC32W instruction.
417297eecfbSDimitry Andric ///
418297eecfbSDimitry Andric /// \param __C
419297eecfbSDimitry Andric ///    An unsigned integer operand to add to the CRC-32C checksum of operand
420297eecfbSDimitry Andric ///    \a  __D.
421297eecfbSDimitry Andric /// \param __D
422297eecfbSDimitry Andric ///    An unsigned 16-bit integer operand used to compute the CRC-32C checksum.
423297eecfbSDimitry Andric /// \returns The result of adding operand \a __C to the CRC-32C checksum of
424297eecfbSDimitry Andric ///    operand \a __D.
425349cc55cSDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CRC32
4260b57cec5SDimitry Andric __crc32w(unsigned int __C, unsigned short __D)
4270b57cec5SDimitry Andric {
4280b57cec5SDimitry Andric   return __builtin_ia32_crc32hi(__C, __D);
4290b57cec5SDimitry Andric }
4300b57cec5SDimitry Andric 
431297eecfbSDimitry Andric /// Adds the unsigned integer operand to the CRC-32C checksum of the
432297eecfbSDimitry Andric ///    second unsigned integer operand.
433297eecfbSDimitry Andric ///
434297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
435297eecfbSDimitry Andric ///
436297eecfbSDimitry Andric /// This intrinsic corresponds to the \c CRC32D instruction.
437297eecfbSDimitry Andric ///
438297eecfbSDimitry Andric /// \param __C
439297eecfbSDimitry Andric ///    An unsigned integer operand to add to the CRC-32C checksum of operand
440297eecfbSDimitry Andric ///    \a  __D.
441297eecfbSDimitry Andric /// \param __D
442297eecfbSDimitry Andric ///    An unsigned 32-bit integer operand used to compute the CRC-32C checksum.
443297eecfbSDimitry Andric /// \returns The result of adding operand \a __C to the CRC-32C checksum of
444297eecfbSDimitry Andric ///    operand \a __D.
445349cc55cSDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CRC32
4460b57cec5SDimitry Andric __crc32d(unsigned int __C, unsigned int __D)
4470b57cec5SDimitry Andric {
4480b57cec5SDimitry Andric   return __builtin_ia32_crc32si(__C, __D);
4490b57cec5SDimitry Andric }
4500b57cec5SDimitry Andric 
4510b57cec5SDimitry Andric #ifdef __x86_64__
452297eecfbSDimitry Andric /// Adds the unsigned integer operand to the CRC-32C checksum of the
453297eecfbSDimitry Andric ///    unsigned 64-bit integer operand.
454297eecfbSDimitry Andric ///
455297eecfbSDimitry Andric /// \headerfile <x86intrin.h>
456297eecfbSDimitry Andric ///
457297eecfbSDimitry Andric /// This intrinsic corresponds to the \c CRC32Q instruction.
458297eecfbSDimitry Andric ///
459297eecfbSDimitry Andric /// \param __C
460297eecfbSDimitry Andric ///    An unsigned integer operand to add to the CRC-32C checksum of operand
461297eecfbSDimitry Andric ///    \a  __D.
462297eecfbSDimitry Andric /// \param __D
463297eecfbSDimitry Andric ///    An unsigned 64-bit integer operand used to compute the CRC-32C checksum.
464297eecfbSDimitry Andric /// \returns The result of adding operand \a __C to the CRC-32C checksum of
465297eecfbSDimitry Andric ///    operand \a __D.
466349cc55cSDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS_CRC32
4670b57cec5SDimitry Andric __crc32q(unsigned long long __C, unsigned long long __D)
4680b57cec5SDimitry Andric {
4690b57cec5SDimitry Andric   return __builtin_ia32_crc32di(__C, __D);
4700b57cec5SDimitry Andric }
4710b57cec5SDimitry Andric #endif /* __x86_64__ */
4720b57cec5SDimitry Andric 
473*7a6dacacSDimitry Andric /// Reads the specified performance monitoring counter. Refer to your
474*7a6dacacSDimitry Andric ///    processor's documentation to determine which performance counters are
475*7a6dacacSDimitry Andric ///    supported.
476*7a6dacacSDimitry Andric ///
477*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
478*7a6dacacSDimitry Andric ///
479*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c RDPMC instruction.
480*7a6dacacSDimitry Andric ///
481*7a6dacacSDimitry Andric /// \param __A
482*7a6dacacSDimitry Andric ///    The performance counter to read.
483*7a6dacacSDimitry Andric /// \returns The 64-bit value read from the performance counter.
484*7a6dacacSDimitry Andric /// \see _rdpmc
485e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS
4860b57cec5SDimitry Andric __rdpmc(int __A) {
4870b57cec5SDimitry Andric   return __builtin_ia32_rdpmc(__A);
4880b57cec5SDimitry Andric }
4890b57cec5SDimitry Andric 
490*7a6dacacSDimitry Andric /// Reads the processor's time stamp counter and the \c IA32_TSC_AUX MSR
491*7a6dacacSDimitry Andric ///    \c (0xc0000103).
492*7a6dacacSDimitry Andric ///
493*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
494*7a6dacacSDimitry Andric ///
495*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c RDTSCP instruction.
496*7a6dacacSDimitry Andric ///
497*7a6dacacSDimitry Andric /// \param __A
498*7a6dacacSDimitry Andric ///    Address of where to store the 32-bit \c IA32_TSC_AUX value.
499*7a6dacacSDimitry Andric /// \returns The 64-bit value of the time stamp counter.
500e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS
5010b57cec5SDimitry Andric __rdtscp(unsigned int *__A) {
5020b57cec5SDimitry Andric   return __builtin_ia32_rdtscp(__A);
5030b57cec5SDimitry Andric }
5040b57cec5SDimitry Andric 
505*7a6dacacSDimitry Andric /// Reads the processor's time stamp counter.
506*7a6dacacSDimitry Andric ///
507*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
508*7a6dacacSDimitry Andric ///
509*7a6dacacSDimitry Andric /// \code
510*7a6dacacSDimitry Andric /// unsigned long long _rdtsc();
511*7a6dacacSDimitry Andric /// \endcode
512*7a6dacacSDimitry Andric ///
513*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c RDTSC instruction.
514*7a6dacacSDimitry Andric ///
515*7a6dacacSDimitry Andric /// \returns The 64-bit value of the time stamp counter.
5160b57cec5SDimitry Andric #define _rdtsc() __rdtsc()
5170b57cec5SDimitry Andric 
518*7a6dacacSDimitry Andric /// Reads the specified performance monitoring counter. Refer to your
519*7a6dacacSDimitry Andric ///    processor's documentation to determine which performance counters are
520*7a6dacacSDimitry Andric ///    supported.
521*7a6dacacSDimitry Andric ///
522*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
523*7a6dacacSDimitry Andric ///
524*7a6dacacSDimitry Andric /// \code
525*7a6dacacSDimitry Andric /// unsigned long long _rdpmc(int A);
526*7a6dacacSDimitry Andric /// \endcode
527*7a6dacacSDimitry Andric ///
528*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c RDPMC instruction.
529*7a6dacacSDimitry Andric ///
530*7a6dacacSDimitry Andric /// \param A
531*7a6dacacSDimitry Andric ///    The performance counter to read.
532*7a6dacacSDimitry Andric /// \returns The 64-bit value read from the performance counter.
533*7a6dacacSDimitry Andric /// \see __rdpmc
5340b57cec5SDimitry Andric #define _rdpmc(A) __rdpmc(A)
5350b57cec5SDimitry Andric 
536e8d8bef9SDimitry Andric static __inline__ void __DEFAULT_FN_ATTRS
5370b57cec5SDimitry Andric _wbinvd(void) {
5380b57cec5SDimitry Andric   __builtin_ia32_wbinvd();
5390b57cec5SDimitry Andric }
5400b57cec5SDimitry Andric 
541*7a6dacacSDimitry Andric /// Rotates an 8-bit value to the left by the specified number of bits.
542*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
543*7a6dacacSDimitry Andric ///    the value.
544*7a6dacacSDimitry Andric ///
545*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
546*7a6dacacSDimitry Andric ///
547*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
548*7a6dacacSDimitry Andric ///
549*7a6dacacSDimitry Andric /// \param __X
550*7a6dacacSDimitry Andric ///    The unsigned 8-bit value to be rotated.
551*7a6dacacSDimitry Andric /// \param __C
552*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
553*7a6dacacSDimitry Andric /// \returns The rotated value.
554e8d8bef9SDimitry Andric static __inline__ unsigned char __DEFAULT_FN_ATTRS_CONSTEXPR
5550b57cec5SDimitry Andric __rolb(unsigned char __X, int __C) {
5560b57cec5SDimitry Andric   return __builtin_rotateleft8(__X, __C);
5570b57cec5SDimitry Andric }
5580b57cec5SDimitry Andric 
559*7a6dacacSDimitry Andric /// Rotates an 8-bit value to the right by the specified number of bits.
560*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
561*7a6dacacSDimitry Andric ///    the value.
562*7a6dacacSDimitry Andric ///
563*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
564*7a6dacacSDimitry Andric ///
565*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
566*7a6dacacSDimitry Andric ///
567*7a6dacacSDimitry Andric /// \param __X
568*7a6dacacSDimitry Andric ///    The unsigned 8-bit value to be rotated.
569*7a6dacacSDimitry Andric /// \param __C
570*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
571*7a6dacacSDimitry Andric /// \returns The rotated value.
572e8d8bef9SDimitry Andric static __inline__ unsigned char __DEFAULT_FN_ATTRS_CONSTEXPR
5730b57cec5SDimitry Andric __rorb(unsigned char __X, int __C) {
5740b57cec5SDimitry Andric   return __builtin_rotateright8(__X, __C);
5750b57cec5SDimitry Andric }
5760b57cec5SDimitry Andric 
577*7a6dacacSDimitry Andric /// Rotates a 16-bit value to the left by the specified number of bits.
578*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
579*7a6dacacSDimitry Andric ///    the value.
580*7a6dacacSDimitry Andric ///
581*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
582*7a6dacacSDimitry Andric ///
583*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
584*7a6dacacSDimitry Andric ///
585*7a6dacacSDimitry Andric /// \param __X
586*7a6dacacSDimitry Andric ///    The unsigned 16-bit value to be rotated.
587*7a6dacacSDimitry Andric /// \param __C
588*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
589*7a6dacacSDimitry Andric /// \returns The rotated value.
590*7a6dacacSDimitry Andric /// \see _rotwl
591e8d8bef9SDimitry Andric static __inline__ unsigned short __DEFAULT_FN_ATTRS_CONSTEXPR
5920b57cec5SDimitry Andric __rolw(unsigned short __X, int __C) {
5930b57cec5SDimitry Andric   return __builtin_rotateleft16(__X, __C);
5940b57cec5SDimitry Andric }
5950b57cec5SDimitry Andric 
596*7a6dacacSDimitry Andric /// Rotates a 16-bit value to the right by the specified number of bits.
597*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
598*7a6dacacSDimitry Andric ///    the value.
599*7a6dacacSDimitry Andric ///
600*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
601*7a6dacacSDimitry Andric ///
602*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
603*7a6dacacSDimitry Andric ///
604*7a6dacacSDimitry Andric /// \param __X
605*7a6dacacSDimitry Andric ///    The unsigned 16-bit value to be rotated.
606*7a6dacacSDimitry Andric /// \param __C
607*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
608*7a6dacacSDimitry Andric /// \returns The rotated value.
609*7a6dacacSDimitry Andric /// \see _rotwr
610e8d8bef9SDimitry Andric static __inline__ unsigned short __DEFAULT_FN_ATTRS_CONSTEXPR
6110b57cec5SDimitry Andric __rorw(unsigned short __X, int __C) {
6120b57cec5SDimitry Andric   return __builtin_rotateright16(__X, __C);
6130b57cec5SDimitry Andric }
6140b57cec5SDimitry Andric 
615*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the left by the specified number of bits.
616*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
617*7a6dacacSDimitry Andric ///    the value.
618*7a6dacacSDimitry Andric ///
619*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
620*7a6dacacSDimitry Andric ///
621*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
622*7a6dacacSDimitry Andric ///
623*7a6dacacSDimitry Andric /// \param __X
624*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
625*7a6dacacSDimitry Andric /// \param __C
626*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
627*7a6dacacSDimitry Andric /// \returns The rotated value.
628*7a6dacacSDimitry Andric /// \see _rotl
629e8d8bef9SDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CONSTEXPR
6300b57cec5SDimitry Andric __rold(unsigned int __X, int __C) {
63181ad6265SDimitry Andric   return __builtin_rotateleft32(__X, (unsigned int)__C);
6320b57cec5SDimitry Andric }
6330b57cec5SDimitry Andric 
634*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the right by the specified number of bits.
635*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
636*7a6dacacSDimitry Andric ///    the value.
637*7a6dacacSDimitry Andric ///
638*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
639*7a6dacacSDimitry Andric ///
640*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
641*7a6dacacSDimitry Andric ///
642*7a6dacacSDimitry Andric /// \param __X
643*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
644*7a6dacacSDimitry Andric /// \param __C
645*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
646*7a6dacacSDimitry Andric /// \returns The rotated value.
647*7a6dacacSDimitry Andric /// \see _rotr
648e8d8bef9SDimitry Andric static __inline__ unsigned int __DEFAULT_FN_ATTRS_CONSTEXPR
6490b57cec5SDimitry Andric __rord(unsigned int __X, int __C) {
65081ad6265SDimitry Andric   return __builtin_rotateright32(__X, (unsigned int)__C);
6510b57cec5SDimitry Andric }
6520b57cec5SDimitry Andric 
6530b57cec5SDimitry Andric #ifdef __x86_64__
654*7a6dacacSDimitry Andric /// Rotates a 64-bit value to the left by the specified number of bits.
655*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
656*7a6dacacSDimitry Andric ///    the value.
657*7a6dacacSDimitry Andric ///
658*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
659*7a6dacacSDimitry Andric ///
660*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
661*7a6dacacSDimitry Andric ///
662*7a6dacacSDimitry Andric /// \param __X
663*7a6dacacSDimitry Andric ///    The unsigned 64-bit value to be rotated.
664*7a6dacacSDimitry Andric /// \param __C
665*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
666*7a6dacacSDimitry Andric /// \returns The rotated value.
667e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS_CONSTEXPR
6680b57cec5SDimitry Andric __rolq(unsigned long long __X, int __C) {
66981ad6265SDimitry Andric   return __builtin_rotateleft64(__X, (unsigned long long)__C);
6700b57cec5SDimitry Andric }
6710b57cec5SDimitry Andric 
672*7a6dacacSDimitry Andric /// Rotates a 64-bit value to the right by the specified number of bits.
673*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
674*7a6dacacSDimitry Andric ///    the value.
675*7a6dacacSDimitry Andric ///
676*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
677*7a6dacacSDimitry Andric ///
678*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
679*7a6dacacSDimitry Andric ///
680*7a6dacacSDimitry Andric /// \param __X
681*7a6dacacSDimitry Andric ///    The unsigned 64-bit value to be rotated.
682*7a6dacacSDimitry Andric /// \param __C
683*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
684*7a6dacacSDimitry Andric /// \returns The rotated value.
685e8d8bef9SDimitry Andric static __inline__ unsigned long long __DEFAULT_FN_ATTRS_CONSTEXPR
6860b57cec5SDimitry Andric __rorq(unsigned long long __X, int __C) {
68781ad6265SDimitry Andric   return __builtin_rotateright64(__X, (unsigned long long)__C);
6880b57cec5SDimitry Andric }
6890b57cec5SDimitry Andric #endif /* __x86_64__ */
6900b57cec5SDimitry Andric 
6910b57cec5SDimitry Andric #ifndef _MSC_VER
6920b57cec5SDimitry Andric /* These are already provided as builtins for MSVC. */
6930b57cec5SDimitry Andric /* Select the correct function based on the size of long. */
6940b57cec5SDimitry Andric #ifdef __LP64__
695*7a6dacacSDimitry Andric /// Rotates a 64-bit value to the left by the specified number of bits.
696*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
697*7a6dacacSDimitry Andric ///    the value.
698*7a6dacacSDimitry Andric ///
699*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
700*7a6dacacSDimitry Andric ///
701*7a6dacacSDimitry Andric /// \code
702*7a6dacacSDimitry Andric /// unsigned long long _lrotl(unsigned long long a, int b);
703*7a6dacacSDimitry Andric /// \endcode
704*7a6dacacSDimitry Andric ///
705*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
706*7a6dacacSDimitry Andric ///
707*7a6dacacSDimitry Andric /// \param a
708*7a6dacacSDimitry Andric ///    The unsigned 64-bit value to be rotated.
709*7a6dacacSDimitry Andric /// \param b
710*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
711*7a6dacacSDimitry Andric /// \returns The rotated value.
712*7a6dacacSDimitry Andric /// \see __rolq
7130b57cec5SDimitry Andric #define _lrotl(a,b) __rolq((a), (b))
714*7a6dacacSDimitry Andric 
715*7a6dacacSDimitry Andric /// Rotates a 64-bit value to the right by the specified number of bits.
716*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
717*7a6dacacSDimitry Andric ///    the value.
718*7a6dacacSDimitry Andric ///
719*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
720*7a6dacacSDimitry Andric ///
721*7a6dacacSDimitry Andric /// \code
722*7a6dacacSDimitry Andric /// unsigned long long _lrotr(unsigned long long a, int b);
723*7a6dacacSDimitry Andric /// \endcode
724*7a6dacacSDimitry Andric ///
725*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
726*7a6dacacSDimitry Andric ///
727*7a6dacacSDimitry Andric /// \param a
728*7a6dacacSDimitry Andric ///    The unsigned 64-bit value to be rotated.
729*7a6dacacSDimitry Andric /// \param b
730*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
731*7a6dacacSDimitry Andric /// \returns The rotated value.
732*7a6dacacSDimitry Andric /// \see __rorq
7330b57cec5SDimitry Andric #define _lrotr(a,b) __rorq((a), (b))
734*7a6dacacSDimitry Andric #else // __LP64__
735*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the left by the specified number of bits.
736*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
737*7a6dacacSDimitry Andric ///    the value.
738*7a6dacacSDimitry Andric ///
739*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
740*7a6dacacSDimitry Andric ///
741*7a6dacacSDimitry Andric /// \code
742*7a6dacacSDimitry Andric /// unsigned int _lrotl(unsigned int a, int b);
743*7a6dacacSDimitry Andric /// \endcode
744*7a6dacacSDimitry Andric ///
745*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
746*7a6dacacSDimitry Andric ///
747*7a6dacacSDimitry Andric /// \param a
748*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
749*7a6dacacSDimitry Andric /// \param b
750*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
751*7a6dacacSDimitry Andric /// \returns The rotated value.
752*7a6dacacSDimitry Andric /// \see __rold
7530b57cec5SDimitry Andric #define _lrotl(a,b) __rold((a), (b))
754*7a6dacacSDimitry Andric 
755*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the right by the specified number of bits.
756*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
757*7a6dacacSDimitry Andric ///    the value.
758*7a6dacacSDimitry Andric ///
759*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
760*7a6dacacSDimitry Andric ///
761*7a6dacacSDimitry Andric /// \code
762*7a6dacacSDimitry Andric /// unsigned int _lrotr(unsigned int a, int b);
763*7a6dacacSDimitry Andric /// \endcode
764*7a6dacacSDimitry Andric ///
765*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
766*7a6dacacSDimitry Andric ///
767*7a6dacacSDimitry Andric /// \param a
768*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
769*7a6dacacSDimitry Andric /// \param b
770*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
771*7a6dacacSDimitry Andric /// \returns The rotated value.
772*7a6dacacSDimitry Andric /// \see __rord
7730b57cec5SDimitry Andric #define _lrotr(a,b) __rord((a), (b))
774*7a6dacacSDimitry Andric #endif // __LP64__
775*7a6dacacSDimitry Andric 
776*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the left by the specified number of bits.
777*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
778*7a6dacacSDimitry Andric ///    the value.
779*7a6dacacSDimitry Andric ///
780*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
781*7a6dacacSDimitry Andric ///
782*7a6dacacSDimitry Andric /// \code
783*7a6dacacSDimitry Andric /// unsigned int _rotl(unsigned int a, int b);
784*7a6dacacSDimitry Andric /// \endcode
785*7a6dacacSDimitry Andric ///
786*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
787*7a6dacacSDimitry Andric ///
788*7a6dacacSDimitry Andric /// \param a
789*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
790*7a6dacacSDimitry Andric /// \param b
791*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
792*7a6dacacSDimitry Andric /// \returns The rotated value.
793*7a6dacacSDimitry Andric /// \see __rold
7940b57cec5SDimitry Andric #define _rotl(a,b) __rold((a), (b))
795*7a6dacacSDimitry Andric 
796*7a6dacacSDimitry Andric /// Rotates a 32-bit value to the right by the specified number of bits.
797*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
798*7a6dacacSDimitry Andric ///    the value.
799*7a6dacacSDimitry Andric ///
800*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
801*7a6dacacSDimitry Andric ///
802*7a6dacacSDimitry Andric /// \code
803*7a6dacacSDimitry Andric /// unsigned int _rotr(unsigned int a, int b);
804*7a6dacacSDimitry Andric /// \endcode
805*7a6dacacSDimitry Andric ///
806*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
807*7a6dacacSDimitry Andric ///
808*7a6dacacSDimitry Andric /// \param a
809*7a6dacacSDimitry Andric ///    The unsigned 32-bit value to be rotated.
810*7a6dacacSDimitry Andric /// \param b
811*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
812*7a6dacacSDimitry Andric /// \returns The rotated value.
813*7a6dacacSDimitry Andric /// \see __rord
8140b57cec5SDimitry Andric #define _rotr(a,b) __rord((a), (b))
8150b57cec5SDimitry Andric #endif // _MSC_VER
8160b57cec5SDimitry Andric 
8170b57cec5SDimitry Andric /* These are not builtins so need to be provided in all modes. */
818*7a6dacacSDimitry Andric /// Rotates a 16-bit value to the left by the specified number of bits.
819*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
820*7a6dacacSDimitry Andric ///    the value.
821*7a6dacacSDimitry Andric ///
822*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
823*7a6dacacSDimitry Andric ///
824*7a6dacacSDimitry Andric /// \code
825*7a6dacacSDimitry Andric /// unsigned short _rotwl(unsigned short a, int b);
826*7a6dacacSDimitry Andric /// \endcode
827*7a6dacacSDimitry Andric ///
828*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROL instruction.
829*7a6dacacSDimitry Andric ///
830*7a6dacacSDimitry Andric /// \param a
831*7a6dacacSDimitry Andric ///    The unsigned 16-bit value to be rotated.
832*7a6dacacSDimitry Andric /// \param b
833*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
834*7a6dacacSDimitry Andric /// \returns The rotated value.
835*7a6dacacSDimitry Andric /// \see __rolw
8360b57cec5SDimitry Andric #define _rotwl(a,b) __rolw((a), (b))
837*7a6dacacSDimitry Andric 
838*7a6dacacSDimitry Andric /// Rotates a 16-bit value to the right by the specified number of bits.
839*7a6dacacSDimitry Andric ///    This operation is undefined if the number of bits exceeds the size of
840*7a6dacacSDimitry Andric ///    the value.
841*7a6dacacSDimitry Andric ///
842*7a6dacacSDimitry Andric /// \headerfile <x86intrin.h>
843*7a6dacacSDimitry Andric ///
844*7a6dacacSDimitry Andric /// \code
845*7a6dacacSDimitry Andric /// unsigned short _rotwr(unsigned short a, int b);
846*7a6dacacSDimitry Andric /// \endcode
847*7a6dacacSDimitry Andric ///
848*7a6dacacSDimitry Andric /// This intrinsic corresponds to the \c ROR instruction.
849*7a6dacacSDimitry Andric ///
850*7a6dacacSDimitry Andric /// \param a
851*7a6dacacSDimitry Andric ///    The unsigned 16-bit value to be rotated.
852*7a6dacacSDimitry Andric /// \param b
853*7a6dacacSDimitry Andric ///    The number of bits to rotate the value.
854*7a6dacacSDimitry Andric /// \returns The rotated value.
855*7a6dacacSDimitry Andric /// \see __rorw
8560b57cec5SDimitry Andric #define _rotwr(a,b) __rorw((a), (b))
8570b57cec5SDimitry Andric 
858e8d8bef9SDimitry Andric #undef __DEFAULT_FN_ATTRS
859e8d8bef9SDimitry Andric #undef __DEFAULT_FN_ATTRS_CAST
860349cc55cSDimitry Andric #undef __DEFAULT_FN_ATTRS_CRC32
861e8d8bef9SDimitry Andric #undef __DEFAULT_FN_ATTRS_CONSTEXPR
862e8d8bef9SDimitry Andric 
8630b57cec5SDimitry Andric #endif /* __IA32INTRIN_H */
864