zig

fork of https://codeberg.org/ziglang/zig
Log | Files | Refs | README | LICENSE

swab.h (6939B) - Raw


      1 /* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
      2 #ifndef _LINUX_SWAB_H
      3 #define _LINUX_SWAB_H
      4 
      5 #include <linux/types.h>
      6 #include <linux/stddef.h>
      7 #include <asm/bitsperlong.h>
      8 #include <asm/swab.h>
      9 
     10 /*
     11  * casts are necessary for constants, because we never know how for sure
     12  * how U/UL/ULL map to __u16, __u32, __u64. At least not in a portable way.
     13  */
     14 #define ___constant_swab16(x) ((__u16)(				\
     15 	(((__u16)(x) & (__u16)0x00ffU) << 8) |			\
     16 	(((__u16)(x) & (__u16)0xff00U) >> 8)))
     17 
     18 #define ___constant_swab32(x) ((__u32)(				\
     19 	(((__u32)(x) & (__u32)0x000000ffUL) << 24) |		\
     20 	(((__u32)(x) & (__u32)0x0000ff00UL) <<  8) |		\
     21 	(((__u32)(x) & (__u32)0x00ff0000UL) >>  8) |		\
     22 	(((__u32)(x) & (__u32)0xff000000UL) >> 24)))
     23 
     24 #define ___constant_swab64(x) ((__u64)(				\
     25 	(((__u64)(x) & (__u64)0x00000000000000ffULL) << 56) |	\
     26 	(((__u64)(x) & (__u64)0x000000000000ff00ULL) << 40) |	\
     27 	(((__u64)(x) & (__u64)0x0000000000ff0000ULL) << 24) |	\
     28 	(((__u64)(x) & (__u64)0x00000000ff000000ULL) <<  8) |	\
     29 	(((__u64)(x) & (__u64)0x000000ff00000000ULL) >>  8) |	\
     30 	(((__u64)(x) & (__u64)0x0000ff0000000000ULL) >> 24) |	\
     31 	(((__u64)(x) & (__u64)0x00ff000000000000ULL) >> 40) |	\
     32 	(((__u64)(x) & (__u64)0xff00000000000000ULL) >> 56)))
     33 
     34 #define ___constant_swahw32(x) ((__u32)(			\
     35 	(((__u32)(x) & (__u32)0x0000ffffUL) << 16) |		\
     36 	(((__u32)(x) & (__u32)0xffff0000UL) >> 16)))
     37 
     38 #define ___constant_swahb32(x) ((__u32)(			\
     39 	(((__u32)(x) & (__u32)0x00ff00ffUL) << 8) |		\
     40 	(((__u32)(x) & (__u32)0xff00ff00UL) >> 8)))
     41 
     42 /*
     43  * Implement the following as inlines, but define the interface using
     44  * macros to allow constant folding when possible:
     45  * ___swab16, ___swab32, ___swab64, ___swahw32, ___swahb32
     46  */
     47 
     48 static __inline__  __u16 __fswab16(__u16 val)
     49 {
     50 #if defined (__arch_swab16)
     51 	return __arch_swab16(val);
     52 #else
     53 	return ___constant_swab16(val);
     54 #endif
     55 }
     56 
     57 static __inline__  __u32 __fswab32(__u32 val)
     58 {
     59 #if defined(__arch_swab32)
     60 	return __arch_swab32(val);
     61 #else
     62 	return ___constant_swab32(val);
     63 #endif
     64 }
     65 
     66 static __inline__  __u64 __fswab64(__u64 val)
     67 {
     68 #if defined (__arch_swab64)
     69 	return __arch_swab64(val);
     70 #elif defined(__SWAB_64_THRU_32__)
     71 	__u32 h = val >> 32;
     72 	__u32 l = val & ((1ULL << 32) - 1);
     73 	return (((__u64)__fswab32(l)) << 32) | ((__u64)(__fswab32(h)));
     74 #else
     75 	return ___constant_swab64(val);
     76 #endif
     77 }
     78 
     79 static __inline__  __u32 __fswahw32(__u32 val)
     80 {
     81 #ifdef __arch_swahw32
     82 	return __arch_swahw32(val);
     83 #else
     84 	return ___constant_swahw32(val);
     85 #endif
     86 }
     87 
     88 static __inline__  __u32 __fswahb32(__u32 val)
     89 {
     90 #ifdef __arch_swahb32
     91 	return __arch_swahb32(val);
     92 #else
     93 	return ___constant_swahb32(val);
     94 #endif
     95 }
     96 
     97 /**
     98  * __swab16 - return a byteswapped 16-bit value
     99  * @x: value to byteswap
    100  */
    101 #ifdef __HAVE_BUILTIN_BSWAP16__
    102 #define __swab16(x) (__u16)__builtin_bswap16((__u16)(x))
    103 #else
    104 #define __swab16(x)				\
    105 	(__u16)(__builtin_constant_p(x) ?	\
    106 	___constant_swab16(x) :			\
    107 	__fswab16(x))
    108 #endif
    109 
    110 /**
    111  * __swab32 - return a byteswapped 32-bit value
    112  * @x: value to byteswap
    113  */
    114 #ifdef __HAVE_BUILTIN_BSWAP32__
    115 #define __swab32(x) (__u32)__builtin_bswap32((__u32)(x))
    116 #else
    117 #define __swab32(x)				\
    118 	(__u32)(__builtin_constant_p(x) ?	\
    119 	___constant_swab32(x) :			\
    120 	__fswab32(x))
    121 #endif
    122 
    123 /**
    124  * __swab64 - return a byteswapped 64-bit value
    125  * @x: value to byteswap
    126  */
    127 #ifdef __HAVE_BUILTIN_BSWAP64__
    128 #define __swab64(x) (__u64)__builtin_bswap64((__u64)(x))
    129 #else
    130 #define __swab64(x)				\
    131 	(__u64)(__builtin_constant_p(x) ?	\
    132 	___constant_swab64(x) :			\
    133 	__fswab64(x))
    134 #endif
    135 
    136 static __always_inline unsigned long __swab(const unsigned long y)
    137 {
    138 #if __BITS_PER_LONG == 64
    139 	return __swab64(y);
    140 #else /* __BITS_PER_LONG == 32 */
    141 	return __swab32(y);
    142 #endif
    143 }
    144 
    145 /**
    146  * __swahw32 - return a word-swapped 32-bit value
    147  * @x: value to wordswap
    148  *
    149  * __swahw32(0x12340000) is 0x00001234
    150  */
    151 #define __swahw32(x)				\
    152 	(__builtin_constant_p((__u32)(x)) ?	\
    153 	___constant_swahw32(x) :		\
    154 	__fswahw32(x))
    155 
    156 /**
    157  * __swahb32 - return a high and low byte-swapped 32-bit value
    158  * @x: value to byteswap
    159  *
    160  * __swahb32(0x12345678) is 0x34127856
    161  */
    162 #define __swahb32(x)				\
    163 	(__builtin_constant_p((__u32)(x)) ?	\
    164 	___constant_swahb32(x) :		\
    165 	__fswahb32(x))
    166 
    167 /**
    168  * __swab16p - return a byteswapped 16-bit value from a pointer
    169  * @p: pointer to a naturally-aligned 16-bit value
    170  */
    171 static __always_inline __u16 __swab16p(const __u16 *p)
    172 {
    173 #ifdef __arch_swab16p
    174 	return __arch_swab16p(p);
    175 #else
    176 	return __swab16(*p);
    177 #endif
    178 }
    179 
    180 /**
    181  * __swab32p - return a byteswapped 32-bit value from a pointer
    182  * @p: pointer to a naturally-aligned 32-bit value
    183  */
    184 static __always_inline __u32 __swab32p(const __u32 *p)
    185 {
    186 #ifdef __arch_swab32p
    187 	return __arch_swab32p(p);
    188 #else
    189 	return __swab32(*p);
    190 #endif
    191 }
    192 
    193 /**
    194  * __swab64p - return a byteswapped 64-bit value from a pointer
    195  * @p: pointer to a naturally-aligned 64-bit value
    196  */
    197 static __always_inline __u64 __swab64p(const __u64 *p)
    198 {
    199 #ifdef __arch_swab64p
    200 	return __arch_swab64p(p);
    201 #else
    202 	return __swab64(*p);
    203 #endif
    204 }
    205 
    206 /**
    207  * __swahw32p - return a wordswapped 32-bit value from a pointer
    208  * @p: pointer to a naturally-aligned 32-bit value
    209  *
    210  * See __swahw32() for details of wordswapping.
    211  */
    212 static __inline__ __u32 __swahw32p(const __u32 *p)
    213 {
    214 #ifdef __arch_swahw32p
    215 	return __arch_swahw32p(p);
    216 #else
    217 	return __swahw32(*p);
    218 #endif
    219 }
    220 
    221 /**
    222  * __swahb32p - return a high and low byteswapped 32-bit value from a pointer
    223  * @p: pointer to a naturally-aligned 32-bit value
    224  *
    225  * See __swahb32() for details of high/low byteswapping.
    226  */
    227 static __inline__ __u32 __swahb32p(const __u32 *p)
    228 {
    229 #ifdef __arch_swahb32p
    230 	return __arch_swahb32p(p);
    231 #else
    232 	return __swahb32(*p);
    233 #endif
    234 }
    235 
    236 /**
    237  * __swab16s - byteswap a 16-bit value in-place
    238  * @p: pointer to a naturally-aligned 16-bit value
    239  */
    240 static __inline__ void __swab16s(__u16 *p)
    241 {
    242 #ifdef __arch_swab16s
    243 	__arch_swab16s(p);
    244 #else
    245 	*p = __swab16p(p);
    246 #endif
    247 }
    248 /**
    249  * __swab32s - byteswap a 32-bit value in-place
    250  * @p: pointer to a naturally-aligned 32-bit value
    251  */
    252 static __always_inline void __swab32s(__u32 *p)
    253 {
    254 #ifdef __arch_swab32s
    255 	__arch_swab32s(p);
    256 #else
    257 	*p = __swab32p(p);
    258 #endif
    259 }
    260 
    261 /**
    262  * __swab64s - byteswap a 64-bit value in-place
    263  * @p: pointer to a naturally-aligned 64-bit value
    264  */
    265 static __always_inline void __swab64s(__u64 *p)
    266 {
    267 #ifdef __arch_swab64s
    268 	__arch_swab64s(p);
    269 #else
    270 	*p = __swab64p(p);
    271 #endif
    272 }
    273 
    274 /**
    275  * __swahw32s - wordswap a 32-bit value in-place
    276  * @p: pointer to a naturally-aligned 32-bit value
    277  *
    278  * See __swahw32() for details of wordswapping
    279  */
    280 static __inline__ void __swahw32s(__u32 *p)
    281 {
    282 #ifdef __arch_swahw32s
    283 	__arch_swahw32s(p);
    284 #else
    285 	*p = __swahw32p(p);
    286 #endif
    287 }
    288 
    289 /**
    290  * __swahb32s - high and low byteswap a 32-bit value in-place
    291  * @p: pointer to a naturally-aligned 32-bit value
    292  *
    293  * See __swahb32() for details of high and low byte swapping
    294  */
    295 static __inline__ void __swahb32s(__u32 *p)
    296 {
    297 #ifdef __arch_swahb32s
    298 	__arch_swahb32s(p);
    299 #else
    300 	*p = __swahb32p(p);
    301 #endif
    302 }
    303 
    304 
    305 #endif /* _LINUX_SWAB_H */