3 ms·
Here is an assert that is static if possible: #ifndef __clang__ #define assume(expr) \ __extension__ ({ \ static_assert(__builtin_choose_ex
by okl 6y ago
Here is an assert that is static if possible:
#ifndef __clang__
#define assume(expr) \
__extension__ ({ \
static_assert(__builtin_choose_expr( \
__builtin_constant_p(expr), expr, true), #expr); \
assert(__builtin_choose_expr( \
__builtin_constant_p(expr), true, expr)); \
})
#else
#define assume(expr) \
__extension__ ({ \
static_assert(__builtin_constant_p(expr) ? (expr) : true, #expr); \
assert(__builtin_choose_expr( \
__builtin_constant_p(expr), true, expr)); \
})
#endif
Note that the clang semantics of language extensions sometimes differ from GCC.
I also like to use __auto_type very much:
#define var __auto_type
#define let __auto_type const
As in:
#define m_max(a, b) \
__extension__ ({ \
let _a = (a); \
let _b = (b); \
_a > _b ? _a : _b; \
})
- boomer_joe 6y agoWhat is the advantage of your assume macro over regular C11 static_assert / assert? Apologies if it is immediately obvious. And in case anyone else is wondering, the advantage of that m_max macro is that it evaluates each of its arguments only once.
- saagarjha 6y agoThe types of things that _Static_assert takes is substantially more limited than this construct, as it can only take an "integral constant expression" which is in practice basic integer arithmetic and nothing else. This construct works with more complicated things that are nonetheless known at compile time, such as "asdf"[4] (should be 0).