Merge topic 'imported-target-visibility'

f9c1c62 Add test covering imported target scope rules
ca39c5c Optionally allow IMPORTED targets to be globally visible
This commit is contained in:
David Cole 2012-02-01 14:49:10 -05:00 committed by CMake Topic Stage
commit 3e0eeb9fc8
13 changed files with 81 additions and 13 deletions

View File

@ -29,6 +29,7 @@ bool cmAddExecutableCommand
bool use_macbundle = false; bool use_macbundle = false;
bool excludeFromAll = false; bool excludeFromAll = false;
bool importTarget = false; bool importTarget = false;
bool importGlobal = false;
while ( s != args.end() ) while ( s != args.end() )
{ {
if (*s == "WIN32") if (*s == "WIN32")
@ -51,6 +52,11 @@ bool cmAddExecutableCommand
++s; ++s;
importTarget = true; importTarget = true;
} }
else if(importTarget && *s == "GLOBAL")
{
++s;
importGlobal = true;
}
else else
{ {
break; break;
@ -92,7 +98,8 @@ bool cmAddExecutableCommand
} }
// Create the imported target. // Create the imported target.
this->Makefile->AddImportedTarget(exename.c_str(), cmTarget::EXECUTABLE); this->Makefile->AddImportedTarget(exename.c_str(), cmTarget::EXECUTABLE,
importGlobal);
return true; return true;
} }

View File

@ -92,12 +92,12 @@ public:
"\n" "\n"
"The add_executable command can also create IMPORTED executable " "The add_executable command can also create IMPORTED executable "
"targets using this signature:\n" "targets using this signature:\n"
" add_executable(<name> IMPORTED)\n" " add_executable(<name> IMPORTED [GLOBAL])\n"
"An IMPORTED executable target references an executable file located " "An IMPORTED executable target references an executable file located "
"outside the project. " "outside the project. "
"No rules are generated to build it. " "No rules are generated to build it. "
"The target name has scope in the directory in which it is created " "The target name has scope in the directory in which it is created "
"and below. " "and below, but the GLOBAL option extends visibility. "
"It may be referenced like any target built within the project. " "It may be referenced like any target built within the project. "
"IMPORTED executables are useful for convenient reference from " "IMPORTED executables are useful for convenient reference from "
"commands like add_custom_command. " "commands like add_custom_command. "

View File

@ -31,6 +31,7 @@ bool cmAddLibraryCommand
} }
bool excludeFromAll = false; bool excludeFromAll = false;
bool importTarget = false; bool importTarget = false;
bool importGlobal = false;
std::vector<std::string>::const_iterator s = args.begin(); std::vector<std::string>::const_iterator s = args.begin();
@ -79,6 +80,11 @@ bool cmAddLibraryCommand
++s; ++s;
importTarget = true; importTarget = true;
} }
else if(importTarget && *s == "GLOBAL")
{
++s;
importGlobal = true;
}
else else
{ {
break; break;
@ -124,7 +130,7 @@ bool cmAddLibraryCommand
} }
// Create the imported target. // Create the imported target.
this->Makefile->AddImportedTarget(libName.c_str(), type); this->Makefile->AddImportedTarget(libName.c_str(), type, importGlobal);
return true; return true;
} }

View File

@ -96,12 +96,13 @@ public:
"\n" "\n"
"The add_library command can also create IMPORTED library " "The add_library command can also create IMPORTED library "
"targets using this signature:\n" "targets using this signature:\n"
" add_library(<name> <SHARED|STATIC|MODULE|UNKNOWN> IMPORTED)\n" " add_library(<name> <SHARED|STATIC|MODULE|UNKNOWN> IMPORTED\n"
" [GLOBAL])\n"
"An IMPORTED library target references a library file located " "An IMPORTED library target references a library file located "
"outside the project. " "outside the project. "
"No rules are generated to build it. " "No rules are generated to build it. "
"The target name has scope in the directory in which it is created " "The target name has scope in the directory in which it is created "
"and below. " "and below, but the GLOBAL option extends visibility. "
"It may be referenced like any target built within the project. " "It may be referenced like any target built within the project. "
"IMPORTED libraries are useful for convenient reference from " "IMPORTED libraries are useful for convenient reference from "
"commands like target_link_libraries. " "commands like target_link_libraries. "

View File

