diff options
author | Brad King <brad.king@kitware.com> | 2024-12-11 16:53:26 (GMT) |
---|---|---|
committer | Brad King <brad.king@kitware.com> | 2024-12-11 17:34:29 (GMT) |
commit | 854eba0c53505190adb8fdd32cbdaed318d8dfda (patch) | |
tree | 7ccb5e38573b93dee2be4cad4bf8f05b7fb95b83 | |
parent | cd179e75606c6dc821b10574927e449b397b931c (diff) | |
download | CMake-854eba0c53505190adb8fdd32cbdaed318d8dfda.zip CMake-854eba0c53505190adb8fdd32cbdaed318d8dfda.tar.gz CMake-854eba0c53505190adb8fdd32cbdaed318d8dfda.tar.bz2 |
target_sources: Improve error message for CXX_MODULES on INTERFACE libraries
We support non-compiled `SOURCES` on `INTERFACE` libraries, and also
support `CXX_MODULES` on *imported* `INTERFACE` libraries (via synthetic
targets that compile module interface units). However, we do not
support `CXX_MODULES` on non-imported `INTERFACE` libraries because
there is no place to hold module interface unit's object files for their
module initializers. Previously this was not explicitly rejected, and
so was diagnosed only by "CMake Internal Error" messages due to
assumption violations in the implementation.
Fixes: #26524
Co-authored-by: Ben Boeckel <ben.boeckel@kitware.com>
11 files changed, 61 insertions, 0 deletions
diff --git a/Source/cmTargetSourcesCommand.cxx b/Source/cmTargetSourcesCommand.cxx index babbaa5..cdb9836 100644 --- a/Source/cmTargetSourcesCommand.cxx +++ b/Source/cmTargetSourcesCommand.cxx @@ -265,6 +265,18 @@ bool TargetSourcesImpl::HandleOneFileSet( return false; } + if (cmFileSetVisibilityIsForSelf(visibility) && + this->Target->GetType() == cmStateEnums::INTERFACE_LIBRARY && + !this->Target->IsImported()) { + if (type == "CXX_MODULES"_s) { + this->SetError(R"(File set TYPE "CXX_MODULES" may not have "PUBLIC" )" + R"(or "PRIVATE" visibility on INTERFACE libraries.)"); + return false; + } + } + + // FIXME(https://wg21.link/P3470): This condition can go + // away when interface-only module units are a thing. if (cmFileSetVisibilityIsForInterface(visibility) && !cmFileSetVisibilityIsForSelf(visibility) && !this->Target->IsImported()) { diff --git a/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-result.txt b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-stderr.txt b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-stderr.txt new file mode 100644 index 0000000..d14a221 --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface-stderr.txt @@ -0,0 +1,5 @@ +CMake Error at FileSetModulesInterfaceOnInterface.cmake:[0-9]+ \(target_sources\): + target_sources File set TYPE "CXX_MODULES" may not have "INTERFACE" + visibility +Call Stack \(most recent call first\): + CMakeLists.txt:[0-9]+ \(include\) diff --git a/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface.cmake b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface.cmake new file mode 100644 index 0000000..c2c4d63 --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesInterfaceOnInterface.cmake @@ -0,0 +1,8 @@ +add_library(module INTERFACE) +target_sources(module + INTERFACE + FILE_SET fs TYPE CXX_MODULES FILES + sources/module.cxx) +target_compile_features(module + INTERFACE + cxx_std_20) diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-result.txt b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-stderr.txt b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-stderr.txt new file mode 100644 index 0000000..f949df9 --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface-stderr.txt @@ -0,0 +1,5 @@ +^CMake Error at FileSetModulesPrivateOnInterface\.cmake:[0-9]+ \(target_sources\): + target_sources File set TYPE "CXX_MODULES" may not have "PUBLIC" or + "PRIVATE" visibility on INTERFACE libraries\. +Call Stack \(most recent call first\): + CMakeLists\.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface.cmake b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface.cmake new file mode 100644 index 0000000..9ee4024 --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPrivateOnInterface.cmake @@ -0,0 +1,11 @@ +enable_language(CXX) +set(CMAKE_CXX_SCANDEP_SOURCE "") + +add_library(module INTERFACE) +target_sources(module + PRIVATE + FILE_SET fs TYPE CXX_MODULES FILES + sources/module.cxx) +target_compile_features(module + INTERFACE + cxx_std_20) diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-result.txt b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-result.txt new file mode 100644 index 0000000..d00491f --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-result.txt @@ -0,0 +1 @@ +1 diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-stderr.txt b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-stderr.txt new file mode 100644 index 0000000..7d732eb --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface-stderr.txt @@ -0,0 +1,5 @@ +^CMake Error at FileSetModulesPublicOnInterface\.cmake:[0-9]+ \(target_sources\): + target_sources File set TYPE "CXX_MODULES" may not have "PUBLIC" or + "PRIVATE" visibility on INTERFACE libraries\. +Call Stack \(most recent call first\): + CMakeLists\.txt:[0-9]+ \(include\)$ diff --git a/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface.cmake b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface.cmake new file mode 100644 index 0000000..0bc4123 --- /dev/null +++ b/Tests/RunCMake/CXXModules/FileSetModulesPublicOnInterface.cmake @@ -0,0 +1,11 @@ +enable_language(CXX) +set(CMAKE_CXX_SCANDEP_SOURCE "") + +add_library(module INTERFACE) +target_sources(module + PUBLIC + FILE_SET fs TYPE CXX_MODULES FILES + sources/module.cxx) +target_compile_features(module + INTERFACE + cxx_std_20) diff --git a/Tests/RunCMake/CXXModules/RunCMakeTest.cmake b/Tests/RunCMake/CXXModules/RunCMakeTest.cmake index 0413793..8780ff2 100644 --- a/Tests/RunCMake/CXXModules/RunCMakeTest.cmake +++ b/Tests/RunCMake/CXXModules/RunCMakeTest.cmake @@ -72,6 +72,7 @@ set(scopes Private Public) set(target_types + Interface Static ) foreach (fileset_type IN LISTS fileset_types) |