From f64ebfd4d8e59ec3c0d3a63ce4a23acbf0019858 Mon Sep 17 00:00:00 2001 From: 12345qiupeng Date: Sat, 4 Oct 2025 12:04:44 +0800 Subject: [PATCH] =?UTF-8?q?feat:=E4=BF=AE=E6=AD=A3boost=E9=AB=98=E7=89=88?= =?UTF-8?q?=E6=9C=AC=E9=97=AE=E9=A2=98=EF=BC=8C=E4=B8=8D=E5=86=8D=E4=BD=BF?= =?UTF-8?q?=E7=94=A8system=E5=8C=85?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- cmake/HandleBoost.cmake | 95 ++++++++++++++++++++++++++++------------- 1 file changed, 66 insertions(+), 29 deletions(-) diff --git a/cmake/HandleBoost.cmake b/cmake/HandleBoost.cmake index 03251126e..a45326cfe 100644 --- a/cmake/HandleBoost.cmake +++ b/cmake/HandleBoost.cmake @@ -6,51 +6,88 @@ # Boost_NO_SYSTEM_PATHS: set to true to keep the find script from ignoring BOOST_ROOT if(MSVC) - # By default, boost only builds static libraries on windows - set(Boost_USE_STATIC_LIBS ON) # only find static libs - # If we ever reset above on windows and, ... - # If we use Boost shared libs, disable auto linking. - # Some libraries, at least Boost Program Options, rely on this to export DLL symbols. + set(Boost_USE_STATIC_LIBS ON) if(NOT Boost_USE_STATIC_LIBS) list_append_cache(GTSAM_COMPILE_DEFINITIONS_PUBLIC BOOST_ALL_NO_LIB BOOST_ALL_DYN_LINK) endif() - # Virtual memory range for PCH exceeded on VS2015 - if(MSVC_VERSION LESS 1910) # older than VS2017 - list_append_cache(GTSAM_COMPILE_OPTIONS_PRIVATE -Zm295) + if(MSVC_VERSION LESS 1910) + list_append_cache(GTSAM_COMPILE_OPTIONS_PRIVATE -Zm295) endif() endif() +# ---- 关键修改:强制使用 FindBoost 模块模式,而不是 CONFIG 模式 ---- +set(Boost_NO_BOOST_CMAKE ON CACHE BOOL "Use FindBoost module mode" FORCE) -# Store these in variables so they are automatically replicated in GTSAMConfig.cmake and such. +# 允许多线程库(照旧) +set(Boost_USE_MULTITHREADED ON) + +# 最低版本 set(BOOST_FIND_MINIMUM_VERSION 1.65) -set(BOOST_FIND_MINIMUM_COMPONENTS serialization system filesystem thread program_options date_time timer chrono regex) -find_package(Boost ${BOOST_FIND_MINIMUM_VERSION} COMPONENTS ${BOOST_FIND_MINIMUM_COMPONENTS} REQUIRED) +# ---- 关键修改:按版本决定是否需要 system 组件 ---- +set(BOOST_FIND_MINIMUM_COMPONENTS + serialization filesystem thread program_options date_time timer chrono regex +) -# Required components -if(NOT Boost_SERIALIZATION_LIBRARY OR NOT Boost_SYSTEM_LIBRARY OR NOT Boost_FILESYSTEM_LIBRARY OR - NOT Boost_THREAD_LIBRARY OR NOT Boost_DATE_TIME_LIBRARY) - message(FATAL_ERROR "Missing required Boost components >= v1.65, please install/upgrade Boost or configure your search paths.") +# 只有旧版 Boost (< 1.69) 需要 system;>=1.69 为 header-only,不再要求 +# 注意:Boost_VERSION 是 find_package 之后才有的,这里用一个预探测逻辑: +# 先尝试不带 system;失败再带上 system 尝试一次(兼容极老环境)。 +# 也可以用工具链变量提前注入 Boost_VERSION,这里采用两段式最稳妥。 + +# 第一次尝试:不含 system(适配 Boost>=1.69) +message(STATUS "Trying Boost without 'system' component first (>=1.69 header-only)...") +set(_boost_try_components ${BOOST_FIND_MINIMUM_COMPONENTS}) +set(_boost_found FALSE) +find_package(Boost ${BOOST_FIND_MINIMUM_VERSION} COMPONENTS ${_boost_try_components} QUIET) +if(Boost_FOUND) + set(_boost_found TRUE) +else() + # 第二次尝试:加入 system(兼容 Boost<1.69) + message(STATUS "Retrying Boost with 'system' component for older Boost (<1.69)...") + list(APPEND _boost_try_components system) + find_package(Boost ${BOOST_FIND_MINIMUM_VERSION} COMPONENTS ${_boost_try_components} REQUIRED) endif() +# 记录最终组件集合 +set(BOOST_FIND_MINIMUM_COMPONENTS ${_boost_try_components}) + +# ---- 必要组件检查(按最终集合判断),不要无条件检查 Boost_SYSTEM_LIBRARY ---- +set(_missing_required FALSE) +foreach(_comp IN LISTS BOOST_FIND_MINIMUM_COMPONENTS) + string(TOUPPER "${_comp}" _COMP_UP) + if(NOT DEFINED "Boost_${_COMP_UP}_LIBRARY" AND NOT TARGET "Boost::${_comp}") + # 某些组件(如 header-only)可能没有 *_LIBRARY 变量,但会有导入目标或仅头文件 + # 对 header-only 的 system(>=1.69)这里不会要求 + message(STATUS "Note: Boost component '${_comp}' has no explicit *_LIBRARY var; relying on imported target or headers.") + endif() +endforeach() + +# ---- 计时接口选择,与原逻辑一致 ---- option(GTSAM_DISABLE_NEW_TIMERS "Disables using Boost.chrono for timing" OFF) -# Allow for not using the timer libraries on boost < 1.48 (GTSAM timing code falls back to old timer library) + +# ---- 链接库列表(不再无条件包含 Boost::system)---- set(GTSAM_BOOST_LIBRARIES - Boost::serialization - Boost::system - Boost::filesystem - Boost::thread - Boost::date_time - Boost::regex + Boost::serialization + Boost::filesystem + Boost::thread + Boost::date_time + Boost::regex ) + +# 如果最终组件包含 chrono/timer,则追加 +if(TARGET Boost::chrono) + list(APPEND GTSAM_BOOST_LIBRARIES Boost::chrono) +endif() +if(TARGET Boost::timer) + list(APPEND GTSAM_BOOST_LIBRARIES Boost::timer) +endif() + +# 仅当真的找了 system(即老版本 Boost)时才链接 Boost::system +if("system" IN_LIST BOOST_FIND_MINIMUM_COMPONENTS AND TARGET Boost::system) + list(APPEND GTSAM_BOOST_LIBRARIES Boost::system) +endif() + if (GTSAM_DISABLE_NEW_TIMERS) message("WARNING: GTSAM timing instrumentation manually disabled") list_append_cache(GTSAM_COMPILE_DEFINITIONS_PUBLIC DGTSAM_DISABLE_NEW_TIMERS) -else() - if(Boost_TIMER_LIBRARY) - list(APPEND GTSAM_BOOST_LIBRARIES Boost::timer Boost::chrono) - else() - list(APPEND GTSAM_BOOST_LIBRARIES rt) # When using the header-only boost timer library, need -lrt - message("WARNING: GTSAM timing instrumentation will use the older, less accurate, Boost timer library because boost older than 1.48 was found.") - endif() endif()