exports: accept a missing target if it is exported exactly once
If a target is exported, and a library it depends on is not part of the same export set, before this patch cmake errored out. With this patch, it now checks whether the missing target is exported somewhere else exactly once, and accepts in this case (because then it can determine the namespace for the missing target and use this). Alex
This commit is contained in:
parent
999061a4c2
commit
87f4c01910
|
@ -135,7 +135,8 @@ cmExportBuildFileGenerator
|
||||||
void
|
void
|
||||||
cmExportBuildFileGenerator
|
cmExportBuildFileGenerator
|
||||||
::ComplainAboutMissingTarget(cmTarget* depender,
|
::ComplainAboutMissingTarget(cmTarget* depender,
|
||||||
cmTarget* dependee)
|
cmTarget* dependee,
|
||||||
|
int occurrences)
|
||||||
{
|
{
|
||||||
if(!this->ExportCommand || !this->ExportCommand->ErrorMessage.empty())
|
if(!this->ExportCommand || !this->ExportCommand->ErrorMessage.empty())
|
||||||
{
|
{
|
||||||
|
@ -143,10 +144,20 @@ cmExportBuildFileGenerator
|
||||||
}
|
}
|
||||||
|
|
||||||
cmOStringStream e;
|
cmOStringStream e;
|
||||||
|
if (occurrences == 0)
|
||||||
|
{
|
||||||
e << "called with target \"" << depender->GetName()
|
e << "called with target \"" << depender->GetName()
|
||||||
<< "\" which requires target \"" << dependee->GetName()
|
<< "\" which requires target \"" << dependee->GetName()
|
||||||
<< "\" that is not in the export list.\n"
|
<< "\" that is not in the export list.\n"
|
||||||
<< "If the required target is not easy to reference in this call, "
|
<< "If the required target is not easy to reference in this call, "
|
||||||
<< "consider using the APPEND option with multiple separate calls.";
|
<< "consider using the APPEND option with multiple separate calls.";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
e << "called with target \"" << depender->GetName()
|
||||||
|
<< "\" which requires target \"" << dependee->GetName()
|
||||||
|
<< "\" that is exported " << occurrences << " times in other "
|
||||||
|
<< "export ""lists.\n";
|
||||||
|
}
|
||||||
this->ExportCommand->ErrorMessage = e.str();
|
this->ExportCommand->ErrorMessage = e.str();
|
||||||
}
|
}
|
||||||
|
|
|
@ -46,7 +46,8 @@ protected:
|
||||||
const char* config,
|
const char* config,
|
||||||
std::string const& suffix);
|
std::string const& suffix);
|
||||||
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
||||||
cmTarget* dependee);
|
cmTarget* dependee,
|
||||||
|
int occurrences);
|
||||||
|
|
||||||
/** Fill in properties indicating built file locations. */
|
/** Fill in properties indicating built file locations. */
|
||||||
void SetImportLocationProperty(const char* config,
|
void SetImportLocationProperty(const char* config,
|
||||||
|
|
|
@ -11,10 +11,15 @@
|
||||||
============================================================================*/
|
============================================================================*/
|
||||||
#include "cmExportFileGenerator.h"
|
#include "cmExportFileGenerator.h"
|
||||||
|
|
||||||
|
#include "cmExportSet.h"
|
||||||
#include "cmGeneratedFileStream.h"
|
#include "cmGeneratedFileStream.h"
|
||||||
|
#include "cmGlobalGenerator.h"
|
||||||
|
#include "cmInstallExportGenerator.h"
|
||||||
|
#include "cmLocalGenerator.h"
|
||||||
#include "cmMakefile.h"
|
#include "cmMakefile.h"
|
||||||
#include "cmSystemTools.h"
|
#include "cmSystemTools.h"
|
||||||
#include "cmTarget.h"
|
#include "cmTarget.h"
|
||||||
|
#include "cmTargetExport.h"
|
||||||
#include "cmVersion.h"
|
#include "cmVersion.h"
|
||||||
|
|
||||||
#include <cmsys/auto_ptr.hxx>
|
#include <cmsys/auto_ptr.hxx>
|
||||||
|
@ -222,6 +227,16 @@ cmExportFileGenerator
|
||||||
link_libs += this->Namespace;
|
link_libs += this->Namespace;
|
||||||
link_libs += *li;
|
link_libs += *li;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
std::vector<std::string> namespaces = this->FindNamespaces(mf, *li);
|
||||||
|
int targetOccurrences = (int)namespaces.size();
|
||||||
|
|
||||||
|
if (targetOccurrences == 1)
|
||||||
|
{
|
||||||
|
link_libs += namespaces[0];
|
||||||
|
link_libs += *li;
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// The target is not in the export.
|
// The target is not in the export.
|
||||||
|
@ -229,7 +244,7 @@ cmExportFileGenerator
|
||||||
{
|
{
|
||||||
// We are not appending, so all exported targets should be
|
// We are not appending, so all exported targets should be
|
||||||
// known here. This is probably user-error.
|
// known here. This is probably user-error.
|
||||||
this->ComplainAboutMissingTarget(target, tgt);
|
this->ComplainAboutMissingTarget(target, tgt, targetOccurrences);
|
||||||
}
|
}
|
||||||
// Assume the target will be exported by another command.
|
// Assume the target will be exported by another command.
|
||||||
// Append it with the export namespace.
|
// Append it with the export namespace.
|
||||||
|
@ -237,6 +252,7 @@ cmExportFileGenerator
|
||||||
link_libs += *li;
|
link_libs += *li;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Append the raw name.
|
// Append the raw name.
|
||||||
|
@ -250,6 +266,48 @@ cmExportFileGenerator
|
||||||
properties[prop] = link_libs;
|
properties[prop] = link_libs;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
std::vector<std::string> cmExportFileGenerator::FindNamespaces(cmMakefile* mf,
|
||||||
|
const std::string& name)
|
||||||
|
{
|
||||||
|
std::vector<std::string> namespaces;
|
||||||
|
cmGlobalGenerator* gg = mf->GetLocalGenerator()->GetGlobalGenerator();
|
||||||
|
const cmExportSetMap& exportSets = gg->GetExportSets();
|
||||||
|
|
||||||
|
for(cmExportSetMap::const_iterator expIt = exportSets.begin();
|
||||||
|
expIt != exportSets.end();
|
||||||
|
++expIt)
|
||||||
|
{
|
||||||
|
const cmExportSet* exportSet = expIt->second;
|
||||||
|
std::vector<cmTargetExport const*> const* targets =
|
||||||
|
exportSet->GetTargetExports();
|
||||||
|
|
||||||
|
bool containsTarget = false;
|
||||||
|
for(unsigned int i=0; i<targets->size(); i++)
|
||||||
|
{
|
||||||
|
if (name == (*targets)[i]->Target->GetName())
|
||||||
|
{
|
||||||
|
containsTarget = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (containsTarget)
|
||||||
|
{
|
||||||
|
std::vector<cmInstallExportGenerator const*> const* installs =
|
||||||
|
exportSet->GetInstallations();
|
||||||
|
for(unsigned int i=0; i<installs->size(); i++)
|
||||||
|
{
|
||||||
|
namespaces.push_back((*installs)[i]->GetNamespace());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return namespaces;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
void cmExportFileGenerator::GenerateImportHeaderCode(std::ostream& os,
|
void cmExportFileGenerator::GenerateImportHeaderCode(std::ostream& os,
|
||||||
const char* config)
|
const char* config)
|
||||||
|
|
|
@ -83,7 +83,12 @@ protected:
|
||||||
/** Each subclass knows how to complain about a target that is
|
/** Each subclass knows how to complain about a target that is
|
||||||
missing from an export set. */
|
missing from an export set. */
|
||||||
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
||||||
cmTarget* dependee) = 0;
|
cmTarget* dependee,
|
||||||
|
int occurrences) = 0;
|
||||||
|
|
||||||
|
std::vector<std::string> FindNamespaces(cmMakefile* mf,
|
||||||
|
const std::string& name);
|
||||||
|
|
||||||
|
|
||||||
// The namespace in which the exports are placed in the generated file.
|
// The namespace in which the exports are placed in the generated file.
|
||||||
std::string Namespace;
|
std::string Namespace;
|
||||||
|
|
|
@ -327,14 +327,24 @@ cmExportInstallFileGenerator
|
||||||
//----------------------------------------------------------------------------
|
//----------------------------------------------------------------------------
|
||||||
void
|
void
|
||||||
cmExportInstallFileGenerator
|
cmExportInstallFileGenerator
|
||||||
::ComplainAboutMissingTarget(cmTarget* depender, cmTarget* dependee)
|
::ComplainAboutMissingTarget(cmTarget* depender,
|
||||||
|
cmTarget* dependee,
|
||||||
|
int occurrences)
|
||||||
{
|
{
|
||||||
cmOStringStream e;
|
cmOStringStream e;
|
||||||
e << "INSTALL(EXPORT \""
|
e << "INSTALL(EXPORT \""
|
||||||
<< this->IEGen->GetExportSet()->GetName()
|
<< this->IEGen->GetExportSet()->GetName()
|
||||||
<< "\" ...) "
|
<< "\" ...) "
|
||||||
<< "includes target \"" << depender->GetName()
|
<< "includes target \"" << depender->GetName()
|
||||||
<< "\" which requires target \"" << dependee->GetName()
|
<< "\" which requires target \"" << dependee->GetName() << "\" ";
|
||||||
<< "\" that is not in the export set.";
|
if (occurrences == 0)
|
||||||
|
{
|
||||||
|
e << "that is not in the export set.";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
e << "that is not in this export set, but " << occurrences
|
||||||
|
<< " times in others.";
|
||||||
|
}
|
||||||
cmSystemTools::Error(e.str().c_str());
|
cmSystemTools::Error(e.str().c_str());
|
||||||
}
|
}
|
||||||
|
|
|
@ -58,7 +58,8 @@ protected:
|
||||||
const char* config,
|
const char* config,
|
||||||
std::string const& suffix);
|
std::string const& suffix);
|
||||||
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
virtual void ComplainAboutMissingTarget(cmTarget* depender,
|
||||||
cmTarget* dependee);
|
cmTarget* dependee,
|
||||||
|
int occurrences);
|
||||||
|
|
||||||
/** Generate a per-configuration file for the targets. */
|
/** Generate a per-configuration file for the targets. */
|
||||||
bool GenerateImportFileConfig(const char* config);
|
bool GenerateImportFileConfig(const char* config);
|
||||||
|
|
|
@ -34,7 +34,10 @@ public:
|
||||||
cmMakefile* mf);
|
cmMakefile* mf);
|
||||||
~cmInstallExportGenerator();
|
~cmInstallExportGenerator();
|
||||||
|
|
||||||
cmExportSet* GetExportSet() {return ExportSet;}
|
cmExportSet* GetExportSet() {return this->ExportSet;}
|
||||||
|
|
||||||
|
const std::string& GetNamespace() const { return this->Namespace; }
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
virtual void GenerateScript(std::ostream& os);
|
virtual void GenerateScript(std::ostream& os);
|
||||||
virtual void GenerateScriptConfigs(std::ostream& os, Indent const& indent);
|
virtual void GenerateScriptConfigs(std::ostream& os, Indent const& indent);
|
||||||
|
|
Loading…
Reference in New Issue