summaryrefslogtreecommitdiff
path: root/Source/cmLinkLineComputer.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'Source/cmLinkLineComputer.cxx')
-rw-r--r--Source/cmLinkLineComputer.cxx103
1 files changed, 84 insertions, 19 deletions
diff --git a/Source/cmLinkLineComputer.cxx b/Source/cmLinkLineComputer.cxx
index 469faca88..0dc6236a0 100644
--- a/Source/cmLinkLineComputer.cxx
+++ b/Source/cmLinkLineComputer.cxx
@@ -4,13 +4,17 @@
#include "cmLinkLineComputer.h"
#include <sstream>
+#include <utility>
#include <vector>
#include "cmComputeLinkInformation.h"
#include "cmGeneratorTarget.h"
+#include "cmLinkItem.h"
+#include "cmListFileCache.h"
#include "cmOutputConverter.h"
#include "cmStateDirectory.h"
#include "cmStateTypes.h"
+#include "cmStringAlgorithms.h"
#include "cmSystemTools.h"
cmLinkLineComputer::cmLinkLineComputer(cmOutputConverter* outputConverter,
@@ -55,22 +59,49 @@ std::string cmLinkLineComputer::ConvertToLinkReference(
std::string cmLinkLineComputer::ComputeLinkLibs(cmComputeLinkInformation& cli)
{
std::string linkLibs;
- typedef cmComputeLinkInformation::ItemVector ItemVector;
+ std::vector<BT<std::string>> linkLibsList;
+ this->ComputeLinkLibs(cli, linkLibsList);
+ cli.AppendValues(linkLibs, linkLibsList);
+ return linkLibs;
+}
+
+void cmLinkLineComputer::ComputeLinkLibs(
+ cmComputeLinkInformation& cli, std::vector<BT<std::string>>& linkLibraries)
+{
+ using ItemVector = cmComputeLinkInformation::ItemVector;
ItemVector const& items = cli.GetItems();
for (auto const& item : items) {
if (item.Target &&
item.Target->GetType() == cmStateEnums::INTERFACE_LIBRARY) {
continue;
}
+
+ BT<std::string> linkLib;
if (item.IsPath) {
- linkLibs +=
+ linkLib.Value += cli.GetLibLinkFileFlag();
+ linkLib.Value +=
this->ConvertToOutputFormat(this->ConvertToLinkReference(item.Value));
} else {
- linkLibs += item.Value;
+ linkLib.Value += item.Value;
}
- linkLibs += " ";
+ linkLib.Value += " ";
+
+ const cmLinkImplementation* linkImpl =
+ cli.GetTarget()->GetLinkImplementation(cli.GetConfig());
+
+ for (const cmLinkImplItem& iter : linkImpl->Libraries) {
+ if (iter.Target != nullptr &&
+ iter.Target->GetType() != cmStateEnums::INTERFACE_LIBRARY) {
+ std::string libPath = iter.Target->GetLocation(cli.GetConfig());
+ if (item.Value == libPath) {
+ linkLib.Backtrace = iter.Backtrace;
+ break;
+ }
+ }
+ }
+
+ linkLibraries.emplace_back(linkLib);
}
- return linkLibs;
}
std::string cmLinkLineComputer::ConvertToOutputFormat(std::string const& input)
@@ -99,8 +130,19 @@ std::string cmLinkLineComputer::ComputeLinkPath(
std::string const& libPathTerminator)
{
std::string linkPath;
+ std::vector<BT<std::string>> linkPathList;
+ this->ComputeLinkPath(cli, libPathFlag, libPathTerminator, linkPathList);
+ cli.AppendValues(linkPath, linkPathList);
+ return linkPath;
+}
+void cmLinkLineComputer::ComputeLinkPath(
+ cmComputeLinkInformation& cli, std::string const& libPathFlag,
+ std::string const& libPathTerminator, std::vector<BT<std::string>>& linkPath)
+{
if (cli.GetLinkLanguage() == "Swift") {
+ std::string linkPathNoBT;
+
for (const cmComputeLinkInformation::Item& item : cli.GetItems()) {
const cmGeneratorTarget* target = item.Target;
if (!target) {
@@ -110,24 +152,27 @@ std::string cmLinkLineComputer::ComputeLinkPath(
if (target->GetType() == cmStateEnums::STATIC_LIBRARY ||
target->GetType() == cmStateEnums::SHARED_LIBRARY) {
cmStateEnums::ArtifactType type = cmStateEnums::RuntimeBinaryArtifact;
- if (target->GetType() == cmStateEnums::SHARED_LIBRARY &&
- target->IsDLLPlatform()) {
+ if (target->HasImportLibrary(cli.GetConfig())) {
type = cmStateEnums::ImportLibraryArtifact;
}
- linkPath += " " + libPathFlag +
- item.Target->GetDirectory(cli.GetConfig(), type) +
- libPathTerminator + " ";
+ linkPathNoBT += cmStrCat(
+ " ", libPathFlag, item.Target->GetDirectory(cli.GetConfig(), type),
+ libPathTerminator, " ");
}
}
- }
- for (std::string const& libDir : cli.GetDirectories()) {
- linkPath += " " + libPathFlag + this->ConvertToOutputForExisting(libDir) +
- libPathTerminator + " ";
+ if (!linkPathNoBT.empty()) {
+ linkPath.emplace_back(std::move(linkPathNoBT));
+ }
}
- return linkPath;
+ for (BT<std::string> libDir : cli.GetDirectoriesWithBacktraces()) {
+ libDir.Value = cmStrCat(" ", libPathFlag,
+ this->ConvertToOutputForExisting(libDir.Value),
+ libPathTerminator, " ");
+ linkPath.emplace_back(libDir);
+ }
}
std::string cmLinkLineComputer::ComputeRPath(cmComputeLinkInformation& cli)
@@ -177,13 +222,30 @@ std::string cmLinkLineComputer::ComputeFrameworkPath(
std::string cmLinkLineComputer::ComputeLinkLibraries(
cmComputeLinkInformation& cli, std::string const& stdLibString)
{
- std::ostringstream fout;
- fout << this->ComputeRPath(cli);
+ std::string linkLibraries;
+ std::vector<BT<std::string>> linkLibrariesList;
+ this->ComputeLinkLibraries(cli, stdLibString, linkLibrariesList);
+ cli.AppendValues(linkLibraries, linkLibrariesList);
+ return linkLibraries;
+}
+
+void cmLinkLineComputer::ComputeLinkLibraries(
+ cmComputeLinkInformation& cli, std::string const& stdLibString,
+ std::vector<BT<std::string>>& linkLibraries)
+{
+ std::ostringstream rpathOut;
+ rpathOut << this->ComputeRPath(cli);
+
+ std::string rpath = rpathOut.str();
+ if (!rpath.empty()) {
+ linkLibraries.emplace_back(std::move(rpath));
+ }
// Write the library flags to the build rule.
- fout << this->ComputeLinkLibs(cli);
+ this->ComputeLinkLibs(cli, linkLibraries);
// Add the linker runtime search path if any.
+ std::ostringstream fout;
std::string rpath_link = cli.GetRPathLinkString();
if (!cli.GetRPathLinkFlag().empty() && !rpath_link.empty()) {
fout << cli.GetRPathLinkFlag();
@@ -196,7 +258,10 @@ std::string cmLinkLineComputer::ComputeLinkLibraries(
fout << stdLibString << " ";
}
- return fout.str();
+ std::string remainingLibs = fout.str();
+ if (!remainingLibs.empty()) {
+ linkLibraries.emplace_back(remainingLibs);
+ }
}
std::string cmLinkLineComputer::GetLinkerLanguage(cmGeneratorTarget* target,