Bài 38.228 phút đọc
Build type, tùy chọn, phụ thuộc
Sau bài này bạn sẽ làm được
- Cấu hình build type và cờ theo từng type
- Thêm một option bật tắt sanitizer
- Sinh compile_commands.json cho công cụ
- Kéo một phụ thuộc bằng FetchContent
CMake không dùng biến theo mục tiêu như Make. Thay vào đó nó có build type, tuỳ chọn bật tắt, và một hệ quản lý phụ thuộc kéo được thư viện từ internet. Bài này lắp ba thứ đó vào dự án ở bài trước.
#Build type
Cấu hình cờ theo build type
if(NOT CMAKE_BUILD_TYPE)
set(CMAKE_BUILD_TYPE Debug) # mac dinh Debug neu khong chon
endif()
set(CMAKE_C_FLAGS_DEBUG "-g3 -O0 -DDEBUG")
set(CMAKE_C_FLAGS_RELEASE "-O2 -DNDEBUG")
set(CMAKE_C_FLAGS_RELWITHDEBINFO "-O2 -g -DNDEBUG")
set(CMAKE_C_FLAGS_MINSIZEREL "-Os -DNDEBUG")terminal
# Chon build type luc CAU HINH, khong phai luc dung
cmake -S . -B build -G "MinGW Makefiles" -DCMAKE_BUILD_TYPE=Debug
cmake --build build
[100%] Built target app
| Build type | Cờ điển hình | Dùng khi |
|---|---|---|
| Debug | -g3 -O0 | Phát triển, gỡ lỗi |
| Release | -O2 -DNDEBUG | Phát hành |
| RelWithDebInfo | -O2 -g -DNDEBUG | Phát hành nhưng vẫn gỡ lỗi được khi sập |
| MinSizeRel | -Os -DNDEBUG | Hệ nhúng, tối ưu kích thước |
#Tùy chọn
Một tuỳ chọn bật tắt sanitizer
option(ENABLE_ASAN "Bat AddressSanitizer" OFF)
if(ENABLE_ASAN)
target_compile_options(app PRIVATE -fsanitize=address,undefined)
target_link_options(app PRIVATE -fsanitize=address,undefined)
endif()terminal
# Bat tuy chon bang -D khi cau hinh
cmake -S . -B build-asan -G "MinGW Makefiles" -DENABLE_ASAN=ON
cmake --build build-asan --target app
ld.exe: cannot find -lasan ld.exe: cannot find -lubsan collect2.exe: error: ld returned 1 exit status
#compile_commands.json
terminal
# Mot dong, sinh co so du lieu bien dich cho cong cu
cmake -S . -B build -G "MinGW Makefiles" -DCMAKE_EXPORT_COMPILE_COMMANDS=ON
head -8 build/compile_commands.json
[
{
"directory": ".../build",
"command": "gcc.exe ... -std=c17 -Wall -Wextra -o CMakeFiles/toan.dir/src/toan.c.obj -c .../src/toan.c",
"file": ".../src/toan.c",
"output": "CMakeFiles/toan.dir/src/toan.c.obj"
},#FetchContent
Kéo một thư viện từ internet
include(FetchContent)
FetchContent_Declare(unity
GIT_REPOSITORY https://github.com/ThrowTheSwitch/Unity.git
GIT_TAG v2.6.0 # GHIM phien ban cu the, khong dung nhanh
)
FetchContent_MakeAvailable(unity)
# Bay gio dung unity nhu mot target binh thuong:
target_link_libraries(test_toan PRIVATE unity)FetchContent
Cơ chế của CMake để tải mã nguồn của một phụ thuộc lúc cấu hình, dựng nó cùng dự án của bạn. Khác với cài thư viện lên hệ thống: phụ thuộc nằm trong thư mục dựng, phiên bản ghim trong
CMakeLists.txt, nên mọi người dựng cùng một phiên bản.#Preset
CMakePresets.json, lưu cấu hình thành tên
{
"version": 3,
"configurePresets": [
{
"name": "debug",
"generator": "Ninja",
"binaryDir": "build/debug",
"cacheVariables": {
"CMAKE_BUILD_TYPE": "Debug",
"ENABLE_ASAN": "ON"
}
},
{
"name": "release",
"generator": "Ninja",
"binaryDir": "build/release",
"cacheVariables": { "CMAKE_BUILD_TYPE": "Release" }
}
]
}terminal
# Thay vi go dong -D dai, dung ten preset
cmake --preset debug
cmake --build build/debug
cmake --preset release && cmake --build build/release
Tự làm thử
- Cấu hình dự án của bạn với
DebugvàReleasevào hai thư mục khác nhau. - Thêm một
optionbật LTO và kiểm tra cờ xuất hiện trong lệnh dịch. - Sinh
compile_commands.jsonvà mở nó để đọc lệnh dịch một tệp. - Xác nhận cờ
-stdlàc17chứ khônggnu17trong tệp đó. - Trên máy có mạng, dùng
FetchContentkéo một thư viện kiểm thử. - Viết một
CMakePresets.jsonvới hai preset và dùng chúng.
Trình chấm điểm tự động sẽ được bổ sung ở giai đoạn sau. Hiện tại bạn tự chạy thử trên máy.
Tóm tắt
- Build type chọn cờ và chọn lúc cấu hình; một thư mục dựng cho mỗi type.
optioncho người dùng bật tắt tính năng từ dòng lệnh bằng-D.CMAKE_EXPORT_COMPILE_COMMANDS=ONsinhcompile_commands.jsoncho clang-tidy, clangd, và các công cụ khác.FetchContenttải mã phụ thuộc lúc cấu hình với phiên bản ghim;find_packagedùng thư viện đã cài.CMakePresets.jsonlưu cấu hình thành tên để cả đội và CI dùng giống nhau.