summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Source/cmTargetLinkLibrariesCommand.cxx42
-rw-r--r--Tests/CMakeCommands/target_link_libraries/cmp0022/CMakeLists.txt10
2 files changed, 48 insertions, 4 deletions
diff --git a/Source/cmTargetLinkLibrariesCommand.cxx b/Source/cmTargetLinkLibrariesCommand.cxx
index 1cd8a7e..94fcdd9 100644
--- a/Source/cmTargetLinkLibrariesCommand.cxx
+++ b/Source/cmTargetLinkLibrariesCommand.cxx
@@ -2,11 +2,14 @@
file Copyright.txt or https://cmake.org/licensing for details. */
#include "cmTargetLinkLibrariesCommand.h"
+#include <cassert>
#include <memory>
#include <sstream>
#include <unordered_set>
#include <utility>
+#include <cm/optional>
+
#include "cmExecutionStatus.h"
#include "cmGeneratorExpression.h"
#include "cmGlobalGenerator.h"
@@ -178,6 +181,28 @@ bool cmTargetLinkLibrariesCommand(std::vector<std::string> const& args,
// specification if the keyword is encountered as the first argument.
ProcessingState currentProcessingState = ProcessingLinkLibraries;
+ // Accumulate consectuive non-keyword arguments into one entry in
+ // order to handle unquoted generator expressions containing ';'.
+ cm::optional<std::string> currentEntry;
+ auto processCurrentEntry = [&]() -> bool {
+ if (currentEntry) {
+ assert(!haveLLT);
+ if (!tll.HandleLibrary(currentProcessingState, *currentEntry,
+ GENERAL_LibraryType)) {
+ return false;
+ }
+ currentEntry = cm::nullopt;
+ }
+ return true;
+ };
+ auto extendCurrentEntry = [&currentEntry](std::string const& arg) {
+ if (currentEntry) {
+ currentEntry = cmStrCat(*currentEntry, ';', arg);
+ } else {
+ currentEntry = arg;
+ }
+ };
+
// Keep this list in sync with the keyword dispatch below.
static std::unordered_set<std::string> const keywords{
"LINK_INTERFACE_LIBRARIES",
@@ -195,6 +220,11 @@ bool cmTargetLinkLibrariesCommand(std::vector<std::string> const& args,
// of debug and optimized that can be used.
for (unsigned int i = 1; i < args.size(); ++i) {
if (keywords.count(args[i])) {
+ // A keyword argument terminates any preceding accumulated entry.
+ if (!processCurrentEntry()) {
+ return false;
+ }
+
// Process this keyword argument.
if (args[i] == "LINK_INTERFACE_LIBRARIES") {
currentProcessingState = ProcessingPlainLinkInterface;
@@ -285,18 +315,22 @@ bool cmTargetLinkLibrariesCommand(std::vector<std::string> const& args,
} else if (haveLLT) {
// The link type was specified by the previous argument.
haveLLT = false;
+ assert(!currentEntry);
if (!tll.HandleLibrary(currentProcessingState, args[i], llt)) {
return false;
}
llt = GENERAL_LibraryType;
} else {
- if (!tll.HandleLibrary(currentProcessingState, args[i],
- GENERAL_LibraryType)) {
- return false;
- }
+ // Accumulate this argument in the current entry.
+ extendCurrentEntry(args[i]);
}
}
+ // Process the last accumulated entry, if any.
+ if (!processCurrentEntry()) {
+ return false;
+ }
+
// Make sure the last argument was not a library type specifier.
if (haveLLT) {
mf.IssueMessage(MessageType::FATAL_ERROR,
diff --git a/Tests/CMakeCommands/target_link_libraries/cmp0022/CMakeLists.txt b/Tests/CMakeCommands/target_link_libraries/cmp0022/CMakeLists.txt
index 83103cf..ca6309b 100644
--- a/Tests/CMakeCommands/target_link_libraries/cmp0022/CMakeLists.txt
+++ b/Tests/CMakeCommands/target_link_libraries/cmp0022/CMakeLists.txt
@@ -1,3 +1,4 @@
+cmake_policy(SET CMP0028 NEW)
include(GenerateExportHeader)
set(CMAKE_INCLUDE_CURRENT_DIR ON)
@@ -17,6 +18,15 @@ assert_property(cmp0022ifacelib INTERFACE_LINK_LIBRARIES "")
add_executable(cmp0022exe cmp0022exe.cpp)
target_link_libraries(cmp0022exe cmp0022lib)
+# Test adding unquoted genex with ';' to LINK_LIBRARIES and INTERFACE_LINK_LIBRARIES.
+target_link_libraries(cmp0022lib
+ PUBLIC $<0:imp::missing1;imp::missing2>
+ PRIVATE $<0:imp::missing3;imp::missing4>
+ INTERFACE $<0:imp::missing5;imp::missing6>
+ )
+assert_property(cmp0022lib INTERFACE_LINK_LIBRARIES "cmp0022ifacelib;$<0:imp::missing1;imp::missing2>;$<0:imp::missing5;imp::missing6>")
+assert_property(cmp0022lib LINK_LIBRARIES "cmp0022ifacelib;$<0:imp::missing1;imp::missing2>;$<0:imp::missing3;imp::missing4>")
+
add_library(staticlib1 STATIC staticlib1.cpp)
generate_export_header(staticlib1)
add_library(staticlib2 STATIC staticlib2.cpp)