前言
跨平台编译一直是 C/C++的大坑之一。作为一个跨平台的语言,理想情况当然是一套代码到处跑,本系列文章就让我们聊聊 C++/C 跨平台的那些事
在开始交叉编译之前,我们需要先解决本地构建这一前置任务
我们以跑通以下代码为例(第三方库来自GitHub - libcpr/cpr: C++ Requests: Curl for People, a spiritual port of Python Requests.)一起看看 C++的环境配置
#include <iostream>
#include <cpr/cpr.h>
int main(int argc, char** argv) {
cpr::Response r = cpr::Get(cpr::Url{"http://www.httpbin.org/get"});
std::cout<<r.text<<std::endl; // JSON text string
return 0;
}
本地构建环境搭建
C/C++具有很多可供选择的包管理器/构建工具,这可能与其他语言不同
本教程将使用较为流行的 CMake+vcpkg 搭配作为构建工具和包管理器。这一搭配基本可以满足绝大部分本地构建和交叉编译的需求,另外,本文未使用 vcpkg 的 manifest 模式,如需了解可前往清单模式参考 | Microsoft Learn查看
Windows 篇
首先是 Visual Studio,vcpkg 需要他,本文也将使用 MSVC 作为 Windows 下的编译器,你可以从这里下载
Visual Studio Community 版本即可满足本文需要,但在安装时,请记得勾选“使用 C++的桌面开发”和“英语”语言包(vcpkg 的奇怪需求)
其他选项可以按需选择,直接下一步安装即可,正常情况下,Visual Studio 会附带一个 CMake,可以按需将其加到 PATH 环境变量中或者另装一个CMake
Git 也是必需的。实际上在这里 Visual Studio 也会附带 Git,但个人建议还是最好前往Git (git-scm.com)自行安装一个,如果没有特别需要,一路下一步即可
另外,推荐安装 Ninja Build 作为 CMake 后端,可以直接将 Visual Studio 自带的或在 vcpkg 安装软件包时自动下载的 ninja 加入 PATH 中或前往Releases · ninja-build/ninja (github.com)下载
在这之后,就可以安装 vcpkg 了
首先,找一块风水宝地,cd 进去,vcpkg 理论上可以安装在任何地方,但官方建议为了避免某些库构建工具可能的路径问题,可以优先考虑将 vcpkg 作为 CMake 项目的子模块,使用例如 C:\src\vcpkg
或 C:\dev\vcpkg
的安装目录
然后
git clone https://github.com/microsoft/vcpkg
.\vcpkg\bootstrap-vcpkg.bat
如果网络不好,可以考虑浅克隆,即改用
git clone https://github.com/microsoft/vcpkg --depth=1
如果网络依旧不给力,或在执行.\vcpkg\bootstrap-vcpkg.bat
时出现了问题,可以考虑使用Watt Toolkit (steampp.net)或1.1.1.1 — The free app that makes your Internet faster.等代理/加速器
不建议使用 Github 镜像站
然后,就可以安装我们需要的库了
.\vcpkg\vcpkg install cpr:x64-windows
到目前为止,Windows 下的环境搭建就基本完成了
注:vcpkg 在最近将 Windows 下的默认安装版本从 x86-windows 更改为了 x64-windows,为了避免歧义,本文显示指定了安装版本为 x64-windows。
Linux 篇
在 Linux 下的常用编译器一般为 gcc/g++,使用以下命令来安装他们,顺便装上 Git 和 CMake 及 Ninja(用于替代 GNU make)
#Debian/Ubuntu and derivatives
sudo apt install gcc g++ cmake git ninja-build
#SUSE and derivatives
sudo zypper in gcc gcc-c++ cmake git ninja
#CentOS/RedHat/Fedora and derivatives
sudo yum install gcc gcc-c++ cmake git ninja-build
#or
sudo dnf install gcc gcc-c++ cmake git ninja-build
#ArchLinux and derivatives
sudo pacman -S gcc cmake git ninja
#Alpine
apk add build-base cmake ninja git
#NixOS/Others
自行解决
如果顺利的话,到此为止,我们就完成了基本编译环境的配置
和 Windows 一样,我们现在就可以找一块风水宝地去配置 vcpkg 了
git clone https://github.com/microsoft/vcpkg
./vcpkg/bootstrap-vcpkg.sh
如果缺少某些依赖,按照提示安装即可,如果顺利的话,我们就可以在 vcpkg 目录下面得到一个叫 vcpkg 的可执行文件,然后,就可以安装我们需要的库了
./vcpkg/vcpkg install cpr
到目前为止,Linux 下的环境搭建就基本完成了
MacOS
另请高明
构建!
关于编辑环境的配置可以看我的另外一篇文章,但现在还没写,所以在此以命令行方式演示
首先我们需要一个文件夹来放我们的源代码,然后将上文代码命名为”main.cc”然后放进去,对于 CMake 项目,我们需要一个CMakeLists.txt
内容像下面这样
cmake_minimum_required(VERSION 3.5.0)
project(example VERSION 0.1.0 LANGUAGES C CXX)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
include(CTest)
enable_testing()
find_package(cpr CONFIG REQUIRED)#导入cpr包
add_executable(example main.cc)
target_link_libraries(example PRIVATE cpr::cpr)#链接cpr
set(CPACK_PROJECT_NAME ${PROJECT_NAME})
set(CPACK_PROJECT_VERSION ${PROJECT_VERSION})
include(CPack)
然后就可以准备构建了
按照惯例,我们在源代码文件夹中新建”build”文件夹然后 cd 进去
mkdir build
cd build
然后执行 CMake Configure,在这里,需要注意,我们需要使用到我们前面配置好的 vcpkg 的 CMake Toolchain File,具体位置为 vcpkg 目录下的 scripts/buildsystems/vcpkg.cmake,在这里最好转换为绝对路径传入,另外,在执行 vcpkg integrate install 时也可以看到相应提示,在这里,我们假设 vcpkg 安装在/home/mwx/vcpkg 中
cmake .. -GNinja -DCMAKE_TOOLCHAIN_FILE=/home/mwx/vcpkg/scripts/buildsystems/vcpkg.cmake
如果一切顺利,我们应该可以看到类似如下输出
-- Configuring done
-- Generating done
-- Build files have been written to: xxx
如果看到类似如下报错
CMake Error at CMakeLists.txt:7 (find_package):
Could not find a package configuration file provided by "cpr" with any of
the following names:
cprConfig.cmake
cpr-config.cmake
Add the installation prefix of "cpr" to CMAKE_PREFIX_PATH or set "cpr_DIR"
to a directory containing one of the above files. If "cpr" provides a
separate development package or SDK, be sure it has been installed.
-- Configuring incomplete, errors occurred!
可以考虑以下几种可能:
CMake Toolchain File 未正确设置
vcpkg 未安装对应包或系统类型不匹配(如 x64-windows 与 x86-windows 混淆)
CMake 缓存未清除(删除 build 目录下的 CMakeCache.txt)
如果看到类似如下报错
CMake Error: CMake was unable to find a build program corresponding to "Ninja". CMAKE_MAKE_PROGRAM is not set. You probably need to select a different build tool.
CMake Error: CMAKE_C_COMPILER not set, after EnableLanguage
CMake Error: CMAKE_CXX_COMPILER not set, after EnableLanguage
-- Configuring incomplete, errors occurred!
则可能是 Ninja 未正确安装,可以通过直接执行ninja --version
检查,或者如果实在不想使用 Ninja,可以在前面的 cmake 命令中直接去掉-GNinja 并删除 CMakeCache.txt 重新运行 cmake 使用 CMake 的缺省设置。
如果一切顺利,那就可以开始正式编译了
cmake --build .
如果使用 Ninja 则直接
ninja
理论上,至此我们就完成了示例的构建,理应可以在 build 目录下看到名为 example 或 example.exe 的可执行文件,如果使用了 MSBuild,则应该在 Debug 文件夹下看到 example.exe,我们可以执行看看
如果一切顺利,我们可以看到类似如下输出
{
"args": {},
"headers": {
"Accept": "*/*",
"Accept-Encoding": "deflate, gzip",
"Host": "www.httpbin.org",
"User-Agent": "curl/8.4.0-DEV",
"X-Amzn-Trace-Id": "Root=x-xxxxxxx-xxxxxxxxxxxxxxxxxxxxxxxx"
},
"origin": "xxx.xxx.xxx.xxx",
"url": "http://www.httpbin.org/get"
}
如果网络异常,你可能看不到任何输出,但这并不能改变我们已经成功构建这一示例项目的事实
那么,至此,大功告成,回见