-
Notifications
You must be signed in to change notification settings - Fork 166
Rewrite modules following the new recommended Boost practice #196
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
|
@anarthal I'd appreciate comments on this PR on modules (as you proposed at boostorg/core#191 (comment)) |
Pull Request Test Coverage Report for Build 14447165733Details
💛 - Coveralls |
Have you tried MSVC? My experience is that clang allows for almost anything, with MSVC being much more restrictive. |
| ./b2 -d0 headers | ||
| ./b2 variant=debug tools/inspect/build | ||
| - name: Run modules tests |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd strongly advise to add a job covering modules under MSVC, since it's much more restrictive than clang. You can have a look at my mp11/charconv proposal for some inspiration.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What problems did you encounter in the tests that you commented out? I might be able to help with them.
include/boost/pfr/core.hpp
Outdated
|
|
||
| #include <boost/pfr/tuple_size.hpp> | ||
|
|
||
| #if defined(BOOST_USE_STD_MODULE) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since PFR is the only library supporting this atm, I'd consider renaming the macro to BOOST_PFR_USE_STD_MODULE
include/boost/pfr/core.hpp
Outdated
|
|
||
| #if defined(BOOST_USE_STD_MODULE) | ||
| import std; | ||
| #else |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd consider replacing this ifdef + includes by either a file like this:
https://github.com/anarthal/mp11/blob/feature/cxx20-modules/include/boost/mp11/detail/std/tuple.hpp
or follow this approach: boostorg/charconv#255 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd rather leave it as is for now. Maybe I'll change it in the next PR
.github/workflows/ci.yml
Outdated
| cd ../boost-root/libs/pfr | ||
| mkdir build_module | ||
| cd build_module | ||
| cmake -DBOOST_USE_MODULES=1 -DBUILD_TESTING=1 -GNinja -DCMAKE_CXX_COMPILER=clang++-19 -DCMAKE_CXX_FLAGS=-I../../../ .. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you're going to support building with and without import std, you need to add a CI build for each config/compiler pair. I think you're missing an include in the import std configuration.
| #include <boost/pfr/detail/unsafe_declval.hpp> | ||
|
|
||
| #ifdef BOOST_PFR_HAS_STD_MODULE | ||
| #if defined(BOOST_USE_STD_MODULE) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think you will get macro definitions like __cpp_lib_is_aggregate without an include (like <version>). #include <version> is safe to use in general, and can be mixed with imports without problem, but you will need to guard it (it's C++20 and above).
Same applies for SIZE_MAX. You can replace this by (std::numeric_limits<std::size_t>::max)() and avoid the problem.
| #if defined(BOOST_USE_STD_MODULE) | ||
| import std; | ||
| #else | ||
| #include <climits> // CHAR_BIT |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You won't get CHAR_BIT with this structure. You will need to include the header even in modular builds. IIRC #include <climits> caused problems under MSVC when mixed with imports, but #include <limits.h> is okay.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll just use std::numeric_limits<unsigned char>::digits instead
| #include <boost/pfr/traits_fwd.hpp> | ||
|
|
||
| #ifdef BOOST_PFR_HAS_STD_MODULE | ||
| #if defined(BOOST_USE_STD_MODULE) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
__cpp_lib_is_aggregate
| #endif | ||
|
|
||
| #ifndef BOOST_PFR_USE_STD_MAKE_INTEGRAL_SEQUENCE | ||
| # if defined(BOOST_USE_MODULES) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe you can attempt to include <version> to get __GLIBCXX__? Although that makes the include heavier.
CMakeLists.txt
Outdated
| FILE_SET modules_public TYPE CXX_MODULES FILES | ||
| ${CMAKE_CURRENT_LIST_DIR}/modules/pfr.cppm | ||
| ) | ||
| if (CXX_MODULE_STD) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think this works like this. If I understood CXX_MODULE_STD correctly, this is a property of targets, not a global variable indicating whether import std is supported or not.
To match the rest of Boost, I'd make import std the default when BOOST_USE_MODULES is defined. Then, if the user sets some CMake option (like BOOST_PFR_DISABLE_IMPORT_STD) fall back to includes. Since stdlib is the main source of compile times, I'd expect most of the people using modules because of compile times to also use import std.
You need to test these workflows to avoid this kind of errors. We commonly test installing the project and consuming it with find_package, and consuming the project directly via add_subdirectory. Have a look at the mp11 CI workflows for examples.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You are right, I have to check the CMAKE_CXX_COMPILER_IMPORT_STD variable instead of the CXX_MODULE_STD property
CMakeLists.txt
Outdated
| if (CMAKE_VERSION VERSION_GREATER_EQUAL "3.28.0" AND BUILD_MODULE) | ||
| add_subdirectory(module) | ||
| target_compile_definitions(boost_pfr PUBLIC BOOST_USE_MODULES) | ||
| target_include_directories(boost_pfr PUBLIC ${CMAKE_CURRENT_LIST_DIR}/include) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be just include, rather than ${CMAKE_CURRENT_LIST_DIR}/include
|
|
||
| int main() { | ||
| #if BOOST_PFR_USE_CPP17 | ||
| #if BOOST_PFR_USE_CPP17 && !defined(BOOST_USE_MODULES) // TODO: fix for BOOST_USE_MODULES |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
what's the problem with this one?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It uses boost::pfr::detail that is an implentation detail and is not exported from module
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah! I see. I've workarounded these in Charconv by just using includes. It may make sense to leave them as you did, too. I tried creating an internal-only module that exported the detail functions to test, but the approach doesn't map very well to CMake, and it tends to either end up creating an extra static library that ends up getting installed (not good) or just refusing to build at all.
Changes:
#include <boost/pfr...is now implicitly changed intoimport boost.pfrif the modules are supportedboost.pfrBoost::pfrtarget if modules are supported1)allows users to mix#include <boost/pfr...andimport boost.pfrin user code without ODR-violations.Significant differences from https://anarthal.github.io/cppblog/modules3:
import std;/includes. This allows usingboost.pfrmodule in C++20 and even without usablestdmodule.