我遇到了 gcc v3.4.4 的错误,需要在代码中添加 #ifdef 来解决该版本编译器的错误。
GCC编译器预处理器预定义宏有哪些来检测编译器的版本号?
来自 gnu cpp 手册...
__GNUC__
__GNUC_MINOR__
__GNUC_PATCHLEVEL__
这些宏由所有使用 C 预处理器的 GNU 编译器定义:C、C++、Objective-C 和 Fortran。它们的值是编译器的主要版本、次要版本和补丁级别,作为整数常量。例如,GCC 3.2.1 将定义
__GNUC__
为 3、__GNUC_MINOR__
为 2、__GNUC_PATCHLEVEL__
为 1。如果直接调用预处理器,也会定义这些宏。
__GNUC_PATCHLEVEL__
是GCC 3.0的新功能;它也存在于 3.0 之前广泛使用的开发快照中(将自己标识为 GCC 2.96 或 2.97,具体取决于您拥有的快照)。
如果您需要知道您的程序是否由 GCC 编译,或者是由声称接受 GNU C 方言的非 GCC 编译器编译,您可以简单地测试
__GNUC__
。如果您需要编写依赖于特定版本的代码,则必须更加小心。每次增加次要版本时,补丁级别都会重置为零;每次增加主要版本(这种情况很少发生)时,次要版本和补丁级别都会重置。如果您希望直接在条件中使用预定义的宏,则需要这样编写:
/* Test for GCC > 3.2.0 */
#if __GNUC__ > 3 || \
(__GNUC__ == 3 && (__GNUC_MINOR__ > 2 || \
(__GNUC_MINOR__ == 2 && \
__GNUC_PATCHLEVEL__ > 0)))
__GNUC__
、__GNUC_MINOR__
和 __GNUC_PATCHLEVEL__
。
例如,GCC 4.0.1 即可:
#define __GNUC__ 4
#define __GNUC_MINOR__ 0
#define __GNUC_PATCHLEVEL__ 1
当您想知道 GNU GCC 编译器在您当前的编程环境下定义了哪些预定义的预处理器指令时,请记住以下一个小命令行:
gcc -E -dM - < /dev/null |less
来自在线文档:
__GNUC__
__GNUC_次要__
__GNUC_PATCHLEVEL__
这些宏由所有使用 C 预处理器的 GNU 编译器定义:C、C++、Objective-C 和 Fortran。它们的值是编译器的主要版本、次要版本和补丁级别,作为整数常量。例如,GCC 3.2.1 将 __GNUC__ 定义为 3,将 __GNUC_MINOR__ 定义为 2,将 __GNUC_PATCHLEVEL__ 定义为 1。如果直接调用预处理器,也会定义这些宏。
和
__版本__
该宏扩展为一个字符串常量,描述正在使用的编译器的版本。您不应依赖其具有任何特定形式的内容,但可以认为它至少包含版本号。
gcc 版本有 3 个宏可供您测试。
__GNUC_MINOR__
__GNUC_PATCHLEVEL__
__GNUC__
例如我的 gcc v 4.1.3 如此定义它们:
#define __GNUC_MINOR__ 1
#define __GNUC_PATCHLEVEL__ 3
#define __GNUC__ 4
运行即可看到定义的“buitin”宏
gcc -E -dM -x c /dev/null
顺便说一句,如果您使用 glib,那么您可以访问以下宏,可用于检查 GNU C/C++ 编译器版本:
#ifdef __GNUC__
#define G_GNUC_CHECK_VERSION(major, minor) \
((__GNUC__ > (major)) || \
((__GNUC__ == (major)) && \
(__GNUC_MINOR__ >= (minor))))
#else
#define G_GNUC_CHECK_VERSION(major, minor) 0
#endif
请注意,当您不使用 GNU 编译器进行编译时,宏总是返回 false (0)。
因此,我在我的 snapdev 库 version.h 标头中使用以下宏。就我而言,我还想检查补丁并且我使用了很多库,所以我编写了一个更通用的版本:
#define SNAPDEV_CHECK_VERSION(wanted_major, wanted_minor, wanted_patch, current_major, current_minor, current_patch) \
(((current_major) > (wanted_major)) || \
(((current_major) == (wanted_major)) \
&& (((current_minor) > (wanted_minor)) || \
(((current_minor) == (wanted_minor)) \
&& ((current_patch) >= (wanted_patch))))))
我对 GCC 有专门的检查,所以你不必记住宏的名称,包括版本:
#define SNAPDEV_CHECK_GCC_VERSION(wanted_major, wanted_minor, wanted_patch) \
SNAPDEV_CHECK_VERSION(wanted_major, wanted_minor, wanted_patch, \
__GNUC__, __GNUC_MINOR__, __GNUC_PATCHLEVEL__)
正如我对大部分代码所做的那样,我编写了一个单元测试,因此我可以说,除非您向其提供无效数据(著名的最后一句话),否则测试不太可能失败。