[英]How do I test if _Static_assert is defined?
_Static_assert
is built-in to some C compilers such as gcc and clang, but it may not be included in all C compilers. _Static_assert
内置于某些 C 编译器(例如 gcc 和 clang)中,但可能并非所有 C 编译器都包含它。 I would like to use the _Static_assert
functionality while keeping my code as cross-platform as possible.我想使用
_Static_assert
功能,同时尽可能保持我的代码跨平台。 I figured the best way to do this was to test我认为最好的方法是测试
#ifdef _Static_assert
_Static_assert(0, "Test");
#endif
but that doesn't seem to work out.但这似乎行不通。 It compiles, but it does not detect that
_Static_assert
is defined.它编译,但它没有检测到
_Static_assert
已定义。 Then I figured I could test if the compiler was GCC or not, but I read that having __GNUC__
defined doesn't necessarily prove that the compiler used is GCC.然后我想我可以测试编译器是否是 GCC,但我读到定义
__GNUC__
并不一定证明使用的编译器是 GCC。 This also doesn't detect other compilers where _Static_assert
is defined that I may not know about.这也不会检测到其他我可能不知道的
_Static_assert
被定义的编译器。 So my question is, what is the best way to detect if the compiler supports _Static_assert
in the preprocessor?所以我的问题是,检测编译器
_Static_assert
在预处理器中支持_Static_assert
的最佳方法是什么?
EDIT : This is the solution I came up with that suits my purposes.编辑:这是我想出的适合我的目的的解决方案。 Thanks to @KamilCuk below for the link that helped me out.
感谢下面的@KamilCuk 提供帮助我的链接。
// Check that we can use built-in _Static_assert
#if defined( __STDC_VERSION__ ) && __STDC_VERSION__ >= 201112L
#define WE_HAVE_STATIC_ASSERT 1
#endif
#if WE_HAVE_STATIC_ASSERT
_Static_assert(0, "Test");
#endif
This code works for me on both gcc and clang: https://godbolt.org/z/svaYjWj4j这段代码在 gcc 和 clang 上都适用于我: https : //godbolt.org/z/svaYjWj4j
FINAL EDIT (I think): This provides an answer to my original question about how to detect if _Static_assert
is available.最终编辑(我认为):这为我关于如何检测
_Static_assert
是否可用的原始问题提供了答案。 It also provides a fallback option that results in relatively helpful errors in most compilers I tested.它还提供了一个回退选项,可以在我测试的大多数编译器中产生相对有用的错误。
Here is the link to the test code: https://godbolt.org/z/TYEj7Tezd这是测试代码的链接: https : //godbolt.org/z/TYEj7Tezd
// Check if we can use built-in _Static_assert
#if defined( __STDC_VERSION__ ) && __STDC_VERSION__ >= 201112L
#define MY_STATIC_ASSERT(cond, msg) _Static_assert(cond, msg)
#else // We make our own
// MY_JOIN macro trick generates a unique token
#define MY_JOIN2(pre, post) MY_JOIN3(pre, post)
#define MY_JOIN3(pre, post) pre ## post
#if defined( __COUNTER__ ) // try to do it the smart way...
#define MY_JOIN(pre) MY_JOIN2(pre, __COUNTER__)
#define MY_STATIC_ASSERT(cond, msg) \
static const char *MY_JOIN(static_assert)[(cond) * 2 - 1] = { msg }
#else // we did our best...
//will break if static assert on same line in different file
#define MY_JOIN(pre) MY_JOIN2(pre, __LINE__)
#define MY_STATIC_ASSERT(cond, msg) \
static const char *MY_JOIN(static_assert)[(cond) * 2 - 1] = { msg }
#endif
#endif
/* - CHANGE CODE HERE TO TEST THE ASSERTIONS - */
enum {
A = 3,
B = 3,
C = B - A
};
/* - --------------------------------------- - */
// Test to see if the enum values match our assertions
MY_STATIC_ASSERT(B > A, "B must be greater than A");
MY_STATIC_ASSERT(C > 0, "C must be greater than zero");
Helpful information I used to make this came from these links:我用来做这件事的有用信息来自以下链接:
http://jonjagger.blogspot.com/2017/07/compile-time-assertions-in-c.html http://jonjagger.blogspot.com/2017/07/compile-time-assertions-in-c.html
https://www.tutorialspoint.com/cprogramming/c_preprocessors.htm https://www.tutorialspoint.com/cprogramming/c_preprocessors.htm
https://stackoverflow.com/a/43990067/16292858 https://stackoverflow.com/a/43990067/16292858
How do I test if _Static_assert is defined?
如何测试 _Static_assert 是否已定义?
_Static_assert
is part of C11. _Static_assert
是 C11 的一部分。 So check for C11.所以检查C11。
#if __STDC_VERSION__ > 201112L
You could also #include <assert.h>
and check for #ifdef static_assert
.您还可以
#include <assert.h>
并检查#ifdef static_assert
。
My first google hit for static_assert.h github
has a nice example how to handle different tools and compilers: https://github.com/wc-duck/dbgtools/blob/master/include/dbgtools/static_assert.h#L68 .我第一次在 google 上搜索
static_assert.h github
有一个很好的例子,如何处理不同的工具和编译器: https : //github.com/wc-duck/dbgtools/blob/master/include/dbgtools/static_assert.h#L68 。
If you want to write a C11 compatibility layer and use static assertion in your code, for example use this answer and fallback to your own wrapper:如果您想编写 C11 兼容层并在代码中使用静态断言,例如使用此答案并回退到您自己的包装器:
// static_assert.h
#define CTASTR2(pre,post) pre ## post
#define CTASTR(pre,post) CTASTR2(pre,post)
#define STATIC_ASSERT(cond) \
typedef struct { int static_assertion_failed : !!(cond); } \
CTASTR(static_assertion_failed_,__COUNTER__)
#include <assert.h>
#ifndef static_assert
#define static_assert(expr, str) STATIC_ASSERT(expr)
#endif
// somefile.c
#include <static_assert.h>
static_assert(something == something, "Uwu");
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.