base: static_assert(expr, msg)
authorMarko Kreen <markokr@gmail.com>
Thu, 5 Apr 2012 14:01:27 +0000 (17:01 +0300)
committerMarko Kreen <markokr@gmail.com>
Thu, 5 Apr 2012 14:16:22 +0000 (17:16 +0300)
Provide static_assert() macro.  On newer compilers
it tries to use built-in implementation, on older
ones compat one.

The detection does not need to be too strict as there
is always fallback implementation available.

Include <assert.h>, as that is where C1x will provide it.

test/compile.c
usual/base.h

index c715981ab28df404ab0f87d64c2072c6150f84da..a306513729a2cac7b8c03ea512d6a7fb722003ac 100644 (file)
@@ -39,6 +39,8 @@ int main(void)
        struct md5_ctx md5;
        char buf[128];
 
+       static_assert(sizeof(int) >= 4, "unsupported int size");
+
        aatree_init(&aatree, NULL, NULL);
        cbtree = cbtree_create(NULL, NULL, NULL, USUAL_ALLOC);
        cbtree_destroy(cbtree);
index 0846ff148a410ba127de8823881b1cf042237749..9f4d065e4c9ba2913e405b54914db4cbb118cc9a 100644 (file)
@@ -43,6 +43,7 @@
 #include <stdlib.h>
 #include <errno.h>
 #include <unistd.h>
+#include <assert.h>
 
 #ifdef WIN32
 #include <usual/base_win32.h>
 
 /* @} */
 
+
+/**
+ * Compile-time assert.
+ *
+ * Expression must be evaluatable at compile time.
+ * If false, stop compilation with message.
+ *
+ * It can be used in either global or function scope.
+ */
+#ifndef static_assert
+#if _COMPILER_GNUC(4,6) || _COMPILER_CLANG(3,0) || _COMPILER_MSC(1600)
+/* Version for new compilers */
+#define static_assert(expr, msg) _Static_assert(expr, msg)
+#else
+/* Version for old compilers */
+#define static_assert(expr, msg) enum { CONCAT4(static_assert_failure_, __LINE__, _, __COUNTER__) = 1/(1 != (1 + (expr))) }
+#endif
+#endif /* !static_assert */
+
+
 /** assert() that uses <usual/logging> module  */
 #ifndef Assert
 #ifdef CASSERT