-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathCMakeLists.txt
More file actions
325 lines (261 loc) · 13.3 KB
/
CMakeLists.txt
File metadata and controls
325 lines (261 loc) · 13.3 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
# 3.13支持LINK_FLAGS, 3.15支持CMAKE_MSVC_RUNTIME_LIBRARY
cmake_minimum_required(VERSION 3.15 FATAL_ERROR)
# ---------------------------------------------------------------------------------------
# Start project
# ---------------------------------------------------------------------------------------
include(CheckSymbolExists)
# include(cmake/ide.cmake)
include(cmake/compiler_warnings.cmake)
include(cmake/macros.cmake)
include(cmake/utility.cmake)
prj_extract_version() # <-- extract PRJ_VERSION variable from src/version.h
project(my_prj VERSION ${PRJ_VERSION} LANGUAGES C CXX)
message(STATUS "PROJECT => ${PROJECT_NAME} : ${PROJECT_VERSION}")
# include(GNUInstallDirs)
set(CMAKE_VERBOSE_MAKEFILE ON)
set(CMAKE_COLOR_MAKEFILE ON)
# default we enable it on below.
# set(CMAKE_POSITION_INDEPENDENT_CODE ON)
# show version of toochain.
prj_show_toolchain_version()
# ---------------------------------------------------------------------------------------
# Compiler config
# ---------------------------------------------------------------------------------------
if(NOT CMAKE_C_STANDARD)
message(STATUS "now define CMAKE_C_STANDARD for project")
set(CMAKE_C_STANDARD 11)
set(CMAKE_C_STANDARD_REQUIRED ON)
endif()
if(NOT CMAKE_CXX_STANDARD)
message(STATUS "now define CMAKE_CXX_STANDARD for project")
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
endif()
set(PRJ_C_STANDARD ${CMAKE_C_STANDARD})
set(PRJ_CXX_STANDARD ${CMAKE_CXX_STANDARD})
message(STATUS "PRJ_C_STANDARD=${PRJ_C_STANDARD}, PRJ_CXX_STANDARD=${PRJ_CXX_STANDARD}")
# ---------------------------------------------------------------------------------------
# Set PRJ_MASTER_PROJECT to ON if we are building this project
# ---------------------------------------------------------------------------------------
# Check if project is being used directly or via add_subdirectory, but allow overriding
if(NOT DEFINED PRJ_MASTER_PROJECT)
# CMAKE_CURRENT_SOURCE_DIR:这个变量表示当前正在处理的 CMakeLists.txt 文件所在的源代码目录。例如,如果有一个子目录中的 CMakeLists.txt 文件被读取和处理,那么 CMAKE_CURRENT_SOURCE_DIR 会指向这个子目录。
# CMAKE_SOURCE_DIR:此变量代表最外层的 CMakeLists.txt 文件所在的源代码目录。换句话说,这是项目源代码的根目录
if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR)
set(PRJ_MASTER_PROJECT ON)
else()
set(PRJ_MASTER_PROJECT OFF)
endif()
endif()
message(STATUS "PRJ_MASTER_PROJECT => ${PRJ_MASTER_PROJECT}")
# ---------------------------------------------------------------------------------------
# Set default build type to release
# ---------------------------------------------------------------------------------------
if(NOT CMAKE_BUILD_TYPE)
set(CMAKE_BUILD_TYPE "Release" CACHE STRING "Choose Release or Debug" FORCE)
endif()
message(STATUS "CMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}")
# ---------------------------------------------------------------------------------------
# detect platform / abi, and setup output dir.
# ---------------------------------------------------------------------------------------
# 项目根目录, 用于sub_dir下的cmake去获取使用。
set(PRJ_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR} CACHE STRING "")
# 第三方库目录,存放第三方库/头文件/资源
set(PRJ_THIRD_PARTY_DIR "${PRJ_SOURCE_DIR}/src/third_party" CACHE STRING "")
# 项目通用 include 目录(所有模块都可以访问的头文件目录), 可以支持配置多个
set(PRJ_COMMON_INCLUDE_DIRS ${PRJ_SOURCE_DIR}/src CACHE STRING "")
# 项目编译输出文件夹
set(PRJ_OUTPUT_DIR ${PRJ_SOURCE_DIR}/tool/deploy CACHE STRING "")
# The IDE folder for Project that will be used
# if Project is included in a CMake project that sets.
# set_property(GLOBAL PROPERTY USE_FOLDERS ON)
# For example, Visual Studio supports folders.
set(PRJ_IDE_FOLDER ${PRJ_OUTPUT_DIR} CACHE STRING "")
message(STATUS "root of project: PRJ_SOURCE_DIR => ${PRJ_SOURCE_DIR}")
# ---------------------------------------------------------------------------------------
# now we can include platform_detector.cmake,
# because we have defined PRJ_SOURCE_DIR/PRJ_OUTPUT_DIR.
# ---------------------------------------------------------------------------------------
include(cmake/platform_detector.cmake)
# make sure __cplusplus is defined when using msvc and enable parallel build
if(MSVC)
string(APPEND CMAKE_CXX_FLAGS " /Zc:__cplusplus /MP")
endif()
#
# This property specifies whether compiler specific extensions should be used.
# For some compilers, this results in adding a flag such as -std=gnu++11 instead of -std=c++11 to the compile line.
# This property is ON by default. The basic C++ standard level is controlled by the CXX_STANDARD target property.
#
# here we disable it.
#
set(CMAKE_CXX_EXTENSIONS OFF)
if(CMAKE_SYSTEM_NAME MATCHES "CYGWIN" OR CMAKE_SYSTEM_NAME MATCHES "MSYS")
set(CMAKE_CXX_EXTENSIONS ON)
endif()
# ---------------------------------------------------------------------------------------
# setup PRJ_REPO_BRANCH / PRJ_REPO_REVISION, and also add_definitions to code.
# ---------------------------------------------------------------------------------------
prj_setup_repo_info(${PRJ_SOURCE_DIR})
# ---------------------------------------------------------------------------------------
# Build options
# ---------------------------------------------------------------------------------------
# build all in one option
option(PRJ_BUILD_ALL_IN_ONE "Build all in one library" ON)
# build shared option
option(PRJ_BUILD_SHARED "Build shared library" OFF)
option(BUILD_SHARED_LIBS "Build shared library, alias for PRJ_BUILD_SHARED" ${PRJ_BUILD_SHARED})
if(PRJ_BUILD_SHARED OR BUILD_SHARED_LIBS)
set(PRJ_BUILD_SHARED ON)
set(BUILD_SHARED_LIBS ON)
endif()
# testing options
option(PRJ_BUILD_TESTS "Build tests" OFF)
# not used at current now.
option(PRJ_MINIMIZE "Minimize project library size for mobile deploy" OFF)
# precompiled headers option
option(PRJ_ENABLE_PCH "Build static or shared library using precompiled header to speed up compilation time" OFF)
# build position independent code, default ON
option(PRJ_BUILD_PIC "Build position independent code (-fPIC)" ON)
# =================== ASan options start ======================================
set(_DEFAULT_ASAN OFF)
if(PRJ_MASTER_PROJECT AND(CMAKE_BUILD_TYPE STREQUAL "Debug"))
set(_DEFAULT_ASAN ON)
endif()
# ASan: address sanitizer options
option(PRJ_ENABLE_ASAN "Enable address sanitizer in tests" ${_DEFAULT_ASAN})
if(PRJ_ENABLE_ASAN)
if(MSVC AND("${MSVC_VERSION}" VERSION_LESS "1929"))
message(STATUS "ASan begin supported from msvc 2019(16.9), but yours MSVC_VERSION=${MSVC_VERSION}, so disabled ASan.")
set(PRJ_ENABLE_ASAN OFF)
else()
add_compile_definitions(PRJ_ENABLE_ASAN=1)
endif()
endif(PRJ_ENABLE_ASAN)
# =================== ASan options end ======================================
# warning options
option(PRJ_BUILD_WARNINGS "Enable compiler warnings" OFF)
# install options
option(PRJ_INSTALL "Generate the install target" ${PRJ_MASTER_PROJECT})
# for export all symbols on windows, usually we use "exports.def" file to declare exported symbols.
# cmake -DCMAKE_WINDOWS_EXPORT_ALL_SYMBOLS=TRUE -DBUILD_SHARED_LIBS=TRUE
option(CMAKE_WINDOWS_EXPORT_ALL_SYMBOLS "export dll ALL_SYMBOLS on windows" OFF)
# third_party lib shared options: if ON, use third_party shared lib.
option(PRJ_THIRD_LIB_SHARED "use shared lib on third_party" OFF)
message(STATUS "PRJ_THIRD_LIB_SHARED=${PRJ_THIRD_LIB_SHARED}")
# =================== PRJ_HIDDEN_SYMBOLS options start ======================================
if(PRJ_MASTER_PROJECT AND NOT(CMAKE_BUILD_TYPE STREQUAL "Debug"))
set(_DEFAULT_HIDDEN_SYMBOLS ON)
else()
set(_DEFAULT_HIDDEN_SYMBOLS OFF)
endif()
# hidden symbols options
option(PRJ_HIDDEN_SYMBOLS "Hidden internal c/cxx symbols" ${_DEFAULT_HIDDEN_SYMBOLS})
# =================== PRJ_HIDDEN_SYMBOLS options end ======================================
# clang-tidy
if(${CMAKE_VERSION} VERSION_GREATER "3.5")
option(PRJ_TIDY "run clang-tidy" OFF)
endif()
if(PRJ_TIDY)
set(CMAKE_CXX_CLANG_TIDY "clang-tidy")
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
message(STATUS "Enabled clang-tidy")
endif()
if(PRJ_BUILD_PIC)
set(CMAKE_POSITION_INDEPENDENT_CODE ON)
endif()
# ---------------------------------------------------------------------------------------
# CMAKE_C_VISIBILITY_PRESET , setup visibility for C symbols
# CMAKE_CXX_VISIBILITY_PRESET , setup visibility for C++ symbols
# CMAKE_VISIBILITY_INLINES_HIDDEN , setup visibility for inline functions
# ---------------------------------------------------------------------------------------
if(PRJ_HIDDEN_SYMBOLS)
if(NOT DEFINED CMAKE_C_VISIBILITY_PRESET)
set_verbose(CMAKE_C_VISIBILITY_PRESET hidden CACHE STRING
"Preset for the export c of private symbols")
set_property(CACHE CMAKE_C_VISIBILITY_PRESET PROPERTY STRINGS
hidden default)
endif()
if(NOT DEFINED CMAKE_CXX_VISIBILITY_PRESET)
set_verbose(CMAKE_CXX_VISIBILITY_PRESET hidden CACHE STRING
"Preset for the export cxx of private symbols")
set_property(CACHE CMAKE_CXX_VISIBILITY_PRESET PROPERTY STRINGS
hidden default)
endif()
if(NOT DEFINED CMAKE_VISIBILITY_INLINES_HIDDEN)
set_verbose(CMAKE_VISIBILITY_INLINES_HIDDEN ON CACHE BOOL
"Whether to add a compile flag to hide symbols of inline functions")
endif()
endif()
message(STATUS " CMAKE_C_VISIBILITY_PRESET=${CMAKE_C_VISIBILITY_PRESET}")
message(STATUS " CMAKE_CXX_VISIBILITY_PRESET=${CMAKE_CXX_VISIBILITY_PRESET}")
message(STATUS " CMAKE_VISIBILITY_INLINES_HIDDEN=${CMAKE_VISIBILITY_INLINES_HIDDEN}")
# ---------------------------------------------------------------------------------------
# cxx_variadic_templates: 在 C++11 中,引入了可变模板(Variadic Templates)的概念,
# 它允许函数或类模板接受可变数量的类型参数
# ---------------------------------------------------------------------------------------
list(FIND CMAKE_CXX_COMPILE_FEATURES "cxx_variadic_templates" _index_for_cxx_variadic_templates)
if(${_index_for_cxx_variadic_templates} GREATER -1)
# Use cxx_variadic_templates instead of more appropriate cxx_std_11 for
# compatibility with older CMake versions.
set(PRJ_REQUIRED_FEATURES cxx_variadic_templates)
endif()
message(STATUS "Required features: ${PRJ_REQUIRED_FEATURES}")
# ---------------------------------------------------------------------------------------
# auto setup install include dir.
# ---------------------------------------------------------------------------------------
if(DEFINED ${CMAKE_INSTALL_INCLUDEDIR})
message(STATUS "CMAKE_INSTALL_INCLUDEDIR is defined.")
set(_install_include_dir ${CMAKE_INSTALL_INCLUDEDIR})
else()
set(_install_include_dir ${PRJ_OUTPUT_DIR}/inc)
endif()
# PRJ_INC_DIR 是cmake install时头文件安装位置
set_verbose(PRJ_INC_DIR ${_install_include_dir} CACHE STRING
"Installation directory for include files, a relative path that "
"will be joined with ${CMAKE_INSTALL_PREFIX} or an absolute path.")
message(STATUS "INSTALL_INCLUDEDIR=${_install_include_dir} PRJ_INC_DIR=${PRJ_INC_DIR}")
option(PRJ_SYSTEM_HEADERS "Expose headers with marking them as system." OFF)
option(PRJ_PEDANTIC "Enable extra warnings and expensive tests." ON)
option(PRJ_WERROR "Halt the compilation with an error on compiler warnings." OFF)
option(PRJ_INSTALL "Generate the install target." OFF)
set(PRJ_SYSTEM_HEADERS_ATTRIBUTE "")
if(PRJ_SYSTEM_HEADERS)
set(PRJ_SYSTEM_HEADERS_ATTRIBUTE SYSTEM)
endif()
if(PRJ_BUILD_TESTS)
message(STATUS "Generating tests")
enable_testing()
endif()
# if (PRJ_MINIMIZE)
# message(NOTICE "*************************************")
# message(NOTICE "PRJ_MINIMIZE is enabled, prj will limit its functionality to minimize build size:")
# message(NOTICE "*************************************")
#
# set(PRJ_MINIMIZE ON)
# endif()
# ---------------------------------------------------------------------------------------
# set postfix for debug library.
# ---------------------------------------------------------------------------------------
set(PRJ_DEBUG_POSTFIX "" CACHE STRING "Debug library postfix.")
# ---------------------------------------------------------------------------------------
# default PRJ_COMPILE_OPTIONS(for C) and PRJ_CXX_COMPILE_OPTIONS(for CXX)
# ---------------------------------------------------------------------------------------
# PRJ_WERROR: set 1 to treat warning as error.
# macro "get_warnings_copts" on CompilerWarnings.cmake
set(PRJ_COMPILE_OPTIONS "")
set(PRJ_CXX_COMPILE_OPTIONS "")
get_warnings_copts(${PRJ_WERROR} PRJ_COMPILE_OPTIONS PRJ_CXX_COMPILE_OPTIONS)
message(STATUS " PRJ_COMPILE_OPTIONS: ${PRJ_COMPILE_OPTIONS} \n PRJ_CXX_COMPILE_OPTIONS=${PRJ_CXX_COMPILE_OPTIONS}\n")
# import 3rdparty
# add_subdirectory("${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/fmt" EXCLUDE_FROM_ALL)
# set(JSON_BuildTests OFF CACHE INTERNAL "")
# set(JSON_MultipleHeader ON CACHE INTERNAL "")
# add_subdirectory("${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/nlohmann-json" EXCLUDE_FROM_ALL)
# if (NOT ANDROID)
# add_subdirectory("${CMAKE_CURRENT_SOURCE_DIR}/3rdparty/abseil-tiny" EXCLUDE_FROM_ALL)
# endif()
# ---------------------------------------------------------------------------------------
# macros.cmake : define "_PRJ_DEPENDENCY_THIRD_LIBS" and "_PRJ_DEPENDENCY_THIRD_ASSETS"
# ---------------------------------------------------------------------------------------
define_dependency_var()
add_subdirectory("${CMAKE_CURRENT_SOURCE_DIR}/src/")