rcx

miscellaneous C library
git clone git://git.rr3.xyz/rcx
Log | Files | Refs | README | LICENSE

def.h (7074B)


      1 #pragma once
      2 
      3 #include <limits.h>
      4 #include <stddef.h>
      5 #include <stdint.h>
      6 
      7 /* Reasonable code assumes CHAR_BIT == 8. */
      8 #if CHAR_BIT != 8
      9 #error "Expected CHAR_BIT == 8"
     10 #endif
     11 
     12 #define JOIN_AUX(a,b) a##b
     13 #define JOIN(a,b) JOIN_AUX(a,b)
     14 
     15 #define STRINGIFY_AUX(x) #x
     16 #define STRINGIFY(x) STRINGIFY_AUX(x)
     17 
     18 #define VA_DROP1_(_0, ...) __VA_ARGS__
     19 #define VA_DROP1(...) VA_DROP1_(__VA_ARGS__)
     20 #define VA_DROP2_(_0, _1, ...) __VA_ARGS__
     21 #define VA_DROP2(...) VA_DROP2_(__VA_ARGS__,)
     22 #define VA_DROP3_(_0, _1, _2, ...) __VA_ARGS__
     23 #define VA_DROP3(...) VA_DROP3_(__VA_ARGS__,,)
     24 
     25 /* VA_DEFAULT is a helper for writing macros with an optional argument. Usage:
     26  *     #define MY_MACRO(...) VA_DEFAULT(,##__VA_ARGS__, "default")
     27  *     MY_MACRO()         ->   "default"
     28  *     MY_MACRO("whoa")   ->   "whoa"
     29  * XXX: Usage of this macro depends on nonstandard features. */
     30 #define VA_DEFAULT(_, v, ...) v
     31 
     32 #define MIN(a,b) ((a) < (b) ? (a) : (b))
     33 #define MAX(a,b) ((a) > (b) ? (a) : (b))
     34 
     35 /* Polymorphic array operations */
     36 #define LEN(a) (sizeof (a) / sizeof (a)[0])
     37 #define SET(a, v) do { memcpy(&(a), (v), sizeof(a)); } while (0)
     38 
     39 #define SWAP(a, b) do { \
     40 		/* The check in the array size is basically a portable static_assert.
     41 		 * The isize cast is necessary; without it, -1 becomes unsigned. */ \
     42 		u8 r_swap_temp_[sizeof(a) == sizeof(b) ? (isize)sizeof(a) : -1]; \
     43 		memcpy(&r_swap_temp_, &(a), sizeof(a)); \
     44 		memcpy(&(a), &(b), sizeof(a)); \
     45 		memcpy(&(b), &r_swap_temp_, sizeof(a)); \
     46 	} while(0)
     47 
     48 #ifdef __GNUC__
     49 #define NOINLINE __attribute__((noinline))
     50 #define UNUSED __attribute__((unused))
     51 #define likely(x)   (__builtin_expect((x), 1))
     52 #define unlikely(x) (__builtin_expect((x), 0))
     53 #else
     54 #define NOINLINE
     55 #define UNUSED
     56 #define likely(x)   (x)
     57 #define unlikely(x) (x)
     58 #endif
     59 
     60 /* STATIC is a macro for creating static literals. Usage:
     61  *     STATIC(int, 3)
     62  *     STATIC(char[], "abc")
     63  *     STATIC(struct {int a; int b;}, {1, 2})
     64  * The result of each of these expressions is a pointer to static data, which
     65  * in particular means it can be passed to functions that retain pointers after
     66  * the caller returns. In the last use case, the value argument contains a
     67  * comma outside of parentheses, which is why we use varargs in the
     68  * implementation. The type argument must never contain a comma outside of
     69  * parentheses. */
     70 #if __STDC_VERSION__ >= 202300L
     71 #define STATIC(T, ...) (&(static T){__VA_ARGS__})
     72 #elif defined(__GNUC__)
     73 #define STATIC(T, ...) ({static __typeof__(T) tmp = __VA_ARGS__; &tmp;})
     74 #endif
     75 
     76 #if !defined(R_LITTLE_ENDIAN) && !defined(R_BIG_ENDIAN)
     77 #if defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
     78 #define R_LITTLE_ENDIAN 1
     79 #elif defined(__BYTE_ORDER__) && __BYTE_ORDER == __ORDER_BIG_ENDIAN__
     80 #define R_BIG_ENDIAN 1
     81 #else
     82 #error "Can not detect endianness"
     83 /* If this ever happens, improve the above tests. */
     84 #endif
     85 #endif
     86 
     87 #ifndef R_CACHE_LINE_BITS
     88 #define R_CACHE_LINE_BITS 6
     89 #endif
     90 #define R_CACHE_LINE_SIZE (1 << (R_CACHE_LINE_BITS))
     91 
     92 #ifdef __MMX__
     93 #define R_HAVE_MMX 1
     94 #endif
     95 #ifdef __SSE__
     96 #define R_HAVE_SSE 1
     97 #endif
     98 #ifdef __SSE2__
     99 #define R_HAVE_SSE2 1
    100 #endif
    101 #ifdef __SSE3__
    102 #define R_HAVE_SSE3 1
    103 #endif
    104 #ifdef __SSSE3__
    105 #define R_HAVE_SSSE3 1
    106 #endif
    107 #ifdef __SSE4_1__
    108 #define R_HAVE_SSE4_1 1
    109 #endif
    110 #ifdef __SSE4_2__
    111 #define R_HAVE_SSE4_2 1
    112 #endif
    113 #ifdef __AVX__
    114 #define R_HAVE_AVX 1
    115 #endif
    116 #ifdef __AVX2__
    117 #define R_HAVE_AVX2 1
    118 #endif
    119 
    120 #ifdef __SIZEOF_INT128__
    121 #define R_HAVE_128 1
    122 #endif
    123 
    124 /* Correct the mistakes of whoever named these macros */
    125 #define SHORT_MIN SHRT_MIN
    126 #define SHORT_MAX SHRT_MAX
    127 #define USHORT_MAX USHRT_MAX
    128 
    129 #define CHAR_BITS 8
    130 
    131 #define SCHAR_BITS 8
    132 typedef signed char schar;
    133 
    134 #define UCHAR_BITS 8
    135 typedef unsigned char uchar;
    136 
    137 #define SHORT_BITS (8 * sizeof(short))
    138 
    139 #define USHORT_BITS (8 * sizeof(ushort))
    140 typedef unsigned short ushort;
    141 
    142 #define INT_BITS (8 * sizeof(int))
    143 
    144 #define UINT_BITS (8 * sizeof(uint))
    145 typedef unsigned int uint;
    146 
    147 #define LONG_BITS (8 * sizeof(long))
    148 
    149 #define ULONG_BITS (8 * sizeof(ulong))
    150 typedef unsigned long ulong;
    151 
    152 #define LLONG_BITS (8 * sizeof(llong))
    153 typedef long long llong;
    154 
    155 #define ULLONG_BITS (8 * sizeof(ullong))
    156 typedef unsigned long long ullong;
    157 
    158 #define I8_BITS 8
    159 #define I8_MIN INT8_MIN
    160 #define I8_MAX INT8_MAX
    161 #define I8_C INT8_C
    162 typedef int8_t i8;
    163 
    164 #define I16_BITS 16
    165 #define I16_MIN INT16_MIN
    166 #define I16_MAX INT16_MAX
    167 #define I16_C INT16_C
    168 typedef int16_t i16;
    169 
    170 #define I32_BITS 32
    171 #define I32_MIN INT32_MIN
    172 #define I32_MAX INT32_MAX
    173 #define I32_C INT32_C
    174 typedef int32_t i32;
    175 
    176 #define I64_BITS 64
    177 #define I64_MIN INT64_MIN
    178 #define I64_MAX INT64_MAX
    179 #define I64_C INT64_C
    180 typedef int64_t i64;
    181 
    182 #ifdef R_HAVE_128
    183 #define I128_BITS 128
    184 #define I128_MIN ((i128)-1 - I128_MAX)
    185 #define I128_MAX ((i128)(U128_MAX >> 1))
    186 typedef __int128 i128;
    187 #endif
    188 
    189 #define IMAX_BITS (8 * sizeof(imax))
    190 #define IMAX_MIN INTMAX_MIN
    191 #define IMAX_MAX INTMAX_MAX
    192 #define IMAX_C INTMAX_C
    193 typedef intmax_t imax;
    194 
    195 #define IPTR_BITS (8 * sizeof(iptr))
    196 #define IPTR_MIN INTPTR_MIN
    197 #define IPTR_MAX INTPTR_MAX
    198 typedef intptr_t iptr;
    199 
    200 /* Avoid dependence on POSIX sys/types.h for ssize_t */
    201 #if   SIZE_MAX == UINT32_MAX
    202 #define ISIZE_BITS 32
    203 #define ISIZE_MIN INT32_MIN
    204 #define ISIZE_MAX INT32_MAX
    205 #define ISIZE_C INT32_C
    206 typedef int32_t isize;
    207 #elif SIZE_MAX == UINT64_MAX
    208 #define ISIZE_BITS 64
    209 #define ISIZE_MIN INT64_MIN
    210 #define ISIZE_MAX INT64_MAX
    211 #define ISIZE_C INT64_C
    212 typedef int64_t isize;
    213 #else /* This won't happen except on weird archs */
    214 #error "Could not find a suitable type for isize"
    215 #endif
    216 
    217 #define U8_BITS 8
    218 #define U8_MAX UINT8_MAX
    219 #define U8_C UINT8_C
    220 typedef uint8_t u8;
    221 
    222 #define U16_BITS 16
    223 #define U16_MAX UINT16_MAX
    224 #define U16_C UINT16_C
    225 typedef uint16_t u16;
    226 
    227 #define U32_BITS 32
    228 #define U32_MAX UINT32_MAX
    229 #define U32_C UINT32_C
    230 typedef uint32_t u32;
    231 
    232 #define U64_BITS 64
    233 #define U64_MAX UINT64_MAX
    234 #define U64_C UINT64_C
    235 typedef uint64_t u64;
    236 
    237 #ifdef R_HAVE_128
    238 #define U128_BITS 128
    239 #define U128_MAX (((u128)U64_MAX << 64) | U64_MAX)
    240 typedef unsigned __int128 u128;
    241 #endif
    242 
    243 #define UMAX_BITS (8 * sizeof(umax))
    244 #define UMAX_MAX UINTMAX_MAX
    245 #define UMAX_C UINTMAX_C
    246 typedef uintmax_t umax;
    247 
    248 #define UPTR_BITS (8 * sizeof(uptr))
    249 #define UPTR_MAX UINTPTR_MAX
    250 typedef uintptr_t uptr;
    251 
    252 #if   SIZE_MAX == UINT32_MAX
    253 #define USIZE_BITS 32
    254 #define USIZE_C UINT32_C
    255 #elif SIZE_MAX == UINT64_MAX
    256 #define USIZE_BITS 64
    257 #define USIZE_C UINT64_C
    258 #else /* This won't happen except on weird archs */
    259 #error "Could not determine the width of usize"
    260 #endif
    261 #define USIZE_MAX SIZE_MAX
    262 typedef size_t usize;
    263 
    264 typedef float f32;
    265 typedef double f64;
    266 
    267 typedef _Complex float c64;
    268 typedef _Complex double c128;
    269 
    270 #define RUNE_BITS 32
    271 #define RUNE_BAD RUNE_C(0xFFFD)
    272 #define RUNE_MAX RUNE_C(0x10FFFF)
    273 #define RUNE_C UINT32_C
    274 typedef uint32_t rune;
    275 
    276 #if __STDC_VERSION__ >= 201100L
    277 typedef max_align_t maxalign;
    278 #else
    279 /* Fallback which is probably correct */
    280 typedef struct {
    281 	intmax_t i;      /* biggest integer */
    282 	long double d;   /* biggest floating point */
    283 	void *p;         /* data pointer */
    284 	void (*f)(void); /* function pointer */
    285 } maxalign;
    286 #endif