1.. _ModulesInLibcxx: 2 3================= 4Modules in libc++ 5================= 6 7.. warning:: Modules are an experimental feature. It has additional build 8 requirements and not all libc++ configurations are supported yet. 9 10 The work is still in an early development state and not 11 considered stable nor complete 12 13This page contains information regarding C++23 module support in libc++. 14There are two kinds of modules available in Clang 15 16 * `Clang specific modules <https://clang.llvm.org/docs/Modules.html>`_ 17 * `C++ modules <https://clang.llvm.org/docs/StandardCPlusPlusModules.html>`_ 18 19This page mainly discusses the C++ modules. In C++20 there are also header units, 20these are not part of this document. 21 22Overview 23======== 24 25The module sources are stored in ``.cppm`` files. Modules need to be available 26as BMIs, which are ``.pcm`` files for Clang. BMIs are not portable, they depend 27on the compiler used and its compilation flags. Therefore there needs to be a 28way to distribute the ``.cppm`` files to the user and offer a way for them to 29build and use the ``.pcm`` files. It is expected this will be done by build 30systems in the future. To aid early adaptor and build system vendors libc++ 31currently ships a CMake project to aid building modules. 32 33.. note:: This CMake file is intended to be a temporary solution and will 34 be removed in the future. The timeline for the removal depends 35 on the availability of build systems with proper module support. 36 37What works 38~~~~~~~~~~ 39 40 * Building BMIs 41 * Running tests using the ``std`` and ``std.compat`` module 42 * Using the ``std`` and ``std.compat`` module in external projects 43 * The following "parts disabled" configuration options are supported 44 45 * ``LIBCXX_ENABLE_LOCALIZATION`` 46 * ``LIBCXX_ENABLE_WIDE_CHARACTERS`` 47 * ``LIBCXX_ENABLE_THREADS`` 48 * ``LIBCXX_ENABLE_FILESYSTEM`` 49 * ``LIBCXX_ENABLE_RANDOM_DEVICE`` 50 * ``LIBCXX_ENABLE_UNICODE`` 51 * ``LIBCXX_ENABLE_EXCEPTIONS`` [#note-no-windows]_ 52 53 * A C++20 based extension 54 55.. note:: 56 57 .. [#note-no-windows] This configuration will probably not work on Windows 58 due to hard-coded compilation flags. 59 60Some of the current limitations 61~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 62 63 * There is no official build system support, libc++ has experimental CMake support 64 * Requires CMake 3.26 for C++20 support 65 * Requires CMake 3.26 for C++23 support 66 * Requires CMake 3.27 for C++26 support 67 * Requires Ninja 1.11 68 * Requires Clang 17 69 * The path to the compiler may not be a symlink, ``clang-scan-deps`` does 70 not handle that case properly 71 * Libc++ is not tested with modules instead of headers 72 * Clang supports modules using GNU extensions, but libc++ does not work using 73 GNU extensions. 74 * Clang: 75 * Including headers after importing the ``std`` module may fail. This is 76 hard to solve and there is a work-around by first including all headers 77 `bug report <https://github.com/llvm/llvm-project/issues/61465>`__. 78 79Blockers 80~~~~~~~~ 81 82 * libc++ 83 84 * Currently the tests only test with modules enabled, but do not import 85 modules instead of headers. When converting tests to using modules there 86 are still failures. These are under investigation. 87 88 * It has not been determined how to fully test libc++ with modules instead 89 of headers. 90 91 * Clang 92 93 * Some concepts do not work properly 94 `bug report <https://github.com/llvm/llvm-project/issues/62943>`__. 95 96 97Using in external projects 98========================== 99 100Users need to be able to build their own BMI files. 101 102.. note:: The requirements for users to build their own BMI files will remain 103 true for the foreseeable future. For now this needs to be done manually. 104 Once libc++'s implementation is more mature we will reach out to build 105 system vendors, with the goal that building the BMI files is done by 106 the build system. 107 108Currently this requires a local build of libc++ with modules enabled. Since 109modules are not part of the installation yet, they are used from the build 110directory. First libc++ needs to be build with module support enabled. 111 112.. code-block:: bash 113 114 $ git clone https://github.com/llvm/llvm-project.git 115 $ cd llvm-project 116 $ mkdir build 117 $ cmake -G Ninja -S runtimes -B build -DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi;libunwind" 118 $ ninja -C build 119 120The above ``build`` directory will be referred to as ``<build>`` in the 121rest of these instructions. 122 123This is a small sample program that uses the module ``std``. It consists of a 124``CMakeLists.txt`` and a ``main.cpp`` file. 125 126.. code-block:: cpp 127 128 import std; // When importing std.compat it's not needed to import std. 129 import std.compat; 130 131 int main() { 132 std::cout << "Hello modular world\n"; 133 ::printf("Hello compat modular world\n"); 134 } 135 136.. code-block:: cmake 137 138 cmake_minimum_required(VERSION 3.26.0 FATAL_ERROR) 139 project("module" 140 LANGUAGES CXX 141 ) 142 143 # 144 # Set language version used 145 # 146 147 set(CMAKE_CXX_STANDARD 23) 148 set(CMAKE_CXX_STANDARD_REQUIRED YES) 149 # Libc++ doesn't support compiler extensions for modules. 150 set(CMAKE_CXX_EXTENSIONS OFF) 151 152 # 153 # Enable modules in CMake 154 # 155 156 # This is required to write your own modules in your project. 157 if(CMAKE_VERSION VERSION_LESS "3.28.0") 158 if(CMAKE_VERSION VERSION_LESS "3.27.0") 159 set(CMAKE_EXPERIMENTAL_CXX_MODULE_CMAKE_API "2182bf5c-ef0d-489a-91da-49dbc3090d2a") 160 else() 161 set(CMAKE_EXPERIMENTAL_CXX_MODULE_CMAKE_API "aa1f7df0-828a-4fcd-9afc-2dc80491aca7") 162 endif() 163 set(CMAKE_EXPERIMENTAL_CXX_MODULE_DYNDEP 1) 164 else() 165 cmake_policy(VERSION 3.28) 166 endif() 167 168 # 169 # Import the modules from libc++ 170 # 171 172 include(FetchContent) 173 FetchContent_Declare( 174 std 175 URL "file://${LIBCXX_BUILD}/modules/c++/v1/" 176 DOWNLOAD_EXTRACT_TIMESTAMP TRUE 177 SYSTEM 178 ) 179 FetchContent_MakeAvailable(std) 180 181 # 182 # Add the project 183 # 184 185 add_executable(main) 186 add_dependencies(main std.compat) 187 target_link_libraries(main std.compat) 188 target_sources(main 189 PRIVATE 190 main.cpp 191 ) 192 193Building this project is done with the following steps, assuming the files 194``main.cpp`` and ``CMakeLists.txt`` are copied in the current directory. 195 196.. code-block:: bash 197 198 $ mkdir build 199 $ cmake -G Ninja -S . -B build -DCMAKE_CXX_COMPILER=<path-to-compiler> -DLIBCXX_BUILD=<build> 200 $ ninja -C build 201 $ build/main 202 203.. warning:: ``<path-to-compiler>`` should point point to the real binary and 204 not to a symlink. 205 206.. warning:: When using these examples in your own projects make sure the 207 compilation flags are the same for the ``std`` module and your 208 project. Some flags will affect the generated code, when these 209 are different the module cannot be used. For example using 210 ``-pthread`` in your project and not in the module will give 211 errors like 212 213 ``error: POSIX thread support was disabled in PCH file but is currently enabled`` 214 215 ``error: module file _deps/std-build/CMakeFiles/std.dir/std.pcm cannot be loaded due to a configuration mismatch with the current compilation [-Wmodule-file-config-mismatch]`` 216 217If you have questions about modules feel free to ask them in the ``#libcxx`` 218channel on `LLVM's Discord server <https://discord.gg/jzUbyP26tQ>`__. 219 220If you think you've found a bug please it using the `LLVM bug tracker 221<https://github.com/llvm/llvm-project/issues>`_. Please make sure the issue 222you found is not one of the known bugs or limitations on this page. 223