Xmake基础----配置编译器特性检测

本文介绍了如何利用Xmake进行编译器特性检测,以C++11的constexpr为例,展示了如何在不支持该特性的编译器上进行适配。通过Xmake的接口,可以方便地检测头文件、库接口、类型定义等,并提供了C/C++代码片段检测以应对复杂需求。实验中还详细说明了如何配置Xmake.lua以实现跨平台的编译检测。

由于不同的编译器对 C++ 标准的支持力度都是不同的,有些编译器可能并不支持 C++ 的一些高版本标准中的特性,这时我们就可以通过 xmake 提供的编译器特性检测接口去检测它们。

这里以 C++11 的 constexpr 为例,在编译代码时,检测判断是否支持 constexpr,如果不支持,我们就不使用这个关键字。

为了简化实验步骤,这里重新修改 xmake.lua 配置,去掉对 config.h 的使用,直接通过 check_features 接口去完成 C++ 特性的检测,例如。

includes("check_features.lua")

target("check")
    set_kind("binary")
    add_files("src/*.cpp")
    check_features("HAS_CONSTEXPR", "cxx_constexpr")

其中 cxx_constexpr 就是指 C++ 的 constexpr 特性名称,关于完整的 C++ 特性名称列表,我们可以到 C++ 特性列表名称 查看。

然后修改 src/main.cpp 中的代码,改成如下对 constexpr 的使用。

#ifdef HAS_CONSTEXPR
constexpr int a = 1;
constexpr int c = a * 2 + 1;
#else
#   error "constexpr not supported!"
#endif

int main(int argc, char** argv)
{
    return 0;
}

这个时候,如果我们执行 xmake 编译后,会发现 constexpr 的特性并没有检测通过,编译也是失败的,如下图。

 

那是因为这个关键字仅仅只在 c++11 标准之后才生效,因此需要对 target 启用 c++11 标准,并且对于 check_features 检测接口,也需要传递 c++11 的语言标准给它才能通过检测。

因此继续修改完善 xmake.lua 配置,修改如下。

includes("check_features.lua")

target("check")
    set_kind("binary")
    add_files("src/*.cpp")
    set_languages("c++11")
    check_features("HAS_CONSTEXPR", "cxx_constexpr", {languages = "c++11"})

设置上 c++11 语言标准后,再来执行 xmake 命令就能顺利通过检测和编译了。

 

配置自定义 C/C++ 代码片段检测

虽然,xmake 提供了很多内置的辅助检测接口,可以方便的检测头文件、库接口、类型定义、编译器特性等等,但是对于一些比较复杂的检测,单纯靠这些是无法满足的,这时我们还可以通过 xmake 提供的通用检测接口,也就是 C/C++ 代码片段检测,来实现任意的用户检测需求。

可以在检测接口中,传入一小段 C/C++ 代码片段,来实现我们所希望的检测逻辑,其中 check_csnippets 用于检测 C 代码片段,而 check_cxxsnippets 用于检测 C++ 代码片段。

继续修改之前的 xmake.lua 文件,加上对这两个接口的配置使用,例如。

includes("check_csnippets.lua")
includes("check_cxxsnippets.lua")

target("check")
    set_kind("binary")
    add_files("src/*.cpp")
    set_languages("c++11")
    check_csnippets("HAS_STATIC_ASSERT", "_Static_assert(1, \"\");")
    check_cxxsnippets("HAS_CONSTEXPR", "constexpr int a = 1;", {languages = "c++11"})

通过上面的配置,我们看到其中加了两个代码片段,一个是 C 代码片段,用来检测能否使用 _Static_assert 来实现静态断言,而另外一个是 C++ 代码片段,用来实现跟之前的编译器特性检测配置一样的效果,也就是检测 constexpr 是否可用。

但是跟之前不同的是,我们这里是直接在配置中传入了完整的 C++ 代码片段,在里面去使用 constexpr,然后 xmake 会尝试调用 gcc 等编译器去编译它,如果编译通过,就会定义 HAS_CONSTEXPR 宏,也就是通过了检测。

同时也需要修改 src/main.cpp 文件,加上对 HAS_STATIC_ASSERT 和 HAS_CONSTEXPR 的宏定义检测。

#ifdef HAS_CONSTEXPR
constexpr int a = 1;
constexpr int c = a * 2 + 1;
#else
#   error "constexpr not supported!"
#endif

#ifndef HAS_STATIC_ASSERT
#   error "_Static_assert not supported!"
#endif

int main(int argc, char** argv)
{
    return 0;
}

然后执行 xmake 编译,如果一切顺利,就会看到下图编译通过的输出信息。

 

在本节实验中,我们了解了怎样才能实现跨平台开发和编译,并且主要学习了如何去使用 xmake 提供的辅助接口来配置检测 C/C++ 的头文件、库接口是否存在,以及检测指定的编译器特性和 C/C++ 代码片段是否能够支持并使用。

本实验的参考代码可以使用如下命令下载:

wget https://labfile.oss-internal.aliyuncs.com/courses/2764/code11.zip
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

红星星

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值