@@ -53,6 +53,9 @@ cmake_dependent_option(BUILD_WALLET_TOOL "Build bitcoin-wallet tool." ON "ENABLE
53
53
54
54
cmake_dependent_option(CXX20 "Enable compilation in C++20 mode." OFF "NOT MSVC" ON )
55
55
option (THREADLOCAL "Enable features that depend on the C++ thread_local keyword (currently just thread names in debug logs)." ON )
56
+ option (HARDENING "Attempt to harden the resulting executables." ON )
57
+ option (REDUCE_EXPORTS "Attempt to reduce exported symbols in the resulting executables." OFF )
58
+ option (WERROR "Treat compiler warnings as errors." OFF )
56
59
57
60
tristate_option(CCACHE "Use ccache for compiling." "if ccache is found." AUTO)
58
61
tristate_option(WITH_NATPMP "Enable NAT-PMP." "if libnatpmp is found." AUTO)
@@ -66,6 +69,7 @@ tristate_option(WITH_USDT
66
69
67
70
option (BUILD_TESTS "Build test_bitcoin executable." ON )
68
71
option (BUILD_BENCH "Build bench_bitcoin executable." ON )
72
+ option (INSTALL_MAN "Install man pages." ON )
69
73
70
74
if (CXX20)
71
75
set (CMAKE_CXX_STANDARD 20)
@@ -135,10 +139,10 @@ if(WIN32)
135
139
_WINDOWS
136
140
_MT
137
141
)
138
- try_append_linker_flag(core "-static" )
142
+ try_append_linker_flag("-static" TARGET core )
139
143
# We require Windows 7 (NT 6.1) or later.
140
- try_append_linker_flag(core "-Wl,--major-subsystem-version,6" )
141
- try_append_linker_flag(core "-Wl,--minor-subsystem-version,1" )
144
+ try_append_linker_flag("-Wl,--major-subsystem-version,6" TARGET core )
145
+ try_append_linker_flag("-Wl,--minor-subsystem-version,1" TARGET core )
142
146
endif ()
143
147
endif ()
144
148
@@ -157,9 +161,9 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Darwin")
157
161
# These flags are specific to ld64, and may cause issues with other linkers.
158
162
# For example: GNU ld will interpret -dead_strip as -de and then try and use
159
163
# "ad_strip" as the symbol for the entry point.
160
- try_append_linker_flag(core "-Wl,-dead_strip" )
161
- try_append_linker_flag(core "-Wl,-dead_strip_dylibs" )
162
- try_append_linker_flag(core "-Wl,-headerpad_max_install_names" )
164
+ try_append_linker_flag("-Wl,-dead_strip" TARGET core )
165
+ try_append_linker_flag("-Wl,-dead_strip_dylibs" TARGET core )
166
+ try_append_linker_flag("-Wl,-headerpad_max_install_names" TARGET core )
163
167
endif ()
164
168
165
169
if (CMAKE_CROSSCOMPILING )
@@ -212,25 +216,89 @@ else()
212
216
replace_c_flag_in_config(Release -O3 -O2)
213
217
replace_cxx_flag_in_config(Release -O3 -O2)
214
218
215
- set (debug_c_flags "" )
216
- set (debug_cxx_flags "" )
217
- try_append_cxx_flags(debug_cxx_flags "-O0" RESULT_VAR compiler_supports_O0 )
218
- if (compiler_supports_O0 )
219
- string (STRIP " ${debug_c_flags} -O0" debug_c_flags )
219
+ set (debug_flags )
220
+ try_append_cxx_flags( "-O0" VAR debug_flags )
221
+ try_append_cxx_flags("-g3" VAR debug_flags RESULT_VAR compiler_supports_g3 )
222
+ if (NOT compiler_supports_g3 )
223
+ try_append_cxx_flags( "-g" VAR debug_flags )
220
224
endif ()
221
- try_append_cxx_flags(debug_cxx_flags "-g3" RESULT_VAR compiler_supports_g3)
222
- if (compiler_supports_g3)
223
- string (STRIP "${debug_c_flags} -g3" debug_c_flags)
225
+ set (CMAKE_C_FLAGS_DEBUG "${debug_flags} " )
226
+ try_append_cxx_flags("-ftrapv" VAR debug_flags)
227
+ set (CMAKE_CXX_FLAGS_DEBUG "${debug_flags} " )
228
+ unset (debug_flags)
229
+ endif ()
230
+
231
+ include (cmake/optional .cmake)
232
+
233
+ # Don't allow extended (non-ASCII) symbols in identifiers. This is easier for code review.
234
+ try_append_cxx_flags("-fno-extended-identifiers" TARGET core)
235
+
236
+ # Currently all versions of gcc are subject to a class of bugs, see the
237
+ # gccbug_90348 test case (only reproduces on GCC 11 and earlier) and
238
+ # https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111843. To work around that, set
239
+ # -fstack-reuse=none for all gcc builds. (Only gcc understands this flag).
240
+ try_append_cxx_flags("-fstack-reuse=none" TARGET core)
241
+
242
+ if (HARDENING)
243
+ add_library (hardening INTERFACE )
244
+ if (MSVC )
245
+ try_append_linker_flag("/DYNAMICBASE" TARGET hardening)
246
+ try_append_linker_flag("/HIGHENTROPYVA" TARGET hardening)
247
+ try_append_linker_flag("/NXCOMPAT" TARGET hardening)
224
248
else ()
225
- try_append_cxx_flags(debug_cxx_flags "-g" )
226
- string (STRIP "${debug_c_flags} -g" debug_c_flags)
249
+ target_compile_options (hardening INTERFACE
250
+ $<$<NOT :$<CONFIG:Debug>>:-U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=3>
251
+ )
252
+
253
+ try_append_cxx_flags("-Wstack-protector" TARGET hardening)
254
+ try_append_cxx_flags("-fstack-protector-all" TARGET hardening)
255
+ try_append_cxx_flags("-fcf-protection=full" TARGET hardening)
256
+
257
+ if (MINGW)
258
+ # stack-clash-protection doesn't compile with GCC 10 and earlier.
259
+ # In any case, it is a no-op for Windows.
260
+ # See https://gcc.gnu.org/bugzilla/show_bug.cgi?id=90458 for more details.
261
+ else ()
262
+ try_append_cxx_flags("-fstack-clash-protection" TARGET hardening)
263
+ endif ()
264
+
265
+ if (CMAKE_SYSTEM_PROCESSOR STREQUAL "aarch64" OR CMAKE_SYSTEM_PROCESSOR STREQUAL "arm64" )
266
+ try_append_cxx_flags("-mbranch-protection=bti" TARGET hardening)
267
+ endif ()
268
+
269
+ try_append_linker_flag("-Wl,--enable-reloc-section" TARGET hardening)
270
+ try_append_linker_flag("-Wl,--dynamicbase" TARGET hardening)
271
+ try_append_linker_flag("-Wl,--nxcompat" TARGET hardening)
272
+ try_append_linker_flag("-Wl,--high-entropy-va" TARGET hardening)
273
+ try_append_linker_flag("-Wl,-z,relro" TARGET hardening)
274
+ try_append_linker_flag("-Wl,-z,now" TARGET hardening)
275
+ try_append_linker_flag("-Wl,-z,separate-code" TARGET hardening)
276
+ if (CMAKE_SYSTEM_NAME STREQUAL "Darwin" )
277
+ try_append_linker_flag("-Wl,-bind_at_load" TARGET hardening)
278
+ try_append_linker_flag("-Wl,-fixup_chains" TARGET hardening)
279
+ endif ()
227
280
endif ()
228
- try_append_cxx_flags(debug_cxx_flags "-ftrapv" )
229
- set (CMAKE_C_FLAGS_DEBUG "${debug_c_flags} " )
230
- set (CMAKE_CXX_FLAGS_DEBUG "${debug_cxx_flags} " )
281
+ target_link_libraries (core INTERFACE hardening)
231
282
endif ()
232
283
233
- include (cmake/optional .cmake)
284
+ if (REDUCE_EXPORTS)
285
+ set (CMAKE_CXX_VISIBILITY_PRESET hidden)
286
+ set (CMAKE_VISIBILITY_INLINES_HIDDEN 1)
287
+ try_append_linker_flag("-Wl,--exclude-libs,ALL" TARGET core)
288
+ endif ()
289
+
290
+ if (WERROR)
291
+ if (MSVC )
292
+ set (werror_flag "/WX" )
293
+ else ()
294
+ set (werror_flag "-Werror" )
295
+ endif ()
296
+ try_append_cxx_flags(${werror_flag} TARGET core RESULT_VAR compiler_supports_werror)
297
+ if (NOT compiler_supports_werror)
298
+ message (FATAL_ERROR "WERROR set but ${werror_flag} is not usable." )
299
+ endif ()
300
+ unset (werror_flag)
301
+ endif ()
234
302
235
303
find_package (Python3 3.9 COMPONENTS Interpreter)
236
304
set (PYTHON_COMMAND ${Python3_EXECUTABLE} )
@@ -279,25 +347,16 @@ message("C++ compiler .......................... ${CMAKE_CXX_COMPILER}")
279
347
list (JOIN DEPENDS_CXX_COMPILER_FLAGS " " depends_cxx_flags)
280
348
string (STRIP "${CMAKE_CXX_FLAGS} ${depends_cxx_flags} " combined_cxx_flags)
281
349
message ("CXXFLAGS .............................. ${combined_cxx_flags} " )
282
- get_target_property (common_compile_options core INTERFACE_COMPILE_OPTIONS)
283
- if (common_compile_options)
284
- list (JOIN common_compile_options " " common_compile_options)
285
- else ()
286
- set (common_compile_options)
287
- endif ()
288
- string (GENEX_STRIP "${common_compile_options} " common_compile_options)
350
+ get_target_interface(common_compile_options core COMPILE_OPTIONS)
289
351
message ("Common compile options ................ ${common_compile_options} " )
290
- get_target_property (common_link_options core INTERFACE_LINK_OPTIONS)
291
- if (common_link_options)
292
- list (JOIN common_link_options " " common_link_options)
293
- else ()
294
- set (common_link_options)
295
- endif ()
352
+ get_target_interface(common_link_options core LINK_OPTIONS)
296
353
message ("Common link options ................... ${common_link_options} " )
297
354
message ("Linker flags for executables .......... ${CMAKE_EXE_LINKER_FLAGS} " )
298
355
message ("Linker flags for shared libraries ..... ${CMAKE_SHARED_LINKER_FLAGS} " )
299
356
print_config_flags()
300
357
message ("Use assembly routines ................. ${ASM} " )
358
+ message ("Attempt to harden executables ......... ${HARDENING} " )
359
+ message ("Treat compiler warnings as errors ..... ${WERROR} " )
301
360
message ("Use ccache for compiling .............. ${CCACHE} " )
302
361
message ("\n " )
303
362
if (configure_warnings)
0 commit comments