vcpkg示例
创建一个简单的CMake项目
先创建一个简单的项目。
main.cpp
:
//
// Created by root on 23-8-22.
//
#include <iostream>
int main()
{
std::cout<<"hello world"<<std::endl;
return EXIT_SUCCESS;
}
CMakeLists.txt
:
cmake_minimum_required(VERSION 3.23)
project(vcpkg_learn)
set(CMAKE_CXX_STANDARD 14)
add_executable(vcpkg_learn main.cpp)
加载项目:
# 进入项目根目录
cd vcpkg_learn
# 加载
cmake -DCMAKE_BUILD_TYPE=Debug -DCMAKE_MAKE_PROGRAM=ninja -G Ninja -S . -B ./cmake-build-debug
如下:
[root@localhost vcpkg_learn]# ls
CMakeLists.txt main.cpp
[root@localhost vcpkg_learn]# cmake -DCMAKE_BUILD_TYPE=Debug -DCMAKE_MAKE_PROGRAM=ninja -G Ninja -S . -B ./cmake-build-debug
-- The C compiler identification is GNU 11.2.1
-- The CXX compiler identification is GNU 11.2.1
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Check for working C compiler: /opt/rh/devtoolset-11/root/usr/bin/cc - skipped
-- Detecting C compile features
-- Detecting C compile features - done
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
-- Check for working CXX compiler: /opt/rh/devtoolset-11/root/usr/bin/c++ - skipped
-- Detecting CXX compile features
-- Detecting CXX compile features - done
-- Configuring done (0.4s)
-- Generating done (0.0s)
-- Build files have been written to: /root/vcpkg_learn/cmake-build-debug
编译代码:
cmake --build ./cmake-build-debug --target vcpkg_learn -j $(nproc)
执行:
./vcpkg_learn
可以看到程序正确执行。
使用vcpkg
我不想像其他博客一样全局安装vcpkg,我希望将其集成在项目中。
将项目初始化为一个git仓库:
git init
添加vcpkg作为git子模块:
git submodule add https://github.com/Microsoft/vcpkg.git
修改CMakeLists.txt
,其内容如下:
cmake_minimum_required(VERSION 3.23)
set(CMAKE_CXX_STANDARD 14)
if(NOT DEFINED URL_BASE)
set(URL_BASE "github.com")
endif()
list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake)
set(VERSION "3.4.0")
set(VERSION_SUFFIX "")
# vcpkg init
if(NOT DEFINED CMAKE_TOOLCHAIN_FILE)
find_package(Git REQUIRED)
execute_process(COMMAND ${GIT_EXECUTABLE} submodule update --init --recursive -- vcpkg WORKING_DIRECTORY ${CMAKE_SOURCE_DIR})
# 将vcpkg集成到cmake项目中,等同于在加载项目时的 -DCMAKE_TOOLCHAIN_FILE=<vcpkg_dir>/scripts/buildsystems/vcpkg.cmake
set(CMAKE_TOOLCHAIN_FILE "${CMAKE_CURRENT_SOURCE_DIR}/vcpkg/scripts/buildsystems/vcpkg.cmake"
CACHE STRING "Vcpkg toolchain file")
endif()
project(vcpkg_learn)
add_executable(vcpkg_learn main.cpp)
加载项目:
# 进入项目根目录
cd vcpkg_learn
# 加载
cmake -DCMAKE_BUILD_TYPE=Debug -DCMAKE_MAKE_PROGRAM=ninja -G Ninja -S . -B ./cmake-build-debug
安装vcpkg:
# 进入项目根目录
cd vcpkg_learn
cd vcpkg && ./bootstrap-vcpkg.sh
完成后在目录中可以看到vcpkg的可执行文件。
安装一个库
搜索cryptopp:
[root@localhost vcpkg]# ./vcpkg search cryptopp
cryptopp 8.8.0 Crypto++ is a free C++ class library of cryptographic schemes.
cryptopp[pem-pack] Crypto++ with PEM pack
The result may be outdated. Run `git pull` to get the latest results.
If your port is not listed, please open an issue at and/or consider making a pull request. - https://github.com/Microsoft/vcpkg/issues
安装cryptopp:
[root@localhost vcpkg]# ./vcpkg install cryptopp
Computing installation plan...
The following packages will be built and installed:
cryptopp:x64-linux -> 8.8.0
* vcpkg-cmake:x64-linux -> 2023-05-04
* vcpkg-cmake-config:x64-linux -> 2022-02-06#1
Additional packages (*) will be modified to complete this operation.
Detecting compiler hash for triplet x64-linux...
Restored 0 package(s) from /root/.cache/vcpkg/archives in 15.2 us. Use --debug to see more details.
Installing 1/3 vcpkg-cmake:x64-linux...
Building vcpkg-cmake:x64-linux...
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake_x64-linux/share/vcpkg-cmake/vcpkg_cmake_configure.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake_x64-linux/share/vcpkg-cmake/vcpkg_cmake_build.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake_x64-linux/share/vcpkg-cmake/vcpkg_cmake_install.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake_x64-linux/share/vcpkg-cmake/vcpkg-port-config.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake_x64-linux/share/vcpkg-cmake/copyright
-- Performing post-build validation
Stored binaries in 1 destinations in 3.45 ms.
Elapsed time to handle vcpkg-cmake:x64-linux: 17.2 ms
Installing 2/3 vcpkg-cmake-config:x64-linux...
Building vcpkg-cmake-config:x64-linux...
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake-config_x64-linux/share/vcpkg-cmake-config/vcpkg_cmake_config_fixup.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake-config_x64-linux/share/vcpkg-cmake-config/vcpkg-port-config.cmake
-- Installing: /root/vcpkg_learn/vcpkg/packages/vcpkg-cmake-config_x64-linux/share/vcpkg-cmake-config/copyright
-- Performing post-build validation
Stored binaries in 1 destinations in 2.62 ms.
Elapsed time to handle vcpkg-cmake-config:x64-linux: 15.9 ms
Installing 3/3 cryptopp:x64-linux...
Building cryptopp:x64-linux...
-- Downloading https://github.com/abdes/cryptopp-cmake/archive/f857b775bcb4ff24e4993d85cce811587f8b0616.tar.gz -> abdes-cryptopp-cmake-f857b775bcb4ff24e4993d85cce811587f8b0616.tar.gz...
-- Extracting source /root/vcpkg_learn/vcpkg/downloads/abdes-cryptopp-cmake-f857b775bcb4ff24e4993d85cce811587f8b0616.tar.gz
-- Applying patch fix-git-branch.patch
-- Using source at /root/vcpkg_learn/vcpkg/buildtrees/cryptopp/src/587f8b0616-6acbde05eb.clean
-- Downloading https://github.com/weidai11/cryptopp/archive/4d0cad5401d1a2c998b314bc89288c9620d3021d.tar.gz -> weidai11-cryptopp-4d0cad5401d1a2c998b314bc89288c9620d3021d.tar.gz...
-- Extracting source /root/vcpkg_learn/vcpkg/downloads/weidai11-cryptopp-4d0cad5401d1a2c998b314bc89288c9620d3021d.tar.gz
-- Applying patch patch.patch
-- Using source at /root/vcpkg_learn/vcpkg/buildtrees/cryptopp/src/9620d3021d-0989fd3960.clean
-- Found external ninja('1.10.2').
-- Configuring x64-linux
-- Building x64-linux-dbg
-- Building x64-linux-rel
-- Fixing pkgconfig file: /root/vcpkg_learn/vcpkg/packages/cryptopp_x64-linux/lib/pkgconfig/cryptopp.pc
-- Fixing pkgconfig file: /root/vcpkg_learn/vcpkg/packages/cryptopp_x64-linux/debug/lib/pkgconfig/cryptopp.pc
-- Performing post-build validation
Stored binaries in 1 destinations in 2.2 s.
Elapsed time to handle cryptopp:x64-linux: 1.2 min
Total install time: 1.2 min
cryptopp provides CMake targets:
# this is heuristically generated, and may not be correct
find_package(cryptopp CONFIG REQUIRED)
target_link_libraries(main PRIVATE cryptopp::cryptopp)
可以看到,依赖库安装在了项目目录的vcpkg/packages/
里面。
列出已经安装的开源库:
[root@localhost vcpkg]# ./vcpkg list
cryptopp:x64-linux 8.8.0 Crypto++ is a free C++ class library of cryptogr...
vcpkg-cmake-config:x64-linux 2022-02-06#1
vcpkg-cmake:x64-linux 2023-05-04
使用cryptopp,修改CMakeLists.txt
:
cmake_minimum_required(VERSION 3.23)
set(CMAKE_CXX_STANDARD 14)
if(NOT DEFINED URL_BASE)
set(URL_BASE "github.com")
endif()
list(APPEND CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake)
set(VERSION "3.4.0")
set(VERSION_SUFFIX "")
# vcpkg init
if(NOT DEFINED CMAKE_TOOLCHAIN_FILE)
find_package(Git REQUIRED)
execute_process(COMMAND ${GIT_EXECUTABLE} submodule update --init --recursive -- vcpkg WORKING_DIRECTORY ${CMAKE_SOURCE_DIR})
set(CMAKE_TOOLCHAIN_FILE "${CMAKE_CURRENT_SOURCE_DIR}/vcpkg/scripts/buildsystems/vcpkg.cmake"
CACHE STRING "Vcpkg toolchain file")
endif()
project(vcpkg_learn)
find_package(cryptopp CONFIG REQUIRED)
add_executable(vcpkg_learn main.cpp)
target_link_libraries(vcpkg_learn PRIVATE cryptopp::cryptopp)
加载项目:
# 进入项目根目录
cd vcpkg_learn
# 加载
cmake -DCMAKE_BUILD_TYPE=Debug -DCMAKE_MAKE_PROGRAM=ninja -G Ninja -S . -B ./cmake-build-debug
是可以加载通过的。
接下来修改代码,main.cpp
:
//
// Created by root on 23-8-22.
//
#include <iostream>
#include <cryptopp/eccrypto.h>
#include <cryptopp/osrng.h>
#include <cryptopp/hex.h>
#include <cryptopp/oids.h>
void printPrivateKey(const CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PrivateKey &privateKey);
void printPublicKey(const CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PublicKey &publicKey);
int main() {
CryptoPP::AutoSeededRandomPool rng;
// 生成ECDSA密钥对
CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PrivateKey privateKey;
privateKey.Initialize(rng, CryptoPP::ASN1::secp256r1());
CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PublicKey publicKey;
privateKey.MakePublicKey(publicKey);
// 输出密钥对
printPrivateKey(privateKey);
printPublicKey(publicKey);
return 0;
}
void printPrivateKey(const CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PrivateKey &privateKey) {
std::string privateKeyStr;
CryptoPP::HexEncoder privateKeyEncoder(new CryptoPP::StringSink(privateKeyStr));
privateKey.Save(privateKeyEncoder);
privateKeyEncoder.MessageEnd();
std::cout << "Private Key (hex): 0x" << privateKeyStr << std::endl;
}
void printPublicKey(const CryptoPP::ECDSA<CryptoPP::ECP, CryptoPP::SHA256>::PublicKey &publicKey) {
std::string publicKeyStr;
CryptoPP::HexEncoder publicKeyEncoder(new CryptoPP::StringSink(publicKeyStr));
publicKey.Save(publicKeyEncoder);
publicKeyEncoder.MessageEnd();
std::cout << "Public Key (hex): 0x" << publicKeyStr << std::endl;
}
加载项目:
# 进入项目根目录
cd vcpkg_learn
# 加载
cmake -DCMAKE_BUILD_TYPE=Debug -DCMAKE_MAKE_PROGRAM=ninja -G Ninja -S . -B ./cmake-build-debug
编译代码:
cmake --build ./cmake-build-debug --target vcpkg_learn -j $(nproc)
执行:
./vcpkg_learn
执行结果:
Private Key (hex): 0x3041020100301306072A8648CE3D020106082A8648CE3D030107042730250201010420B3548E997C3FF239C8348CFED8CD49F9845C12DBB87ADBCD886F6C9653EECCEA
Public Key (hex): 0x3059301306072A8648CE3D020106082A8648CE3D03010703420004D948F253F02CD9EEF933842DF824989EC82EBAD3FAB1EB783660A00704E80EF5CBDAF1E959FAFA800724263E4B0D6F975B646C01B4DDAFAB01AA7F3A9280300A
使用vcpkg清单 - vcpkg.json
类似于NodeJS的package.json、python的requirements.txt、maven的pom.xml、golang的go.mod等,vcpkg也提供了一个文件vcpkg.json用于声明项目依赖。
目前vcpkg似乎还不支持初始化一个空的vcpkg.json或者根据当前项目自动生成vcpkg.json。
文档:https://learn.microsoft.com/en-us/vcpkg/reference/vcpkg-json
在项目根目录下创建vcpkg.json
:
{
"name": "vcpkgexample",
"version-string": "0.0.1",
"description": "vcpkg example",
"dependencies": [
{
"name": "vcpkg-cmake",
"host": true
},
{
"name": "vcpkg-cmake-config",
"host": true
},
"cryptopp"
]
}
这样一来,在cmake加载项目的时候,就会自动下载依赖,并编译为我们所用。
到目前为止,项目可在GitHub中下载:Fu-XDU/vcpkg-example at 332a29
CMake FetchContent使用
如果有一个库使用vcpkg搜不到,要怎么依赖呢?可以使用CMake FetchContent去自动下载依赖。
CMake FetchContent不再是vcpkg的内容,移步文章:CMake FetchContent使用 - 小木槌