1
0
mirror of https://github.com/Kitware/CMake.git synced 2025-10-16 14:08:35 +08:00

Restore support for exporting INTERFACE with missing dependencies

Since commit c16acd35b3 (GenEx: Add support for custom transitive link
properties, 2024-05-09, v3.30.0-rc1~82^2) evaluation of
`TRANSITIVE_LINK_PROPERTIES` by `install(EXPORT)` enables discovery of
missing dependencies on INTERFACE libraries that we did not previously
diagnose.  This regressed existing projects that relied on such
non-diagnosis.  Although commit 2fc9e482a9 (Evaluation of
TRANSITIVE_LINK_PROPERTIES isn't considered a usage, 2024-07-05) fixed
this, it also made a significant change to the `UseTo` infrastructure
that may have other subtle effects.  Replace the fix with an approach
that explicitly models suppression of the relevant diagnostics.

Fixes: #26108
This commit is contained in:
Brad King
2024-07-15 11:52:37 -04:00
parent b9e2f6828f
commit 7a77a6c642
5 changed files with 45 additions and 9 deletions

View File

@@ -613,6 +613,7 @@ void cmExportFileGenerator::PopulateCustomTransitiveInterfaceProperties(
properties);
this->PopulateInterfaceProperty("TRANSITIVE_LINK_PROPERTIES", target,
properties);
cmGeneratorTarget::CheckLinkLibrariesSuppressionRAII cllSuppressRAII;
std::set<std::string> ifaceProperties;
for (std::string const& config : this->Configurations) {
for (auto const& i : target->GetCustomTransitiveProperties(

View File

@@ -99,6 +99,13 @@ public:
// Call this after generation is complete.
void CheckLinkLibraries() const;
class CheckLinkLibrariesSuppressionRAII
{
public:
CheckLinkLibrariesSuppressionRAII();
~CheckLinkLibrariesSuppressionRAII();
};
cmStateEnums::TargetType GetType() const;
const std::string& GetName() const;
std::string GetExportName() const;
@@ -264,7 +271,6 @@ public:
{
Compile, // Usage requirements for compiling. Excludes $<LINK_ONLY>.
Link, // Usage requirements for linking. Includes $<LINK_ONLY>.
LinkInterfaceEval,
};
cmLinkInterfaceLibraries const* GetLinkInterfaceLibraries(

View File

@@ -54,6 +54,20 @@ const std::string kINTERFACE_LINK_LIBRARIES_DIRECT =
"INTERFACE_LINK_LIBRARIES_DIRECT";
const std::string kINTERFACE_LINK_LIBRARIES_DIRECT_EXCLUDE =
"INTERFACE_LINK_LIBRARIES_DIRECT_EXCLUDE";
unsigned int CheckLinkLibrariesSuppressionRAIICount;
void MaybeEnableCheckLinkLibraries(cmOptionalLinkImplementation& impl)
{
if (CheckLinkLibrariesSuppressionRAIICount == 0) {
impl.CheckLinkLibraries = true;
}
}
void MaybeEnableCheckLinkLibraries(cmOptionalLinkInterface& iface)
{
if (CheckLinkLibrariesSuppressionRAIICount == 0) {
iface.CheckLinkLibraries = true;
}
}
}
class cmTargetCollectLinkLanguages
@@ -372,7 +386,8 @@ void cmGeneratorTarget::CheckLinkLibraries() const
// There could be several entries used when computing the pre-CMP0022
// default link interface. Check only the entry for our own link impl.
auto const hmi = hm.find(this);
if (hmi == hm.end() || !hmi->second.LibrariesDone) {
if (hmi == hm.end() || !hmi->second.LibrariesDone ||
!hmi->second.CheckLinkLibraries) {
continue;
}
for (cmLinkImplItem const& item : hmi->second.Libraries) {
@@ -392,7 +407,7 @@ void cmGeneratorTarget::CheckLinkLibraries() const
// should be a subset of LinkInterfaceMap (with LINK_ONLY left out).
for (auto const& hmp : this->LinkInterfaceMap) {
for (auto const& hmi : hmp.second) {
if (!hmi.second.LibrariesDone || hmi.second.LinkOnlyEval) {
if (!hmi.second.LibrariesDone || !hmi.second.CheckLinkLibraries) {
continue;
}
for (cmLinkItem const& item : hmi.second.Libraries) {
@@ -408,6 +423,18 @@ void cmGeneratorTarget::CheckLinkLibraries() const
}
}
cmGeneratorTarget::CheckLinkLibrariesSuppressionRAII::
CheckLinkLibrariesSuppressionRAII()
{
++CheckLinkLibrariesSuppressionRAIICount;
}
cmGeneratorTarget::CheckLinkLibrariesSuppressionRAII::
~CheckLinkLibrariesSuppressionRAII()
{
--CheckLinkLibrariesSuppressionRAIICount;
}
namespace {
cm::string_view missingTargetPossibleReasons =
"Possible reasons include:\n"
@@ -642,7 +669,7 @@ cmLinkInterface const* cmGeneratorTarget::GetLinkInterface(
if (secondPass) {
iface = cmOptionalLinkInterface();
}
iface.LinkOnlyEval = false;
MaybeEnableCheckLinkLibraries(iface);
if (!iface.LibrariesDone) {
iface.LibrariesDone = true;
this->ComputeLinkInterfaceLibraries(config, iface, head, UseTo::Link);
@@ -766,7 +793,7 @@ const cmLinkInterfaceLibraries* cmGeneratorTarget::GetLinkInterfaceLibraries(
}
cmOptionalLinkInterface& iface = hm[head];
iface.LinkOnlyEval = (usage == UseTo::LinkInterfaceEval);
MaybeEnableCheckLinkLibraries(iface);
if (!iface.LibrariesDone) {
iface.LibrariesDone = true;
this->ComputeLinkInterfaceLibraries(config, iface, head, usage);
@@ -1036,7 +1063,7 @@ const cmLinkInterface* cmGeneratorTarget::GetImportLinkInterface(
if (secondPass) {
iface = cmOptionalLinkInterface();
}
iface.LinkOnlyEval = (usage == UseTo::LinkInterfaceEval);
MaybeEnableCheckLinkLibraries(iface);
if (!iface.AllDone) {
iface.AllDone = true;
iface.LibrariesDone = true;
@@ -1109,6 +1136,7 @@ const cmLinkImplementation* cmGeneratorTarget::GetLinkImplementation(
if (secondPass) {
impl = cmOptionalLinkImplementation();
}
MaybeEnableCheckLinkLibraries(impl);
if (!impl.LibrariesDone) {
impl.LibrariesDone = true;
this->ComputeLinkImplementationLibraries(config, impl, this, usage);
@@ -1165,6 +1193,7 @@ cmGeneratorTarget::GetLinkImplementationLibrariesInternal(
}
cmOptionalLinkImplementation& impl = hm[head];
MaybeEnableCheckLinkLibraries(impl);
if (!impl.LibrariesDone) {
impl.LibrariesDone = true;
this->ComputeLinkImplementationLibraries(config, impl, head, usage);

View File

@@ -286,8 +286,7 @@ cmGeneratorTarget::GetCustomTransitiveProperties(std::string const& config,
}
}
};
addTransitiveProperties("TRANSITIVE_LINK_PROPERTIES",
UseTo::LinkInterfaceEval);
addTransitiveProperties("TRANSITIVE_LINK_PROPERTIES", UseTo::Link);
addTransitiveProperties("TRANSITIVE_COMPILE_PROPERTIES", UseTo::Compile);
i = ctpm.emplace(config, std::move(ctp)).first;
}

View File

@@ -120,11 +120,11 @@ struct cmLinkInterface : public cmLinkInterfaceLibraries
struct cmOptionalLinkInterface : public cmLinkInterface
{
bool LinkOnlyEval = false;
bool LibrariesDone = false;
bool AllDone = false;
bool Exists = false;
bool Explicit = false;
bool CheckLinkLibraries = false;
};
struct cmHeadToLinkInterfaceMap
@@ -149,6 +149,7 @@ struct cmOptionalLinkImplementation : public cmLinkImplementation
bool LibrariesDone = false;
bool LanguagesDone = false;
bool HadHeadSensitiveCondition = false;
bool CheckLinkLibraries = false;
};
/** Compute the link type to use for the given configuration. */