Genex: Simplify TARGET_PROPERTY transitive lookup

In cmGeneratorExpressionEvaluator, make getLinkedTargetsContent a
template so it can traverse over either the Libraries in a cmTarget
LinkImplementationLibraries or a cmTarget LinkInterfaceLibraries.  This
also avoids creating a separate vector<cmTarget*>.
This commit is contained in:
Brad King 2014-07-15 11:50:32 -04:00
parent 0a8fbac19a
commit 8cb9105431
1 changed files with 30 additions and 64 deletions

View File

@ -799,72 +799,51 @@ static const char* targetPropertyTransitiveWhitelist[] = {
#undef TRANSITIVE_PROPERTY_NAME
template <typename T>
std::string
getLinkedTargetsContent(
std::vector<cmTarget const*> &targets,
std::vector<T> const &libraries,
cmTarget const* target,
cmTarget const* headTarget,
cmGeneratorExpressionContext *context,
cmGeneratorExpressionDAGChecker *dagChecker,
const std::string &interfacePropertyName)
{
cmGeneratorExpression ge(&context->Backtrace);
std::string linkedTargetsContent;
std::string sep;
std::string depString;
for (std::vector<cmTarget const*>::const_iterator
it = targets.begin();
it != targets.end(); ++it)
for (typename std::vector<T>::const_iterator it = libraries.begin();
it != libraries.end(); ++it)
{
if (*it == target)
// Broken code can have a target in its own link interface.
// Don't follow such link interface entries so as not to create a
// self-referencing loop.
if (it->Target && it->Target != target)
{
// Broken code can have a target in its own link interface.
// Don't follow such link interface entries so as not to create a
// self-referencing loop.
continue;
depString +=
sep + "$<TARGET_PROPERTY:" +
it->Target->GetName() + "," + interfacePropertyName + ">";
sep = ";";
}
depString +=
sep + "$<TARGET_PROPERTY:" +
(*it)->GetName() + "," + interfacePropertyName + ">";
sep = ";";
}
cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(depString);
std::string linkedTargetsContent = cge->Evaluate(target->GetMakefile(),
context->Config,
context->Quiet,
headTarget,
target,
dagChecker);
if (cge->GetHadContextSensitiveCondition())
if(!depString.empty())
{
context->HadContextSensitiveCondition = true;
cmGeneratorExpression ge(&context->Backtrace);
cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(depString);
linkedTargetsContent = cge->Evaluate(target->GetMakefile(),
context->Config,
context->Quiet,
headTarget,
target,
dagChecker);
if (cge->GetHadContextSensitiveCondition())
{
context->HadContextSensitiveCondition = true;
}
}
return linkedTargetsContent;
}
std::string
getLinkedTargetsContent(
std::vector<cmLinkImplItem> const &libraries,
cmTarget const* target,
cmTarget const* headTarget,
cmGeneratorExpressionContext *context,
cmGeneratorExpressionDAGChecker *dagChecker,
const std::string &interfacePropertyName)
{
std::vector<cmTarget const*> tgts;
for (std::vector<cmLinkImplItem>::const_iterator
it = libraries.begin();
it != libraries.end(); ++it)
{
if (it->Target)
{
tgts.push_back(it->Target);
}
}
return getLinkedTargetsContent(tgts, target, headTarget, context,
dagChecker, interfacePropertyName);
}
//----------------------------------------------------------------------------
static const struct TargetPropertyNode : public cmGeneratorExpressionNode
{
@ -1098,27 +1077,14 @@ static const struct TargetPropertyNode : public cmGeneratorExpressionNode
if (std::find_if(transBegin, transEnd,
cmStrCmp(propertyName)) != transEnd)
{
std::vector<cmTarget const*> tgts;
if(cmTarget::LinkInterfaceLibraries const* iface =
target->GetLinkInterfaceLibraries(context->Config, headTarget, true))
{
for(std::vector<cmLinkItem>::const_iterator
it = iface->Libraries.begin();
it != iface->Libraries.end(); ++it)
{
if (it->Target)
{
tgts.push_back(it->Target);
}
}
}
if (!tgts.empty())
{
linkedTargetsContent =
getLinkedTargetsContent(tgts, target,
headTarget,
context, &dagChecker,
interfacePropertyName);
getLinkedTargetsContent(iface->Libraries, target,
headTarget,
context, &dagChecker,
interfacePropertyName);
}
}
else if (std::find_if(transBegin, transEnd,