From b57e45713a4d53afb3746f89f3957fe092c9444f Mon Sep 17 00:00:00 2001 From: fruffy Date: Fri, 10 May 2024 15:01:29 -0400 Subject: [PATCH] Depend on Boost using FetchContent instead of relying on system-provided Boost. Signed-off-by: fruffy --- CMakeLists.txt | 19 ++----- backends/graphs/CMakeLists.txt | 5 +- cmake/Boost.cmake | 93 ++++++++++++++++++++++++++++++++++ ir/CMakeLists.txt | 2 +- lib/CMakeLists.txt | 1 + tools/ci-build.sh | 3 -- tools/install_mac_deps.sh | 7 --- 7 files changed, 102 insertions(+), 28 deletions(-) create mode 100644 cmake/Boost.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 89acddc6872..9ff196a03eb 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -153,10 +153,6 @@ if(STATIC_BUILD_WITH_DYNAMIC_GLIBC OR STATIC_BUILD_WITH_DYNAMIC_STDLIB) endif() set(BUILD_SHARED_LIBS OFF) set(CMAKE_FIND_LIBRARY_SUFFIXES .a) - # Link Boost statically - # See https://cmake.org/cmake/help/latest/module/FindBoost.html for details - set(Boost_USE_STATIC_LIBS ON) - set(Boost_USE_STATIC_RUNTIME OFF) # Set the static variable set(P4C_STATIC_BUILD STATIC) # TODO: We can not use -static here because of compilation and portability problems: @@ -205,19 +201,13 @@ p4c_obtain_abseil() include(Protobuf) p4c_obtain_protobuf() +include(Boost) +p4c_obtain_boost() + # We require -pthread to make std::call_once work, even if we're not using threads... set(THREADS_PREFER_PTHREAD_FLAG ON) find_package(Threads REQUIRED) -# The boost graph headers are optional and only required by the graphs back end. -find_package (Boost QUIET COMPONENTS graph) -if (Boost_FOUND) - set (HAVE_LIBBOOST_GRAPH 1) -else () - message (WARNING "Boost graph headers not found, will not build 'graphs' backend") -endif () -find_package (Boost REQUIRED COMPONENTS iostreams) - # Compile with the Boehm garbage collector (https://github.com/ivmai/bdwgc), if requested. # One can disable the GC, e.g., to run under Valgrind, by editing config.h. if (ENABLE_GC) @@ -228,9 +218,6 @@ if (ENABLE_MULTITHREAD) add_definitions(-DMULTITHREAD) endif() list (APPEND P4C_LIB_DEPS ${CMAKE_THREAD_LIBS_INIT}) -include_directories(SYSTEM ${Boost_INCLUDE_DIRS}) -set (HAVE_LIBBOOST_IOSTREAMS 1) -list (APPEND P4C_LIB_DEPS ${Boost_LIBRARIES}) if (ENABLE_GC) list (APPEND P4C_LIB_DEPS ${LIBGC_LIBRARIES}) endif () diff --git a/backends/graphs/CMakeLists.txt b/backends/graphs/CMakeLists.txt index 2d05d43d592..20ee2d545d2 100644 --- a/backends/graphs/CMakeLists.txt +++ b/backends/graphs/CMakeLists.txt @@ -30,7 +30,10 @@ set (GRAPHS_HDRS ) add_library(p4cgraphs STATIC ${GRAPHS_SRCS} ${EXTENSION_P4_14_CONV_SOURCES}) -target_link_libraries(p4cgraphs ir-generated frontend) +target_link_libraries(p4cgraphs + PRIVATE ir-generated frontend + PUBLIC Boost::graph +) add_executable(p4c-graphs p4c-graphs.cpp) target_link_libraries (p4c-graphs p4cgraphs ir-generated frontend ${P4C_LIBRARIES} ${P4C_LIB_DEPS}) diff --git a/cmake/Boost.cmake b/cmake/Boost.cmake new file mode 100644 index 00000000000..01cc8392d5e --- /dev/null +++ b/cmake/Boost.cmake @@ -0,0 +1,93 @@ +macro(p4c_obtain_boost) + option( + P4C_USE_PREINSTALLED_BOOST + "Look for a preinstalled version of Boost in the system instead of installing the library using FetchContent." + OFF + ) + + # If P4C_USE_PREINSTALLED_BOOST is ON just try to find a preinstalled version of Boost. + if(P4C_USE_PREINSTALLED_BOOST) + if(NOT BUILD_SHARED_LIBS) + # Link Boost statically. + # See https://cmake.org/cmake/help/latest/module/FindBoost.html for details. + set(Boost_USE_STATIC_LIBS ON) + set(Boost_USE_STATIC_RUNTIME OFF) + endif() + + # The boost graph headers are optional and only required by the graphs back end. + find_package(Boost QUIET COMPONENTS graph) + if(Boost_FOUND) + set(HAVE_LIBBOOST_GRAPH 1) + else() + message(WARNING "Boost graph headers not found, will not build 'graphs' backend") + endif() + find_package(Boost REQUIRED COMPONENTS iostreams) + set(P4C_BOOST_LIBRARIES Boost::iostreams) + else() + # This option can be used to include custom boost modules. + set(P4C_TARGET_BOOST_LIBRARIES "" CACHE STRING "Build and make these boost modules available. Modules are separated with semicolons.") + set(P4C_BOOST_VERSION "1.86.0") + message(STATUS "Fetching Boost version ${P4C_BOOST_VERSION} for P4C...") + # Print out download state while setting up Boost. + set(FETCHCONTENT_QUIET_PREV ${FETCHCONTENT_QUIET}) + set(FETCHCONTENT_QUIET OFF) + # Unity builds do not work for Boost... + set(CMAKE_UNITY_BUILD_PREV ${CMAKE_UNITY_BUILD}) + set(CMAKE_UNITY_BUILD OFF) + + # Add boost modules. + # format, multiprecision, and iostreams are needed by P4C core. + set(BOOST_INCLUDE_LIBRARIES format multiprecision iostreams) + set(BOOST_ENABLE_CMAKE ON) + + # The boost graph module is optional and only required by the graphs back end. + if(ENABLE_P4C_GRAPHS) + set(HAVE_LIBBOOST_GRAPH 1) + list(APPEND BOOST_INCLUDE_LIBRARIES graph) + endif() + list(APPEND BOOST_INCLUDE_LIBRARIES ${P4C_TARGET_BOOST_LIBRARIES}) + + # Always link local Boost statically. + set(Boost_USE_STATIC_LIBS ON) + set(Boost_USE_STATIC_RUNTIME OFF) + + # Download and extract Boost from GitHub. + message(STATUS "Downloading and extracting boost library sources. This may take some time...") + FetchContent_Declare( + Boost + URL https://github.com/boostorg/boost/releases/download/boost-${P4C_BOOST_VERSION}/boost-${P4C_BOOST_VERSION}-cmake.tar.xz + URL_HASH SHA256=c62ce6e64d34414864fef946363db91cea89c1b90360eabed0515f0eda74c75c + USES_TERMINAL_DOWNLOAD TRUE + GIT_PROGRESS TRUE + ) + FetchContent_MakeAvailable(Boost) + + # Suppress warnings for all Boost targets. + get_all_targets(BOOST_BUILD_TARGETS ${Boost_SOURCE_DIR}) + set(boost_target_includes "") + foreach(target in ${BOOST_BUILD_TARGETS}) + if(target MATCHES "boost_*") + # Do not suppress warnings for Boost library targets that are aliased. + get_target_property(target_type ${target} TYPE) + if(NOT ${target_type} STREQUAL "INTERFACE_LIBRARY") + target_compile_options(${target} PRIVATE "-Wno-error" "-w") + endif() + # Force inclusion of the Boost headers as system headers. + # This is necessary because users may have their own system boost headers + # which can be in conflict. Also ensures that linters don't complain. + get_target_property(target_includes ${target} INTERFACE_INCLUDE_DIRECTORIES) + set_target_properties(${target} PROPERTIES INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "${target_includes}") + endif() + endforeach() + # Reset temporary variable modifications. + set(CMAKE_UNITY_BUILD ${CMAKE_UNITY_BUILD_PREV}) + set(FETCHCONTENT_QUIET ${FETCHCONTENT_QUIET_PREV}) + set(P4C_BOOST_LIBRARIES Boost::iostreams Boost::format Boost::multiprecision) + endif() + + include_directories(BEFORE SYSTEM ${Boost_INCLUDE_DIRS}) + set(HAVE_LIBBOOST_IOSTREAMS TRUE) + list(APPEND P4C_LIB_DEPS ${P4C_BOOST_LIBRARIES}) + + message(STATUS "Done with setting up Boost for P4C.") +endmacro(p4c_obtain_boost) diff --git a/ir/CMakeLists.txt b/ir/CMakeLists.txt index bdce1d6aacb..d79f6756e0e 100644 --- a/ir/CMakeLists.txt +++ b/ir/CMakeLists.txt @@ -68,7 +68,7 @@ set (BASE_IR_DEF_FILES set (IR_DEF_FILES ${IR_DEF_FILES} ${BASE_IR_DEF_FILES} PARENT_SCOPE) add_library (ir STATIC ${IR_SRCS}) -target_link_libraries(ir PRIVATE absl::flat_hash_map ${LIBGC_LIBRARIES}) +target_link_libraries(ir PRIVATE absl::flat_hash_map ${LIBGC_LIBRARIES} ${P4C_BOOST_LIBRARIES}) add_dependencies(ir genIR) diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index 21204b63dcf..550334f66a7 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -98,4 +98,5 @@ target_link_libraries(p4ctoolkit PUBLIC absl::bits PUBLIC absl::strings PUBLIC ${LIBGC_LIBRARIES} + PUBLIC ${P4C_BOOST_LIBRARIES} ) diff --git a/tools/ci-build.sh b/tools/ci-build.sh index 36adee6b5d6..a4ef36c2ebe 100755 --- a/tools/ci-build.sh +++ b/tools/ci-build.sh @@ -73,9 +73,6 @@ P4C_DEPS="bison \ g++ \ git \ lld \ - libboost-dev \ - libboost-graph-dev \ - libboost-iostreams-dev \ libfl-dev \ pkg-config \ python3 \ diff --git a/tools/install_mac_deps.sh b/tools/install_mac_deps.sh index 32707cff983..ffb6d3ca795 100755 --- a/tools/install_mac_deps.sh +++ b/tools/install_mac_deps.sh @@ -37,21 +37,14 @@ HOMEBREW_PREFIX=$(brew --prefix) # Fetch the latest formulae brew update -BOOST_LIB="boost@1.85" REQUIRED_PACKAGES=( autoconf automake ccache cmake libtool openssl pkg-config coreutils bison grep ninja - ${BOOST_LIB} ) for package in "${REQUIRED_PACKAGES[@]}"; do brew_install ${package} done -# Check if linking is needed. -if ! brew ls --linked --formula ${BOOST_LIB} > /dev/null 2>&1; then - brew link ${BOOST_LIB} -fi - # Check if PATH modification is needed. if ! grep -q "$(brew --prefix bison)/bin" ~/.bash_profile; then echo 'export PATH="$(brew --prefix bison)/bin:$PATH"' >> ~/.bash_profile