diff options
author | Brad King <brad.king@kitware.com> | 2024-09-25 12:58:00 (GMT) |
---|---|---|
committer | Kitware Robot <kwrobot@kitware.com> | 2024-09-25 12:58:26 (GMT) |
commit | 506255b1f1ba2b7a7d4babce4b86d30238977d87 (patch) | |
tree | 8a1980362f3ea4d24b896021903da1aba2f9e44a /Source | |
parent | 57480c767647601d6a1c541667d781838f56d8ae (diff) | |
parent | e3895f4a8bcce3d9caae7d0e5559e6f057725fad (diff) | |
download | CMake-506255b1f1ba2b7a7d4babce4b86d30238977d87.zip CMake-506255b1f1ba2b7a7d4babce4b86d30238977d87.tar.gz CMake-506255b1f1ba2b7a7d4babce4b86d30238977d87.tar.bz2 |
Merge topic 'nested_linker_prefixes'
e3895f4a8b Linking: Preserve nested LINKER: prefixes as written
4185dfbe1b Tests/LINK_OPTIONS: extract common code in test (NFC)
54381b5a81 Linking: extract wrapping linker options to a lambda (NFC)
Acked-by: Kitware Robot <kwrobot@kitware.com>
Acked-by: buildbot <buildbot@kitware.com>
Merge-request: !9823
Diffstat (limited to 'Source')
-rw-r--r-- | Source/cmGeneratorTarget_Options.cxx | 118 |
1 files changed, 69 insertions, 49 deletions
diff --git a/Source/cmGeneratorTarget_Options.cxx b/Source/cmGeneratorTarget_Options.cxx index f77ef72..d8b3eb3 100644 --- a/Source/cmGeneratorTarget_Options.cxx +++ b/Source/cmGeneratorTarget_Options.cxx @@ -7,6 +7,7 @@ #include "cmConfigure.h" #include <algorithm> +#include <iterator> #include <map> #include <memory> #include <string> @@ -91,10 +92,16 @@ void processOptions(cmGeneratorTarget const* tgt, } } +enum class NestedLinkerFlags +{ + PreserveAsSpelled, + Normalize, +}; + std::vector<BT<std::string>> wrapOptions( std::vector<std::string>& options, const cmListFileBacktrace& bt, const std::vector<std::string>& wrapperFlag, const std::string& wrapperSep, - bool concatFlagAndArgs) + bool concatFlagAndArgs, NestedLinkerFlags nestedLinkerFlags) { std::vector<BT<std::string>> result; @@ -111,6 +118,48 @@ std::vector<BT<std::string>> wrapOptions( return result; } + auto insertWrapped = [&](std::vector<std::string>& opts) { + if (!wrapperSep.empty()) { + if (concatFlagAndArgs) { + // insert flag elements except last one + for (auto i = wrapperFlag.begin(); i != wrapperFlag.end() - 1; ++i) { + result.emplace_back(*i, bt); + } + // concatenate last flag element and all list values + // in one option + result.emplace_back(wrapperFlag.back() + cmJoin(opts, wrapperSep), bt); + } else { + for (std::string const& i : wrapperFlag) { + result.emplace_back(i, bt); + } + // concatenate all list values in one option + result.emplace_back(cmJoin(opts, wrapperSep), bt); + } + } else { + // prefix each element of list with wrapper + if (concatFlagAndArgs) { + std::transform(opts.begin(), opts.end(), opts.begin(), + [&wrapperFlag](std::string const& o) -> std::string { + return wrapperFlag.back() + o; + }); + } + for (std::string& o : opts) { + for (auto i = wrapperFlag.begin(), + e = concatFlagAndArgs ? wrapperFlag.end() - 1 + : wrapperFlag.end(); + i != e; ++i) { + result.emplace_back(*i, bt); + } + result.emplace_back(std::move(o), bt); + } + } + }; + + if (nestedLinkerFlags == NestedLinkerFlags::PreserveAsSpelled) { + insertWrapped(options); + return result; + } + for (std::vector<std::string>::size_type index = 0; index < options.size(); index++) { if (cmHasLiteralPrefix(options[index], "LINKER:")) { @@ -154,40 +203,7 @@ std::vector<BT<std::string>> wrapOptions( continue; } - if (!wrapperSep.empty()) { - if (concatFlagAndArgs) { - // insert flag elements except last one - for (auto i = wrapperFlag.begin(); i != wrapperFlag.end() - 1; ++i) { - result.emplace_back(*i, bt); - } - // concatenate last flag element and all list values - // in one option - result.emplace_back(wrapperFlag.back() + cmJoin(opts, wrapperSep), bt); - } else { - for (std::string const& i : wrapperFlag) { - result.emplace_back(i, bt); - } - // concatenate all list values in one option - result.emplace_back(cmJoin(opts, wrapperSep), bt); - } - } else { - // prefix each element of list with wrapper - if (concatFlagAndArgs) { - std::transform(opts.begin(), opts.end(), opts.begin(), - [&wrapperFlag](std::string const& o) -> std::string { - return wrapperFlag.back() + o; - }); - } - for (std::string& o : opts) { - for (auto i = wrapperFlag.begin(), - e = concatFlagAndArgs ? wrapperFlag.end() - 1 - : wrapperFlag.end(); - i != e; ++i) { - result.emplace_back(*i, bt); - } - result.emplace_back(std::move(o), bt); - } - } + insertWrapped(opts); } return result; } @@ -484,8 +500,9 @@ std::vector<BT<std::string>> cmGeneratorTarget::GetLinkOptions( // host link options must be wrapped std::vector<std::string> options; cmSystemTools::ParseUnixCommandLine(it->Value.c_str(), options); - auto hostOptions = wrapOptions(options, it->Backtrace, wrapperFlag, - wrapperSep, concatFlagAndArgs); + auto hostOptions = + wrapOptions(options, it->Backtrace, wrapperFlag, wrapperSep, + concatFlagAndArgs, NestedLinkerFlags::Normalize); it = result.erase(it); // some compilers (like gcc 4.8 or Intel 19.0 or XLC 16) do not respect // C++11 standard: 'std::vector::insert()' do not returns an iterator, @@ -534,12 +551,11 @@ std::vector<BT<std::string>>& cmGeneratorTarget::ResolveLinkerWrapper( const std::string SHELL{ "SHELL:" }; const std::string LINKER_SHELL = LINKER + SHELL; - std::vector<BT<std::string>>::iterator entry; - while ((entry = std::find_if(result.begin(), result.end(), - [&LINKER](BT<std::string> const& item) -> bool { - return item.Value.compare(0, LINKER.length(), - LINKER) == 0; - })) != result.end()) { + for (auto entry = result.begin(); entry != result.end(); ++entry) { + if (entry->Value.compare(0, LINKER.length(), LINKER) != 0) { + continue; + } + std::string value = std::move(entry->Value); cmListFileBacktrace bt = std::move(entry->Backtrace); entry = result.erase(entry); @@ -569,15 +585,19 @@ std::vector<BT<std::string>>& cmGeneratorTarget::ResolveLinkerWrapper( return result; } - std::vector<BT<std::string>> options = wrapOptions( - linkerOptions, bt, wrapperFlag, wrapperSep, concatFlagAndArgs); + // Very old versions of the C++ standard library return void for insert, so + // can't use it to get the new iterator + const auto index = entry - result.begin(); + std::vector<BT<std::string>> options = + wrapOptions(linkerOptions, bt, wrapperFlag, wrapperSep, + concatFlagAndArgs, NestedLinkerFlags::PreserveAsSpelled); if (joinItems) { - result.insert(entry, - cmJoin(cmRange<decltype(options.cbegin())>( - options.cbegin(), options.cend()), - " "_s)); + result.insert( + entry, cmJoin(cmMakeRange(options.begin(), options.end()), " "_s)); + entry = std::next(result.begin(), index); } else { result.insert(entry, options.begin(), options.end()); + entry = std::next(result.begin(), index + options.size() - 1); } } return result; |