[Cmake-commits] CMake branch, next, updated. v3.0.0-3769-gf8707ba

Brad King brad.king at kitware.com
Mon Jun 16 15:22:53 EDT 2014


This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "CMake".

The branch, next has been updated
       via  f8707babfdda369b82260c53b0ee064901795586 (commit)
       via  71049a249861bb2ddc80c49bec0f3eebdaaba2a4 (commit)
       via  8da2adbc30f636009a5099c5d778d0e1fb3d1606 (commit)
       via  1221d994c9cb074f2bc579f42b7eb504ff96a23d (commit)
       via  8904875a83040b81aa7a52b96ff3fabbcff099eb (commit)
       via  d9f8c8722150f23e07b730d45a50d6b4b77bdf52 (commit)
       via  e6911d51734d128899ac5887098b74811ecc61cf (commit)
       via  1767f227b356df807ccbe85c606ef9e555b5206f (commit)
       via  40f16b63e64242200cb0172208af78f62696fa4c (commit)
       via  0b33ff53030667a540ff42b9960692c7202feff5 (commit)
       via  109f3fee334cfde2ab210470f00b0b5cd32759c4 (commit)
       via  ed00c8c6d1b226ed614ebfaf4fe99b2be3f7ebad (commit)
       via  992821ef04532f377d043b1258d2f46c65dfc988 (commit)
       via  cc923aa541b0d10dbe06c87aaba2ed2096b995ef (commit)
       via  ea985616b79a251e24d8d257da33e1ba290b2699 (commit)
       via  9b268d63435a36525a39dbaced028b21dceee539 (commit)
       via  7d06f2db29f4df8dd4a452dce5291dae6fb81ba9 (commit)
       via  03fe9ec68f9301f070df3f24403d487a26b67887 (commit)
       via  3fed4a603b21aa83a5770b1a1ecff920ab7bb799 (commit)
       via  c5f08a6a068ca9eb8c278e1c8728daa1c9e5a6fb (commit)
       via  1d84985979e1c46fffcb3b09fc305a54396a8e93 (commit)
       via  5d15419d061648cc24ab2bb01a1dace63698e4f3 (commit)
       via  bdd2a90f8aa0fad1e215fe9aac3c0da04c835555 (commit)
      from  9cc7ab89c4fc20dfa85ec271b21c80908247183c (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=f8707babfdda369b82260c53b0ee064901795586
commit f8707babfdda369b82260c53b0ee064901795586
Merge: 9cc7ab8 71049a2
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 15:22:51 2014 -0400
Commit:     CMake Topic Stage <kwrobot at kitware.com>
CommitDate: Mon Jun 16 15:22:51 2014 -0400

    Merge topic 'refactor-link-internals' into next
    
    71049a24 cmTarget: De-duplicate link interface evaluation code for $<LINK_ONLY>
    8da2adbc cmTarget: De-duplicate link interface genex code for $<LINK_ONLY>
    1221d994 cmTarget: Drop GetDirectLinkLibraries methods
    8904875a cmTarget: Improve HaveBuildTreeRPATH implementation
    d9f8c872 cmTarget: Lookup targets in LinkInterface and LinkImplementation
    e6911d51 cmComputeLinkDepends: Simplify CheckWrongConfigItem implementation
    1767f227 cmTarget: Simplify processILibs implementation
    40f16b63 cmTarget: Add GetUtilityItems to get target ordering dependencies
    0b33ff53 cmTarget: Add cmLinkItem to refer to a target by name and pointer
    109f3fee cmTarget: Drop 'head' target from GetImportInfo
    ed00c8c6 cmTarget: De-duplicate library list expansion
    992821ef Fix scope of transitive target name lookups
    cc923aa5 cmTarget: Constify GetLinkImplementationClosure results
    ea985616 cmTarget: Constify GetTransitivePropertyTargets results
    9b268d63 cmComputeTargetDepends: Remove unused 'linking' argument
    7d06f2db cmTarget: Add method to lookup other targets in a target's scope
    ...


http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=71049a249861bb2ddc80c49bec0f3eebdaaba2a4
commit 71049a249861bb2ddc80c49bec0f3eebdaaba2a4
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 14:27:42 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:28 2014 -0400

    cmTarget: De-duplicate link interface evaluation code for $<LINK_ONLY>
    
    Add a 'linking' parameter to GetLinkInterfaceLibraries to indicate
    whether the $<LINK_ONLY> generator expression should evaluate or return
    an empty string.  Teach GetTransitivePropertyTargets to use the method
    with linking==false instead of duplicating INTERFACE_LINK_LIBRARIES
    evaluation code.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index b86a5d8..de40c1e 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -126,11 +126,13 @@ public:
   typedef std::map<TargetConfigPair, OptionalLinkInterface>
                                                           LinkInterfaceMapType;
   LinkInterfaceMapType LinkInterfaceMap;
+  LinkInterfaceMapType LinkInterfaceTransitiveOnlyMap;
   bool PolicyWarnedCMP0022;
 
   typedef std::map<TargetConfigPair, cmTarget::LinkInterface>
                                                     ImportLinkInterfaceMapType;
   ImportLinkInterfaceMapType ImportLinkInterfaceMap;
+  ImportLinkInterfaceMapType ImportLinkInterfaceTransitiveOnlyMap;
 
   typedef std::map<std::string, cmTarget::OutputInfo> OutputInfoMapType;
   OutputInfoMapType OutputInfoMap;
@@ -510,7 +512,9 @@ void cmTarget::ClearLinkMaps()
   this->LinkImplementationLanguageIsContextDependent = true;
   this->Internal->LinkImplMap.clear();
   this->Internal->LinkInterfaceMap.clear();
+  this->Internal->LinkInterfaceTransitiveOnlyMap.clear();
   this->Internal->ImportLinkInterfaceMap.clear();
+  this->Internal->ImportLinkInterfaceTransitiveOnlyMap.clear();
   this->Internal->LinkClosureMap.clear();
   for (cmTargetLinkInformationMap::const_iterator it
       = this->LinkInformation.begin();
@@ -6038,7 +6042,7 @@ cmTarget::LinkInterface const* cmTarget::GetLinkInterface(
   // Imported targets have their own link interface.
   if(this->IsImported())
     {
-    return this->GetImportLinkInterface(config, head);
+    return this->GetImportLinkInterface(config, head, true);
     }
 
   // Link interfaces are not supported for executables that do not
@@ -6059,7 +6063,8 @@ cmTarget::LinkInterface const* cmTarget::GetLinkInterface(
     // Compute the link interface for this configuration.
     cmTargetInternals::OptionalLinkInterface iface;
     iface.ExplicitLibraries =
-        this->ComputeLinkInterfaceLibraries(config, iface, head, iface.Exists);
+      this->ComputeLinkInterfaceLibraries(config, iface, head, true,
+                                          iface.Exists);
     if (iface.Exists)
       {
       this->Internal->ComputeLinkInterface(this, config, iface,
@@ -6082,12 +6087,13 @@ cmTarget::LinkInterface const* cmTarget::GetLinkInterface(
 //----------------------------------------------------------------------------
 cmTarget::LinkInterface const*
 cmTarget::GetLinkInterfaceLibraries(const std::string& config,
-                                    cmTarget const* head) const
+                                    cmTarget const* head,
+                                    bool linking) const
 {
   // Imported targets have their own link interface.
   if(this->IsImported())
     {
-    return this->GetImportLinkInterface(config, head);
+    return this->GetImportLinkInterface(config, head, linking);
     }
 
   // Link interfaces are not supported for executables that do not
@@ -6100,21 +6106,24 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
 
   // Lookup any existing link interface for this configuration.
   TargetConfigPair key(head, cmSystemTools::UpperCase(config));
+  cmTargetInternals::LinkInterfaceMapType& lim =
+    linking? this->Internal->LinkInterfaceMap :
+             this->Internal->LinkInterfaceTransitiveOnlyMap;
 
-  cmTargetInternals::LinkInterfaceMapType::iterator
-    i = this->Internal->LinkInterfaceMap.find(key);
-  if(i == this->Internal->LinkInterfaceMap.end())
+  cmTargetInternals::LinkInterfaceMapType::iterator i = lim.find(key);
+  if(i == lim.end())
     {
     // Compute the link interface for this configuration.
     cmTargetInternals::OptionalLinkInterface iface;
     iface.ExplicitLibraries = this->ComputeLinkInterfaceLibraries(config,
                                                                 iface,
                                                                 head,
+                                                                linking,
                                                                 iface.Exists);
 
     // Store the information for this configuration.
     cmTargetInternals::LinkInterfaceMapType::value_type entry(key, iface);
-    i = this->Internal->LinkInterfaceMap.insert(entry).first;
+    i = lim.insert(entry).first;
     }
 
   return i->second.Exists ? &i->second : 0;
@@ -6123,7 +6132,8 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
 //----------------------------------------------------------------------------
 cmTarget::LinkInterface const*
 cmTarget::GetImportLinkInterface(const std::string& config,
-                                 cmTarget const* headTarget) const
+                                 cmTarget const* headTarget,
+                                 bool linking) const
 {
   cmTarget::ImportInfo const* info = this->GetImportInfo(config);
   if(!info)
@@ -6132,16 +6142,18 @@ cmTarget::GetImportLinkInterface(const std::string& config,
     }
 
   TargetConfigPair key(headTarget, cmSystemTools::UpperCase(config));
+  cmTargetInternals::ImportLinkInterfaceMapType& lim =
+    linking? this->Internal->ImportLinkInterfaceMap :
+             this->Internal->ImportLinkInterfaceTransitiveOnlyMap;
 
-  cmTargetInternals::ImportLinkInterfaceMapType::iterator i =
-    this->Internal->ImportLinkInterfaceMap.find(key);
-  if(i == this->Internal->ImportLinkInterfaceMap.end())
+  cmTargetInternals::ImportLinkInterfaceMapType::iterator i = lim.find(key);
+  if(i == lim.end())
     {
     LinkInterface iface;
     iface.Multiplicity = info->Multiplicity;
     cmSystemTools::ExpandListArgument(info->Languages, iface.Languages);
     this->ExpandLinkItems(info->LibrariesProp, info->Libraries, config,
-                          headTarget, true, iface.Libraries);
+                          headTarget, linking, iface.Libraries);
     {
     std::vector<std::string> deps;
     cmSystemTools::ExpandListArgument(info->SharedDeps, deps);
@@ -6150,7 +6162,7 @@ cmTarget::GetImportLinkInterface(const std::string& config,
 
     cmTargetInternals::ImportLinkInterfaceMapType::value_type
       entry(key, iface);
-    i = this->Internal->ImportLinkInterfaceMap.insert(entry).first;
+    i = lim.insert(entry).first;
     }
   return &i->second;
 }
@@ -6166,7 +6178,7 @@ void processILibs(const std::string& config,
     {
     tgts.push_back(item.Target);
     if(cmTarget::LinkInterface const* iface =
-       item.Target->GetLinkInterfaceLibraries(config, headTarget))
+       item.Target->GetLinkInterfaceLibraries(config, headTarget, true))
       {
       for(std::vector<cmLinkItem>::const_iterator
             it = iface->Libraries.begin();
@@ -6206,15 +6218,8 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
                                       cmTarget const* headTarget,
                                       std::vector<cmTarget const*> &tgts) const
 {
-  cmTarget::LinkInterface const* iface
-                        = this->GetLinkInterfaceLibraries(config, headTarget);
-  if (!iface)
-    {
-    return;
-    }
-  if(this->GetType() != STATIC_LIBRARY
-      || this->GetPolicyStatusCMP0022() == cmPolicies::WARN
-      || this->GetPolicyStatusCMP0022() == cmPolicies::OLD)
+  if(cmTarget::LinkInterface const* iface =
+     this->GetLinkInterfaceLibraries(config, headTarget, false))
     {
     for(std::vector<cmLinkItem>::const_iterator it = iface->Libraries.begin();
         it != iface->Libraries.end(); ++it)
@@ -6224,29 +6229,6 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
         tgts.push_back(it->Target);
         }
       }
-    return;
-    }
-
-  const char* linkIfaceProp = "INTERFACE_LINK_LIBRARIES";
-  const char* interfaceLibs = this->GetProperty(linkIfaceProp);
-
-  if (!interfaceLibs)
-    {
-    return;
-    }
-
-  // The interface libraries have been explicitly set.
-  std::vector<cmLinkItem> libs;
-  this->ExpandLinkItems(linkIfaceProp, interfaceLibs, config,
-                        headTarget, false, libs);
-
-  for(std::vector<cmLinkItem>::const_iterator it = libs.begin();
-      it != libs.end(); ++it)
-    {
-    if (it->Target)
-      {
-      tgts.push_back(it->Target);
-      }
     }
 }
 
@@ -6254,7 +6236,7 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
 const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
                                            LinkInterface& iface,
                                            cmTarget const* headTarget,
-                                           bool &exists) const
+                                           bool linking, bool &exists) const
 {
   // Construct the property name suffix for this configuration.
   std::string suffix = "_";
@@ -6339,7 +6321,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
     {
     // The interface libraries have been explicitly set.
     this->ExpandLinkItems(linkIfaceProp, explicitLibraries, config,
-                          headTarget, true, iface.Libraries);
+                          headTarget, linking, iface.Libraries);
     }
   else if (this->PolicyStatusCMP0022 == cmPolicies::WARN
         || this->PolicyStatusCMP0022 == cmPolicies::OLD)
@@ -6353,7 +6335,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
         this->GetLinkImplementationLibrariesInternal(config, headTarget);
     iface.Libraries = impl->Libraries;
     if(this->PolicyStatusCMP0022 == cmPolicies::WARN &&
-       !this->Internal->PolicyWarnedCMP0022)
+       !this->Internal->PolicyWarnedCMP0022 && linking)
       {
       // Compare the link implementation fallback link interface to the
       // preferred new link interface property and warn if different.
@@ -6362,7 +6344,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
       if(const char* newExplicitLibraries = this->GetProperty(newProp))
         {
         this->ExpandLinkItems(newProp, newExplicitLibraries, config,
-                              headTarget, true, ifaceLibs);
+                              headTarget, linking, ifaceLibs);
         }
       if (ifaceLibs != impl->Libraries)
         {
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 3df5bdd..3b1a88f 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -280,7 +280,8 @@ public:
   LinkInterface const* GetLinkInterface(const std::string& config,
                                         cmTarget const* headTarget) const;
   LinkInterface const* GetLinkInterfaceLibraries(const std::string& config,
-                                        cmTarget const* headTarget) const;
+                                        cmTarget const* headTarget,
+                                        bool linking) const;
   void GetTransitivePropertyTargets(const std::string& config,
                                     cmTarget const* headTarget,
                                     std::vector<cmTarget const*> &libs) const;
@@ -757,11 +758,12 @@ private:
 
   LinkInterface const*
     GetImportLinkInterface(const std::string& config,
-                           cmTarget const* head) const;
+                           cmTarget const* head, bool linking) const;
 
   const char* ComputeLinkInterfaceLibraries(const std::string& config,
                                             LinkInterface& iface,
                                             cmTarget const* head,
+                                            bool linking,
                                             bool &exists) const;
 
   LinkImplementation const*

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=8da2adbc30f636009a5099c5d778d0e1fb3d1606
commit 8da2adbc30f636009a5099c5d778d0e1fb3d1606
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 14:25:40 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:28 2014 -0400

    cmTarget: De-duplicate link interface genex code for $<LINK_ONLY>
    
    Add a 'linking' parameter to ExpandLinkItems so that it knows whether to
    use SetTransitivePropertiesOnly while evaluating generator expressions.
    Use it in GetTransitivePropertyTargets to avoid duplicating the genex
    code.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 71d03df..b86a5d8 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -3688,10 +3688,16 @@ void cmTarget::ExpandLinkItems(std::string const& prop,
                                std::string const& value,
                                std::string const& config,
                                cmTarget const* headTarget,
+                               bool linking,
                                std::vector<cmLinkItem>& items) const
 {
   cmGeneratorExpression ge;
   cmGeneratorExpressionDAGChecker dagChecker(this->GetName(), prop, 0, 0);
+  if(!linking && this->GetType() == cmTarget::STATIC_LIBRARY &&
+     prop == "INTERFACE_LINK_LIBRARIES")
+    {
+    dagChecker.SetTransitivePropertiesOnly();
+    }
   std::vector<std::string> libs;
   cmSystemTools::ExpandListArgument(ge.Parse(value)->Evaluate(
                                       this->Makefile,
@@ -6135,7 +6141,7 @@ cmTarget::GetImportLinkInterface(const std::string& config,
     iface.Multiplicity = info->Multiplicity;
     cmSystemTools::ExpandListArgument(info->Languages, iface.Languages);
     this->ExpandLinkItems(info->LibrariesProp, info->Libraries, config,
-                          headTarget, iface.Libraries);
+                          headTarget, true, iface.Libraries);
     {
     std::vector<std::string> deps;
     cmSystemTools::ExpandListArgument(info->SharedDeps, deps);
@@ -6230,24 +6236,16 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
     }
 
   // The interface libraries have been explicitly set.
-  cmGeneratorExpression ge;
-  cmGeneratorExpressionDAGChecker dagChecker(this->GetName(),
-                                             linkIfaceProp, 0, 0);
-  dagChecker.SetTransitivePropertiesOnly();
-  std::vector<std::string> libs;
-  cmSystemTools::ExpandListArgument(ge.Parse(interfaceLibs)->Evaluate(
-                                      this->Makefile,
-                                      config,
-                                      false,
-                                      headTarget,
-                                      this, &dagChecker), libs);
+  std::vector<cmLinkItem> libs;
+  this->ExpandLinkItems(linkIfaceProp, interfaceLibs, config,
+                        headTarget, false, libs);
 
-  for(std::vector<std::string>::const_iterator it = libs.begin();
+  for(std::vector<cmLinkItem>::const_iterator it = libs.begin();
       it != libs.end(); ++it)
     {
-    if (cmTarget const* tgt = this->FindTargetToLink(*it))
+    if (it->Target)
       {
-      tgts.push_back(tgt);
+      tgts.push_back(it->Target);
       }
     }
 }
@@ -6341,7 +6339,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
     {
     // The interface libraries have been explicitly set.
     this->ExpandLinkItems(linkIfaceProp, explicitLibraries, config,
-                          headTarget, iface.Libraries);
+                          headTarget, true, iface.Libraries);
     }
   else if (this->PolicyStatusCMP0022 == cmPolicies::WARN
         || this->PolicyStatusCMP0022 == cmPolicies::OLD)
@@ -6364,7 +6362,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
       if(const char* newExplicitLibraries = this->GetProperty(newProp))
         {
         this->ExpandLinkItems(newProp, newExplicitLibraries, config,
-                              headTarget, ifaceLibs);
+                              headTarget, true, ifaceLibs);
         }
       if (ifaceLibs != impl->Libraries)
         {
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 3f534f2..3df5bdd 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -777,7 +777,7 @@ private:
 
   void ExpandLinkItems(std::string const& prop, std::string const& value,
                        std::string const& config, cmTarget const* headTarget,
-                       std::vector<cmLinkItem>& items) const;
+                       bool linking, std::vector<cmLinkItem>& items) const;
   void LookupLinkItems(std::vector<std::string> const& names,
                        std::vector<cmLinkItem>& items) const;
 

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=1221d994c9cb074f2bc579f42b7eb504ff96a23d
commit 1221d994c9cb074f2bc579f42b7eb504ff96a23d
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 14:12:18 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:28 2014 -0400

    cmTarget: Drop GetDirectLinkLibraries methods
    
    Inline the implementation in the last remaining caller and drop the
    methods.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index f4a0224..71d03df 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -1227,47 +1227,6 @@ bool cmTarget::NameResolvesToFramework(const std::string& libname) const
 }
 
 //----------------------------------------------------------------------------
-void cmTarget::GetDirectLinkLibraries(const std::string& config,
-                                      std::vector<std::string> &libs) const
-{
-  this->GetDirectLinkLibrariesInternal(config, libs, this);
-}
-
-//----------------------------------------------------------------------------
-void cmTarget::GetDirectLinkLibrariesInternal(const std::string& config,
-                                              std::vector<std::string> &libs,
-                                              cmTarget const* head) const
-{
-  const char *prop = this->GetProperty("LINK_LIBRARIES");
-  if (prop)
-    {
-    cmGeneratorExpression ge;
-    const cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(prop);
-
-    cmGeneratorExpressionDAGChecker dagChecker(
-                                        this->GetName(),
-                                        "LINK_LIBRARIES", 0, 0);
-    cmSystemTools::ExpandListArgument(cge->Evaluate(this->Makefile,
-                                        config,
-                                        false,
-                                        head,
-                                        &dagChecker),
-                                      libs);
-
-    std::set<std::string> const& seenProps = cge->GetSeenTargetProperties();
-    for (std::set<std::string>::const_iterator it = seenProps.begin();
-        it != seenProps.end(); ++it)
-      {
-      if (!this->GetProperty(*it))
-        {
-        this->LinkImplicitNullProperties.insert(*it);
-        }
-      }
-    cge->GetMaxLanguageStandard(this, this->MaxLanguageStandards);
-    }
-}
-
-//----------------------------------------------------------------------------
 std::string cmTarget::GetDebugGeneratorExpressions(const std::string &value,
                                   cmTarget::LinkLibraryType llt) const
 {
@@ -6634,7 +6593,33 @@ void cmTarget::ComputeLinkImplementation(const std::string& config,
 {
   // Collect libraries directly linked in this configuration.
   std::vector<std::string> llibs;
-  this->GetDirectLinkLibrariesInternal(config, llibs, head);
+  if(const char *prop = this->GetProperty("LINK_LIBRARIES"))
+    {
+    cmGeneratorExpression ge;
+    const cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(prop);
+
+    cmGeneratorExpressionDAGChecker dagChecker(
+                                        this->GetName(),
+                                        "LINK_LIBRARIES", 0, 0);
+    cmSystemTools::ExpandListArgument(cge->Evaluate(this->Makefile,
+                                        config,
+                                        false,
+                                        head,
+                                        &dagChecker),
+                                      llibs);
+
+    std::set<std::string> const& seenProps = cge->GetSeenTargetProperties();
+    for (std::set<std::string>::const_iterator it = seenProps.begin();
+        it != seenProps.end(); ++it)
+      {
+      if (!this->GetProperty(*it))
+        {
+        this->LinkImplicitNullProperties.insert(*it);
+        }
+      }
+    cge->GetMaxLanguageStandard(this, this->MaxLanguageStandards);
+    }
+
   for(std::vector<std::string>::const_iterator li = llibs.begin();
       li != llibs.end(); ++li)
     {
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 2e0df42..3f534f2 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -169,8 +169,6 @@ public:
   return this->LinkLibraries;}
   const LinkLibraryVectorType &GetOriginalLinkLibraries() const
     {return this->OriginalLinkLibraries;}
-  void GetDirectLinkLibraries(const std::string& config,
-                              std::vector<std::string> &) const;
 
   /** Compute the link type to use for the given configuration.  */
   LinkLibraryType ComputeLinkType(const std::string& config) const;
@@ -766,9 +764,6 @@ private:
                                             cmTarget const* head,
                                             bool &exists) const;
 
-  void GetDirectLinkLibrariesInternal(const std::string& config,
-                                      std::vector<std::string>& libs,
-                                      cmTarget const* head) const;
   LinkImplementation const*
     GetLinkImplementationLibrariesInternal(const std::string& config,
                                            cmTarget const* head) const;

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=8904875a83040b81aa7a52b96ff3fabbcff099eb
commit 8904875a83040b81aa7a52b96ff3fabbcff099eb
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 14:08:43 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:28 2014 -0400

    cmTarget: Improve HaveBuildTreeRPATH implementation
    
    Use GetLinkImplementationLibraries instead of GetDirectLinkLibraries
    because it tells us whether there will be any libraries to link after
    evaluating generator expressions.  Also GetDirectLinkLibraries will be
    dropped soon.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 7a63db4..f4a0224 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -4551,9 +4551,12 @@ bool cmTarget::HaveBuildTreeRPATH(const std::string& config) const
     {
     return false;
     }
-  std::vector<std::string> libs;
-  this->GetDirectLinkLibraries(config, libs);
-  return !libs.empty();
+  if(LinkImplementation const* impl =
+     this->GetLinkImplementationLibraries(config))
+    {
+    return !impl->Libraries.empty();
+    }
+  return false;
 }
 
 //----------------------------------------------------------------------------

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=d9f8c8722150f23e07b730d45a50d6b4b77bdf52
commit d9f8c8722150f23e07b730d45a50d6b4b77bdf52
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 11:49:10 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:27 2014 -0400

    cmTarget: Lookup targets in LinkInterface and LinkImplementation
    
    Instead of storing just the string names in these structures, lookup any
    target associated with each item and store its cmTarget pointer.  Use
    the cmLinkItem class to hold the name and pointer together.  Update
    client sites to use the pre-stored lookup result instead of looking up
    the target name again.

diff --git a/Source/cmComputeLinkDepends.cxx b/Source/cmComputeLinkDepends.cxx
index 1b2d1cb..6170e92 100644
--- a/Source/cmComputeLinkDepends.cxx
+++ b/Source/cmComputeLinkDepends.cxx
@@ -292,8 +292,7 @@ cmComputeLinkDepends::AllocateLinkEntry(std::string const& item)
 }
 
 //----------------------------------------------------------------------------
-int cmComputeLinkDepends::AddLinkEntry(int depender_index,
-                                       std::string const& item)
+int cmComputeLinkDepends::AddLinkEntry(cmLinkItem const& item)
 {
   // Check if the item entry has already been added.
   std::map<std::string, int>::iterator lei = this->LinkEntryIndex.find(item);
@@ -310,7 +309,7 @@ int cmComputeLinkDepends::AddLinkEntry(int depender_index,
   int index = lei->second;
   LinkEntry& entry = this->EntryList[index];
   entry.Item = item;
-  entry.Target = this->FindTargetToLink(depender_index, entry.Item);
+  entry.Target = item.Target;
   entry.IsFlag = (!entry.Target && item[0] == '-' && item[1] != 'l' &&
                   item.substr(0, 10) != "-framework");
 
@@ -370,11 +369,11 @@ void cmComputeLinkDepends::FollowLinkEntry(BFSEntry const& qe)
       this->FollowSharedDeps(depender_index, iface);
 
       // Support for CMP0003.
-      for(std::vector<std::string>::const_iterator
+      for(std::vector<cmLinkItem>::const_iterator
             oi = iface->WrongConfigLibraries.begin();
           oi != iface->WrongConfigLibraries.end(); ++oi)
         {
-        this->CheckWrongConfigItem(depender_index, *oi);
+        this->CheckWrongConfigItem(*oi);
         }
       }
     }
@@ -406,9 +405,9 @@ cmComputeLinkDepends
 void
 cmComputeLinkDepends
 ::QueueSharedDependencies(int depender_index,
-                          std::vector<std::string> const& deps)
+                          std::vector<cmLinkItem> const& deps)
 {
-  for(std::vector<std::string>::const_iterator li = deps.begin();
+  for(std::vector<cmLinkItem>::const_iterator li = deps.begin();
       li != deps.end(); ++li)
     {
     SharedDepEntry qe;
@@ -432,8 +431,7 @@ void cmComputeLinkDepends::HandleSharedDependency(SharedDepEntry const& dep)
     // Initialize the item entry.
     LinkEntry& entry = this->EntryList[lei->second];
     entry.Item = dep.Item;
-    entry.Target = this->FindTargetToLink(dep.DependerIndex,
-                                          dep.Item);
+    entry.Target = dep.Item.Target;
 
     // This item was added specifically because it is a dependent
     // shared library.  It may get special treatment
@@ -472,7 +470,7 @@ void cmComputeLinkDepends::AddVarLinkEntries(int depender_index,
   cmSystemTools::ExpandListArgument(value, deplist);
 
   // Look for entries meant for this configuration.
-  std::vector<std::string> actual_libs;
+  std::vector<cmLinkItem> actual_libs;
   cmTarget::LinkLibraryType llt = cmTarget::GENERAL;
   bool haveLLT = false;
   for(std::vector<std::string>::const_iterator di = deplist.begin();
@@ -520,11 +518,13 @@ void cmComputeLinkDepends::AddVarLinkEntries(int depender_index,
       // If the library is meant for this link type then use it.
       if(llt == cmTarget::GENERAL || llt == this->LinkType)
         {
-        actual_libs.push_back(*di);
+        cmLinkItem item(*di, this->FindTargetToLink(depender_index, *di));
+        actual_libs.push_back(item);
         }
       else if(this->OldLinkDirMode)
         {
-        this->CheckWrongConfigItem(depender_index, *di);
+        cmLinkItem item(*di, this->FindTargetToLink(depender_index, *di));
+        this->CheckWrongConfigItem(item);
         }
 
       // Reset the link type until another explicit type is given.
@@ -544,36 +544,36 @@ void cmComputeLinkDepends::AddDirectLinkEntries()
   cmTarget::LinkImplementation const* impl =
     this->Target->GetLinkImplementation(this->Config);
   this->AddLinkEntries(-1, impl->Libraries);
-  for(std::vector<std::string>::const_iterator
+  for(std::vector<cmLinkItem>::const_iterator
         wi = impl->WrongConfigLibraries.begin();
       wi != impl->WrongConfigLibraries.end(); ++wi)
     {
-    this->CheckWrongConfigItem(-1, *wi);
+    this->CheckWrongConfigItem(*wi);
     }
 }
 
 //----------------------------------------------------------------------------
 void
-cmComputeLinkDepends::AddLinkEntries(int depender_index,
-                                     std::vector<std::string> const& libs)
+cmComputeLinkDepends::AddLinkEntries(
+  int depender_index, std::vector<cmLinkItem> const& libs)
 {
   // Track inferred dependency sets implied by this list.
   std::map<int, DependSet> dependSets;
 
   // Loop over the libraries linked directly by the depender.
-  for(std::vector<std::string>::const_iterator li = libs.begin();
+  for(std::vector<cmLinkItem>::const_iterator li = libs.begin();
       li != libs.end(); ++li)
     {
     // Skip entries that will resolve to the target getting linked or
     // are empty.
-    std::string item = this->Target->CheckCMP0004(*li);
+    cmLinkItem const& item = *li;
     if(item == this->Target->GetName() || item.empty())
       {
       continue;
       }
 
     // Add a link entry for this item.
-    int dependee_index = this->AddLinkEntry(depender_index, item);
+    int dependee_index = this->AddLinkEntry(*li);
 
     // The dependee must come after the depender.
     if(depender_index >= 0)
@@ -961,8 +961,7 @@ void cmComputeLinkDepends::DisplayFinalEntries()
 }
 
 //----------------------------------------------------------------------------
-void cmComputeLinkDepends::CheckWrongConfigItem(int depender_index,
-                                                std::string const& item)
+void cmComputeLinkDepends::CheckWrongConfigItem(cmLinkItem const& item)
 {
   if(!this->OldLinkDirMode)
     {
@@ -972,9 +971,8 @@ void cmComputeLinkDepends::CheckWrongConfigItem(int depender_index,
   // For CMake 2.4 bug-compatibility we need to consider the output
   // directories of targets linked in another configuration as link
   // directories.
-  cmTarget const* tgt = this->FindTargetToLink(depender_index, item);
-  if(tgt && !tgt->IsImported())
+  if(item.Target && !item.Target->IsImported())
     {
-    this->OldWrongConfigItems.insert(tgt);
+    this->OldWrongConfigItems.insert(item.Target);
     }
 }
diff --git a/Source/cmComputeLinkDepends.h b/Source/cmComputeLinkDepends.h
index 440dc0d..3207ecb 100644
--- a/Source/cmComputeLinkDepends.h
+++ b/Source/cmComputeLinkDepends.h
@@ -77,11 +77,11 @@ private:
 
   std::map<std::string, int>::iterator
   AllocateLinkEntry(std::string const& item);
-  int AddLinkEntry(int depender_index, std::string const& item);
+  int AddLinkEntry(cmLinkItem const& item);
   void AddVarLinkEntries(int depender_index, const char* value);
   void AddDirectLinkEntries();
   void AddLinkEntries(int depender_index,
-                      std::vector<std::string> const& libs);
+                      std::vector<cmLinkItem> const& libs);
   cmTarget const* FindTargetToLink(int depender_index,
                                    const std::string& name);
 
@@ -103,7 +103,7 @@ private:
   // of the interface.
   struct SharedDepEntry
   {
-    std::string Item;
+    cmLinkItem Item;
     int DependerIndex;
   };
   std::queue<SharedDepEntry> SharedDepQueue;
@@ -112,7 +112,7 @@ private:
                         cmTarget::LinkInterface const* iface,
                         bool follow_interface = false);
   void QueueSharedDependencies(int depender_index,
-                               std::vector<std::string> const& deps);
+                               std::vector<cmLinkItem> const& deps);
   void HandleSharedDependency(SharedDepEntry const& dep);
 
   // Dependency inferral for each link item.
@@ -163,7 +163,7 @@ private:
 
   // Compatibility help.
   bool OldLinkDirMode;
-  void CheckWrongConfigItem(int depender_index, std::string const& item);
+  void CheckWrongConfigItem(cmLinkItem const& item);
   std::set<cmTarget const*> OldWrongConfigItems;
 };
 
diff --git a/Source/cmComputeTargetDepends.cxx b/Source/cmComputeTargetDepends.cxx
index 6196542..3929af4 100644
--- a/Source/cmComputeTargetDepends.cxx
+++ b/Source/cmComputeTargetDepends.cxx
@@ -249,13 +249,15 @@ void cmComputeTargetDepends::CollectTargetDepends(int depender_index)
         const_cast<cmTarget*>(depender)->AddUtility(objLib);
         }
       }
-    std::vector<std::string> tlibs;
-    depender->GetDirectLinkLibraries(*it, tlibs);
+
+    cmTarget::LinkImplementation const* impl =
+      depender->GetLinkImplementation(*it);
 
     // A target should not depend on itself.
     emitted.insert(depender->GetName());
-    for(std::vector<std::string>::const_iterator lib = tlibs.begin();
-        lib != tlibs.end(); ++lib)
+    for(std::vector<cmLinkItem>::const_iterator
+          lib = impl->Libraries.begin();
+        lib != impl->Libraries.end(); ++lib)
       {
       // Don't emit the same library twice for this target.
       if(emitted.insert(*lib).second)
@@ -269,11 +271,11 @@ void cmComputeTargetDepends::CollectTargetDepends(int depender_index)
 
   // Loop over all utility dependencies.
   {
-  std::set<std::string> const& tutils = depender->GetUtilities();
+  std::set<cmLinkItem> const& tutils = depender->GetUtilityItems();
   std::set<std::string> emitted;
   // A target should not depend on itself.
   emitted.insert(depender->GetName());
-  for(std::set<std::string>::const_iterator util = tutils.begin();
+  for(std::set<cmLinkItem>::const_iterator util = tutils.begin();
       util != tutils.end(); ++util)
     {
     // Don't emit the same utility twice for this target.
@@ -295,7 +297,7 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
   if(cmTarget::LinkInterface const* iface =
                                 dependee->GetLinkInterface(config, depender))
     {
-    for(std::vector<std::string>::const_iterator
+    for(std::vector<cmLinkItem>::const_iterator
         lib = iface->Libraries.begin();
         lib != iface->Libraries.end(); ++lib)
       {
@@ -311,12 +313,11 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
 
 //----------------------------------------------------------------------------
 void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
-                                             const std::string& dependee_name,
+                                             cmLinkItem const& dependee_name,
                                              std::set<std::string> &emitted)
 {
   cmTarget const* depender = this->Targets[depender_index];
-  cmTarget const* dependee =
-    depender->GetMakefile()->FindTargetToUse(dependee_name);
+  cmTarget const* dependee = dependee_name.Target;
   // Skip targets that will not really be linked.  This is probably a
   // name conflict between an external library and an executable
   // within the project.
@@ -344,16 +345,15 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
 }
 
 //----------------------------------------------------------------------------
-void cmComputeTargetDepends::AddTargetDepend(int depender_index,
-                                             const std::string& dependee_name,
-                                             bool linking)
+void cmComputeTargetDepends::AddTargetDepend(
+  int depender_index, cmLinkItem const& dependee_name,
+  bool linking)
 {
   // Get the depender.
   cmTarget const* depender = this->Targets[depender_index];
 
   // Check the target's makefile first.
-  cmTarget const* dependee =
-    depender->GetMakefile()->FindTargetToUse(dependee_name);
+  cmTarget const* dependee = dependee_name.Target;
 
   if(!dependee && !linking &&
     (depender->GetType() != cmTarget::GLOBAL_TARGET))
diff --git a/Source/cmComputeTargetDepends.h b/Source/cmComputeTargetDepends.h
index b99199f..902f342 100644
--- a/Source/cmComputeTargetDepends.h
+++ b/Source/cmComputeTargetDepends.h
@@ -20,6 +20,7 @@
 
 class cmComputeComponentGraph;
 class cmGlobalGenerator;
+class cmLinkItem;
 class cmTarget;
 class cmTargetDependSet;
 
@@ -46,13 +47,13 @@ private:
   void CollectDepends();
   void CollectTargetDepends(int depender_index);
   void AddTargetDepend(int depender_index,
-                       const std::string& dependee_name,
+                       cmLinkItem const& dependee_name,
                        bool linking);
   void AddTargetDepend(int depender_index, cmTarget const* dependee,
                        bool linking);
   bool ComputeFinalDepends(cmComputeComponentGraph const& ccg);
   void AddInterfaceDepends(int depender_index,
-                           const std::string& dependee_name,
+                           cmLinkItem const& dependee_name,
                            std::set<std::string> &emitted);
   void AddInterfaceDepends(int depender_index, cmTarget const* dependee,
                            const std::string& config,
diff --git a/Source/cmGeneratorExpressionEvaluator.cxx b/Source/cmGeneratorExpressionEvaluator.cxx
index f491882..c925869 100644
--- a/Source/cmGeneratorExpressionEvaluator.cxx
+++ b/Source/cmGeneratorExpressionEvaluator.cxx
@@ -800,7 +800,7 @@ static const char* targetPropertyTransitiveWhitelist[] = {
 #undef TRANSITIVE_PROPERTY_NAME
 
 std::string getLinkedTargetsContent(
-                                  const std::vector<cmTarget const*> &targets,
+                                  std::vector<cmTarget const*> &targets,
                                   cmTarget const* target,
                                   cmTarget const* headTarget,
                                   cmGeneratorExpressionContext *context,
@@ -841,7 +841,7 @@ std::string getLinkedTargetsContent(
   return linkedTargetsContent;
 }
 
-std::string getLinkedTargetsContent(const std::vector<std::string> &libraries,
+std::string getLinkedTargetsContent(std::vector<cmLinkItem> const &libraries,
                                   cmTarget const* target,
                                   cmTarget const* headTarget,
                                   cmGeneratorExpressionContext *context,
@@ -849,13 +849,13 @@ std::string getLinkedTargetsContent(const std::vector<std::string> &libraries,
                                   const std::string &interfacePropertyName)
 {
   std::vector<cmTarget const*> tgts;
-  for (std::vector<std::string>::const_iterator
+  for (std::vector<cmLinkItem>::const_iterator
       it = libraries.begin();
       it != libraries.end(); ++it)
     {
-    if (cmTarget const *tgt = target->FindTargetToLink(*it))
+    if (it->Target)
       {
-      tgts.push_back(tgt);
+      tgts.push_back(it->Target);
       }
     }
   return getLinkedTargetsContent(tgts, target, headTarget, context,
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index 36c5648..fd82d17 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -475,10 +475,10 @@ bool cmGeneratorTarget::IsSystemIncludeDirectory(const std::string& dir,
       }
 
     std::set<cmTarget const*> uniqueDeps;
-    for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
+    for(std::vector<cmLinkItem>::const_iterator li = impl->Libraries.begin();
         li != impl->Libraries.end(); ++li)
       {
-      cmTarget const* tgt = this->Target->FindTargetToLink(*li);
+      cmTarget const* tgt = li->Target;
       if (!tgt)
         {
         continue;
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 555ead0..7a63db4 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -2311,7 +2311,7 @@ cmTarget::GetIncludeDirectories(const std::string& config) const
     if(this->Makefile->IsOn("APPLE"))
       {
       LinkImplementation const* impl = this->GetLinkImplementation(config);
-      for(std::vector<std::string>::const_iterator
+      for(std::vector<cmLinkItem>::const_iterator
           it = impl->Libraries.begin();
           it != impl->Libraries.end(); ++it)
         {
@@ -3513,13 +3513,11 @@ public:
     Makefile(target->GetMakefile()), Target(target)
   { this->Visited.insert(target); }
 
-  void Visit(cmTarget const* from, const std::string& name)
+  void Visit(cmLinkItem const& item)
     {
-    cmTarget const *target = from->FindTargetToLink(name);
-
-    if(!target)
+    if(!item.Target)
       {
-      if(name.find("::") != std::string::npos)
+      if(item.find("::") != std::string::npos)
         {
         bool noMessage = false;
         cmake::MessageType messageType = cmake::FATAL_ERROR;
@@ -3545,7 +3543,7 @@ public:
         if(!noMessage)
           {
           e << "Target \"" << this->Target->GetName()
-            << "\" links to target \"" << name
+            << "\" links to target \"" << item
             << "\" but the target was not found.  Perhaps a find_package() "
             "call is missing for an IMPORTED target, or an ALIAS target is "
             "missing?";
@@ -3556,13 +3554,13 @@ public:
         }
       return;
       }
-    if(!this->Visited.insert(target).second)
+    if(!this->Visited.insert(item.Target).second)
       {
       return;
       }
 
     cmTarget::LinkInterface const* iface =
-      target->GetLinkInterface(this->Config, this->HeadTarget);
+      item.Target->GetLinkInterface(this->Config, this->HeadTarget);
     if(!iface) { return; }
 
     for(std::vector<std::string>::const_iterator
@@ -3571,10 +3569,10 @@ public:
       this->Languages.insert(*li);
       }
 
-    for(std::vector<std::string>::const_iterator
+    for(std::vector<cmLinkItem>::const_iterator
           li = iface->Libraries.begin(); li != iface->Libraries.end(); ++li)
       {
-      this->Visit(target, *li);
+      this->Visit(*li);
       }
     }
 private:
@@ -3677,10 +3675,10 @@ void cmTarget::ComputeLinkClosure(const std::string& config,
 
   // Add interface languages from linked targets.
   cmTargetCollectLinkLanguages cll(this, config, languages, this);
-  for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
+  for(std::vector<cmLinkItem>::const_iterator li = impl->Libraries.begin();
       li != impl->Libraries.end(); ++li)
     {
-    cll.Visit(this, *li);
+    cll.Visit(*li);
     }
 
   // Store the transitive closure of languages.
@@ -3731,16 +3729,34 @@ void cmTarget::ExpandLinkItems(std::string const& prop,
                                std::string const& value,
                                std::string const& config,
                                cmTarget const* headTarget,
-                               std::vector<std::string>& libs) const
+                               std::vector<cmLinkItem>& items) const
 {
   cmGeneratorExpression ge;
   cmGeneratorExpressionDAGChecker dagChecker(this->GetName(), prop, 0, 0);
+  std::vector<std::string> libs;
   cmSystemTools::ExpandListArgument(ge.Parse(value)->Evaluate(
                                       this->Makefile,
                                       config,
                                       false,
                                       headTarget,
                                       this, &dagChecker), libs);
+  this->LookupLinkItems(libs, items);
+}
+
+//----------------------------------------------------------------------------
+void cmTarget::LookupLinkItems(std::vector<std::string> const& names,
+                               std::vector<cmLinkItem>& items) const
+{
+  for(std::vector<std::string>::const_iterator i = names.begin();
+      i != names.end(); ++i)
+    {
+    std::string name = this->CheckCMP0004(*i);
+    if(name == this->GetName() || name.empty())
+      {
+      continue;
+      }
+    items.push_back(cmLinkItem(name, this->FindTargetToLink(name)));
+    }
 }
 
 //----------------------------------------------------------------------------
@@ -6158,7 +6174,11 @@ cmTarget::GetImportLinkInterface(const std::string& config,
     cmSystemTools::ExpandListArgument(info->Languages, iface.Languages);
     this->ExpandLinkItems(info->LibrariesProp, info->Libraries, config,
                           headTarget, iface.Libraries);
-    cmSystemTools::ExpandListArgument(info->SharedDeps, iface.SharedDeps);
+    {
+    std::vector<std::string> deps;
+    cmSystemTools::ExpandListArgument(info->SharedDeps, deps);
+    this->LookupLinkItems(deps, iface.SharedDeps);
+    }
 
     cmTargetInternals::ImportLinkInterfaceMapType::value_type
       entry(key, iface);
@@ -6170,23 +6190,21 @@ cmTarget::GetImportLinkInterface(const std::string& config,
 //----------------------------------------------------------------------------
 void processILibs(const std::string& config,
                   cmTarget const* headTarget,
-                  cmTarget const* curTarget,
-                  std::string const& name,
+                  cmLinkItem const& item,
                   std::vector<cmTarget const*>& tgts,
                   std::set<cmTarget const*>& emitted)
 {
-  cmTarget const* tgt = curTarget->FindTargetToLink(name);
-  if (tgt && emitted.insert(tgt).second)
+  if (item.Target && emitted.insert(item.Target).second)
     {
-    tgts.push_back(tgt);
+    tgts.push_back(item.Target);
     if(cmTarget::LinkInterface const* iface =
-       tgt->GetLinkInterfaceLibraries(config, headTarget))
+       item.Target->GetLinkInterfaceLibraries(config, headTarget))
       {
-      for(std::vector<std::string>::const_iterator
-          it = iface->Libraries.begin();
+      for(std::vector<cmLinkItem>::const_iterator
+            it = iface->Libraries.begin();
           it != iface->Libraries.end(); ++it)
         {
-        processILibs(config, headTarget, tgt, *it, tgts, emitted);
+        processILibs(config, headTarget, *it, tgts, emitted);
         }
       }
     }
@@ -6206,10 +6224,10 @@ cmTarget::GetLinkImplementationClosure(const std::string& config) const
     cmTarget::LinkImplementation const* impl
       = this->GetLinkImplementationLibraries(config);
 
-    for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
+    for(std::vector<cmLinkItem>::const_iterator it = impl->Libraries.begin();
         it != impl->Libraries.end(); ++it)
       {
-      processILibs(config, this, this, *it, tgts , emitted);
+      processILibs(config, this, *it, tgts , emitted);
       }
     }
   return tgts;
@@ -6230,12 +6248,12 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
       || this->GetPolicyStatusCMP0022() == cmPolicies::WARN
       || this->GetPolicyStatusCMP0022() == cmPolicies::OLD)
     {
-    for(std::vector<std::string>::const_iterator it = iface->Libraries.begin();
+    for(std::vector<cmLinkItem>::const_iterator it = iface->Libraries.begin();
         it != iface->Libraries.end(); ++it)
       {
-      if (cmTarget const* tgt = this->FindTargetToLink(*it))
+      if (it->Target)
         {
-        tgts.push_back(tgt);
+        tgts.push_back(it->Target);
         }
       }
     return;
@@ -6379,7 +6397,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
       {
       // Compare the link implementation fallback link interface to the
       // preferred new link interface property and warn if different.
-      std::vector<std::string> ifaceLibs;
+      std::vector<cmLinkItem> ifaceLibs;
       std::string newProp = "INTERFACE_LINK_LIBRARIES";
       if(const char* newExplicitLibraries = this->GetProperty(newProp))
         {
@@ -6391,7 +6409,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
         std::string oldLibraries;
         std::string newLibraries;
         const char *sep = "";
-        for(std::vector<std::string>::const_iterator it
+        for(std::vector<cmLinkItem>::const_iterator it
               = impl->Libraries.begin(); it != impl->Libraries.end(); ++it)
           {
           oldLibraries += sep;
@@ -6399,7 +6417,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
           sep = ";";
           }
         sep = "";
-        for(std::vector<std::string>::const_iterator it
+        for(std::vector<cmLinkItem>::const_iterator it
               = ifaceLibs.begin(); it != ifaceLibs.end(); ++it)
           {
           newLibraries += sep;
@@ -6450,7 +6468,7 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
       // Shared libraries may have runtime implementation dependencies
       // on other shared libraries that are not in the interface.
       std::set<std::string> emitted;
-      for(std::vector<std::string>::const_iterator
+      for(std::vector<cmLinkItem>::const_iterator
           li = iface.Libraries.begin(); li != iface.Libraries.end(); ++li)
         {
         emitted.insert(*li);
@@ -6459,15 +6477,15 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
         {
         cmTarget::LinkImplementation const* impl =
             thisTarget->GetLinkImplementation(config);
-        for(std::vector<std::string>::const_iterator
+        for(std::vector<cmLinkItem>::const_iterator
               li = impl->Libraries.begin(); li != impl->Libraries.end(); ++li)
           {
           if(emitted.insert(*li).second)
             {
-            if(cmTarget* tgt = thisTarget->Makefile->FindTargetToUse(*li))
+            if(li->Target)
               {
               // This is a runtime dependency on another shared library.
-              if(tgt->GetType() == cmTarget::SHARED_LIBRARY)
+              if(li->Target->GetType() == cmTarget::SHARED_LIBRARY)
                 {
                 iface.SharedDeps.push_back(*li);
                 }
@@ -6618,10 +6636,10 @@ void cmTarget::ComputeLinkImplementation(const std::string& config,
       li != llibs.end(); ++li)
     {
     // Skip entries that resolve to the target itself or are empty.
-    std::string item = this->CheckCMP0004(*li);
-    if(item == this->GetName() || item.empty())
+    std::string name = this->CheckCMP0004(*li);
+    if(name == this->GetName() || name.empty())
       {
-      if(item == this->GetName())
+      if(name == this->GetName())
         {
         bool noMessage = false;
         cmake::MessageType messageType = cmake::FATAL_ERROR;
@@ -6660,7 +6678,8 @@ void cmTarget::ComputeLinkImplementation(const std::string& config,
       }
 
     // The entry is meant for this configuration.
-    impl.Libraries.push_back(item);
+    impl.Libraries.push_back(
+      cmLinkItem(name, this->FindTargetToLink(name)));
     }
 
   cmTarget::LinkLibraryType linkType = this->ComputeLinkType(config);
@@ -6670,13 +6689,14 @@ void cmTarget::ComputeLinkImplementation(const std::string& config,
     {
     if(li->second != cmTarget::GENERAL && li->second != linkType)
       {
-      std::string item = this->CheckCMP0004(li->first);
-      if(item == this->GetName() || item.empty())
+      std::string name = this->CheckCMP0004(li->first);
+      if(name == this->GetName() || name.empty())
         {
         continue;
         }
       // Support OLD behavior for CMP0003.
-      impl.WrongConfigLibraries.push_back(item);
+      impl.WrongConfigLibraries.push_back(
+        cmLinkItem(name, this->FindTargetToLink(name)));
       }
     }
 }
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index c56fa98..2e0df42 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -259,10 +259,10 @@ public:
     std::vector<std::string> Languages;
 
     // Libraries listed in the interface.
-    std::vector<std::string> Libraries;
+    std::vector<cmLinkItem> Libraries;
 
     // Shared library dependencies needed for linking on some platforms.
-    std::vector<std::string> SharedDeps;
+    std::vector<cmLinkItem> SharedDeps;
 
     // Number of repetitions of a strongly connected component of two
     // or more static libraries.
@@ -270,7 +270,7 @@ public:
 
     // Libraries listed for other configurations.
     // Needed only for OLD behavior of CMP0003.
-    std::vector<std::string> WrongConfigLibraries;
+    std::vector<cmLinkItem> WrongConfigLibraries;
 
     bool ImplementationIsInterface;
 
@@ -297,11 +297,11 @@ public:
     std::vector<std::string> Languages;
 
     // Libraries linked directly in this configuration.
-    std::vector<std::string> Libraries;
+    std::vector<cmLinkItem> Libraries;
 
     // Libraries linked directly in other configurations.
     // Needed only for OLD behavior of CMP0003.
-    std::vector<std::string> WrongConfigLibraries;
+    std::vector<cmLinkItem> WrongConfigLibraries;
   };
   LinkImplementation const*
     GetLinkImplementation(const std::string& config) const;
@@ -782,7 +782,9 @@ private:
 
   void ExpandLinkItems(std::string const& prop, std::string const& value,
                        std::string const& config, cmTarget const* headTarget,
-                       std::vector<std::string>& libs) const;
+                       std::vector<cmLinkItem>& items) const;
+  void LookupLinkItems(std::vector<std::string> const& names,
+                       std::vector<cmLinkItem>& items) const;
 
   std::string ProcessSourceItemCMP0049(const std::string& s);
 

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=e6911d51734d128899ac5887098b74811ecc61cf
commit e6911d51734d128899ac5887098b74811ecc61cf
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 11:48:31 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:27 2014 -0400

    cmComputeLinkDepends: Simplify CheckWrongConfigItem implementation
    
    Combine the outer two if() conditions into a single one with &&.

diff --git a/Source/cmComputeLinkDepends.cxx b/Source/cmComputeLinkDepends.cxx
index 5abf6dd..1b2d1cb 100644
--- a/Source/cmComputeLinkDepends.cxx
+++ b/Source/cmComputeLinkDepends.cxx
@@ -972,12 +972,9 @@ void cmComputeLinkDepends::CheckWrongConfigItem(int depender_index,
   // For CMake 2.4 bug-compatibility we need to consider the output
   // directories of targets linked in another configuration as link
   // directories.
-  if(cmTarget const* tgt
-                      = this->FindTargetToLink(depender_index, item))
+  cmTarget const* tgt = this->FindTargetToLink(depender_index, item);
+  if(tgt && !tgt->IsImported())
     {
-    if(!tgt->IsImported())
-      {
-      this->OldWrongConfigItems.insert(tgt);
-      }
+    this->OldWrongConfigItems.insert(tgt);
     }
 }

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=1767f227b356df807ccbe85c606ef9e555b5206f
commit 1767f227b356df807ccbe85c606ef9e555b5206f
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 11:44:49 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:27 2014 -0400

    cmTarget: Simplify processILibs implementation
    
    Combine the outer two if() conditions into a single one with &&.
    Scope inner lookup result inside its condition.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 0faf745..555ead0 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -6175,21 +6175,18 @@ void processILibs(const std::string& config,
                   std::vector<cmTarget const*>& tgts,
                   std::set<cmTarget const*>& emitted)
 {
-  if (cmTarget const* tgt = curTarget->FindTargetToLink(name))
+  cmTarget const* tgt = curTarget->FindTargetToLink(name);
+  if (tgt && emitted.insert(tgt).second)
     {
-    if (emitted.insert(tgt).second)
+    tgts.push_back(tgt);
+    if(cmTarget::LinkInterface const* iface =
+       tgt->GetLinkInterfaceLibraries(config, headTarget))
       {
-      tgts.push_back(tgt);
-      cmTarget::LinkInterface const* iface =
-                          tgt->GetLinkInterfaceLibraries(config, headTarget);
-      if (iface)
+      for(std::vector<std::string>::const_iterator
+          it = iface->Libraries.begin();
+          it != iface->Libraries.end(); ++it)
         {
-        for(std::vector<std::string>::const_iterator
-            it = iface->Libraries.begin();
-            it != iface->Libraries.end(); ++it)
-          {
-          processILibs(config, headTarget, tgt, *it, tgts, emitted);
-          }
+        processILibs(config, headTarget, tgt, *it, tgts, emitted);
         }
       }
     }

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=40f16b63e64242200cb0172208af78f62696fa4c
commit 40f16b63e64242200cb0172208af78f62696fa4c
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 10:58:23 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:27 2014 -0400

    cmTarget: Add GetUtilityItems to get target ordering dependencies
    
    Add a method like GetUtilities but that provides the target names
    already looked up and resolved to cmTarget pointers internally.  Update
    call site in cmComputeTargetDepends::AddInterfaceDepends to use the
    already-found target instead of looking it up again.

diff --git a/Source/cmComputeTargetDepends.cxx b/Source/cmComputeTargetDepends.cxx
index a5df060..6196542 100644
--- a/Source/cmComputeTargetDepends.cxx
+++ b/Source/cmComputeTargetDepends.cxx
@@ -421,12 +421,11 @@ void cmComputeTargetDepends::AddTargetDepend(int depender_index,
   if(dependee->IsImported())
     {
     // Skip imported targets but follow their utility dependencies.
-    std::set<std::string> const& utils = dependee->GetUtilities();
-    for(std::set<std::string>::const_iterator i = utils.begin();
+    std::set<cmLinkItem> const& utils = dependee->GetUtilityItems();
+    for(std::set<cmLinkItem>::const_iterator i = utils.begin();
         i != utils.end(); ++i)
       {
-      if(cmTarget const* transitive_dependee =
-         dependee->GetMakefile()->FindTargetToUse(*i))
+      if(cmTarget const* transitive_dependee = i->Target)
         {
         this->AddTargetDepend(depender_index, transitive_dependee, false);
         }
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index f3a09e8..0faf745 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -95,11 +95,13 @@ public:
     : Backtrace(NULL)
     {
     this->PolicyWarnedCMP0022 = false;
+    this->UtilityItemsDone = false;
     }
   cmTargetInternals(cmTargetInternals const&)
     : Backtrace(NULL)
     {
     this->PolicyWarnedCMP0022 = false;
+    this->UtilityItemsDone = false;
     }
   ~cmTargetInternals();
 
@@ -151,6 +153,9 @@ public:
                                                           SourceFilesMapType;
   SourceFilesMapType SourceFilesMap;
 
+  std::set<cmLinkItem> UtilityItems;
+  bool UtilityItemsDone;
+
   struct TargetPropertyEntry {
     TargetPropertyEntry(cmsys::auto_ptr<cmCompiledGeneratorExpression> cge,
       const std::string &targetName = std::string())
@@ -471,6 +476,22 @@ cmListFileBacktrace const* cmTarget::GetUtilityBacktrace(
 }
 
 //----------------------------------------------------------------------------
+std::set<cmLinkItem> const& cmTarget::GetUtilityItems() const
+{
+  if(!this->Internal->UtilityItemsDone)
+    {
+    this->Internal->UtilityItemsDone = true;
+    for(std::set<std::string>::const_iterator i = this->Utilities.begin();
+        i != this->Utilities.end(); ++i)
+      {
+      this->Internal->UtilityItems.insert(
+        cmLinkItem(*i, this->Makefile->FindTargetToUse(*i)));
+      }
+    }
+  return this->Internal->UtilityItems;
+}
+
+//----------------------------------------------------------------------------
 void cmTarget::FinishConfigure()
 {
   // Erase any cached link information that might have been comptued
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 97c8bf0..c56fa98 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -227,6 +227,7 @@ public:
   void AddUtility(const std::string& u, cmMakefile *makefile = 0);
   ///! Get the utilities used by this target
   std::set<std::string>const& GetUtilities() const { return this->Utilities; }
+  std::set<cmLinkItem>const& GetUtilityItems() const;
   cmListFileBacktrace const* GetUtilityBacktrace(const std::string& u) const;
 
   /** Finalize the target at the end of the Configure step.  */

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=0b33ff53030667a540ff42b9960692c7202feff5
commit 0b33ff53030667a540ff42b9960692c7202feff5
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 10:55:33 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:27 2014 -0400

    cmTarget: Add cmLinkItem to refer to a target by name and pointer
    
    Many items named in target_link_libraries calls are targets, but not
    all.  Create a cmLinkItem type that acts like std::string so it can name
    an item but also has a pointer to a cmTarget that is the result of
    looking up the item name in the referencing target's scope.  This will
    be useful to avoid duplicate lookup operations later.

diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 049d3ea..97c8bf0 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -43,6 +43,18 @@ class cmTarget;
 class cmGeneratorTarget;
 class cmTargetTraceDependencies;
 
+// Basic information about each link item.
+class cmLinkItem: public std::string
+{
+  typedef std::string std_string;
+public:
+  cmLinkItem(): std_string(), Target(0) {}
+  cmLinkItem(const std_string& n,
+             cmTarget const* t): std_string(n), Target(t) {}
+  cmLinkItem(cmLinkItem const& r): std_string(r), Target(r.Target) {}
+  cmTarget const* Target;
+};
+
 struct cmTargetLinkInformationMap:
   public std::map<std::string, cmComputeLinkInformation*>
 {

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=109f3fee334cfde2ab210470f00b0b5cd32759c4
commit 109f3fee334cfde2ab210470f00b0b5cd32759c4
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 10:36:21 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:26 2014 -0400

    cmTarget: Drop 'head' target from GetImportInfo
    
    Move generator expression evaluation for imported library lists out of
    GetImportInfo and into a new GetImportLinkInterface helper.  This avoids
    duplicating the computation and storage of all imported target info just
    because some of it is parameterized on the 'head' target.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 84646b9..f3a09e8 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -64,11 +64,16 @@ struct cmTarget::OutputInfo
 //----------------------------------------------------------------------------
 struct cmTarget::ImportInfo
 {
+  ImportInfo(): NoSOName(false), Multiplicity(0) {}
   bool NoSOName;
+  int Multiplicity;
   std::string Location;
   std::string SOName;
   std::string ImportLibrary;
-  cmTarget::LinkInterface LinkInterface;
+  std::string Languages;
+  std::string Libraries;
+  std::string LibrariesProp;
+  std::string SharedDeps;
 };
 
 //----------------------------------------------------------------------------
@@ -121,11 +126,14 @@ public:
   LinkInterfaceMapType LinkInterfaceMap;
   bool PolicyWarnedCMP0022;
 
+  typedef std::map<TargetConfigPair, cmTarget::LinkInterface>
+                                                    ImportLinkInterfaceMapType;
+  ImportLinkInterfaceMapType ImportLinkInterfaceMap;
+
   typedef std::map<std::string, cmTarget::OutputInfo> OutputInfoMapType;
   OutputInfoMapType OutputInfoMap;
 
-  typedef std::map<TargetConfigPair, cmTarget::ImportInfo>
-                                                            ImportInfoMapType;
+  typedef std::map<std::string, cmTarget::ImportInfo> ImportInfoMapType;
   ImportInfoMapType ImportInfoMap;
 
   typedef std::map<std::string, cmTarget::CompileInfo> CompileInfoMapType;
@@ -481,6 +489,7 @@ void cmTarget::ClearLinkMaps()
   this->LinkImplementationLanguageIsContextDependent = true;
   this->Internal->LinkImplMap.clear();
   this->Internal->LinkInterfaceMap.clear();
+  this->Internal->ImportLinkInterfaceMap.clear();
   this->Internal->LinkClosureMap.clear();
   for (cmTargetLinkInformationMap::const_iterator it
       = this->LinkInformation.begin();
@@ -3853,7 +3862,7 @@ std::string cmTarget::GetSOName(const std::string& config) const
   if(this->IsImported())
     {
     // Lookup the imported soname.
-    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, this))
+    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config))
       {
       if(info->NoSOName)
         {
@@ -3921,7 +3930,7 @@ bool cmTarget::HasMacOSXRpathInstallNameDir(const std::string& config) const
   else
     {
     // Lookup the imported soname.
-    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, this))
+    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config))
       {
       if(!info->NoSOName && !info->SOName.empty())
         {
@@ -4007,7 +4016,7 @@ bool cmTarget::IsImportedSharedLibWithoutSOName(
 {
   if(this->IsImported() && this->GetType() == cmTarget::SHARED_LIBRARY)
     {
-    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, this))
+    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config))
       {
       return info->NoSOName;
       }
@@ -4131,7 +4140,7 @@ std::string
 cmTarget::ImportedGetFullPath(const std::string& config, bool implib) const
 {
   std::string result;
-  if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, this))
+  if(cmTarget::ImportInfo const* info = this->GetImportInfo(config))
     {
     result = implib? info->ImportLibrary : info->Location;
     }
@@ -5669,8 +5678,7 @@ bool cmTarget::IsChrpathUsed(const std::string& config) const
 
 //----------------------------------------------------------------------------
 cmTarget::ImportInfo const*
-cmTarget::GetImportInfo(const std::string& config,
-                        cmTarget const* headTarget) const
+cmTarget::GetImportInfo(const std::string& config) const
 {
   // There is no imported information for non-imported targets.
   if(!this->IsImported())
@@ -5689,16 +5697,15 @@ cmTarget::GetImportInfo(const std::string& config,
     {
     config_upper = "NOCONFIG";
     }
-  TargetConfigPair key(headTarget, config_upper);
   typedef cmTargetInternals::ImportInfoMapType ImportInfoMapType;
 
   ImportInfoMapType::const_iterator i =
-    this->Internal->ImportInfoMap.find(key);
+    this->Internal->ImportInfoMap.find(config_upper);
   if(i == this->Internal->ImportInfoMap.end())
     {
     ImportInfo info;
-    this->ComputeImportInfo(config_upper, info, headTarget);
-    ImportInfoMapType::value_type entry(key, info);
+    this->ComputeImportInfo(config_upper, info);
+    ImportInfoMapType::value_type entry(config_upper, info);
     i = this->Internal->ImportInfoMap.insert(entry).first;
     }
 
@@ -5850,8 +5857,7 @@ bool cmTarget::GetMappedConfig(std::string const& desired_config,
 
 //----------------------------------------------------------------------------
 void cmTarget::ComputeImportInfo(std::string const& desired_config,
-                                 ImportInfo& info,
-                                 cmTarget const* headTarget) const
+                                 ImportInfo& info) const
 {
   // This method finds information about an imported target from its
   // properties.  The "IMPORTED_" namespace is reserved for properties
@@ -5890,8 +5896,8 @@ void cmTarget::ComputeImportInfo(std::string const& desired_config,
     }
   if(propertyLibs)
     {
-    this->ExpandLinkItems(linkProp, propertyLibs, desired_config,
-                          headTarget, info.LinkInterface.Libraries);
+    info.LibrariesProp = linkProp;
+    info.Libraries = propertyLibs;
     }
   }
   if(this->GetType() == INTERFACE_LIBRARY)
@@ -5977,13 +5983,12 @@ void cmTarget::ComputeImportInfo(std::string const& desired_config,
   linkProp += suffix;
   if(const char* config_libs = this->GetProperty(linkProp))
     {
-    cmSystemTools::ExpandListArgument(config_libs,
-                                      info.LinkInterface.SharedDeps);
+    info.SharedDeps = config_libs;
     }
   else if(const char* libs =
           this->GetProperty("IMPORTED_LINK_DEPENDENT_LIBRARIES"))
     {
-    cmSystemTools::ExpandListArgument(libs, info.LinkInterface.SharedDeps);
+    info.SharedDeps = libs;
     }
   }
 
@@ -5994,14 +5999,12 @@ void cmTarget::ComputeImportInfo(std::string const& desired_config,
     linkProp += suffix;
     if(const char* config_libs = this->GetProperty(linkProp))
       {
-      cmSystemTools::ExpandListArgument(config_libs,
-                                        info.LinkInterface.Languages);
+      info.Languages = config_libs;
       }
     else if(const char* libs =
             this->GetProperty("IMPORTED_LINK_INTERFACE_LANGUAGES"))
       {
-      cmSystemTools::ExpandListArgument(libs,
-                                        info.LinkInterface.Languages);
+      info.Languages = libs;
       }
     }
 
@@ -6012,12 +6015,12 @@ void cmTarget::ComputeImportInfo(std::string const& desired_config,
     linkProp += suffix;
     if(const char* config_reps = this->GetProperty(linkProp))
       {
-      sscanf(config_reps, "%u", &info.LinkInterface.Multiplicity);
+      sscanf(config_reps, "%u", &info.Multiplicity);
       }
     else if(const char* reps =
             this->GetProperty("IMPORTED_LINK_INTERFACE_MULTIPLICITY"))
       {
-      sscanf(reps, "%u", &info.LinkInterface.Multiplicity);
+      sscanf(reps, "%u", &info.Multiplicity);
       }
     }
 }
@@ -6030,11 +6033,7 @@ cmTarget::LinkInterface const* cmTarget::GetLinkInterface(
   // Imported targets have their own link interface.
   if(this->IsImported())
     {
-    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, head))
-      {
-      return &info->LinkInterface;
-      }
-    return 0;
+    return this->GetImportLinkInterface(config, head);
     }
 
   // Link interfaces are not supported for executables that do not
@@ -6083,11 +6082,7 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
   // Imported targets have their own link interface.
   if(this->IsImported())
     {
-    if(cmTarget::ImportInfo const* info = this->GetImportInfo(config, head))
-      {
-      return &info->LinkInterface;
-      }
-    return 0;
+    return this->GetImportLinkInterface(config, head);
     }
 
   // Link interfaces are not supported for executables that do not
@@ -6121,6 +6116,37 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
+cmTarget::LinkInterface const*
+cmTarget::GetImportLinkInterface(const std::string& config,
+                                 cmTarget const* headTarget) const
+{
+  cmTarget::ImportInfo const* info = this->GetImportInfo(config);
+  if(!info)
+    {
+    return 0;
+    }
+
+  TargetConfigPair key(headTarget, cmSystemTools::UpperCase(config));
+
+  cmTargetInternals::ImportLinkInterfaceMapType::iterator i =
+    this->Internal->ImportLinkInterfaceMap.find(key);
+  if(i == this->Internal->ImportLinkInterfaceMap.end())
+    {
+    LinkInterface iface;
+    iface.Multiplicity = info->Multiplicity;
+    cmSystemTools::ExpandListArgument(info->Languages, iface.Languages);
+    this->ExpandLinkItems(info->LibrariesProp, info->Libraries, config,
+                          headTarget, iface.Libraries);
+    cmSystemTools::ExpandListArgument(info->SharedDeps, iface.SharedDeps);
+
+    cmTargetInternals::ImportLinkInterfaceMapType::value_type
+      entry(key, iface);
+    i = this->Internal->ImportLinkInterfaceMap.insert(entry).first;
+    }
+  return &i->second;
+}
+
+//----------------------------------------------------------------------------
 void processILibs(const std::string& config,
                   cmTarget const* headTarget,
                   cmTarget const* curTarget,
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index dbca09c..049d3ea 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -732,10 +732,9 @@ private:
 
   // Cache import information from properties for each configuration.
   struct ImportInfo;
-  ImportInfo const* GetImportInfo(const std::string& config,
-                                        cmTarget const* workingTarget) const;
-  void ComputeImportInfo(std::string const& desired_config, ImportInfo& info,
-                                        cmTarget const* head) const;
+  ImportInfo const* GetImportInfo(const std::string& config) const;
+  void ComputeImportInfo(std::string const& desired_config,
+                         ImportInfo& info) const;
 
   // Cache target compile paths for each configuration.
   struct CompileInfo;
@@ -745,6 +744,10 @@ private:
   void CheckPropertyCompatibility(cmComputeLinkInformation *info,
                                   const std::string& config) const;
 
+  LinkInterface const*
+    GetImportLinkInterface(const std::string& config,
+                           cmTarget const* head) const;
+
   const char* ComputeLinkInterfaceLibraries(const std::string& config,
                                             LinkInterface& iface,
                                             cmTarget const* head,

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=ed00c8c6d1b226ed614ebfaf4fe99b2be3f7ebad
commit ed00c8c6d1b226ed614ebfaf4fe99b2be3f7ebad
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 11:31:11 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:49:26 2014 -0400

    cmTarget: De-duplicate library list expansion
    
    Create an ExpandLinkItems method to handle evaluation of generator
    expressions in a library list and expansion of the ;-list into a vector.
    Replace some duplicate copies of the implementation with calls to the
    new helper.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 462f7f4..84646b9 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -3697,6 +3697,23 @@ void cmTarget::ComputeLinkClosure(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
+void cmTarget::ExpandLinkItems(std::string const& prop,
+                               std::string const& value,
+                               std::string const& config,
+                               cmTarget const* headTarget,
+                               std::vector<std::string>& libs) const
+{
+  cmGeneratorExpression ge;
+  cmGeneratorExpressionDAGChecker dagChecker(this->GetName(), prop, 0, 0);
+  cmSystemTools::ExpandListArgument(ge.Parse(value)->Evaluate(
+                                      this->Makefile,
+                                      config,
+                                      false,
+                                      headTarget,
+                                      this, &dagChecker), libs);
+}
+
+//----------------------------------------------------------------------------
 const char* cmTarget::GetSuffixVariableInternal(bool implib) const
 {
   switch(this->GetType())
@@ -5873,19 +5890,8 @@ void cmTarget::ComputeImportInfo(std::string const& desired_config,
     }
   if(propertyLibs)
     {
-    cmGeneratorExpression ge;
-
-    cmGeneratorExpressionDAGChecker dagChecker(
-                                        this->GetName(),
-                                        linkProp, 0, 0);
-    cmSystemTools::ExpandListArgument(ge.Parse(propertyLibs)
-                                       ->Evaluate(this->Makefile,
-                                                  desired_config,
-                                                  false,
-                                                  headTarget,
-                                                  this,
-                                                  &dagChecker),
-                                    info.LinkInterface.Libraries);
+    this->ExpandLinkItems(linkProp, propertyLibs, desired_config,
+                          headTarget, info.LinkInterface.Libraries);
     }
   }
   if(this->GetType() == INTERFACE_LIBRARY)
@@ -6310,15 +6316,8 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
   if(explicitLibraries)
     {
     // The interface libraries have been explicitly set.
-    cmGeneratorExpression ge;
-    cmGeneratorExpressionDAGChecker dagChecker(this->GetName(),
-                                               linkIfaceProp, 0, 0);
-    cmSystemTools::ExpandListArgument(ge.Parse(explicitLibraries)->Evaluate(
-                                        this->Makefile,
-                                        config,
-                                        false,
-                                        headTarget,
-                                        this, &dagChecker), iface.Libraries);
+    this->ExpandLinkItems(linkIfaceProp, explicitLibraries, config,
+                          headTarget, iface.Libraries);
     }
   else if (this->PolicyStatusCMP0022 == cmPolicies::WARN
         || this->PolicyStatusCMP0022 == cmPolicies::OLD)
@@ -6336,19 +6335,13 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
       {
       // Compare the link implementation fallback link interface to the
       // preferred new link interface property and warn if different.
-      cmGeneratorExpression ge;
-      cmGeneratorExpressionDAGChecker dagChecker(this->GetName(),
-                                      "INTERFACE_LINK_LIBRARIES", 0, 0);
       std::vector<std::string> ifaceLibs;
-      const char* newExplicitLibraries =
-        this->GetProperty("INTERFACE_LINK_LIBRARIES");
-      cmSystemTools::ExpandListArgument(
-        ge.Parse(newExplicitLibraries)->Evaluate(this->Makefile,
-                                                 config,
-                                                 false,
-                                                 headTarget,
-                                                 this, &dagChecker),
-        ifaceLibs);
+      std::string newProp = "INTERFACE_LINK_LIBRARIES";
+      if(const char* newExplicitLibraries = this->GetProperty(newProp))
+        {
+        this->ExpandLinkItems(newProp, newExplicitLibraries, config,
+                              headTarget, ifaceLibs);
+        }
       if (ifaceLibs != impl->Libraries)
         {
         std::string oldLibraries;
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index d94642e..dbca09c 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -764,6 +764,10 @@ private:
                                           cmTarget const* head) const;
   void ComputeLinkClosure(const std::string& config, LinkClosure& lc) const;
 
+  void ExpandLinkItems(std::string const& prop, std::string const& value,
+                       std::string const& config, cmTarget const* headTarget,
+                       std::vector<std::string>& libs) const;
+
   std::string ProcessSourceItemCMP0049(const std::string& s);
 
   void ClearLinkMaps();

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=992821ef04532f377d043b1258d2f46c65dfc988
commit 992821ef04532f377d043b1258d2f46c65dfc988
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 10:10:18 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 14:48:06 2014 -0400

    Fix scope of transitive target name lookups
    
    In cmTarget, cmGeneratorTarget, and cmGeneratorExpressionEvaluator, fix
    target name lookups to occur in the cmMakefile context of the target
    that referenced the name, not the current 'head' target.  The context
    matters for imported targets because they are directory-scoped instead
    of globally unique.  We already do this in cmComputeLinkDepends and
    cmComputeTargetDepends.
    
    Extend the InterfaceLibrary test with an example covering this behavior.

diff --git a/Source/cmGeneratorExpressionEvaluator.cxx b/Source/cmGeneratorExpressionEvaluator.cxx
index 3dee601..f491882 100644
--- a/Source/cmGeneratorExpressionEvaluator.cxx
+++ b/Source/cmGeneratorExpressionEvaluator.cxx
@@ -828,7 +828,7 @@ std::string getLinkedTargetsContent(
     sep = ";";
     }
   cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(depString);
-  std::string linkedTargetsContent = cge->Evaluate(context->Makefile,
+  std::string linkedTargetsContent = cge->Evaluate(target->GetMakefile(),
                       context->Config,
                       context->Quiet,
                       headTarget,
@@ -853,7 +853,7 @@ std::string getLinkedTargetsContent(const std::vector<std::string> &libraries,
       it = libraries.begin();
       it != libraries.end(); ++it)
     {
-    if (cmTarget const *tgt = context->Makefile->FindTargetToUse(*it))
+    if (cmTarget const *tgt = target->FindTargetToLink(*it))
       {
       tgts.push_back(tgt);
       }
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index 392b377..36c5648 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -478,7 +478,7 @@ bool cmGeneratorTarget::IsSystemIncludeDirectory(const std::string& dir,
     for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
         li != impl->Libraries.end(); ++li)
       {
-      cmTarget const* tgt = this->Makefile->FindTargetToUse(*li);
+      cmTarget const* tgt = this->Target->FindTargetToLink(*li);
       if (!tgt)
         {
         continue;
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 4f630a1..462f7f4 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -3483,9 +3483,9 @@ public:
     Makefile(target->GetMakefile()), Target(target)
   { this->Visited.insert(target); }
 
-  void Visit(const std::string& name)
+  void Visit(cmTarget const* from, const std::string& name)
     {
-    cmTarget *target = this->Makefile->FindTargetToUse(name);
+    cmTarget const *target = from->FindTargetToLink(name);
 
     if(!target)
       {
@@ -3544,7 +3544,7 @@ public:
     for(std::vector<std::string>::const_iterator
           li = iface->Libraries.begin(); li != iface->Libraries.end(); ++li)
       {
-      this->Visit(*li);
+      this->Visit(target, *li);
       }
     }
 private:
@@ -3650,7 +3650,7 @@ void cmTarget::ComputeLinkClosure(const std::string& config,
   for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
       li != impl->Libraries.end(); ++li)
     {
-    cll.Visit(*li);
+    cll.Visit(this, *li);
     }
 
   // Store the transitive closure of languages.
@@ -6117,12 +6117,12 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
 //----------------------------------------------------------------------------
 void processILibs(const std::string& config,
                   cmTarget const* headTarget,
+                  cmTarget const* curTarget,
                   std::string const& name,
                   std::vector<cmTarget const*>& tgts,
                   std::set<cmTarget const*>& emitted)
 {
-  if (cmTarget* tgt = headTarget->GetMakefile()
-                                ->FindTargetToUse(name))
+  if (cmTarget const* tgt = curTarget->FindTargetToLink(name))
     {
     if (emitted.insert(tgt).second)
       {
@@ -6135,7 +6135,7 @@ void processILibs(const std::string& config,
             it = iface->Libraries.begin();
             it != iface->Libraries.end(); ++it)
           {
-          processILibs(config, headTarget, *it, tgts, emitted);
+          processILibs(config, headTarget, tgt, *it, tgts, emitted);
           }
         }
       }
@@ -6159,7 +6159,7 @@ cmTarget::GetLinkImplementationClosure(const std::string& config) const
     for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
         it != impl->Libraries.end(); ++it)
       {
-      processILibs(config, this, *it, tgts , emitted);
+      processILibs(config, this, this, *it, tgts , emitted);
       }
     }
   return tgts;
@@ -6183,8 +6183,7 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
     for(std::vector<std::string>::const_iterator it = iface->Libraries.begin();
         it != iface->Libraries.end(); ++it)
       {
-      if (cmTarget const* tgt = headTarget->GetMakefile()
-                                    ->FindTargetToUse(*it))
+      if (cmTarget const* tgt = this->FindTargetToLink(*it))
         {
         tgts.push_back(tgt);
         }
@@ -6216,8 +6215,7 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
   for(std::vector<std::string>::const_iterator it = libs.begin();
       it != libs.end(); ++it)
     {
-    if (cmTarget* tgt = headTarget->GetMakefile()
-                                  ->FindTargetToUse(*it))
+    if (cmTarget const* tgt = this->FindTargetToLink(*it))
       {
       tgts.push_back(tgt);
       }
diff --git a/Tests/InterfaceLibrary/CMakeLists.txt b/Tests/InterfaceLibrary/CMakeLists.txt
index 81b34e6..d4f49c2 100644
--- a/Tests/InterfaceLibrary/CMakeLists.txt
+++ b/Tests/InterfaceLibrary/CMakeLists.txt
@@ -8,8 +8,18 @@ target_compile_definitions(iface_nodepends INTERFACE IFACE_DEFINE)
 
 add_subdirectory(headerdir)
 
+# Add an interface target in a subdirectory that uses an imported interface.
+add_subdirectory(ifacedir)
+
+# Poison an imported interface with the same name as that in the subdir
+# to ensure that the transitive lookup occurs in the subdir.
+add_library(imp::iface INTERFACE IMPORTED)
+set_property(TARGET imp::iface APPEND PROPERTY COMPATIBLE_INTERFACE_BOOL SOMEPROP)
+set_property(TARGET imp::iface PROPERTY INTERFACE_SOMEPROP OFF)
+set_property(TARGET imp::iface PROPERTY INTERFACE_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/does_not_exist.cpp)
+
 add_executable(InterfaceLibrary definetestexe.cpp)
-target_link_libraries(InterfaceLibrary iface_nodepends headeriface)
+target_link_libraries(InterfaceLibrary iface_nodepends headeriface subiface)
 
 add_subdirectory(libsdir)
 
diff --git a/Tests/InterfaceLibrary/definetestexe.cpp b/Tests/InterfaceLibrary/definetestexe.cpp
index e7a10c1..30f2925 100644
--- a/Tests/InterfaceLibrary/definetestexe.cpp
+++ b/Tests/InterfaceLibrary/definetestexe.cpp
@@ -15,7 +15,9 @@
 #error Expected IFACE_HEADER_BUILDDIR
 #endif
 
+extern int sub();
+
 int main(int,char**)
 {
-  return 0;
+  return sub();
 }
diff --git a/Tests/InterfaceLibrary/ifacedir/CMakeLists.txt b/Tests/InterfaceLibrary/ifacedir/CMakeLists.txt
new file mode 100644
index 0000000..228715e
--- /dev/null
+++ b/Tests/InterfaceLibrary/ifacedir/CMakeLists.txt
@@ -0,0 +1,8 @@
+add_library(imp::iface INTERFACE IMPORTED)
+set_property(TARGET imp::iface APPEND PROPERTY COMPATIBLE_INTERFACE_BOOL SOMEPROP)
+set_property(TARGET imp::iface PROPERTY INTERFACE_SOMEPROP ON)
+set_property(TARGET imp::iface PROPERTY INTERFACE_SOURCES ${CMAKE_CURRENT_SOURCE_DIR}/sub.cpp)
+
+add_library(subiface INTERFACE)
+target_link_libraries(subiface INTERFACE imp::iface)
+set_property(TARGET subiface PROPERTY INTERFACE_SOMEPROP ON)
diff --git a/Tests/InterfaceLibrary/ifacedir/sub.cpp b/Tests/InterfaceLibrary/ifacedir/sub.cpp
new file mode 100644
index 0000000..165a66a
--- /dev/null
+++ b/Tests/InterfaceLibrary/ifacedir/sub.cpp
@@ -0,0 +1 @@
+int sub() { return 0; }

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=cc923aa541b0d10dbe06c87aaba2ed2096b995ef
commit cc923aa541b0d10dbe06c87aaba2ed2096b995ef
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 10:09:46 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:24:55 2014 -0400

    cmTarget: Constify GetLinkImplementationClosure results
    
    Populate a vector of "cmTarget const*" instead of "cmTarget*".

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index bed787c..4f630a1 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -169,7 +169,7 @@ public:
                                 CachedLinkInterfaceSourcesEntries;
   mutable std::map<std::string, std::vector<TargetPropertyEntry*> >
                                 CachedLinkInterfaceCompileFeaturesEntries;
-  mutable std::map<std::string, std::vector<cmTarget*> >
+  mutable std::map<std::string, std::vector<cmTarget const*> >
                                 CachedLinkImplementationClosure;
 
   mutable std::map<std::string, bool> CacheLinkInterfaceIncludeDirectoriesDone;
@@ -5193,7 +5193,7 @@ PropertyType checkInterfacePropertyCompatibility(cmTarget const* tgt,
   assert((impliedByUse ^ explicitlySet)
       || (!impliedByUse && !explicitlySet));
 
-  std::vector<cmTarget*> const& deps =
+  std::vector<cmTarget const*> const& deps =
     tgt->GetLinkImplementationClosure(config);
 
   if(deps.empty())
@@ -5219,7 +5219,7 @@ PropertyType checkInterfacePropertyCompatibility(cmTarget const* tgt,
     report += "\" property not set.\n";
     }
 
-  for(std::vector<cmTarget*>::const_iterator li =
+  for(std::vector<cmTarget const*>::const_iterator li =
       deps.begin();
       li != deps.end(); ++li)
     {
@@ -5409,7 +5409,7 @@ bool isLinkDependentProperty(cmTarget const* tgt, const std::string &p,
                              const std::string& interfaceProperty,
                              const std::string& config)
 {
-  std::vector<cmTarget*> const& deps =
+  std::vector<cmTarget const*> const& deps =
     tgt->GetLinkImplementationClosure(config);
 
   if(deps.empty())
@@ -5417,8 +5417,7 @@ bool isLinkDependentProperty(cmTarget const* tgt, const std::string &p,
     return false;
     }
 
-  for(std::vector<cmTarget*>::const_iterator li =
-      deps.begin();
+  for(std::vector<cmTarget const*>::const_iterator li = deps.begin();
       li != deps.end(); ++li)
     {
     const char *prop = (*li)->GetProperty(interfaceProperty);
@@ -6119,7 +6118,8 @@ cmTarget::GetLinkInterfaceLibraries(const std::string& config,
 void processILibs(const std::string& config,
                   cmTarget const* headTarget,
                   std::string const& name,
-                  std::vector<cmTarget*>& tgts, std::set<cmTarget*>& emitted)
+                  std::vector<cmTarget const*>& tgts,
+                  std::set<cmTarget const*>& emitted)
 {
   if (cmTarget* tgt = headTarget->GetMakefile()
                                 ->FindTargetToUse(name))
@@ -6143,15 +6143,15 @@ void processILibs(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
-std::vector<cmTarget*> const&
+std::vector<cmTarget const*> const&
 cmTarget::GetLinkImplementationClosure(const std::string& config) const
 {
-  std::vector<cmTarget*>& tgts =
+  std::vector<cmTarget const*>& tgts =
     this->Internal->CachedLinkImplementationClosure[config];
   if(!this->Internal->CacheLinkImplementationClosureDone[config])
     {
     this->Internal->CacheLinkImplementationClosureDone[config] = true;
-    std::set<cmTarget*> emitted;
+    std::set<cmTarget const*> emitted;
 
     cmTarget::LinkImplementation const* impl
       = this->GetLinkImplementationLibraries(config);
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 023c4e2..d94642e 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -273,7 +273,7 @@ public:
   void GetTransitivePropertyTargets(const std::string& config,
                                     cmTarget const* headTarget,
                                     std::vector<cmTarget const*> &libs) const;
-  std::vector<cmTarget*> const&
+  std::vector<cmTarget const*> const&
     GetLinkImplementationClosure(const std::string& config) const;
 
   /** The link implementation specifies the direct library

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=ea985616b79a251e24d8d257da33e1ba290b2699
commit ea985616b79a251e24d8d257da33e1ba290b2699
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 09:55:20 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:22:22 2014 -0400

    cmTarget: Constify GetTransitivePropertyTargets results
    
    Populate a vector of "cmTarget const*" instead of "cmTarget*".

diff --git a/Source/cmGeneratorExpressionEvaluator.cxx b/Source/cmGeneratorExpressionEvaluator.cxx
index cefdd63..3dee601 100644
--- a/Source/cmGeneratorExpressionEvaluator.cxx
+++ b/Source/cmGeneratorExpressionEvaluator.cxx
@@ -799,7 +799,8 @@ static const char* targetPropertyTransitiveWhitelist[] = {
 
 #undef TRANSITIVE_PROPERTY_NAME
 
-std::string getLinkedTargetsContent(const std::vector<cmTarget*> &targets,
+std::string getLinkedTargetsContent(
+                                  const std::vector<cmTarget const*> &targets,
                                   cmTarget const* target,
                                   cmTarget const* headTarget,
                                   cmGeneratorExpressionContext *context,
@@ -810,7 +811,7 @@ std::string getLinkedTargetsContent(const std::vector<cmTarget*> &targets,
 
   std::string sep;
   std::string depString;
-  for (std::vector<cmTarget*>::const_iterator
+  for (std::vector<cmTarget const*>::const_iterator
       it = targets.begin();
       it != targets.end(); ++it)
     {
@@ -847,12 +848,12 @@ std::string getLinkedTargetsContent(const std::vector<std::string> &libraries,
                                   cmGeneratorExpressionDAGChecker *dagChecker,
                                   const std::string &interfacePropertyName)
 {
-  std::vector<cmTarget*> tgts;
+  std::vector<cmTarget const*> tgts;
   for (std::vector<std::string>::const_iterator
       it = libraries.begin();
       it != libraries.end(); ++it)
     {
-    if (cmTarget *tgt = context->Makefile->FindTargetToUse(*it))
+    if (cmTarget const *tgt = context->Makefile->FindTargetToUse(*it))
       {
       tgts.push_back(tgt);
       }
@@ -1082,7 +1083,7 @@ static const struct TargetPropertyNode : public cmGeneratorExpressionNode
                      cmStrCmp(propertyName)) != transEnd)
       {
 
-      std::vector<cmTarget*> tgts;
+      std::vector<cmTarget const*> tgts;
       target->GetTransitivePropertyTargets(context->Config,
                                                  headTarget, tgts);
       if (!tgts.empty())
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index 381a0ed..392b377 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -252,7 +252,7 @@ cmGeneratorTarget::GetSourceDepends(cmSourceFile const* sf) const
   return 0;
 }
 
-static void handleSystemIncludesDep(cmMakefile *mf, cmTarget* depTgt,
+static void handleSystemIncludesDep(cmMakefile *mf, cmTarget const* depTgt,
                                   const std::string& config,
                                   cmTarget *headTarget,
                                   cmGeneratorExpressionDAGChecker *dagChecker,
@@ -474,11 +474,11 @@ bool cmGeneratorTarget::IsSystemIncludeDirectory(const std::string& dir,
                                           &dagChecker), result);
       }
 
-    std::set<cmTarget*> uniqueDeps;
+    std::set<cmTarget const*> uniqueDeps;
     for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
         li != impl->Libraries.end(); ++li)
       {
-      cmTarget* tgt = this->Makefile->FindTargetToUse(*li);
+      cmTarget const* tgt = this->Makefile->FindTargetToUse(*li);
       if (!tgt)
         {
         continue;
@@ -489,10 +489,10 @@ bool cmGeneratorTarget::IsSystemIncludeDirectory(const std::string& dir,
         handleSystemIncludesDep(this->Makefile, tgt, config, this->Target,
                                 &dagChecker, result, excludeImported);
 
-        std::vector<cmTarget*> deps;
+        std::vector<cmTarget const*> deps;
         tgt->GetTransitivePropertyTargets(config, this->Target, deps);
 
-        for(std::vector<cmTarget*>::const_iterator di = deps.begin();
+        for(std::vector<cmTarget const*>::const_iterator di = deps.begin();
             di != deps.end(); ++di)
           {
           if (uniqueDeps.insert(*di).second)
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 2c7a6cd..bed787c 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -6168,7 +6168,7 @@ cmTarget::GetLinkImplementationClosure(const std::string& config) const
 //----------------------------------------------------------------------------
 void cmTarget::GetTransitivePropertyTargets(const std::string& config,
                                       cmTarget const* headTarget,
-                                      std::vector<cmTarget*> &tgts) const
+                                      std::vector<cmTarget const*> &tgts) const
 {
   cmTarget::LinkInterface const* iface
                         = this->GetLinkInterfaceLibraries(config, headTarget);
@@ -6183,7 +6183,7 @@ void cmTarget::GetTransitivePropertyTargets(const std::string& config,
     for(std::vector<std::string>::const_iterator it = iface->Libraries.begin();
         it != iface->Libraries.end(); ++it)
       {
-      if (cmTarget* tgt = headTarget->GetMakefile()
+      if (cmTarget const* tgt = headTarget->GetMakefile()
                                     ->FindTargetToUse(*it))
         {
         tgts.push_back(tgt);
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 0a24cf7..023c4e2 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -271,8 +271,8 @@ public:
   LinkInterface const* GetLinkInterfaceLibraries(const std::string& config,
                                         cmTarget const* headTarget) const;
   void GetTransitivePropertyTargets(const std::string& config,
-                                        cmTarget const* headTarget,
-                                        std::vector<cmTarget*> &libs) const;
+                                    cmTarget const* headTarget,
+                                    std::vector<cmTarget const*> &libs) const;
   std::vector<cmTarget*> const&
     GetLinkImplementationClosure(const std::string& config) const;
 

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=9b268d63435a36525a39dbaced028b21dceee539
commit 9b268d63435a36525a39dbaced028b21dceee539
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 09:49:13 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:22:21 2014 -0400

    cmComputeTargetDepends: Remove unused 'linking' argument
    
    The AddInterfaceDepends method is never called with a non-true value for
    its 'linking' argument.  Drop it.

diff --git a/Source/cmComputeTargetDepends.cxx b/Source/cmComputeTargetDepends.cxx
index 3082ef3..a5df060 100644
--- a/Source/cmComputeTargetDepends.cxx
+++ b/Source/cmComputeTargetDepends.cxx
@@ -261,8 +261,7 @@ void cmComputeTargetDepends::CollectTargetDepends(int depender_index)
       if(emitted.insert(*lib).second)
         {
         this->AddTargetDepend(depender_index, *lib, true);
-        this->AddInterfaceDepends(depender_index, *lib,
-                                  true, emitted);
+        this->AddInterfaceDepends(depender_index, *lib, emitted);
         }
       }
     }
@@ -304,8 +303,7 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
       if(emitted.insert(*lib).second)
         {
         this->AddTargetDepend(depender_index, *lib, true);
-        this->AddInterfaceDepends(depender_index, *lib,
-                                  true, emitted);
+        this->AddInterfaceDepends(depender_index, *lib, emitted);
         }
       }
     }
@@ -314,7 +312,6 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
 //----------------------------------------------------------------------------
 void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
                                              const std::string& dependee_name,
-                                             bool linking,
                                              std::set<std::string> &emitted)
 {
   cmTarget const* depender = this->Targets[depender_index];
@@ -323,7 +320,7 @@ void cmComputeTargetDepends::AddInterfaceDepends(int depender_index,
   // Skip targets that will not really be linked.  This is probably a
   // name conflict between an external library and an executable
   // within the project.
-  if(linking && dependee &&
+  if(dependee &&
      dependee->GetType() == cmTarget::EXECUTABLE &&
      !dependee->IsExecutableWithExports())
     {
diff --git a/Source/cmComputeTargetDepends.h b/Source/cmComputeTargetDepends.h
index 7553816..b99199f 100644
--- a/Source/cmComputeTargetDepends.h
+++ b/Source/cmComputeTargetDepends.h
@@ -53,7 +53,7 @@ private:
   bool ComputeFinalDepends(cmComputeComponentGraph const& ccg);
   void AddInterfaceDepends(int depender_index,
                            const std::string& dependee_name,
-                           bool linking, std::set<std::string> &emitted);
+                           std::set<std::string> &emitted);
   void AddInterfaceDepends(int depender_index, cmTarget const* dependee,
                            const std::string& config,
                            std::set<std::string> &emitted);

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=7d06f2db29f4df8dd4a452dce5291dae6fb81ba9
commit 7d06f2db29f4df8dd4a452dce5291dae6fb81ba9
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 09:45:46 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:22:21 2014 -0400

    cmTarget: Add method to lookup other targets in a target's scope
    
    Move the main implementation of cmComputeLinkDepends::FindTargetToLink
    into cmTarget.

diff --git a/Source/cmComputeLinkDepends.cxx b/Source/cmComputeLinkDepends.cxx
index a07072a..5abf6dd 100644
--- a/Source/cmComputeLinkDepends.cxx
+++ b/Source/cmComputeLinkDepends.cxx
@@ -623,40 +623,15 @@ cmTarget const* cmComputeLinkDepends::FindTargetToLink(int depender_index,
                                                  const std::string& name)
 {
   // Look for a target in the scope of the depender.
-  cmMakefile* mf = this->Makefile;
+  cmTarget const* from = this->Target;
   if(depender_index >= 0)
     {
     if(cmTarget const* depender = this->EntryList[depender_index].Target)
       {
-      mf = depender->GetMakefile();
+      from = depender;
       }
     }
-  cmTarget const* tgt = mf->FindTargetToUse(name);
-
-  // Skip targets that will not really be linked.  This is probably a
-  // name conflict between an external library and an executable
-  // within the project.
-  if(tgt && tgt->GetType() == cmTarget::EXECUTABLE &&
-     !tgt->IsExecutableWithExports())
-    {
-    tgt = 0;
-    }
-
-  if(tgt && tgt->GetType() == cmTarget::OBJECT_LIBRARY)
-    {
-    cmOStringStream e;
-    e << "Target \"" << this->Target->GetName() << "\" links to "
-      "OBJECT library \"" << tgt->GetName() << "\" but this is not "
-      "allowed.  "
-      "One may link only to STATIC or SHARED libraries, or to executables "
-      "with the ENABLE_EXPORTS property set.";
-    this->CMakeInstance->IssueMessage(cmake::FATAL_ERROR, e.str(),
-                                      this->Target->GetBacktrace());
-    tgt = 0;
-    }
-
-  // Return the target found, if any.
-  return tgt;
+  return from->FindTargetToLink(name);
 }
 
 //----------------------------------------------------------------------------
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 80976eb..2c7a6cd 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -6665,6 +6665,37 @@ cmTarget::ComputeLinkImplementationLanguages(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
+cmTarget const* cmTarget::FindTargetToLink(std::string const& name) const
+{
+  cmTarget const* tgt = this->Makefile->FindTargetToUse(name);
+
+  // Skip targets that will not really be linked.  This is probably a
+  // name conflict between an external library and an executable
+  // within the project.
+  if(tgt && tgt->GetType() == cmTarget::EXECUTABLE &&
+     !tgt->IsExecutableWithExports())
+    {
+    tgt = 0;
+    }
+
+  if(tgt && tgt->GetType() == cmTarget::OBJECT_LIBRARY)
+    {
+    cmOStringStream e;
+    e << "Target \"" << this->GetName() << "\" links to "
+      "OBJECT library \"" << tgt->GetName() << "\" but this is not "
+      "allowed.  "
+      "One may link only to STATIC or SHARED libraries, or to executables "
+      "with the ENABLE_EXPORTS property set.";
+    cmake* cm = this->Makefile->GetCMakeInstance();
+    cm->IssueMessage(cmake::FATAL_ERROR, e.str(), this->GetBacktrace());
+    tgt = 0;
+    }
+
+  // Return the target found, if any.
+  return tgt;
+}
+
+//----------------------------------------------------------------------------
 std::string cmTarget::CheckCMP0004(std::string const& item) const
 {
   // Strip whitespace off the library names because we used to do this
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index b80d4f8..0a24cf7 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -308,6 +308,8 @@ public:
   };
   LinkClosure const* GetLinkClosure(const std::string& config) const;
 
+  cmTarget const* FindTargetToLink(std::string const& name) const;
+
   /** Strip off leading and trailing whitespace from an item named in
       the link dependencies of this target.  */
   std::string CheckCMP0004(std::string const& item) const;

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=03fe9ec68f9301f070df3f24403d487a26b67887
commit 03fe9ec68f9301f070df3f24403d487a26b67887
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 09:38:04 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:22:21 2014 -0400

    cmExportFileGenerator: Make SetImportLinkProperty a template
    
    Allow the vector of property entries to have any element type
    that can convert to std::string.

diff --git a/Source/cmExportFileGenerator.cxx b/Source/cmExportFileGenerator.cxx
index 9f5eee5..1f39d7a 100644
--- a/Source/cmExportFileGenerator.cxx
+++ b/Source/cmExportFileGenerator.cxx
@@ -865,15 +865,16 @@ cmExportFileGenerator
 }
 
 //----------------------------------------------------------------------------
+template <typename T>
 void
 cmExportFileGenerator
 ::SetImportLinkProperty(std::string const& suffix,
                         cmTarget* target,
                         const std::string& propName,
-                        std::vector<std::string> const& entries,
+                        std::vector<T> const& entries,
                         ImportPropertyMap& properties,
                         std::vector<std::string>& missingTargets
-                       )
+  )
 {
   // Skip the property if there are no entries.
   if(entries.empty())
@@ -884,7 +885,7 @@ cmExportFileGenerator
   // Construct the property value.
   std::string link_entries;
   const char* sep = "";
-  for(std::vector<std::string>::const_iterator li = entries.begin();
+  for(typename std::vector<T>::const_iterator li = entries.begin();
       li != entries.end(); ++li)
     {
     // Separate this from the previous entry.
@@ -902,7 +903,6 @@ cmExportFileGenerator
   properties[prop] = link_entries;
 }
 
-
 //----------------------------------------------------------------------------
 void cmExportFileGenerator::GenerateImportHeaderCode(std::ostream& os,
                                                     const std::string& config)
diff --git a/Source/cmExportFileGenerator.h b/Source/cmExportFileGenerator.h
index abd8ad5..919924e 100644
--- a/Source/cmExportFileGenerator.h
+++ b/Source/cmExportFileGenerator.h
@@ -95,9 +95,11 @@ protected:
                                  std::string const& suffix, cmTarget* target,
                                  ImportPropertyMap& properties,
                                  std::vector<std::string>& missingTargets);
+
+  template <typename T>
   void SetImportLinkProperty(std::string const& suffix,
                              cmTarget* target, const std::string& propName,
-                             std::vector<std::string> const& entries,
+                             std::vector<T> const& entries,
                              ImportPropertyMap& properties,
                              std::vector<std::string>& missingTargets);
 

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=3fed4a603b21aa83a5770b1a1ecff920ab7bb799
commit 3fed4a603b21aa83a5770b1a1ecff920ab7bb799
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Mon Jun 16 09:36:24 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 11:22:18 2014 -0400

    cmTarget: Remove unused GetInterfaceLinkLibraries method

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 9d2e1b5..80976eb 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -1238,29 +1238,6 @@ void cmTarget::GetDirectLinkLibrariesInternal(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
-void cmTarget::GetInterfaceLinkLibraries(const std::string& config,
-                                         std::vector<std::string> &libs,
-                                         cmTarget const* head) const
-{
-  const char *prop = this->GetProperty("INTERFACE_LINK_LIBRARIES");
-  if (prop)
-    {
-    cmGeneratorExpression ge;
-    const cmsys::auto_ptr<cmCompiledGeneratorExpression> cge = ge.Parse(prop);
-
-    cmGeneratorExpressionDAGChecker dagChecker(
-                                        this->GetName(),
-                                        "INTERFACE_LINK_LIBRARIES", 0, 0);
-    cmSystemTools::ExpandListArgument(cge->Evaluate(this->Makefile,
-                                        config,
-                                        false,
-                                        head,
-                                        &dagChecker),
-                                      libs);
-    }
-}
-
-//----------------------------------------------------------------------------
 std::string cmTarget::GetDebugGeneratorExpressions(const std::string &value,
                                   cmTarget::LinkLibraryType llt) const
 {
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 6f02522..b80d4f8 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -159,9 +159,6 @@ public:
     {return this->OriginalLinkLibraries;}
   void GetDirectLinkLibraries(const std::string& config,
                               std::vector<std::string> &) const;
-  void GetInterfaceLinkLibraries(const std::string& config,
-                              std::vector<std::string> &,
-                              cmTarget const* head) const;
 
   /** Compute the link type to use for the given configuration.  */
   LinkLibraryType ComputeLinkType(const std::string& config) const;

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=c5f08a6a068ca9eb8c278e1c8728daa1c9e5a6fb
commit c5f08a6a068ca9eb8c278e1c8728daa1c9e5a6fb
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Thu Jun 12 16:22:11 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Mon Jun 16 09:34:43 2014 -0400

    cmTarget: Remove unused 'head' argument from several linking APIs
    
    Many of the 'head' arguments added by commit v2.8.11~289^2~1 (Make
    linking APIs aware of 'head' target, 2013-01-04) turned out not to be
    needed.  The "link implementation" of a target never needs to be
    computed with anything but itself as the 'head' target (except for
    CMP0022 OLD behavior because then it is the link interface).
    
    Remove the unused 'head' target paths.  Add "internal" versions of
    cmTarget::GetDirectLinkLibraries and GetLinkImplementationLibraries
    to support the CMP0022 OLD behavior without otherwise exposing the
    'head' target option of these methods.

diff --git a/Source/cmComputeLinkDepends.cxx b/Source/cmComputeLinkDepends.cxx
index 995f191..a07072a 100644
--- a/Source/cmComputeLinkDepends.cxx
+++ b/Source/cmComputeLinkDepends.cxx
@@ -172,12 +172,10 @@ satisfy dependencies.
 
 //----------------------------------------------------------------------------
 cmComputeLinkDepends
-::cmComputeLinkDepends(cmTarget const* target, const std::string& config,
-                       cmTarget const* head)
+::cmComputeLinkDepends(cmTarget const* target, const std::string& config)
 {
   // Store context information.
   this->Target = target;
-  this->HeadTarget = head;
   this->Makefile = this->Target->GetMakefile();
   this->LocalGenerator = this->Makefile->GetLocalGenerator();
   this->GlobalGenerator = this->LocalGenerator->GetGlobalGenerator();
@@ -356,7 +354,7 @@ void cmComputeLinkDepends::FollowLinkEntry(BFSEntry const& qe)
     {
     // Follow the target dependencies.
     if(cmTarget::LinkInterface const* iface =
-       entry.Target->GetLinkInterface(this->Config, this->HeadTarget))
+       entry.Target->GetLinkInterface(this->Config, this->Target))
       {
       const bool isIface =
                       entry.Target->GetType() == cmTarget::INTERFACE_LIBRARY;
@@ -455,7 +453,7 @@ void cmComputeLinkDepends::HandleSharedDependency(SharedDepEntry const& dep)
   if(entry.Target)
     {
     if(cmTarget::LinkInterface const* iface =
-       entry.Target->GetLinkInterface(this->Config, this->HeadTarget))
+       entry.Target->GetLinkInterface(this->Config, this->Target))
       {
       // Follow public and private dependencies transitively.
       this->FollowSharedDeps(index, iface, true);
@@ -544,7 +542,7 @@ void cmComputeLinkDepends::AddDirectLinkEntries()
 {
   // Add direct link dependencies in this configuration.
   cmTarget::LinkImplementation const* impl =
-    this->Target->GetLinkImplementation(this->Config, this->HeadTarget);
+    this->Target->GetLinkImplementation(this->Config);
   this->AddLinkEntries(-1, impl->Libraries);
   for(std::vector<std::string>::const_iterator
         wi = impl->WrongConfigLibraries.begin();
@@ -955,7 +953,7 @@ int cmComputeLinkDepends::ComputeComponentCount(NodeList const& nl)
     if(cmTarget const* target = this->EntryList[*ni].Target)
       {
       if(cmTarget::LinkInterface const* iface =
-         target->GetLinkInterface(this->Config, this->HeadTarget))
+         target->GetLinkInterface(this->Config, this->Target))
         {
         if(iface->Multiplicity > count)
           {
diff --git a/Source/cmComputeLinkDepends.h b/Source/cmComputeLinkDepends.h
index 13fc993..440dc0d 100644
--- a/Source/cmComputeLinkDepends.h
+++ b/Source/cmComputeLinkDepends.h
@@ -32,8 +32,7 @@ class cmake;
 class cmComputeLinkDepends
 {
 public:
-  cmComputeLinkDepends(cmTarget const* target, const std::string& config,
-                       cmTarget const* head);
+  cmComputeLinkDepends(cmTarget const* target, const std::string& config);
   ~cmComputeLinkDepends();
 
   // Basic information about each link item.
@@ -60,7 +59,6 @@ private:
 
   // Context information.
   cmTarget const* Target;
-  cmTarget const* HeadTarget;
   cmMakefile* Makefile;
   cmLocalGenerator* LocalGenerator;
   cmGlobalGenerator const* GlobalGenerator;
diff --git a/Source/cmComputeLinkInformation.cxx b/Source/cmComputeLinkInformation.cxx
index 0ce04a5..e1852a3 100644
--- a/Source/cmComputeLinkInformation.cxx
+++ b/Source/cmComputeLinkInformation.cxx
@@ -239,12 +239,10 @@ because this need be done only for shared libraries without soname-s.
 
 //----------------------------------------------------------------------------
 cmComputeLinkInformation
-::cmComputeLinkInformation(cmTarget const* target, const std::string& config,
-                           cmTarget const* headTarget)
+::cmComputeLinkInformation(cmTarget const* target, const std::string& config)
 {
   // Store context information.
   this->Target = target;
-  this->HeadTarget = headTarget;
   this->Makefile = this->Target->GetMakefile();
   this->LocalGenerator = this->Makefile->GetLocalGenerator();
   this->GlobalGenerator = this->LocalGenerator->GetGlobalGenerator();
@@ -267,7 +265,7 @@ cmComputeLinkInformation
   this->OrderDependentRPath = 0;
 
   // Get the language used for linking this target.
-  this->LinkLanguage = this->Target->GetLinkerLanguage(config, headTarget);
+  this->LinkLanguage = this->Target->GetLinkerLanguage(config);
   if(this->LinkLanguage.empty())
     {
     // The Compute method will do nothing, so skip the rest of the
@@ -505,8 +503,7 @@ bool cmComputeLinkInformation::Compute()
     }
 
   // Compute the ordered link line items.
-  cmComputeLinkDepends cld(this->Target, this->Config,
-                           this->HeadTarget);
+  cmComputeLinkDepends cld(this->Target, this->Config);
   cld.SetOldLinkDirMode(this->OldLinkDirMode);
   cmComputeLinkDepends::EntryVector const& linkEntries = cld.Compute();
 
@@ -572,8 +569,7 @@ bool cmComputeLinkInformation::Compute()
 void cmComputeLinkInformation::AddImplicitLinkInfo()
 {
   // The link closure lists all languages whose implicit info is needed.
-  cmTarget::LinkClosure const* lc=this->Target->GetLinkClosure(this->Config,
-                                                          this->HeadTarget);
+  cmTarget::LinkClosure const* lc=this->Target->GetLinkClosure(this->Config);
   for(std::vector<std::string>::const_iterator li = lc->Languages.begin();
       li != lc->Languages.end(); ++li)
     {
@@ -1972,7 +1968,7 @@ void cmComputeLinkInformation::GetRPath(std::vector<std::string>& runtimeDirs,
   // present.  This is done even when skipping rpath support.
   {
   cmTarget::LinkClosure const* lc =
-    this->Target->GetLinkClosure(this->Config, this->HeadTarget);
+    this->Target->GetLinkClosure(this->Config);
   for(std::vector<std::string>::const_iterator li = lc->Languages.begin();
       li != lc->Languages.end(); ++li)
     {
diff --git a/Source/cmComputeLinkInformation.h b/Source/cmComputeLinkInformation.h
index e345fe2..e5d674a 100644
--- a/Source/cmComputeLinkInformation.h
+++ b/Source/cmComputeLinkInformation.h
@@ -29,8 +29,7 @@ class cmOrderDirectories;
 class cmComputeLinkInformation
 {
 public:
-  cmComputeLinkInformation(cmTarget const* target, const std::string& config,
-                           cmTarget const* headTarget);
+  cmComputeLinkInformation(cmTarget const* target, const std::string& config);
   ~cmComputeLinkInformation();
   bool Compute();
 
@@ -75,7 +74,6 @@ private:
 
   // Context information.
   cmTarget const* Target;
-  cmTarget const* HeadTarget;
   cmMakefile* Makefile;
   cmLocalGenerator* LocalGenerator;
   cmGlobalGenerator* GlobalGenerator;
diff --git a/Source/cmComputeTargetDepends.cxx b/Source/cmComputeTargetDepends.cxx
index f28217f..3082ef3 100644
--- a/Source/cmComputeTargetDepends.cxx
+++ b/Source/cmComputeTargetDepends.cxx
@@ -250,7 +250,7 @@ void cmComputeTargetDepends::CollectTargetDepends(int depender_index)
         }
       }
     std::vector<std::string> tlibs;
-    depender->GetDirectLinkLibraries(*it, tlibs, depender);
+    depender->GetDirectLinkLibraries(*it, tlibs);
 
     // A target should not depend on itself.
     emitted.insert(depender->GetName());
diff --git a/Source/cmGeneratorExpressionEvaluator.cxx b/Source/cmGeneratorExpressionEvaluator.cxx
index 7dcb335..cefdd63 100644
--- a/Source/cmGeneratorExpressionEvaluator.cxx
+++ b/Source/cmGeneratorExpressionEvaluator.cxx
@@ -1098,8 +1098,7 @@ static const struct TargetPropertyNode : public cmGeneratorExpressionNode
                           cmStrCmp(interfacePropertyName)) != transEnd)
       {
       const cmTarget::LinkImplementation *impl
-          = target->GetLinkImplementationLibraries(context->Config,
-                                                   headTarget);
+        = target->GetLinkImplementationLibraries(context->Config);
       if(impl)
         {
         linkedTargetsContent =
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index a7576ed..381a0ed 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -449,7 +449,7 @@ bool cmGeneratorTarget::IsSystemIncludeDirectory(const std::string& dir,
   if (iter == this->SystemIncludesCache.end())
     {
     cmTarget::LinkImplementation const* impl
-                  = this->Target->GetLinkImplementation(config, this->Target);
+      = this->Target->GetLinkImplementation(config);
     if(!impl)
       {
       return false;
diff --git a/Source/cmGlobalXCodeGenerator.cxx b/Source/cmGlobalXCodeGenerator.cxx
index 29a5955..9a36df5 100644
--- a/Source/cmGlobalXCodeGenerator.cxx
+++ b/Source/cmGlobalXCodeGenerator.cxx
@@ -1255,7 +1255,7 @@ void cmGlobalXCodeGenerator::ForceLinkerLanguage(cmTarget& cmtarget)
 
   // If the language is compiled as a source trust Xcode to link with it.
   cmTarget::LinkImplementation const* impl =
-    cmtarget.GetLinkImplementation("NOCONFIG", &cmtarget);
+    cmtarget.GetLinkImplementation("NOCONFIG");
   for(std::vector<std::string>::const_iterator li = impl->Languages.begin();
       li != impl->Languages.end(); ++li)
     {
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 9d82d88..9d2e1b5 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -136,8 +136,7 @@ public:
                    cmTarget::LinkImplementation> LinkImplMapType;
   LinkImplMapType LinkImplMap;
 
-  typedef std::map<TargetConfigPair, cmTarget::LinkClosure>
-                                                          LinkClosureMapType;
+  typedef std::map<std::string, cmTarget::LinkClosure> LinkClosureMapType;
   LinkClosureMapType LinkClosureMap;
 
   typedef std::map<TargetConfigPair, std::vector<cmSourceFile*> >
@@ -1199,8 +1198,15 @@ bool cmTarget::NameResolvesToFramework(const std::string& libname) const
 
 //----------------------------------------------------------------------------
 void cmTarget::GetDirectLinkLibraries(const std::string& config,
-                            std::vector<std::string> &libs,
-                            cmTarget const* head) const
+                                      std::vector<std::string> &libs) const
+{
+  this->GetDirectLinkLibrariesInternal(config, libs, this);
+}
+
+//----------------------------------------------------------------------------
+void cmTarget::GetDirectLinkLibrariesInternal(const std::string& config,
+                                              std::vector<std::string> &libs,
+                                              cmTarget const* head) const
 {
   const char *prop = this->GetProperty("LINK_LIBRARIES");
   if (prop)
@@ -2297,8 +2303,7 @@ cmTarget::GetIncludeDirectories(const std::string& config) const
 
     if(this->Makefile->IsOn("APPLE"))
       {
-      LinkImplementation const* impl = this->GetLinkImplementation(config,
-                                                                   this);
+      LinkImplementation const* impl = this->GetLinkImplementation(config);
       for(std::vector<std::string>::const_iterator
           it = impl->Libraries.begin();
           it != impl->Libraries.end(); ++it)
@@ -3575,25 +3580,22 @@ private:
 };
 
 //----------------------------------------------------------------------------
-std::string cmTarget::GetLinkerLanguage(const std::string& config,
-                                        cmTarget const* head) const
+std::string cmTarget::GetLinkerLanguage(const std::string& config) const
 {
-  cmTarget const* headTarget = head ? head : this;
-  return this->GetLinkClosure(config, headTarget)->LinkerLanguage;
+  return this->GetLinkClosure(config)->LinkerLanguage;
 }
 
 //----------------------------------------------------------------------------
-cmTarget::LinkClosure const* cmTarget::GetLinkClosure(
-                                                  const std::string& config,
-                                                  cmTarget const* head) const
+cmTarget::LinkClosure const*
+cmTarget::GetLinkClosure(const std::string& config) const
 {
-  TargetConfigPair key(head, cmSystemTools::UpperCase(config));
+  std::string key(cmSystemTools::UpperCase(config));
   cmTargetInternals::LinkClosureMapType::iterator
     i = this->Internal->LinkClosureMap.find(key);
   if(i == this->Internal->LinkClosureMap.end())
     {
     LinkClosure lc;
-    this->ComputeLinkClosure(config, lc, head);
+    this->ComputeLinkClosure(config, lc);
     cmTargetInternals::LinkClosureMapType::value_type entry(key, lc);
     i = this->Internal->LinkClosureMap.insert(entry).first;
     }
@@ -3654,12 +3656,12 @@ public:
 };
 
 //----------------------------------------------------------------------------
-void cmTarget::ComputeLinkClosure(const std::string& config, LinkClosure& lc,
-                                  cmTarget const* head) const
+void cmTarget::ComputeLinkClosure(const std::string& config,
+                                  LinkClosure& lc) const
 {
   // Get languages built in this target.
   std::set<std::string> languages;
-  LinkImplementation const* impl = this->GetLinkImplementation(config, head);
+  LinkImplementation const* impl = this->GetLinkImplementation(config);
   for(std::vector<std::string>::const_iterator li = impl->Languages.begin();
       li != impl->Languages.end(); ++li)
     {
@@ -3667,7 +3669,7 @@ void cmTarget::ComputeLinkClosure(const std::string& config, LinkClosure& lc,
     }
 
   // Add interface languages from linked targets.
-  cmTargetCollectLinkLanguages cll(this, config, languages, head);
+  cmTargetCollectLinkLanguages cll(this, config, languages, this);
   for(std::vector<std::string>::const_iterator li = impl->Libraries.begin();
       li != impl->Libraries.end(); ++li)
     {
@@ -3848,8 +3850,7 @@ bool cmTarget::HasSOName(const std::string& config) const
   return ((this->GetType() == cmTarget::SHARED_LIBRARY ||
            this->GetType() == cmTarget::MODULE_LIBRARY) &&
           !this->GetPropertyAsBool("NO_SONAME") &&
-          this->Makefile->GetSONameFlag(this->GetLinkerLanguage(config,
-                                                                this)));
+          this->Makefile->GetSONameFlag(this->GetLinkerLanguage(config)));
 }
 
 //----------------------------------------------------------------------------
@@ -4222,7 +4223,7 @@ void cmTarget::GetFullNameInternal(const std::string& config,
   const char* suffixVar = this->GetSuffixVariableInternal(implib);
 
   // Check for language-specific default prefix and suffix.
-  std::string ll = this->GetLinkerLanguage(config, this);
+  std::string ll = this->GetLinkerLanguage(config);
   if(!ll.empty())
     {
     if(!targetSuffix && suffixVar && *suffixVar)
@@ -4511,7 +4512,7 @@ bool cmTarget::HaveBuildTreeRPATH(const std::string& config) const
     return false;
     }
   std::vector<std::string> libs;
-  this->GetDirectLinkLibraries(config, libs, this);
+  this->GetDirectLinkLibraries(config, libs);
   return !libs.empty();
 }
 
@@ -4561,7 +4562,7 @@ bool cmTarget::NeedRelinkBeforeInstall(const std::string& config) const
     }
 
   // Check for rpath support on this platform.
-  std::string ll = this->GetLinkerLanguage(config, this);
+  std::string ll = this->GetLinkerLanguage(config);
   if(!ll.empty())
     {
     std::string flagVar = "CMAKE_SHARED_LIBRARY_RUNTIME_";
@@ -5650,7 +5651,7 @@ bool cmTarget::IsChrpathUsed(const std::string& config) const
 #if defined(CMAKE_USE_ELF_PARSER)
   // Enable if the rpath flag uses a separator and the target uses ELF
   // binaries.
-  std::string ll = this->GetLinkerLanguage(config, this);
+  std::string ll = this->GetLinkerLanguage(config);
   if(!ll.empty())
     {
     std::string sepVar = "CMAKE_SHARED_LIBRARY_RUNTIME_";
@@ -6176,7 +6177,7 @@ cmTarget::GetLinkImplementationClosure(const std::string& config) const
     std::set<cmTarget*> emitted;
 
     cmTarget::LinkImplementation const* impl
-      = this->GetLinkImplementationLibraries(config, this);
+      = this->GetLinkImplementationLibraries(config);
 
     for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
         it != impl->Libraries.end(); ++it)
@@ -6353,7 +6354,7 @@ const char* cmTarget::ComputeLinkInterfaceLibraries(const std::string& config,
     {
     // The link implementation is the default link interface.
     LinkImplementation const* impl =
-        this->GetLinkImplementationLibraries(config, headTarget);
+        this->GetLinkImplementationLibrariesInternal(config, headTarget);
     iface.Libraries = impl->Libraries;
     if(this->PolicyStatusCMP0022 == cmPolicies::WARN &&
        !this->Internal->PolicyWarnedCMP0022)
@@ -6445,7 +6446,7 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
       if (thisTarget->GetType() != cmTarget::INTERFACE_LIBRARY)
         {
         cmTarget::LinkImplementation const* impl =
-            thisTarget->GetLinkImplementation(config, headTarget);
+            thisTarget->GetLinkImplementation(config);
         for(std::vector<std::string>::const_iterator
               li = impl->Libraries.begin(); li != impl->Libraries.end(); ++li)
           {
@@ -6476,7 +6477,8 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
     {
     // The link implementation is the default link interface.
     cmTarget::LinkImplementation const*
-                impl = thisTarget->GetLinkImplementation(config, headTarget);
+      impl = thisTarget->GetLinkImplementationLibrariesInternal(config,
+                                                                headTarget);
     iface.ImplementationIsInterface = true;
     iface.WrongConfigLibraries = impl->WrongConfigLibraries;
     }
@@ -6485,7 +6487,7 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
     {
     // Targets using this archive need its language runtime libraries.
     if(cmTarget::LinkImplementation const* impl =
-       thisTarget->GetLinkImplementation(config, headTarget))
+       thisTarget->GetLinkImplementation(config))
       {
       iface.Languages = impl->Languages;
       }
@@ -6523,8 +6525,7 @@ void cmTargetInternals::ComputeLinkInterface(cmTarget const* thisTarget,
 
 //----------------------------------------------------------------------------
 cmTarget::LinkImplementation const*
-cmTarget::GetLinkImplementation(const std::string& config,
-                                cmTarget const* head) const
+cmTarget::GetLinkImplementation(const std::string& config) const
 {
   // There is no link implementation for imported targets.
   if(this->IsImported())
@@ -6533,7 +6534,7 @@ cmTarget::GetLinkImplementation(const std::string& config,
     }
 
   // Lookup any existing link implementation for this configuration.
-  TargetConfigPair key(head, cmSystemTools::UpperCase(config));
+  TargetConfigPair key(this, cmSystemTools::UpperCase(config));
 
   cmTargetInternals::LinkImplMapType::iterator
     i = this->Internal->LinkImplMap.find(key);
@@ -6541,8 +6542,8 @@ cmTarget::GetLinkImplementation(const std::string& config,
     {
     // Compute the link implementation for this configuration.
     LinkImplementation impl;
-    this->ComputeLinkImplementation(config, impl, head);
-    this->ComputeLinkImplementationLanguages(config, impl, head);
+    this->ComputeLinkImplementation(config, impl, this);
+    this->ComputeLinkImplementationLanguages(config, impl, this);
 
     // Store the information for this configuration.
     cmTargetInternals::LinkImplMapType::value_type entry(key, impl);
@@ -6550,7 +6551,7 @@ cmTarget::GetLinkImplementation(const std::string& config,
     }
   else if (i->second.Languages.empty())
     {
-    this->ComputeLinkImplementationLanguages(config, i->second, head);
+    this->ComputeLinkImplementationLanguages(config, i->second, this);
     }
 
   return &i->second;
@@ -6558,8 +6559,15 @@ cmTarget::GetLinkImplementation(const std::string& config,
 
 //----------------------------------------------------------------------------
 cmTarget::LinkImplementation const*
-cmTarget::GetLinkImplementationLibraries(const std::string& config,
-                                         cmTarget const* head) const
+cmTarget::GetLinkImplementationLibraries(const std::string& config) const
+{
+  return this->GetLinkImplementationLibrariesInternal(config, this);
+}
+
+//----------------------------------------------------------------------------
+cmTarget::LinkImplementation const*
+cmTarget::GetLinkImplementationLibrariesInternal(const std::string& config,
+                                                 cmTarget const* head) const
 {
   // There is no link implementation for imported targets.
   if(this->IsImported())
@@ -6593,7 +6601,7 @@ void cmTarget::ComputeLinkImplementation(const std::string& config,
 {
   // Collect libraries directly linked in this configuration.
   std::vector<std::string> llibs;
-  this->GetDirectLinkLibraries(config, llibs, head);
+  this->GetDirectLinkLibrariesInternal(config, llibs, head);
   for(std::vector<std::string>::const_iterator li = llibs.begin();
       li != llibs.end(); ++li)
     {
@@ -6976,19 +6984,17 @@ void cmTarget::CheckPropertyCompatibility(cmComputeLinkInformation *info,
 
 //----------------------------------------------------------------------------
 cmComputeLinkInformation*
-cmTarget::GetLinkInformation(const std::string& config,
-                             cmTarget const* head) const
+cmTarget::GetLinkInformation(const std::string& config) const
 {
-  cmTarget const* headTarget = head ? head : this;
   // Lookup any existing information for this configuration.
-  TargetConfigPair key(headTarget, cmSystemTools::UpperCase(config));
+  std::string key(cmSystemTools::UpperCase(config));
   cmTargetLinkInformationMap::iterator
     i = this->LinkInformation.find(key);
   if(i == this->LinkInformation.end())
     {
     // Compute information for this configuration.
     cmComputeLinkInformation* info =
-      new cmComputeLinkInformation(this, config, headTarget);
+      new cmComputeLinkInformation(this, config);
     if(!info || !info->Compute())
       {
       delete info;
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 14aef5f..6f02522 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -44,11 +44,9 @@ class cmGeneratorTarget;
 class cmTargetTraceDependencies;
 
 struct cmTargetLinkInformationMap:
-  public std::map<std::pair<cmTarget const* , std::string>,
-                  cmComputeLinkInformation*>
+  public std::map<std::string, cmComputeLinkInformation*>
 {
-  typedef std::map<std::pair<cmTarget const* , std::string>,
-                   cmComputeLinkInformation*> derived;
+  typedef std::map<std::string, cmComputeLinkInformation*> derived;
   cmTargetLinkInformationMap() {}
   cmTargetLinkInformationMap(cmTargetLinkInformationMap const& r);
   ~cmTargetLinkInformationMap();
@@ -160,8 +158,7 @@ public:
   const LinkLibraryVectorType &GetOriginalLinkLibraries() const
     {return this->OriginalLinkLibraries;}
   void GetDirectLinkLibraries(const std::string& config,
-                              std::vector<std::string> &,
-                              cmTarget const* head) const;
+                              std::vector<std::string> &) const;
   void GetInterfaceLinkLibraries(const std::string& config,
                               std::vector<std::string> &,
                               cmTarget const* head) const;
@@ -296,12 +293,11 @@ public:
     // Needed only for OLD behavior of CMP0003.
     std::vector<std::string> WrongConfigLibraries;
   };
-  LinkImplementation const* GetLinkImplementation(const std::string& config,
-                                                  cmTarget const* head) const;
+  LinkImplementation const*
+    GetLinkImplementation(const std::string& config) const;
 
-  LinkImplementation const* GetLinkImplementationLibraries(
-                                                  const std::string& config,
-                                                  cmTarget const* head) const;
+  LinkImplementation const*
+    GetLinkImplementationLibraries(const std::string& config) const;
 
   /** Link information from the transitive closure of the link
       implementation and the interfaces of its dependencies.  */
@@ -313,8 +309,7 @@ public:
     // Languages whose runtime libraries must be linked.
     std::vector<std::string> Languages;
   };
-  LinkClosure const* GetLinkClosure(const std::string& config,
-                                    cmTarget const* head) const;
+  LinkClosure const* GetLinkClosure(const std::string& config) const;
 
   /** Strip off leading and trailing whitespace from an item named in
       the link dependencies of this target.  */
@@ -360,8 +355,7 @@ public:
   GetTargetVersion(bool soversion, int& major, int& minor, int& patch) const;
 
   ///! Return the preferred linker language for this target
-  std::string GetLinkerLanguage(const std::string& config = "",
-                                cmTarget const* head = 0) const;
+  std::string GetLinkerLanguage(const std::string& config = "") const;
 
   /** Get the full name of the target according to the settings in its
       makefile.  */
@@ -445,8 +439,8 @@ public:
     * install tree.  For example: "\@rpath/" or "\@loader_path/". */
   std::string GetInstallNameDirForInstallTree() const;
 
-  cmComputeLinkInformation* GetLinkInformation(const std::string& config,
-                                               cmTarget const* head = 0) const;
+  cmComputeLinkInformation*
+    GetLinkInformation(const std::string& config) const;
 
   // Get the properties
   cmPropertyMap &GetProperties() const { return this->Properties; }
@@ -757,14 +751,19 @@ private:
                                             cmTarget const* head,
                                             bool &exists) const;
 
+  void GetDirectLinkLibrariesInternal(const std::string& config,
+                                      std::vector<std::string>& libs,
+                                      cmTarget const* head) const;
+  LinkImplementation const*
+    GetLinkImplementationLibrariesInternal(const std::string& config,
+                                           cmTarget const* head) const;
   void ComputeLinkImplementation(const std::string& config,
                                  LinkImplementation& impl,
                                  cmTarget const* head) const;
   void ComputeLinkImplementationLanguages(const std::string& config,
                                           LinkImplementation& impl,
                                           cmTarget const* head) const;
-  void ComputeLinkClosure(const std::string& config, LinkClosure& lc,
-                          cmTarget const* head) const;
+  void ComputeLinkClosure(const std::string& config, LinkClosure& lc) const;
 
   std::string ProcessSourceItemCMP0049(const std::string& s);
 

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=1d84985979e1c46fffcb3b09fc305a54396a8e93
commit 1d84985979e1c46fffcb3b09fc305a54396a8e93
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Wed Jun 11 10:40:36 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Wed Jun 11 10:40:36 2014 -0400

    cmTarget: Cache GetLinkImplementationClosure results
    
    Store them internally and return by reference to avoid duplicate
    computation.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 6a0826f..9d82d88 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -170,12 +170,15 @@ public:
                                 CachedLinkInterfaceSourcesEntries;
   mutable std::map<std::string, std::vector<TargetPropertyEntry*> >
                                 CachedLinkInterfaceCompileFeaturesEntries;
+  mutable std::map<std::string, std::vector<cmTarget*> >
+                                CachedLinkImplementationClosure;
 
   mutable std::map<std::string, bool> CacheLinkInterfaceIncludeDirectoriesDone;
   mutable std::map<std::string, bool> CacheLinkInterfaceCompileDefinitionsDone;
   mutable std::map<std::string, bool> CacheLinkInterfaceCompileOptionsDone;
   mutable std::map<std::string, bool> CacheLinkInterfaceSourcesDone;
   mutable std::map<std::string, bool> CacheLinkInterfaceCompileFeaturesDone;
+  mutable std::map<std::string, bool> CacheLinkImplementationClosureDone;
 };
 
 //----------------------------------------------------------------------------
@@ -5212,8 +5215,8 @@ PropertyType checkInterfacePropertyCompatibility(cmTarget const* tgt,
   assert((impliedByUse ^ explicitlySet)
       || (!impliedByUse && !explicitlySet));
 
-  std::vector<cmTarget*> deps;
-  tgt->GetLinkImplementationClosure(config, deps);
+  std::vector<cmTarget*> const& deps =
+    tgt->GetLinkImplementationClosure(config);
 
   if(deps.empty())
     {
@@ -5428,8 +5431,8 @@ bool isLinkDependentProperty(cmTarget const* tgt, const std::string &p,
                              const std::string& interfaceProperty,
                              const std::string& config)
 {
-  std::vector<cmTarget*> deps;
-  tgt->GetLinkImplementationClosure(config, deps);
+  std::vector<cmTarget*> const& deps =
+    tgt->GetLinkImplementationClosure(config);
 
   if(deps.empty())
     {
@@ -6162,19 +6165,26 @@ void processILibs(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
-void cmTarget::GetLinkImplementationClosure(const std::string& config,
-                                      std::vector<cmTarget*> &tgts) const
+std::vector<cmTarget*> const&
+cmTarget::GetLinkImplementationClosure(const std::string& config) const
 {
-  std::set<cmTarget*> emitted;
+  std::vector<cmTarget*>& tgts =
+    this->Internal->CachedLinkImplementationClosure[config];
+  if(!this->Internal->CacheLinkImplementationClosureDone[config])
+    {
+    this->Internal->CacheLinkImplementationClosureDone[config] = true;
+    std::set<cmTarget*> emitted;
 
-  cmTarget::LinkImplementation const* impl
+    cmTarget::LinkImplementation const* impl
       = this->GetLinkImplementationLibraries(config, this);
 
-  for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
-      it != impl->Libraries.end(); ++it)
-    {
-      processILibs(config, this, *it, tgts, emitted);
+    for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
+        it != impl->Libraries.end(); ++it)
+      {
+      processILibs(config, this, *it, tgts , emitted);
+      }
     }
+  return tgts;
 }
 
 //----------------------------------------------------------------------------
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index ea50179..14aef5f 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -279,8 +279,8 @@ public:
   void GetTransitivePropertyTargets(const std::string& config,
                                         cmTarget const* headTarget,
                                         std::vector<cmTarget*> &libs) const;
-  void GetLinkImplementationClosure(const std::string& config,
-                                    std::vector<cmTarget*> &libs) const;
+  std::vector<cmTarget*> const&
+    GetLinkImplementationClosure(const std::string& config) const;
 
   /** The link implementation specifies the direct library
       dependencies needed by the object files of the target.  */

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=5d15419d061648cc24ab2bb01a1dace63698e4f3
commit 5d15419d061648cc24ab2bb01a1dace63698e4f3
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Wed Jun 11 10:39:51 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Wed Jun 11 10:39:51 2014 -0400

    cmTarget: Rename Get{TransitiveTarget => LinkImplementation}Closure
    
    The method computes the transitive closure of targets starting with
    the current target link implementation libraries.  Clarify the name.

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index cb382ff..6a0826f 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -5213,7 +5213,7 @@ PropertyType checkInterfacePropertyCompatibility(cmTarget const* tgt,
       || (!impliedByUse && !explicitlySet));
 
   std::vector<cmTarget*> deps;
-  tgt->GetTransitiveTargetClosure(config, deps);
+  tgt->GetLinkImplementationClosure(config, deps);
 
   if(deps.empty())
     {
@@ -5429,7 +5429,7 @@ bool isLinkDependentProperty(cmTarget const* tgt, const std::string &p,
                              const std::string& config)
 {
   std::vector<cmTarget*> deps;
-  tgt->GetTransitiveTargetClosure(config, deps);
+  tgt->GetLinkImplementationClosure(config, deps);
 
   if(deps.empty())
     {
@@ -6162,7 +6162,7 @@ void processILibs(const std::string& config,
 }
 
 //----------------------------------------------------------------------------
-void cmTarget::GetTransitiveTargetClosure(const std::string& config,
+void cmTarget::GetLinkImplementationClosure(const std::string& config,
                                       std::vector<cmTarget*> &tgts) const
 {
   std::set<cmTarget*> emitted;
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 0b95a50..ea50179 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -279,8 +279,8 @@ public:
   void GetTransitivePropertyTargets(const std::string& config,
                                         cmTarget const* headTarget,
                                         std::vector<cmTarget*> &libs) const;
-  void GetTransitiveTargetClosure(const std::string& config,
-                                        std::vector<cmTarget*> &libs) const;
+  void GetLinkImplementationClosure(const std::string& config,
+                                    std::vector<cmTarget*> &libs) const;
 
   /** The link implementation specifies the direct library
       dependencies needed by the object files of the target.  */

http://cmake.org/gitweb?p=cmake.git;a=commitdiff;h=bdd2a90f8aa0fad1e215fe9aac3c0da04c835555
commit bdd2a90f8aa0fad1e215fe9aac3c0da04c835555
Author:     Brad King <brad.king at kitware.com>
AuthorDate: Wed Jun 11 10:39:13 2014 -0400
Commit:     Brad King <brad.king at kitware.com>
CommitDate: Wed Jun 11 10:39:13 2014 -0400

    cmTarget: Drop unused GetTransitiveTargetClosure argument
    
    The method is never called with any headTarget besides "this".

diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 01edde9..cb382ff 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -5213,7 +5213,7 @@ PropertyType checkInterfacePropertyCompatibility(cmTarget const* tgt,
       || (!impliedByUse && !explicitlySet));
 
   std::vector<cmTarget*> deps;
-  tgt->GetTransitiveTargetClosure(config, tgt, deps);
+  tgt->GetTransitiveTargetClosure(config, deps);
 
   if(deps.empty())
     {
@@ -5429,7 +5429,7 @@ bool isLinkDependentProperty(cmTarget const* tgt, const std::string &p,
                              const std::string& config)
 {
   std::vector<cmTarget*> deps;
-  tgt->GetTransitiveTargetClosure(config, tgt, deps);
+  tgt->GetTransitiveTargetClosure(config, deps);
 
   if(deps.empty())
     {
@@ -6163,18 +6163,17 @@ void processILibs(const std::string& config,
 
 //----------------------------------------------------------------------------
 void cmTarget::GetTransitiveTargetClosure(const std::string& config,
-                                      cmTarget const* headTarget,
                                       std::vector<cmTarget*> &tgts) const
 {
   std::set<cmTarget*> emitted;
 
   cmTarget::LinkImplementation const* impl
-      = this->GetLinkImplementationLibraries(config, headTarget);
+      = this->GetLinkImplementationLibraries(config, this);
 
   for(std::vector<std::string>::const_iterator it = impl->Libraries.begin();
       it != impl->Libraries.end(); ++it)
     {
-      processILibs(config, headTarget, *it, tgts, emitted);
+      processILibs(config, this, *it, tgts, emitted);
     }
 }
 
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index 2d51835..0b95a50 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -280,7 +280,6 @@ public:
                                         cmTarget const* headTarget,
                                         std::vector<cmTarget*> &libs) const;
   void GetTransitiveTargetClosure(const std::string& config,
-                                        cmTarget const* headTarget,
                                         std::vector<cmTarget*> &libs) const;
 
   /** The link implementation specifies the direct library

-----------------------------------------------------------------------

Summary of changes:
 Source/cmComputeLinkDepends.cxx                |   92 ++--
 Source/cmComputeLinkDepends.h                  |   14 +-
 Source/cmComputeLinkInformation.cxx            |   14 +-
 Source/cmComputeLinkInformation.h              |    4 +-
 Source/cmComputeTargetDepends.cxx              |   46 +-
 Source/cmComputeTargetDepends.h                |    7 +-
 Source/cmExportFileGenerator.cxx               |    8 +-
 Source/cmExportFileGenerator.h                 |    4 +-
 Source/cmGeneratorExpressionEvaluator.cxx      |   22 +-
 Source/cmGeneratorTarget.cxx                   |   14 +-
 Source/cmGlobalXCodeGenerator.cxx              |    2 +-
 Source/cmTarget.cxx                            |  604 +++++++++++++-----------
 Source/cmTarget.h                              |   92 ++--
 Tests/InterfaceLibrary/CMakeLists.txt          |   12 +-
 Tests/InterfaceLibrary/definetestexe.cpp       |    4 +-
 Tests/InterfaceLibrary/ifacedir/CMakeLists.txt |    8 +
 Tests/InterfaceLibrary/ifacedir/sub.cpp        |    1 +
 17 files changed, 495 insertions(+), 453 deletions(-)
 create mode 100644 Tests/InterfaceLibrary/ifacedir/CMakeLists.txt
 create mode 100644 Tests/InterfaceLibrary/ifacedir/sub.cpp


hooks/post-receive
-- 
CMake


More information about the Cmake-commits mailing list