@ -1666,6 +1666,11 @@ cmGlobalGenerator::FindTarget(const char* project, const char* name)
{ {
return i->second; return i->second;
} }
i = this->ImportedTargets.find(name);
if ( i != this->ImportedTargets.end() )
{
return i->second;
}
} }
return 0; return 0;
} }
@ -2046,10 +2051,16 @@ cmGlobalGenerator::GetTargetDirectDepends(cmTarget & target)
return this->TargetDependencies[&target]; return this->TargetDependencies[&target];
} }
void cmGlobalGenerator::AddTarget(cmTargets::value_type &v) void cmGlobalGenerator::AddTarget(cmTarget* t)
{ {
assert(!v.second.IsImported()); if(t->IsImported())
this->TotalTargets[v.first] = &v.second; {
this->ImportedTargets[t->GetName()] = t;
}
else
{
this->TotalTargets[t->GetName()] = t;
}
} }
void cmGlobalGenerator::SetExternalMakefileProjectGenerator( void cmGlobalGenerator::SetExternalMakefileProjectGenerator(

View File

@ -230,7 +230,7 @@ public:
std::set<cmStdString> const& GetDirectoryContent(std::string const& dir, std::set<cmStdString> const& GetDirectoryContent(std::string const& dir,
bool needDisk = true); bool needDisk = true);
void AddTarget(cmTargets::value_type &v); void AddTarget(cmTarget* t);
virtual const char* GetAllTargetName() const { return "ALL_BUILD"; } virtual const char* GetAllTargetName() const { return "ALL_BUILD"; }
virtual const char* GetInstallTargetName() const { return "INSTALL"; } virtual const char* GetInstallTargetName() const { return "INSTALL"; }
@ -333,6 +333,7 @@ protected:
// All targets in the entire project. // All targets in the entire project.
std::map<cmStdString,cmTarget *> TotalTargets; std::map<cmStdString,cmTarget *> TotalTargets;
std::map<cmStdString,cmTarget *> ImportedTargets;
virtual const char* GetPredefinedTargetsFolder(); virtual const char* GetPredefinedTargetsFolder();
virtual bool UseFolderProperty(); virtual bool UseFolderProperty();

View File

@ -1937,7 +1937,7 @@ cmMakefile::AddNewTarget(cmTarget::TargetType type, const char* name)
cmTarget& target = it->second; cmTarget& target = it->second;
target.SetType(type, name); target.SetType(type, name);
target.SetMakefile(this); target.SetMakefile(this);
this->LocalGenerator->GetGlobalGenerator()->AddTarget(*it); this->LocalGenerator->GetGlobalGenerator()->AddTarget(&it->second);
return &it->second; return &it->second;
} }
@ -3894,7 +3894,8 @@ void cmMakefile::DefineProperties(cmake *cm)
//---------------------------------------------------------------------------- //----------------------------------------------------------------------------
cmTarget* cmTarget*
cmMakefile::AddImportedTarget(const char* name, cmTarget::TargetType type) cmMakefile::AddImportedTarget(const char* name, cmTarget::TargetType type,
bool global)
{ {
// Create the target. // Create the target.
cmsys::auto_ptr<cmTarget> target(new cmTarget); cmsys::auto_ptr<cmTarget> target(new cmTarget);
@ -3904,6 +3905,10 @@ cmMakefile::AddImportedTarget(const char* name, cmTarget::TargetType type)
// Add to the set of available imported targets. // Add to the set of available imported targets.
this->ImportedTargets[name] = target.get(); this->ImportedTargets[name] = target.get();
if(global)
{
this->LocalGenerator->GetGlobalGenerator()->AddTarget(target.get());
}
// Transfer ownership to this cmMakefile object. // Transfer ownership to this cmMakefile object.
this->ImportedTargetsOwned.push_back(target.get()); this->ImportedTargetsOwned.push_back(target.get());

View File

@ -203,7 +203,8 @@ public:
void RemoveDefineFlag(const char* definition); void RemoveDefineFlag(const char* definition);
/** Create a new imported target with the name and type given. */ /** Create a new imported target with the name and type given. */
cmTarget* AddImportedTarget(const char* name, cmTarget::TargetType type); cmTarget* AddImportedTarget(const char* name, cmTarget::TargetType type,
bool global);
cmTarget* AddNewTarget(cmTarget::TargetType type, const char* name); cmTarget* AddNewTarget(cmTarget::TargetType type, const char* name);

View File

@ -16,3 +16,5 @@ add_CMakeOnly_test(CheckSymbolExists)
add_CMakeOnly_test(CheckCXXSymbolExists) add_CMakeOnly_test(CheckCXXSymbolExists)
add_CMakeOnly_test(AllFindModules) add_CMakeOnly_test(AllFindModules)
add_CMakeOnly_test(TargetScope)

View File

@ -0,0 +1,13 @@
cmake_minimum_required (VERSION 2.8)
project(TargetScope NONE)
add_subdirectory(Sub)
if(TARGET SubLibLocal)
message(FATAL_ERROR "SubLibLocal visible in top directory")
endif()
if(NOT TARGET SubLibGlobal)
message(FATAL_ERROR "SubLibGlobal not visible in top directory")
endif()
add_subdirectory(Sib)

View File

@ -0,0 +1,6 @@
if(TARGET SubLibLocal)
message(FATAL_ERROR "SubLibLocal visible in sibling directory")
endif()
if(NOT TARGET SubLibGlobal)
message(FATAL_ERROR "SubLibGlobal not visible in sibling directory")
endif()

View File

@ -0,0 +1,9 @@
add_library(SubLibLocal UNKNOWN IMPORTED)
add_library(SubLibGlobal UNKNOWN IMPORTED GLOBAL)
add_subdirectory(Sub)
if(NOT TARGET SubLibLocal)
message(FATAL_ERROR "SubLibLocal not visible in own directory")
endif()
if(NOT TARGET SubLibGlobal)
message(FATAL_ERROR "SubLibGlobal not visible in own directory")
endif()

View File

@ -0,0 +1,6 @@
if(NOT TARGET SubLibLocal)
message(FATAL_ERROR "SubLibLocal not visible in subdirectory")
endif()
if(NOT TARGET SubLibGlobal)
message(FATAL_ERROR "SubLibGlobal not visible in subdirectory")
endif()