Skip to content
This repository was archived by the owner on Jan 29, 2026. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 31 additions & 18 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
cmake_minimum_required(VERSION 3.28)

project(msft_proxy VERSION 3.3.0 LANGUAGES CXX)
add_library(msft_proxy INTERFACE)
project(msft_proxy4 VERSION 3.3.0 LANGUAGES CXX)
add_library(msft_proxy4 INTERFACE)
set_target_properties(msft_proxy4 PROPERTIES EXPORT_NAME proxy4)
add_library(msft_proxy::proxy4 ALIAS msft_proxy4)

# Do not enable building tests if proxy is consumed as
# subdirectory (e.g. by CMake FetchContent_Declare).
Expand All @@ -19,7 +21,7 @@ if(PROJECT_IS_TOP_LEVEL)
)
endif()

target_sources(msft_proxy
target_sources(msft_proxy4
INTERFACE
FILE_SET public_headers
TYPE HEADERS
Expand All @@ -28,53 +30,64 @@ target_sources(msft_proxy
include/proxy/proxy.h
include/proxy/proxy_macros.h
include/proxy/proxy_fmt.h
include/proxy/proxy.ixx
include/proxy/v4/proxy.ixx
include/proxy/v4/proxy.h
include/proxy/v4/proxy_macros.h
include/proxy/v4/proxy_fmt.h
)

target_compile_features(msft_proxy INTERFACE cxx_std_20)
target_include_directories(msft_proxy INTERFACE $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>
target_compile_features(msft_proxy4 INTERFACE cxx_std_20)
target_include_directories(msft_proxy4 INTERFACE $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>
$<INSTALL_INTERFACE:include>)

# Do not set the module target if proxy is consumed as a subdirectory.
if(PROJECT_IS_TOP_LEVEL)
set(proxy_INCLUDE_DIR include)
set(proxy4_INCLUDE_DIR include)
if(PROXY_BUILD_MODULES)
include(cmake/proxyModuleTargets.cmake)
include(cmake/proxy4ModuleTargets.cmake)
endif()
else()
# Propagate the variable to the parent project
set(proxy_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include PARENT_SCOPE)
set(proxy4_INCLUDE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/include PARENT_SCOPE)
endif()

# install and export the project. project name - proxy

include(GNUInstallDirs)

install(TARGETS msft_proxy
EXPORT proxyTargets
install(TARGETS msft_proxy4
EXPORT proxy4Targets
FILE_SET public_headers DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
)

install(EXPORT proxyTargets DESTINATION ${CMAKE_INSTALL_DATADIR}/proxy)
export(TARGETS msft_proxy FILE proxyTargets.cmake)
install(
EXPORT proxy4Targets
NAMESPACE msft_proxy::
DESTINATION ${CMAKE_INSTALL_DATADIR}/proxy
)
export(
TARGETS msft_proxy4
NAMESPACE msft_proxy::
FILE proxy4Targets.cmake
)

include(CMakePackageConfigHelpers)
configure_package_config_file(
cmake/proxyConfig.cmake.in
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxyConfig.cmake
cmake/proxy4Config.cmake.in
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxy4Config.cmake
INSTALL_DESTINATION ${CMAKE_INSTALL_DATADIR}/proxy
PATH_VARS CMAKE_INSTALL_INCLUDEDIR
)

include(CMakePackageConfigHelpers)
write_basic_package_version_file(cmake/proxyConfigVersion.cmake
write_basic_package_version_file(cmake/proxy4ConfigVersion.cmake
COMPATIBILITY SameMajorVersion
ARCH_INDEPENDENT)

install(
FILES
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxyConfig.cmake
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxyConfigVersion.cmake
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxy4Config.cmake
${CMAKE_CURRENT_BINARY_DIR}/cmake/proxy4ConfigVersion.cmake
DESTINATION ${CMAKE_INSTALL_DATADIR}/proxy
)

Expand Down
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ Please refer to the [Proxy's Frequently Asked Questions](https://microsoft.githu

```cmake
CPMAddPackage(
NAME proxy
NAME proxy4
GIT_TAG 4.0.0 # or above
GIT_REPOSITORY https://github.com/microsoft/proxy.git
)

target_link_libraries(main PRIVATE msft_proxy)
target_link_libraries(main PRIVATE msft_proxy::proxy4)
```

### Hello World
Expand Down
2 changes: 1 addition & 1 deletion benchmarks/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ add_executable(msft_proxy_benchmarks
proxy_management_benchmark.cpp
)
target_include_directories(msft_proxy_benchmarks PRIVATE .)
target_link_libraries(msft_proxy_benchmarks PRIVATE msft_proxy benchmark::benchmark benchmark::benchmark_main)
target_link_libraries(msft_proxy_benchmarks PRIVATE msft_proxy::proxy4 benchmark::benchmark benchmark::benchmark_main)

if (MSVC)
target_compile_options(msft_proxy_benchmarks PRIVATE /W4)
Expand Down
5 changes: 5 additions & 0 deletions cmake/proxy4Config.cmake.in
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
@PACKAGE_INIT@

include("${CMAKE_CURRENT_LIST_DIR}/proxy4Targets.cmake")

set(proxy4_INCLUDE_DIR "@PACKAGE_CMAKE_INSTALL_INCLUDEDIR@")
25 changes: 25 additions & 0 deletions cmake/proxy4ModuleTargets.cmake
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@

if(NOT DEFINED proxy4_INCLUDE_DIR)
message(FATAL_ERROR "proxy4_INCLUDE_DIR must be defined to use this script.")
endif()

message(STATUS "Declaring `msft_proxy::proxy4_module` target for include path ${proxy4_INCLUDE_DIR}")

add_library(msft_proxy4_module)
set_target_properties(
msft_proxy4_module
PROPERTIES
SYSTEM TRUE
EXCLUDE_FROM_ALL TRUE
)

add_library(msft_proxy::proxy4_module ALIAS msft_proxy4_module)
target_sources(msft_proxy4_module PUBLIC
FILE_SET CXX_MODULES
BASE_DIRS ${proxy4_INCLUDE_DIR}
FILES
${proxy4_INCLUDE_DIR}/proxy/v4/proxy.ixx
)
target_compile_features(msft_proxy4_module PUBLIC cxx_std_20)
target_link_libraries(msft_proxy4_module PUBLIC msft_proxy::proxy4)

5 changes: 0 additions & 5 deletions cmake/proxyConfig.cmake.in

This file was deleted.

25 changes: 0 additions & 25 deletions cmake/proxyModuleTargets.cmake

This file was deleted.

2 changes: 1 addition & 1 deletion docs/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ set_source_files_properties(${EXAMPLE_SOURCES} PROPERTIES GENERATED TRUE)
foreach(SOURCE ${EXAMPLE_SOURCES})
get_filename_component(EXECUTABLE_NAME ${SOURCE} NAME_WE)
add_executable(${EXECUTABLE_NAME} ${SOURCE})
target_link_libraries(${EXECUTABLE_NAME} PRIVATE msft_proxy)
target_link_libraries(${EXECUTABLE_NAME} PRIVATE msft_proxy::proxy4)
if (MSVC)
target_compile_options(${EXECUTABLE_NAME} PRIVATE /W4)
elseif(CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
Expand Down
38 changes: 19 additions & 19 deletions docs/cpp20_modules_support.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,43 +5,43 @@ The "Proxy" library ships with `.ixx` files starting with version **4.0.0**. Com
As of 2025-05-11, CMake lacks support for forward compatibility when consuming C++ modules, which causes consumers with newer C++ standard to be unable to use modules with older standard. Until this is implemented by CMake, a CMake target containing the module can be manually declared using the following CMake script:

```cmake
find_package(proxy REQUIRED)
find_package(proxy4 REQUIRED)

if(NOT DEFINED proxy_INCLUDE_DIR) # (1)
if(NOT DEFINED proxy4_INCLUDE_DIR) # (1)
if(NOT DEFINED proxy_SOURCE_DIR)
message(FATAL_ERROR "proxy_INCLUDE_DIR or proxy_SOURCE_DIR must be defined to use this script.")
message(FATAL_ERROR "proxy4_INCLUDE_DIR or proxy_SOURCE_DIR must be defined to use this script.")
endif()
set(proxy_INCLUDE_DIR ${proxy_SOURCE_DIR}/include)
set(proxy4_INCLUDE_DIR ${proxy_SOURCE_DIR}/include)
endif()

message(STATUS "Declaring `msft_proxy::module` target for include path ${proxy_INCLUDE_DIR}")
message(STATUS "Declaring `msft_proxy::proxy4_module` target for include path ${proxy4_INCLUDE_DIR}")

add_library(msft_proxy_module)
add_library(msft_proxy4_module)
set_target_properties(
msft_proxy_module
msft_proxy4_module
PROPERTIES
SYSTEM TRUE
EXCLUDE_FROM_ALL TRUE
)

add_library(msft_proxy::module ALIAS msft_proxy_module)
target_sources(msft_proxy_module PUBLIC
add_library(msft_proxy::proxy4_module ALIAS msft_proxy4_module)
target_sources(msft_proxy4_module PUBLIC
FILE_SET CXX_MODULES
BASE_DIRS ${proxy_INCLUDE_DIR}
BASE_DIRS ${proxy4_INCLUDE_DIR}
FILES
${proxy_INCLUDE_DIR}/proxy/proxy.ixx
${proxy4_INCLUDE_DIR}/proxy/v4/proxy.ixx
)
target_compile_features(msft_proxy_module PUBLIC cxx_std_20) # (2)
target_link_libraries(msft_proxy_module PUBLIC msft_proxy)
target_compile_features(msft_proxy4_module PUBLIC cxx_std_20) # (2)
target_link_libraries(msft_proxy4_module PUBLIC msft_proxy::proxy4)
```

- (1) `proxy_INCLUDE_DIR` is automatically declared after `find_package(proxy)`. CPM uses a slightly different convention where `proxy_SOURCE_DIR` is declared after `CPMAddPackage`.
- (2) The C++ standard version for `msft_proxy_module` target should be the same or higher than the consumer CMake target. For example if your project is using C++23 mode, this line should be changed to `cxx_std_23` or `cxx_std_26` / newer standards.
- (1) `proxy4_INCLUDE_DIR` is automatically declared after `find_package(proxy4)`. CPM uses a slightly different convention where `proxy_SOURCE_DIR` is declared after `CPMAddPackage`.
- (2) The C++ standard version for `msft_proxy4_module` target should be the same or higher than the consumer CMake target. For example if your project is using C++23 mode, this line should be changed to `cxx_std_23` or `cxx_std_26` / newer standards.

It can then be consumed like this:

```cmake
target_link_libraries(main PRIVATE msft_proxy::module)
target_link_libraries(main PRIVATE msft_proxy::proxy4_module)
```

## Example
Expand All @@ -58,7 +58,7 @@ module;

export module dictionary;

import proxy; // (3)
import proxy.v4; // (3)

extern "C++" { // (4)
PRO_DEF_MEM_DISPATCH(MemAt, at);
Expand All @@ -77,7 +77,7 @@ Client:
#include <vector>
#include <iostream>

import proxy;
import proxy.v4;
import dictionary;

int main() {
Expand All @@ -90,6 +90,6 @@ int main() {

- (1) This is a traditional header rather than a module. It should be declared in global fragment (after `module` and before `export module`).
- (2) This makes all `PRO_DEF_` macros available. This header file contains only some macros and are therefore very fast to compile.
- (3) `import proxy;` makes all public interfaces from `pro` namespace available in the current translation unit.
- (3) `import proxy.v4;` makes all public interfaces from `pro::v4` namespace available in the current translation unit.
- (4) As of 2025-05-11, clangd requires the accessor struct to be either `export`-ed, or be declared within an `extern "C++"` block, in order to have auto completion working.

Loading