假设我有一个带有这样的行的头文件:
#if LONG_BIT != 8 * SIZEOF_LONG
/* 04-Oct-2000 LONG_BIT is apparently (mis)defined as 64 on some recent
* 32-bit platforms using gcc. We try to catch that here at compile-time
* rather than waiting for integer multiplication to trigger bogus
* overflows.
*/
#error "pp897: LONG_BIT definition appears wrong for platform (bad gcc/glibc config?)."
#endif
我想输出LONG_BIT和SIZEOF_LONG的值。可以这样做,还是从头文件中做到这一点呢?
答案 0 :(得分:3)
_Static_assert
或C ++中的static_assert
可以测试条件并显示字符串,并且可以使用预处理程序扩展来构造该字符串:
#define LONG_BIT 64
#define SIZEOF_LONG 4
#define StringizeHelper(x) #x
#define Stringize(x) StringizeHelper(x)
_Static_assert(LONG_BIT == 8 * SIZEOF_LONG,
"LONG_BIT is " Stringize(LONG_BIT) " but must be 8 * "
Stringize(SIZEOF_LONG) ".");
使用Clang输出
x.c:7:1: error: static_assert failed "LONG_BIT is 64 but must be 8 * 4." _Static_assert(LONG_BIT == 8 * SIZEOF_LONG, ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~ 1 error generated.
答案 1 :(得分:1)
在这种情况下,您需要测试一些值。您可以像switch / case语句一样对可能的选项进行逐一测试,以防万一。
独立示例。前两个define
语句在这里进行测试,从最终代码中删除
// completely bogus/incoherent values just to test
#define LONG_BIT 32
#define SIZEOF_LONG 4444
// operational test from now on
#if LONG_BIT != 8 * SIZEOF_LONG
#if LONG_BIT == 32
#error "pp897: LONG_BIT definition appears wrong for platform (bad gcc/glibc config?): size 32"
#elif LONG_BIT == 64
#error "pp897: LONG_BIT definition appears wrong for platform (bad gcc/glibc config?): size 64"
#else
#error "pp897: LONG_BIT definition appears wrong for platform (bad gcc/glibc config?): size ???"
#endif
#endif
编译输出:
test.c:7:2: error: #error "pp897: LONG_BIT definition appears wrong for platfo
rm (bad gcc/glibc config?): size 32"
此方法与包括C89在内的所有标准兼容
答案 2 :(得分:0)
(至少)使用GCC或Clang,您可以打印出预处理器宏的值:
#define LONG_BIT 60
#pragma message "LONG_BIT is " STRINGIFY(LONG_BIT)
但这不会为您提供sizeof(long)
的值,它不是预处理程序的构造。它也不做算术; LONG_BIT
必须是实际数字,以便产生所需的消息。
这不适用于#error
,后者不能在文本中进行宏替换。
在这里,STRINGIFY
具有通常的两阶段定义:
#define STRINGIFY_(x) #x
#define STRINGIFY(x) STRINGIFY_(x)
至少在这种情况下,您也可以将整个消息写在参数中,但要注意意外的扩展:
#pragma message STRINGIFY(LONG BIT is LONG_BIT)