summaryrefslogtreecommitdiffstats
path: root/Source/cmNinjaNormalTargetGenerator.cxx
diff options
context:
space:
mode:
authorBill Hoffman <bill.hoffman@kitware.com>2016-06-02 22:08:30 (GMT)
committerBrad King <brad.king@kitware.com>2016-06-17 14:56:40 (GMT)
commit96242f8022fa4bc718ef36cda43f5dfe6236c066 (patch)
treeeb344591def11380b95fba62e71aa950e3671b87 /Source/cmNinjaNormalTargetGenerator.cxx
parentba92e11f8b461513566d5cc3c0b53b2215bb85f7 (diff)
downloadCMake-96242f8022fa4bc718ef36cda43f5dfe6236c066.zip
CMake-96242f8022fa4bc718ef36cda43f5dfe6236c066.tar.gz
CMake-96242f8022fa4bc718ef36cda43f5dfe6236c066.tar.bz2
Add options to run `ldd -u -r` as a "link-what-you-use" tool
Create a LINK_WHAT_YOU_USE target property and corresponding CMAKE_LINK_WHAT_YOU_USE variable to enable this behavior. Extend link commands by running `ldd -u -r` to detect shared libraries that are linked but not needed.
Diffstat (limited to 'Source/cmNinjaNormalTargetGenerator.cxx')
-rw-r--r--Source/cmNinjaNormalTargetGenerator.cxx24
1 files changed, 22 insertions, 2 deletions
diff --git a/Source/cmNinjaNormalTargetGenerator.cxx b/Source/cmNinjaNormalTargetGenerator.cxx
index 3e91545..7c18414 100644
--- a/Source/cmNinjaNormalTargetGenerator.cxx
+++ b/Source/cmNinjaNormalTargetGenerator.cxx
@@ -295,6 +295,22 @@ std::vector<std::string> cmNinjaNormalTargetGenerator::ComputeLinkCmd()
const char* linkCmd = mf->GetDefinition(linkCmdVar);
if (linkCmd) {
cmSystemTools::ExpandListArgument(linkCmd, linkCmds);
+ if (this->GetGeneratorTarget()->GetProperty("LINK_WHAT_YOU_USE")) {
+ std::string cmakeCommand =
+ this->GetLocalGenerator()->ConvertToOutputFormat(
+ cmSystemTools::GetCMakeCommand(), cmLocalGenerator::SHELL);
+ cmakeCommand += " -E __run_iwyu --lwyu=";
+ cmGeneratorTarget& gt = *this->GetGeneratorTarget();
+ const std::string cfgName = this->GetConfigName();
+ std::string targetOutput = ConvertToNinjaPath(gt.GetFullPath(cfgName));
+ std::string targetOutputReal =
+ this->ConvertToNinjaPath(gt.GetFullPath(cfgName,
+ /*implib=*/false,
+ /*realpath=*/true));
+ cmakeCommand += targetOutputReal;
+ cmakeCommand += " || true";
+ linkCmds.push_back(cmakeCommand);
+ }
return linkCmds;
}
}
@@ -467,6 +483,10 @@ void cmNinjaNormalTargetGenerator::WriteLinkStatement()
vars["MANIFESTS"] = this->GetManifests();
vars["LINK_PATH"] = frameworkPath + linkPath;
+ std::string lwyuFlags;
+ if (genTarget.GetProperty("LINK_WHAT_YOU_USE")) {
+ lwyuFlags = " -Wl,--no-as-needed";
+ }
// Compute architecture specific link flags. Yes, these go into a different
// variable for executables, probably due to a mistake made when duplicating
@@ -474,16 +494,17 @@ void cmNinjaNormalTargetGenerator::WriteLinkStatement()
if (targetType == cmState::EXECUTABLE) {
std::string t = vars["FLAGS"];
localGen.AddArchitectureFlags(t, &genTarget, TargetLinkLanguage, cfgName);
+ t += lwyuFlags;
vars["FLAGS"] = t;
} else {
std::string t = vars["ARCH_FLAGS"];
localGen.AddArchitectureFlags(t, &genTarget, TargetLinkLanguage, cfgName);
vars["ARCH_FLAGS"] = t;
t = "";
+ t += lwyuFlags;
localGen.AddLanguageFlags(t, TargetLinkLanguage, cfgName);
vars["LANGUAGE_COMPILE_FLAGS"] = t;
}
-
if (this->GetGeneratorTarget()->HasSOName(cfgName)) {
vars["SONAME_FLAG"] = mf->GetSONameFlag(this->TargetLinkLanguage);
vars["SONAME"] = this->TargetNameSO;
@@ -607,7 +628,6 @@ void cmNinjaNormalTargetGenerator::WriteLinkStatement()
vars["POST_BUILD"] = ":";
symlinkVars["POST_BUILD"] = postBuildCmdLine;
}
-
cmGlobalNinjaGenerator& globalGen = *this->GetGlobalGenerator();
int commandLineLengthLimit = -1;