summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Cole <david.cole@kitware.com>2012-07-24 21:03:46 (GMT)
committerCMake Topic Stage <kwrobot@kitware.com>2012-07-24 21:03:46 (GMT)
commita51e1529e79ef46c8f7f346328c788a4e630e474 (patch)
tree7fed8476e05fe1278f09a130cdf2080c12762c42
parentc1bbdbff57651a24fd8d7d5abe67dd24e7e6ed27 (diff)
parent1fc8df9ca22c23f42afa94a949918cda008b07ce (diff)
downloadCMake-a51e1529e79ef46c8f7f346328c788a4e630e474.zip
CMake-a51e1529e79ef46c8f7f346328c788a4e630e474.tar.gz
CMake-a51e1529e79ef46c8f7f346328c788a4e630e474.tar.bz2
Merge topic 'ninja-fix-macosx'
1fc8df9 Add missing this->. 7a3ecf5 Fix memory leak in Makefile generator. 9f7dc83 Ninja: also bootstrap ninja files 5d365b2 Ninja: enable ninja support everywhere d569f3e Ninja: void function can't return a value 52160bf Ninja: enable ninja on Mac so all Mac CDash-builds are tested, cleanup later 56aeac6 Ninja: fixes for bcc 7a6bc9e Ninja: remove 'this' from member initializer list 44ba4cf Ninja: remove warnings 7751966 Ninja: remove 'friend' in ninja code c3988ee Re-factor OS X content generator start up. f8e0a51 Re-factor framework directory computation. f36c7b0 Re-factor Mac OS X content directory computation. 5d885db Re-factor bundle content copying rules generation. 3b2a01e Ninja: Use same echo message as makefiles. 7bb56c5 Re-factor CFBundle generation. ...
-rw-r--r--Source/CMakeLists.txt55
-rw-r--r--Source/QtDialog/CMakeLists.txt9
-rw-r--r--Source/cmExtraCodeBlocksGenerator.cxx2
-rw-r--r--Source/cmExtraEclipseCDT4Generator.cxx2
-rw-r--r--Source/cmGlobalNinjaGenerator.cxx47
-rw-r--r--Source/cmGlobalNinjaGenerator.h106
-rw-r--r--Source/cmLocalNinjaGenerator.cxx2
-rw-r--r--Source/cmLocalNinjaGenerator.h62
-rw-r--r--Source/cmMakefileExecutableTargetGenerator.cxx45
-rw-r--r--Source/cmMakefileExecutableTargetGenerator.h4
-rw-r--r--Source/cmMakefileLibraryTargetGenerator.cxx172
-rw-r--r--Source/cmMakefileLibraryTargetGenerator.h9
-rw-r--r--Source/cmMakefileTargetGenerator.cxx87
-rw-r--r--Source/cmMakefileTargetGenerator.h20
-rw-r--r--Source/cmMakefileUtilityTargetGenerator.cxx13
-rw-r--r--Source/cmMakefileUtilityTargetGenerator.h7
-rw-r--r--Source/cmNinjaNormalTargetGenerator.cxx59
-rw-r--r--Source/cmNinjaNormalTargetGenerator.h4
-rw-r--r--Source/cmNinjaTargetGenerator.cxx51
-rw-r--r--Source/cmNinjaTargetGenerator.h22
-rw-r--r--Source/cmOSXBundleGenerator.cxx236
-rw-r--r--Source/cmOSXBundleGenerator.h71
-rw-r--r--Source/cmTarget.cxx112
-rw-r--r--Source/cmTarget.h16
-rw-r--r--Source/cmake.cxx6
-rw-r--r--Tests/CMakeLists.txt66
-rwxr-xr-xbootstrap22
27 files changed, 845 insertions, 462 deletions
diff --git a/Source/CMakeLists.txt b/Source/CMakeLists.txt
index 14af796..e9c5a58 100644
--- a/Source/CMakeLists.txt
+++ b/Source/CMakeLists.txt
@@ -219,6 +219,8 @@ SET(SRCS
cmMakefileExecutableTargetGenerator.cxx
cmMakefileLibraryTargetGenerator.cxx
cmMakefileUtilityTargetGenerator.cxx
+ cmOSXBundleGenerator.cxx
+ cmOSXBundleGenerator.h
cmNewLineStyle.h
cmNewLineStyle.cxx
cmOrderDirectories.cxx
@@ -357,40 +359,25 @@ IF (WIN32)
ENDIF(NOT UNIX)
ENDIF (WIN32)
-# Turn on Ninja by default, but disable it
-# on platforms where it does not pass all tests.
-# Enforce Ninja support by setting CMAKE_USE_NINJA
-set(_CMAKE_DEFAULT_NINJA_VALUE TRUE)
-if(APPLE)
- SET(_CMAKE_DEFAULT_NINJA_VALUE FALSE)
-endif()
-SET(CMAKE_ENABLE_NINJA ${_CMAKE_DEFAULT_NINJA_VALUE} CACHE BOOL
- "Enable the ninja generator for CMake. When enabled, some CMake tests still fail on OSX")
-MARK_AS_ADVANCED(CMAKE_ENABLE_NINJA)
-IF(CMAKE_ENABLE_NINJA)
- MESSAGE(STATUS "Ninja generator enabled.")
- SET(SRCS ${SRCS}
- cmGlobalNinjaGenerator.cxx
- cmGlobalNinjaGenerator.h
- cmNinjaTypes.h
- cmLocalNinjaGenerator.cxx
- cmLocalNinjaGenerator.h
- cmNinjaTargetGenerator.cxx
- cmNinjaTargetGenerator.h
- cmNinjaNormalTargetGenerator.cxx
- cmNinjaNormalTargetGenerator.h
- cmNinjaUtilityTargetGenerator.cxx
- cmNinjaUtilityTargetGenerator.h
- )
- ADD_DEFINITIONS(-DCMAKE_USE_NINJA)
- IF(WIN32 AND NOT CYGWIN AND NOT BORLAND)
- SET_SOURCE_FILES_PROPERTIES(cmcldeps.cxx PROPERTIES COMPILE_DEFINITIONS _WIN32_WINNT=0x0501)
- ADD_EXECUTABLE(cmcldeps cmcldeps.cxx)
- TARGET_LINK_LIBRARIES(cmcldeps CMakeLib)
- INSTALL_TARGETS(/bin cmcldeps)
- ENDIF()
-ELSE()
- MESSAGE(STATUS "Ninja generator disabled, enable it with -DCMAKE_ENABLE_NINJA=ON")
+# Ninja support
+SET(SRCS ${SRCS}
+ cmGlobalNinjaGenerator.cxx
+ cmGlobalNinjaGenerator.h
+ cmNinjaTypes.h
+ cmLocalNinjaGenerator.cxx
+ cmLocalNinjaGenerator.h
+ cmNinjaTargetGenerator.cxx
+ cmNinjaTargetGenerator.h
+ cmNinjaNormalTargetGenerator.cxx
+ cmNinjaNormalTargetGenerator.h
+ cmNinjaUtilityTargetGenerator.cxx
+ cmNinjaUtilityTargetGenerator.h
+ )
+IF(WIN32 AND NOT CYGWIN AND NOT BORLAND)
+ SET_SOURCE_FILES_PROPERTIES(cmcldeps.cxx PROPERTIES COMPILE_DEFINITIONS _WIN32_WINNT=0x0501)
+ ADD_EXECUTABLE(cmcldeps cmcldeps.cxx)
+ TARGET_LINK_LIBRARIES(cmcldeps CMakeLib)
+ INSTALL_TARGETS(/bin cmcldeps)
ENDIF()
# create a library used by the command line and the GUI
diff --git a/Source/QtDialog/CMakeLists.txt b/Source/QtDialog/CMakeLists.txt
index 056e48e..07ec106 100644
--- a/Source/QtDialog/CMakeLists.txt
+++ b/Source/QtDialog/CMakeLists.txt
@@ -36,14 +36,14 @@ ELSE(NOT QT4_FOUND)
QMacInstallDialog.cxx
QMacInstallDialog.h
)
- QT4_WRAP_UI(UI_SRCS
+ QT4_WRAP_UI(UI_SRCS
CMakeSetupDialog.ui
Compilers.ui
CrossCompiler.ui
AddCacheEntry.ui
MacInstallDialog.ui
)
- QT4_WRAP_CPP(MOC_SRCS
+ QT4_WRAP_CPP(MOC_SRCS
AddCacheEntry.h
Compilers.h
CMakeSetupDialog.h
@@ -76,7 +76,7 @@ ELSE(NOT QT4_FOUND)
SET_TARGET_PROPERTIES(cmake-gui PROPERTIES
OUTPUT_NAME ${CMAKE_BUNDLE_NAME})
ENDIF(APPLE)
- SET(CMAKE_INSTALL_DESTINATION_ARGS
+ SET(CMAKE_INSTALL_DESTINATION_ARGS
BUNDLE DESTINATION "${CMAKE_BUNDLE_LOCATION}")
ENDIF(${CMAKE_MAJOR_VERSION}.${CMAKE_MINOR_VERSION} GREATER 2.4)
@@ -112,11 +112,12 @@ ELSE(NOT QT4_FOUND)
endif(APPLE)
install(CODE "
include(\"${CMake_SOURCE_DIR}/Modules/BundleUtilities.cmake\")
+ set(BU_CHMOD_BUNDLE_ITEMS ON)
fixup_bundle(\"${fixup_exe}\" \"\" \"${QT_LIBRARY_DIR};${QT_BINARY_DIR}\")
")
endif(APPLE OR WIN32)
CONFIGURE_FILE("${QtDialog_SOURCE_DIR}/QtDialogCPack.cmake.in"
- "${QtDialog_BINARY_DIR}/QtDialogCPack.cmake" @ONLY)
+ "${QtDialog_BINARY_DIR}/QtDialogCPack.cmake" @ONLY)
ENDIF(NOT QT4_FOUND)
diff --git a/Source/cmExtraCodeBlocksGenerator.cxx b/Source/cmExtraCodeBlocksGenerator.cxx
index 5df8627..ad4ab76 100644
--- a/Source/cmExtraCodeBlocksGenerator.cxx
+++ b/Source/cmExtraCodeBlocksGenerator.cxx
@@ -60,9 +60,7 @@ cmExtraCodeBlocksGenerator::cmExtraCodeBlocksGenerator()
// disable until somebody actually tests it:
// this->SupportedGlobalGenerators.push_back("MSYS Makefiles");
#endif
-#ifdef CMAKE_USE_NINJA
this->SupportedGlobalGenerators.push_back("Ninja");
-#endif
this->SupportedGlobalGenerators.push_back("Unix Makefiles");
}
diff --git a/Source/cmExtraEclipseCDT4Generator.cxx b/Source/cmExtraEclipseCDT4Generator.cxx
index ab11307..78a8704 100644
--- a/Source/cmExtraEclipseCDT4Generator.cxx
+++ b/Source/cmExtraEclipseCDT4Generator.cxx
@@ -34,9 +34,7 @@ cmExtraEclipseCDT4Generator
this->SupportedGlobalGenerators.push_back("MinGW Makefiles");
// this->SupportedGlobalGenerators.push_back("MSYS Makefiles");
#endif
-#ifdef CMAKE_USE_NINJA
this->SupportedGlobalGenerators.push_back("Ninja");
-#endif
this->SupportedGlobalGenerators.push_back("Unix Makefiles");
this->SupportsVirtualFolders = true;
diff --git a/Source/cmGlobalNinjaGenerator.cxx b/Source/cmGlobalNinjaGenerator.cxx
index 912e53e..3f3cfbb 100644
--- a/Source/cmGlobalNinjaGenerator.cxx
+++ b/Source/cmGlobalNinjaGenerator.cxx
@@ -252,6 +252,48 @@ cmGlobalNinjaGenerator::WriteCustomCommandBuild(const std::string& command,
vars);
}
+void
+cmGlobalNinjaGenerator::AddMacOSXContentRule()
+{
+ cmLocalGenerator *lg = this->LocalGenerators[0];
+ cmMakefile* mfRoot = lg->GetMakefile();
+
+ cmOStringStream cmd;
+ cmd << lg->ConvertToOutputFormat(
+ mfRoot->GetRequiredDefinition("CMAKE_COMMAND"),
+ cmLocalGenerator::SHELL)
+ << " -E copy $in $out";
+
+ this->AddRule("COPY_OSX_CONTENT",
+ cmd.str(),
+ "Copying OS X Content $out",
+ "Rule for copying OS X bundle content file."
+ /*depfile*/ "",
+ /*rspfile*/ "");
+}
+
+void
+cmGlobalNinjaGenerator::WriteMacOSXContentBuild(const std::string& input,
+ const std::string& output)
+{
+ this->AddMacOSXContentRule();
+
+ cmNinjaDeps outputs;
+ outputs.push_back(output);
+ cmNinjaDeps deps;
+ deps.push_back(input);
+ cmNinjaVars vars;
+
+ cmGlobalNinjaGenerator::WriteBuild(*this->BuildFileStream,
+ "",
+ "COPY_OSX_CONTENT",
+ outputs,
+ deps,
+ cmNinjaDeps(),
+ cmNinjaDeps(),
+ cmNinjaVars());
+}
+
void cmGlobalNinjaGenerator::WriteRule(std::ostream& os,
const std::string& name,
const std::string& command,
@@ -781,6 +823,11 @@ void cmGlobalNinjaGenerator::AddDependencyToAll(cmTarget* target)
this->AppendTargetOutputs(target, this->AllDependencies);
}
+void cmGlobalNinjaGenerator::AddDependencyToAll(const std::string& input)
+{
+ this->AllDependencies.push_back(input);
+}
+
void cmGlobalNinjaGenerator::WriteAssumedSourceDependencies()
{
for (std::map<std::string, std::set<std::string> >::iterator
diff --git a/Source/cmGlobalNinjaGenerator.h b/Source/cmGlobalNinjaGenerator.h
index ff4f85d..b2fe243 100644
--- a/Source/cmGlobalNinjaGenerator.h
+++ b/Source/cmGlobalNinjaGenerator.h
@@ -103,6 +103,8 @@ public:
const cmNinjaDeps& outputs,
const cmNinjaDeps& deps = cmNinjaDeps(),
const cmNinjaDeps& orderOnlyDeps = cmNinjaDeps());
+ void WriteMacOSXContentBuild(const std::string& input,
+ const std::string& output);
/**
* Write a rule statement named @a name to @a os with the @a comment,
@@ -151,6 +153,7 @@ public:
static bool IsMinGW() { return UsingMinGW; }
+
public:
/// Default constructor.
cmGlobalNinjaGenerator();
@@ -214,12 +217,12 @@ public:
}
virtual const char* GetCleanTargetName() const { return "clean"; }
-public:
- cmGeneratedFileStream* GetBuildFileStream() const
- { return this->BuildFileStream; }
- cmGeneratedFileStream* GetRulesFileStream() const
- { return this->RulesFileStream; }
+ cmGeneratedFileStream* GetBuildFileStream() const {
+ return this->BuildFileStream; }
+
+ cmGeneratedFileStream* GetRulesFileStream() const {
+ return this->RulesFileStream; }
void AddCXXCompileCommand(const std::string &commandLine,
const std::string &sourceFile);
@@ -242,6 +245,52 @@ public:
bool HasRule(const std::string& name);
void AddCustomCommandRule();
+ void AddMacOSXContentRule();
+
+ bool HasCustomCommandOutput(const std::string &output) {
+ return this->CustomCommandOutputs.find(output) !=
+ this->CustomCommandOutputs.end();
+ }
+
+ /// Called when we have seen the given custom command. Returns true
+ /// if we has seen it before.
+ bool SeenCustomCommand(cmCustomCommand const *cc) {
+ return !this->CustomCommands.insert(cc).second;
+ }
+
+ /// Called when we have seen the given custom command output.
+ void SeenCustomCommandOutput(const std::string &output) {
+ this->CustomCommandOutputs.insert(output);
+ // We don't need the assumed dependencies anymore, because we have
+ // an output.
+ this->AssumedSourceDependencies.erase(output);
+ }
+
+ void AddAssumedSourceDependencies(const std::string &source,
+ const cmNinjaDeps &deps) {
+ std::set<std::string> &ASD = this->AssumedSourceDependencies[source];
+ // Because we may see the same source file multiple times (same source
+ // specified in multiple targets), compute the union of any assumed
+ // dependencies.
+ ASD.insert(deps.begin(), deps.end());
+ }
+
+ void AppendTargetOutputs(cmTarget* target, cmNinjaDeps& outputs);
+ void AppendTargetDepends(cmTarget* target, cmNinjaDeps& outputs);
+ void AddDependencyToAll(cmTarget* target);
+ void AddDependencyToAll(const std::string& input);
+
+ const std::vector<cmLocalGenerator*>& GetLocalGenerators() const {
+ return LocalGenerators; }
+
+ bool IsExcluded(cmLocalGenerator* root, cmTarget& target) {
+ return cmGlobalGenerator::IsExcluded(root, target); }
+
+ int GetRuleCmdLength(const std::string& name) {
+ return RuleCmdLength[name]; }
+
+ void AddTargetAlias(const std::string& alias, cmTarget* target);
+
protected:
@@ -249,21 +298,12 @@ protected:
/// @see cmGlobalGenerator::CheckALLOW_DUPLICATE_CUSTOM_TARGETS()
virtual bool CheckALLOW_DUPLICATE_CUSTOM_TARGETS() { return true; }
+
private:
/// @see cmGlobalGenerator::ComputeTargetObjects
virtual void ComputeTargetObjects(cmGeneratorTarget* gt) const;
-private:
- // In order to access the AddDependencyToAll() functions and co.
- friend class cmLocalNinjaGenerator;
-
- // In order to access the SeenCustomCommand() function.
- friend class cmNinjaTargetGenerator;
- friend class cmNinjaNormalTargetGenerator;
- friend class cmNinjaUtilityTargetGenerator;
-
-private:
void OpenBuildFileStream();
void CloseBuildFileStream();
@@ -275,14 +315,8 @@ private:
/// Write the common disclaimer text at the top of each build file.
void WriteDisclaimer(std::ostream& os);
- void AddDependencyToAll(cmTarget* target);
-
void WriteAssumedSourceDependencies();
- void AppendTargetOutputs(cmTarget* target, cmNinjaDeps& outputs);
- void AppendTargetDepends(cmTarget* target, cmNinjaDeps& outputs);
-
- void AddTargetAlias(const std::string& alias, cmTarget* target);
void WriteTargetAliases(std::ostream& os);
void WriteBuiltinTargets(std::ostream& os);
@@ -291,39 +325,9 @@ private:
void WriteTargetClean(std::ostream& os);
void WriteTargetHelp(std::ostream& os);
- /// Called when we have seen the given custom command. Returns true
- /// if we has seen it before.
- bool SeenCustomCommand(cmCustomCommand const *cc) {
- return !this->CustomCommands.insert(cc).second;
- }
-
- /// Called when we have seen the given custom command output.
- void SeenCustomCommandOutput(const std::string &output) {
- this->CustomCommandOutputs.insert(output);
- // We don't need the assumed dependencies anymore, because we have
- // an output.
- this->AssumedSourceDependencies.erase(output);
- }
-
- bool HasCustomCommandOutput(const std::string &output) {
- return this->CustomCommandOutputs.find(output) !=
- this->CustomCommandOutputs.end();
- }
-
- void AddAssumedSourceDependencies(const std::string &source,
- const cmNinjaDeps &deps) {
- std::set<std::string> &ASD = this->AssumedSourceDependencies[source];
- // Because we may see the same source file multiple times (same source
- // specified in multiple targets), compute the union of any assumed
- // dependencies.
- ASD.insert(deps.begin(), deps.end());
- }
-
std::string ninjaCmd() const;
- int GetRuleCmdLength(const std::string& name) { return RuleCmdLength[name]; }
-private:
/// The file containing the build statement. (the relation ship of the
/// compilation DAG).
cmGeneratedFileStream* BuildFileStream;
diff --git a/Source/cmLocalNinjaGenerator.cxx b/Source/cmLocalNinjaGenerator.cxx
index ea9c406..d902f4e 100644
--- a/Source/cmLocalNinjaGenerator.cxx
+++ b/Source/cmLocalNinjaGenerator.cxx
@@ -61,7 +61,7 @@ void cmLocalNinjaGenerator::Generate()
tg->Generate();
// Add the target to "all" if required.
if (!this->GetGlobalNinjaGenerator()->IsExcluded(
- this->GetGlobalNinjaGenerator()->LocalGenerators[0],
+ this->GetGlobalNinjaGenerator()->GetLocalGenerators()[0],
t->second))
this->GetGlobalNinjaGenerator()->AddDependencyToAll(&t->second);
delete tg;
diff --git a/Source/cmLocalNinjaGenerator.h b/Source/cmLocalNinjaGenerator.h
index ea44b2f..c450841 100644
--- a/Source/cmLocalNinjaGenerator.h
+++ b/Source/cmLocalNinjaGenerator.h
@@ -45,7 +45,6 @@ public:
/// Overloaded methods. @see cmLocalGenerator::GetTargetDirectory()
virtual std::string GetTargetDirectory(cmTarget const& target) const;
-public:
const cmGlobalNinjaGenerator* GetGlobalNinjaGenerator() const;
cmGlobalNinjaGenerator* GetGlobalNinjaGenerator();
@@ -67,33 +66,8 @@ public:
std::string GetHomeRelativeOutputPath() const
{ return this->HomeRelativeOutputPath; }
-protected:
- virtual std::string ConvertToLinkReference(std::string const& lib);
- virtual std::string ConvertToIncludeReference(std::string const& path);
-
-private:
- friend class cmGlobalNinjaGenerator;
-
- // In order to access to protected member of the local generator.
- friend class cmNinjaTargetGenerator;
- friend class cmNinjaNormalTargetGenerator;
- friend class cmNinjaUtilityTargetGenerator;
-
-private:
- cmGeneratedFileStream& GetBuildFileStream() const;
- cmGeneratedFileStream& GetRulesFileStream() const;
-
- void WriteBuildFileTop();
- void WriteProjectHeader(std::ostream& os);
- void WriteNinjaFilesInclusion(std::ostream& os);
- void WriteProcessedMakefile(std::ostream& os);
-
- void SetConfigName();
-
std::string ConvertToNinjaPath(const char *path);
- struct map_to_ninja_path;
- friend struct map_to_ninja_path;
struct map_to_ninja_path {
cmLocalNinjaGenerator *LocalGenerator;
map_to_ninja_path(cmLocalNinjaGenerator *LocalGen)
@@ -102,26 +76,52 @@ private:
return LocalGenerator->ConvertToNinjaPath(path.c_str());
}
};
+
map_to_ninja_path MapToNinjaPath() {
return map_to_ninja_path(this);
}
+ void ExpandRuleVariables(std::string& string,
+ const RuleVariables& replaceValues) {
+ cmLocalGenerator::ExpandRuleVariables(string, replaceValues);
+ }
+
+ std::string BuildCommandLine(const std::vector<std::string> &cmdLines);
+
void AppendTargetOutputs(cmTarget* target, cmNinjaDeps& outputs);
void AppendTargetDepends(cmTarget* target, cmNinjaDeps& outputs);
- void AppendCustomCommandDeps(const cmCustomCommand *cc,
- cmNinjaDeps &ninjaDeps);
- std::string BuildCommandLine(const std::vector<std::string> &cmdLines);
+ void AddCustomCommandTarget(cmCustomCommand const* cc, cmTarget* target);
void AppendCustomCommandLines(const cmCustomCommand *cc,
std::vector<std::string> &cmdLines);
+ void AppendCustomCommandDeps(const cmCustomCommand *cc,
+ cmNinjaDeps &ninjaDeps);
+
+ virtual std::string ConvertToLinkReference(std::string const& lib);
+
+
+protected:
+ virtual std::string ConvertToIncludeReference(std::string const& path);
+
+
+private:
+ cmGeneratedFileStream& GetBuildFileStream() const;
+ cmGeneratedFileStream& GetRulesFileStream() const;
+
+ void WriteBuildFileTop();
+ void WriteProjectHeader(std::ostream& os);
+ void WriteNinjaFilesInclusion(std::ostream& os);
+ void WriteProcessedMakefile(std::ostream& os);
+
+ void SetConfigName();
+
void WriteCustomCommandRule();
void WriteCustomCommandBuildStatement(cmCustomCommand const *cc,
const cmNinjaDeps& orderOnlyDeps);
- void AddCustomCommandTarget(cmCustomCommand const* cc, cmTarget* target);
void WriteCustomCommandBuildStatements();
-private:
+
std::string ConfigName;
std::string HomeRelativeOutputPath;
diff --git a/Source/cmMakefileExecutableTargetGenerator.cxx b/Source/cmMakefileExecutableTargetGenerator.cxx
index 78278cb..ab5150a 100644
--- a/Source/cmMakefileExecutableTargetGenerator.cxx
+++ b/Source/cmMakefileExecutableTargetGenerator.cxx
@@ -29,13 +29,19 @@ cmMakefileExecutableTargetGenerator
this->TargetNameOut, this->TargetNameReal, this->TargetNameImport,
this->TargetNamePDB, this->ConfigName);
- if(this->Target->IsAppBundleOnApple())
- {
- this->MacContentDirectory = this->Target->GetDirectory(this->ConfigName);
- this->MacContentDirectory += "/";
- this->MacContentDirectory += this->TargetNameOut;
- this->MacContentDirectory += ".app/Contents/";
- }
+ this->OSXBundleGenerator = new cmOSXBundleGenerator(this->Target,
+ this->TargetNameOut,
+ this->ConfigName);
+ this->OSXBundleGenerator->SetMacContentFolders(&this->MacContentFolders);
+ this->MacContentDirectory =
+ this->OSXBundleGenerator->GetMacContentDirectory();
+}
+
+//----------------------------------------------------------------------------
+cmMakefileExecutableTargetGenerator
+::~cmMakefileExecutableTargetGenerator()
+{
+ delete this->OSXBundleGenerator;
}
//----------------------------------------------------------------------------
@@ -100,7 +106,7 @@ void cmMakefileExecutableTargetGenerator::WriteExecutableRule(bool relink)
outpath += "/";
if(this->Target->IsAppBundleOnApple())
{
- this->CreateAppBundle(targetName, outpath);
+ this->OSXBundleGenerator->CreateAppBundle(targetName, outpath);
}
std::string outpathImp;
if(relink)
@@ -129,7 +135,7 @@ void cmMakefileExecutableTargetGenerator::WriteExecutableRule(bool relink)
std::string targetFullPathReal = outpath + targetNameReal;
std::string targetFullPathPDB = outpath + targetNamePDB;
std::string targetFullPathImport = outpathImp + targetNameImport;
- std::string targetOutPathPDB =
+ std::string targetOutPathPDB =
this->Convert(targetFullPathPDB.c_str(),
cmLocalGenerator::NONE,
cmLocalGenerator::SHELL);
@@ -440,24 +446,3 @@ void cmMakefileExecutableTargetGenerator::WriteExecutableRule(bool relink)
exeCleanFiles.begin(),
exeCleanFiles.end());
}
-
-//----------------------------------------------------------------------------
-void
-cmMakefileExecutableTargetGenerator::CreateAppBundle(std::string& targetName,
- std::string& outpath)
-{
- // Compute bundle directory names.
- outpath = this->MacContentDirectory;
- outpath += "MacOS";
- cmSystemTools::MakeDirectory(outpath.c_str());
- this->Makefile->AddCMakeOutputFile(outpath.c_str());
- outpath += "/";
-
- // Configure the Info.plist file. Note that it needs the executable name
- // to be set.
- std::string plist = this->MacContentDirectory + "Info.plist";
- this->LocalGenerator->GenerateAppleInfoPList(this->Target,
- targetName.c_str(),
- plist.c_str());
- this->Makefile->AddCMakeOutputFile(plist.c_str());
-}
diff --git a/Source/cmMakefileExecutableTargetGenerator.h b/Source/cmMakefileExecutableTargetGenerator.h
index 985f207..3b18166 100644
--- a/Source/cmMakefileExecutableTargetGenerator.h
+++ b/Source/cmMakefileExecutableTargetGenerator.h
@@ -18,14 +18,14 @@ class cmMakefileExecutableTargetGenerator: public cmMakefileTargetGenerator
{
public:
cmMakefileExecutableTargetGenerator(cmTarget* target);
+ virtual ~cmMakefileExecutableTargetGenerator();
/* the main entry point for this class. Writes the Makefiles associated
with this target */
virtual void WriteRuleFiles();
-
+
protected:
virtual void WriteExecutableRule(bool relink);
- void CreateAppBundle(std::string& targetName, std::string& outpath);
};
#endif
diff --git a/Source/cmMakefileLibraryTargetGenerator.cxx b/Source/cmMakefileLibraryTargetGenerator.cxx
index db59ffd..577e5fd 100644
--- a/Source/cmMakefileLibraryTargetGenerator.cxx
+++ b/Source/cmMakefileLibraryTargetGenerator.cxx
@@ -26,41 +26,26 @@ cmMakefileLibraryTargetGenerator
::cmMakefileLibraryTargetGenerator(cmTarget* target):
cmMakefileTargetGenerator(target)
{
- if(this->Target->IsCFBundleOnApple())
- {
- target->SetProperty("PREFIX", "");
- target->SetProperty("SUFFIX", "");
- }
+ cmOSXBundleGenerator::PrepareTargetProperties(this->Target);
this->CustomCommandDriver = OnDepends;
this->Target->GetLibraryNames(
this->TargetNameOut, this->TargetNameSO, this->TargetNameReal,
this->TargetNameImport, this->TargetNamePDB, this->ConfigName);
- if(this->Target->IsFrameworkOnApple())
- {
- this->FrameworkVersion = this->Target->GetFrameworkVersion();
- this->MacContentDirectory = this->Target->GetDirectory(this->ConfigName);
- this->MacContentDirectory += "/";
- this->MacContentDirectory += this->TargetNameOut;
- this->MacContentDirectory += ".framework/Versions/";
- this->MacContentDirectory += this->FrameworkVersion;
- this->MacContentDirectory += "/";
- }
- else if(this->Target->IsCFBundleOnApple())
- {
- this->MacContentDirectory = this->Target->GetDirectory(this->ConfigName);
- this->MacContentDirectory += "/";
- this->MacContentDirectory += this->TargetNameOut;
- this->MacContentDirectory += ".";
- const char *ext = this->Target->GetProperty("BUNDLE_EXTENSION");
- if (!ext)
- {
- ext = "bundle";
- }
- this->MacContentDirectory += ext;
- this->MacContentDirectory += "/Contents/";
- }
+ this->OSXBundleGenerator = new cmOSXBundleGenerator(this->Target,
+ this->TargetNameOut,
+ this->ConfigName);
+ this->OSXBundleGenerator->SetMacContentFolders(&this->MacContentFolders);
+ this->MacContentDirectory =
+ this->OSXBundleGenerator->GetMacContentDirectory();
+}
+
+//----------------------------------------------------------------------------
+cmMakefileLibraryTargetGenerator
+::~cmMakefileLibraryTargetGenerator()
+{
+ delete this->OSXBundleGenerator;
}
//----------------------------------------------------------------------------
@@ -199,7 +184,7 @@ void cmMakefileLibraryTargetGenerator::WriteSharedLibraryRules(bool relink)
linkFlagsConfig += cmSystemTools::UpperCase(this->ConfigName);
this->LocalGenerator->AppendFlags
(extraFlags, this->Target->GetProperty(linkFlagsConfig.c_str()));
-
+
this->LocalGenerator->AddConfigVariableFlags
(extraFlags, "CMAKE_SHARED_LINKER_FLAGS", this->ConfigName);
this->AddModuleDefinitionFlag(extraFlags);
@@ -220,7 +205,7 @@ void cmMakefileLibraryTargetGenerator::WriteModuleLibraryRules(bool relink)
linkRuleVar += "_CREATE_SHARED_MODULE";
std::string extraFlags;
- this->LocalGenerator->AppendFlags(extraFlags,
+ this->LocalGenerator->AppendFlags(extraFlags,
this->Target->GetProperty("LINK_FLAGS"));
std::string linkFlagsConfig = "LINK_FLAGS_";
linkFlagsConfig += cmSystemTools::UpperCase(this->ConfigName);
@@ -246,7 +231,7 @@ void cmMakefileLibraryTargetGenerator::WriteFrameworkRules(bool relink)
linkRuleVar += "_CREATE_MACOSX_FRAMEWORK";
std::string extraFlags;
- this->LocalGenerator->AppendFlags(extraFlags,
+ this->LocalGenerator->AppendFlags(extraFlags,
this->Target->GetProperty("LINK_FLAGS"));
std::string linkFlagsConfig = "LINK_FLAGS_";
linkFlagsConfig += cmSystemTools::UpperCase(this->ConfigName);
@@ -259,115 +244,6 @@ void cmMakefileLibraryTargetGenerator::WriteFrameworkRules(bool relink)
}
//----------------------------------------------------------------------------
-void
-cmMakefileLibraryTargetGenerator
-::CreateFramework(std::string const& targetName)
-{
- // Configure the Info.plist file into the Resources directory.
- this->MacContentFolders.insert("Resources");
- std::string plist = this->MacContentDirectory + "Resources/Info.plist";
- this->LocalGenerator->GenerateFrameworkInfoPList(this->Target,
- targetName.c_str(),
- plist.c_str());
-
- // TODO: Use the cmMakefileTargetGenerator::ExtraFiles vector to
- // drive rules to create these files at build time.
- std::string oldName;
- std::string newName;
-
- // Compute the location of the top-level foo.framework directory.
- std::string top = this->Target->GetDirectory(this->ConfigName);
- top += "/";
- top += this->TargetNameOut;
- top += ".framework/";
-
- // Make foo.framework/Versions
- std::string versions = top;
- versions += "Versions";
- cmSystemTools::MakeDirectory(versions.c_str());
-
- // Make foo.framework/Versions/version
- std::string version = versions;
- version += "/";
- version += this->FrameworkVersion;
- cmSystemTools::MakeDirectory(version.c_str());
-
- // Current -> version
- oldName = this->FrameworkVersion;
- newName = versions;
- newName += "/Current";
- cmSystemTools::RemoveFile(newName.c_str());
- cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
- this->Makefile->AddCMakeOutputFile(newName.c_str());
-
- // foo -> Versions/Current/foo
- oldName = "Versions/Current/";
- oldName += this->TargetNameOut;
- newName = top;
- newName += this->TargetNameOut;
- cmSystemTools::RemoveFile(newName.c_str());
- cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
- this->Makefile->AddCMakeOutputFile(newName.c_str());
-
- // Resources -> Versions/Current/Resources
- if(this->MacContentFolders.find("Resources") !=
- this->MacContentFolders.end())
- {
- oldName = "Versions/Current/Resources";
- newName = top;
- newName += "Resources";
- cmSystemTools::RemoveFile(newName.c_str());
- cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
- this->Makefile->AddCMakeOutputFile(newName.c_str());
- }
-
- // Headers -> Versions/Current/Headers
- if(this->MacContentFolders.find("Headers") !=
- this->MacContentFolders.end())
- {
- oldName = "Versions/Current/Headers";
- newName = top;
- newName += "Headers";
- cmSystemTools::RemoveFile(newName.c_str());
- cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
- this->Makefile->AddCMakeOutputFile(newName.c_str());
- }
-
- // PrivateHeaders -> Versions/Current/PrivateHeaders
- if(this->MacContentFolders.find("PrivateHeaders") !=
- this->MacContentFolders.end())
- {
- oldName = "Versions/Current/PrivateHeaders";
- newName = top;
- newName += "PrivateHeaders";
- cmSystemTools::RemoveFile(newName.c_str());
- cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
- this->Makefile->AddCMakeOutputFile(newName.c_str());
- }
-}
-
-//----------------------------------------------------------------------------
-void
-cmMakefileLibraryTargetGenerator::CreateCFBundle(std::string& targetName,
- std::string& outpath)
-{
- // Compute bundle directory names.
- outpath = this->MacContentDirectory;
- outpath += "MacOS";
- cmSystemTools::MakeDirectory(outpath.c_str());
- this->Makefile->AddCMakeOutputFile(outpath.c_str());
- outpath += "/";
-
- // Configure the Info.plist file. Note that it needs the executable name
- // to be set.
- std::string plist = this->MacContentDirectory + "Info.plist";
- this->LocalGenerator->GenerateAppleInfoPList(this->Target,
- targetName.c_str(),
- plist.c_str());
- this->Makefile->AddCMakeOutputFile(plist.c_str());
-}
-
-//----------------------------------------------------------------------------
void cmMakefileLibraryTargetGenerator::WriteLibraryRules
(const char* linkRuleVar, const char* extraFlags, bool relink)
{
@@ -419,13 +295,13 @@ void cmMakefileLibraryTargetGenerator::WriteLibraryRules
if(this->Target->IsFrameworkOnApple())
{
outpath = this->MacContentDirectory;
- this->CreateFramework(targetName);
+ this->OSXBundleGenerator->CreateFramework(targetName);
}
else if(this->Target->IsCFBundleOnApple())
{
outpath = this->Target->GetDirectory(this->ConfigName);
outpath += "/";
- this->CreateCFBundle(targetName, outpath);
+ this->OSXBundleGenerator->CreateCFBundle(targetName, outpath);
}
else if(relink)
{
@@ -460,16 +336,16 @@ void cmMakefileLibraryTargetGenerator::WriteLibraryRules
// Construct the output path version of the names for use in command
// arguments.
- std::string targetOutPathPDB =
+ std::string targetOutPathPDB =
this->Convert(targetFullPathPDB.c_str(),cmLocalGenerator::NONE,
cmLocalGenerator::SHELL);
- std::string targetOutPath =
+ std::string targetOutPath =
this->Convert(targetFullPath.c_str(),cmLocalGenerator::START_OUTPUT,
cmLocalGenerator::SHELL);
- std::string targetOutPathSO =
+ std::string targetOutPathSO =
this->Convert(targetFullPathSO.c_str(),cmLocalGenerator::START_OUTPUT,
cmLocalGenerator::SHELL);
- std::string targetOutPathReal =
+ std::string targetOutPathReal =
this->Convert(targetFullPathReal.c_str(),cmLocalGenerator::START_OUTPUT,
cmLocalGenerator::SHELL);
std::string targetOutPathImport =
@@ -569,7 +445,7 @@ void cmMakefileLibraryTargetGenerator::WriteLibraryRules
std::vector<std::string> commands1;
// Add a command to remove any existing files for this library.
- // for static libs only
+ // for static libs only
if(this->Target->GetType() == cmTarget::STATIC_LIBRARY)
{
this->LocalGenerator->AppendCleanCommand(commands1, libCleanFiles,
diff --git a/Source/cmMakefileLibraryTargetGenerator.h b/Source/cmMakefileLibraryTargetGenerator.h
index e6a5867..07f828b 100644
--- a/Source/cmMakefileLibraryTargetGenerator.h
+++ b/Source/cmMakefileLibraryTargetGenerator.h
@@ -14,16 +14,17 @@
#include "cmMakefileTargetGenerator.h"
-class cmMakefileLibraryTargetGenerator:
+class cmMakefileLibraryTargetGenerator:
public cmMakefileTargetGenerator
{
public:
cmMakefileLibraryTargetGenerator(cmTarget* target);
+ virtual ~cmMakefileLibraryTargetGenerator();
/* the main entry point for this class. Writes the Makefiles associated
with this target */
- virtual void WriteRuleFiles();
-
+ virtual void WriteRuleFiles();
+
protected:
void WriteObjectLibraryRules();
void WriteStaticLibraryRules();
@@ -33,8 +34,6 @@ protected:
bool relink);
// MacOSX Framework support methods
void WriteFrameworkRules(bool relink);
- void CreateFramework(std::string const& targetName);
- void CreateCFBundle(std::string& targetName, std::string& outpath);
// Store the computd framework version for OS X Frameworks.
std::string FrameworkVersion;
diff --git a/Source/cmMakefileTargetGenerator.cxx b/Source/cmMakefileTargetGenerator.cxx
index 16e3e02..0de182e 100644
--- a/Source/cmMakefileTargetGenerator.cxx
+++ b/Source/cmMakefileTargetGenerator.cxx
@@ -28,6 +28,8 @@
cmMakefileTargetGenerator::cmMakefileTargetGenerator(cmTarget* target)
+ : OSXBundleGenerator(0)
+ , MacOSXContentGenerator(0)
{
this->BuildFileStream = 0;
this->InfoFileStream = 0;
@@ -50,6 +52,12 @@ cmMakefileTargetGenerator::cmMakefileTargetGenerator(cmTarget* target)
{
this->NoRuleMessages = cmSystemTools::IsOff(ruleStatus);
}
+ MacOSXContentGenerator = new MacOSXContentGeneratorType(this);
+}
+
+cmMakefileTargetGenerator::~cmMakefileTargetGenerator()
+{
+ delete MacOSXContentGenerator;
}
cmMakefileTargetGenerator *
@@ -153,8 +161,12 @@ void cmMakefileTargetGenerator::WriteTargetBuildRules()
}
}
}
- this->WriteMacOSXContentRules(this->GeneratorTarget->HeaderSources);
- this->WriteMacOSXContentRules(this->GeneratorTarget->ExtraSources);
+ this->OSXBundleGenerator->GenerateMacOSXContentStatements(
+ this->GeneratorTarget->HeaderSources,
+ this->MacOSXContentGenerator);
+ this->OSXBundleGenerator->GenerateMacOSXContentStatements(
+ this->GeneratorTarget->ExtraSources,
+ this->MacOSXContentGenerator);
for(std::vector<cmSourceFile*>::const_iterator
si = this->GeneratorTarget->ExternalObjects.begin();
si != this->GeneratorTarget->ExternalObjects.end(); ++si)
@@ -173,7 +185,6 @@ void cmMakefileTargetGenerator::WriteTargetBuildRules()
this->GeneratorTarget->UseObjectLibraries(this->ExternalObjects);
}
-
//----------------------------------------------------------------------------
void cmMakefileTargetGenerator::WriteCommonCodeRules()
{
@@ -343,44 +354,20 @@ void cmMakefileTargetGenerator::WriteTargetLanguageFlags()
}
}
-//----------------------------------------------------------------------------
-void cmMakefileTargetGenerator::WriteMacOSXContentRules(
- std::vector<cmSourceFile*> const& sources)
-{
- for(std::vector<cmSourceFile*>::const_iterator
- si = sources.begin(); si != sources.end(); ++si)
- {
- cmTarget::SourceFileFlags tsFlags =
- this->Target->GetTargetSourceFileFlags(*si);
- if(tsFlags.Type != cmTarget::SourceFileTypeNormal)
- {
- this->WriteMacOSXContentRules(**si, tsFlags.MacFolder);
- }
- }
-}
//----------------------------------------------------------------------------
-void cmMakefileTargetGenerator::WriteMacOSXContentRules(cmSourceFile& source,
- const char* pkgloc)
+void
+cmMakefileTargetGenerator::MacOSXContentGeneratorType::operator()
+ (cmSourceFile& source, const char* pkgloc)
{
// Skip OS X content when not building a Framework or Bundle.
- if(this->MacContentDirectory.empty())
+ if(this->Generator->MacContentDirectory.empty())
{
return;
}
- // Construct the full path to the content subdirectory.
- std::string macdir = this->MacContentDirectory;
- macdir += pkgloc;
- cmSystemTools::MakeDirectory(macdir.c_str());
-
- // Record use of this content location. Only the first level
- // directory is needed.
- {
- std::string loc = pkgloc;
- loc = loc.substr(0, loc.find('/'));
- this->MacContentFolders.insert(loc);
- }
+ std::string macdir =
+ this->Generator->OSXBundleGenerator->InitMacOSXContentDirectory(pkgloc);
// Get the input file location.
std::string input = source.GetFullPath();
@@ -389,9 +376,11 @@ void cmMakefileTargetGenerator::WriteMacOSXContentRules(cmSourceFile& source,
std::string output = macdir;
output += "/";
output += cmSystemTools::GetFilenameName(input);
- this->CleanFiles.push_back(this->Convert(output.c_str(),
- cmLocalGenerator::START_OUTPUT));
- output = this->Convert(output.c_str(), cmLocalGenerator::HOME_OUTPUT);
+ this->Generator->CleanFiles.push_back(
+ this->Generator->Convert(output.c_str(),
+ cmLocalGenerator::START_OUTPUT));
+ output = this->Generator->Convert(output.c_str(),
+ cmLocalGenerator::HOME_OUTPUT);
// Create a rule to copy the content into the bundle.
std::vector<std::string> depends;
@@ -399,21 +388,23 @@ void cmMakefileTargetGenerator::WriteMacOSXContentRules(cmSourceFile& source,
depends.push_back(input);
std::string copyEcho = "Copying OS X content ";
copyEcho += output;
- this->LocalGenerator->AppendEcho(commands, copyEcho.c_str(),
- cmLocalUnixMakefileGenerator3::EchoBuild);
+ this->Generator->LocalGenerator->AppendEcho(
+ commands, copyEcho.c_str(),
+ cmLocalUnixMakefileGenerator3::EchoBuild);
std::string copyCommand = "$(CMAKE_COMMAND) -E copy ";
- copyCommand += this->Convert(input.c_str(),
- cmLocalGenerator::NONE,
- cmLocalGenerator::SHELL);
+ copyCommand += this->Generator->Convert(input.c_str(),
+ cmLocalGenerator::NONE,
+ cmLocalGenerator::SHELL);
copyCommand += " ";
- copyCommand += this->Convert(output.c_str(),
- cmLocalGenerator::NONE,
- cmLocalGenerator::SHELL);
+ copyCommand += this->Generator->Convert(output.c_str(),
+ cmLocalGenerator::NONE,
+ cmLocalGenerator::SHELL);
commands.push_back(copyCommand);
- this->LocalGenerator->WriteMakeRule(*this->BuildFileStream, 0,
- output.c_str(),
- depends, commands, false);
- this->ExtraFiles.insert(output);
+ this->Generator->LocalGenerator->WriteMakeRule(
+ *this->Generator->BuildFileStream, 0,
+ output.c_str(),
+ depends, commands, false);
+ this->Generator->ExtraFiles.insert(output);
}
//----------------------------------------------------------------------------
diff --git a/Source/cmMakefileTargetGenerator.h b/Source/cmMakefileTargetGenerator.h
index 36a1f68..2798e54 100644
--- a/Source/cmMakefileTargetGenerator.h
+++ b/Source/cmMakefileTargetGenerator.h
@@ -13,6 +13,7 @@
#define cmMakefileTargetGenerator_h
#include "cmLocalUnixMakefileGenerator3.h"
+#include "cmOSXBundleGenerator.h"
class cmCustomCommand;
class cmDependInformation;
@@ -34,7 +35,7 @@ class cmMakefileTargetGenerator
public:
// constructor to set the ivars
cmMakefileTargetGenerator(cmTarget* target);
- virtual ~cmMakefileTargetGenerator() {};
+ virtual ~cmMakefileTargetGenerator();
// construct using this factory call
static cmMakefileTargetGenerator *New(cmTarget *tgt);
@@ -50,6 +51,7 @@ public:
{ return this->ProgressFileNameFull; }
cmTarget* GetTarget() { return this->Target;}
+
protected:
// create the file and directory etc
@@ -73,8 +75,18 @@ protected:
void WriteTargetDependRules();
// write rules for Mac OS X Application Bundle content.
- void WriteMacOSXContentRules(std::vector<cmSourceFile*> const& sources);
- void WriteMacOSXContentRules(cmSourceFile& source, const char* pkgloc);
+ struct MacOSXContentGeneratorType :
+ cmOSXBundleGenerator::MacOSXContentGeneratorType
+ {
+ MacOSXContentGeneratorType(cmMakefileTargetGenerator* gen) :
+ Generator(gen) {}
+
+ void operator()(cmSourceFile& source, const char* pkgloc);
+
+ private:
+ cmMakefileTargetGenerator* Generator;
+ };
+ friend struct MacOSXContentGeneratorType;
// write the rules for an object
void WriteObjectRuleFiles(cmSourceFile& source);
@@ -223,6 +235,8 @@ protected:
// Mac OS X content info.
std::string MacContentDirectory;
std::set<cmStdString> MacContentFolders;
+ cmOSXBundleGenerator* OSXBundleGenerator;
+ MacOSXContentGeneratorType* MacOSXContentGenerator;
typedef std::map<cmStdString, cmStdString> ByLanguageMap;
std::string GetFlags(const std::string &l);
diff --git a/Source/cmMakefileUtilityTargetGenerator.cxx b/Source/cmMakefileUtilityTargetGenerator.cxx
index a82c503..4456aa7 100644
--- a/Source/cmMakefileUtilityTargetGenerator.cxx
+++ b/Source/cmMakefileUtilityTargetGenerator.cxx
@@ -24,6 +24,19 @@ cmMakefileUtilityTargetGenerator
cmMakefileTargetGenerator(target)
{
this->CustomCommandDriver = OnUtility;
+ this->OSXBundleGenerator = new cmOSXBundleGenerator(this->Target,
+ this->TargetNameOut,
+ this->ConfigName);
+ this->OSXBundleGenerator->SetMacContentFolders(&this->MacContentFolders);
+ this->MacContentDirectory =
+ this->OSXBundleGenerator->GetMacContentDirectory();
+}
+
+//----------------------------------------------------------------------------
+cmMakefileUtilityTargetGenerator
+::~cmMakefileUtilityTargetGenerator()
+{
+ delete this->OSXBundleGenerator;
}
//----------------------------------------------------------------------------
diff --git a/Source/cmMakefileUtilityTargetGenerator.h b/Source/cmMakefileUtilityTargetGenerator.h
index 99c16fc..fc47b38 100644
--- a/Source/cmMakefileUtilityTargetGenerator.h
+++ b/Source/cmMakefileUtilityTargetGenerator.h
@@ -14,16 +14,17 @@
#include "cmMakefileTargetGenerator.h"
-class cmMakefileUtilityTargetGenerator:
+class cmMakefileUtilityTargetGenerator:
public cmMakefileTargetGenerator
{
public:
cmMakefileUtilityTargetGenerator(cmTarget* target);
+ virtual ~cmMakefileUtilityTargetGenerator();
/* the main entry point for this class. Writes the Makefiles associated
with this target */
- virtual void WriteRuleFiles();
-
+ virtual void WriteRuleFiles();
+
protected:
};
diff --git a/Source/cmNinjaNormalTargetGenerator.cxx b/Source/cmNinjaNormalTargetGenerator.cxx
index 7805fe8..a923d60 100644
--- a/Source/cmNinjaNormalTargetGenerator.cxx
+++ b/Source/cmNinjaNormalTargetGenerator.cxx
@@ -16,6 +16,7 @@
#include "cmSourceFile.h"
#include "cmGeneratedFileStream.h"
#include "cmMakefile.h"
+#include "cmOSXBundleGenerator.h"
#include <assert.h>
#include <algorithm>
@@ -33,7 +34,10 @@ cmNinjaNormalTargetGenerator(cmTarget* target)
, TargetNameReal()
, TargetNameImport()
, TargetNamePDB()
+ , TargetLinkLanguage(0)
{
+ cmOSXBundleGenerator::PrepareTargetProperties(target);
+
this->TargetLinkLanguage = target->GetLinkerLanguage(this->GetConfigName());
if (target->GetType() == cmTarget::EXECUTABLE)
target->GetExecutableNames(this->TargetNameOut,
@@ -55,10 +59,16 @@ cmNinjaNormalTargetGenerator(cmTarget* target)
// ensure the directory exists (OutDir test)
EnsureDirectoryExists(target->GetDirectory(this->GetConfigName()));
}
+
+ this->OSXBundleGenerator = new cmOSXBundleGenerator(target,
+ this->TargetNameOut,
+ this->GetConfigName());
+ this->OSXBundleGenerator->SetMacContentFolders(&this->MacContentFolders);
}
cmNinjaNormalTargetGenerator::~cmNinjaNormalTargetGenerator()
{
+ delete this->OSXBundleGenerator;
}
void cmNinjaNormalTargetGenerator::Generate()
@@ -115,7 +125,10 @@ const char *cmNinjaNormalTargetGenerator::GetVisibleTypeName() const
case cmTarget::SHARED_LIBRARY:
return "shared library";
case cmTarget::MODULE_LIBRARY:
- return "shared module";
+ if (this->GetTarget()->IsCFBundleOnApple())
+ return "CFBundle shared module";
+ else
+ return "shared module";
case cmTarget::EXECUTABLE:
return "executable";
default:
@@ -348,6 +361,40 @@ void cmNinjaNormalTargetGenerator::WriteLinkStatement()
{
cmTarget::TargetType targetType = this->GetTarget()->GetType();
+ std::string targetOutput = ConvertToNinjaPath(
+ this->GetTarget()->GetFullPath(this->GetConfigName()).c_str());
+ std::string targetOutputReal = ConvertToNinjaPath(
+ this->GetTarget()->GetFullPath(this->GetConfigName(),
+ /*implib=*/false,
+ /*realpath=*/true).c_str());
+ std::string targetOutputImplib = ConvertToNinjaPath(
+ this->GetTarget()->GetFullPath(this->GetConfigName(),
+ /*implib=*/true).c_str());
+
+ if (this->GetTarget()->IsAppBundleOnApple())
+ {
+ // Create the app bundle
+ std::string outpath;
+ this->OSXBundleGenerator->CreateAppBundle(this->TargetNameOut, outpath);
+
+ // Calculate the output path
+ targetOutput = outpath + this->TargetNameOut;
+ targetOutput = this->ConvertToNinjaPath(targetOutput.c_str());
+ targetOutputReal = outpath + this->TargetNameReal;
+ targetOutputReal = this->ConvertToNinjaPath(targetOutputReal.c_str());
+ }
+ else if (this->GetTarget()->IsFrameworkOnApple())
+ {
+ // Create the library framework.
+ this->OSXBundleGenerator->CreateFramework(this->TargetNameOut);
+ }
+ else if(this->GetTarget()->IsCFBundleOnApple())
+ {
+ // Create the core foundation bundle.
+ std::string outpath;
+ this->OSXBundleGenerator->CreateCFBundle(this->TargetNameOut, outpath);
+ }
+
// Write comments.
cmGlobalNinjaGenerator::WriteDivider(this->GetBuildFileStream());
this->GetBuildFileStream()
@@ -360,16 +407,6 @@ void cmNinjaNormalTargetGenerator::WriteLinkStatement()
cmNinjaDeps emptyDeps;
cmNinjaVars vars;
- std::string targetOutput = ConvertToNinjaPath(
- this->GetTarget()->GetFullPath(this->GetConfigName()).c_str());
- std::string targetOutputReal = ConvertToNinjaPath(
- this->GetTarget()->GetFullPath(this->GetConfigName(),
- /*implib=*/false,
- /*realpath=*/true).c_str());
- std::string targetOutputImplib = ConvertToNinjaPath(
- this->GetTarget()->GetFullPath(this->GetConfigName(),
- /*implib=*/true).c_str());
-
// Compute the comment.
cmOStringStream comment;
comment << "Link the " << this->GetVisibleTypeName() << " "
diff --git a/Source/cmNinjaNormalTargetGenerator.h b/Source/cmNinjaNormalTargetGenerator.h
index 1ef9567..284804b 100644
--- a/Source/cmNinjaNormalTargetGenerator.h
+++ b/Source/cmNinjaNormalTargetGenerator.h
@@ -15,8 +15,12 @@
# include "cmNinjaTargetGenerator.h"
# include "cmNinjaTypes.h"
+# include "cmStandardIncludes.h"
+
+# include <set>
class cmSourceFile;
+class cmOSXBundleGenerator;
class cmNinjaNormalTargetGenerator : public cmNinjaTargetGenerator
{
diff --git a/Source/cmNinjaTargetGenerator.cxx b/Source/cmNinjaTargetGenerator.cxx
index 0d02039..3532c8b 100644
--- a/Source/cmNinjaTargetGenerator.cxx
+++ b/Source/cmNinjaTargetGenerator.cxx
@@ -56,7 +56,11 @@ cmNinjaTargetGenerator::New(cmTarget* target)
}
cmNinjaTargetGenerator::cmNinjaTargetGenerator(cmTarget* target)
- : Target(target),
+ :
+ MacOSXContentGenerator(0),
+ OSXBundleGenerator(0),
+ MacContentFolders(),
+ Target(target),
Makefile(target->GetMakefile()),
LocalGenerator(
static_cast<cmLocalNinjaGenerator*>(Makefile->GetLocalGenerator())),
@@ -64,10 +68,12 @@ cmNinjaTargetGenerator::cmNinjaTargetGenerator(cmTarget* target)
{
this->GeneratorTarget =
this->GetGlobalGenerator()->GetGeneratorTarget(target);
+ MacOSXContentGenerator = new MacOSXContentGeneratorType(this);
}
cmNinjaTargetGenerator::~cmNinjaTargetGenerator()
{
+ delete this->MacOSXContentGenerator;
}
cmGeneratedFileStream& cmNinjaTargetGenerator::GetBuildFileStream() const
@@ -87,7 +93,7 @@ cmGlobalNinjaGenerator* cmNinjaTargetGenerator::GetGlobalGenerator() const
const char* cmNinjaTargetGenerator::GetConfigName() const
{
- return this->LocalGenerator->ConfigName.c_str();
+ return this->LocalGenerator->GetConfigName();
}
// TODO: Picked up from cmMakefileTargetGenerator. Refactor it.
@@ -430,6 +436,12 @@ cmNinjaTargetGenerator
cmCustomCommand const* cc = (*si)->GetCustomCommand();
this->GetLocalGenerator()->AddCustomCommandTarget(cc, this->GetTarget());
}
+ this->OSXBundleGenerator->GenerateMacOSXContentStatements(
+ this->GeneratorTarget->HeaderSources,
+ this->MacOSXContentGenerator);
+ this->OSXBundleGenerator->GenerateMacOSXContentStatements(
+ this->GeneratorTarget->ExtraSources,
+ this->MacOSXContentGenerator);
for(std::vector<cmSourceFile*>::const_iterator
si = this->GeneratorTarget->ExternalObjects.begin();
si != this->GeneratorTarget->ExternalObjects.end(); ++si)
@@ -640,3 +652,38 @@ cmNinjaTargetGenerator
{
EnsureDirectoryExists(cmSystemTools::GetParentDirectory(path.c_str()));
}
+
+
+//----------------------------------------------------------------------------
+void
+cmNinjaTargetGenerator::MacOSXContentGeneratorType::operator()(
+ cmSourceFile& source, const char* pkgloc)
+{
+ // Skip OS X content when not building a Framework or Bundle.
+ if(this->Generator->OSXBundleGenerator->GetMacContentDirectory().empty())
+ {
+ return;
+ }
+
+ std::string macdir =
+ this->Generator->OSXBundleGenerator->InitMacOSXContentDirectory(pkgloc);
+
+ // Get the input file location.
+ std::string input = source.GetFullPath();
+ input =
+ this->Generator->GetLocalGenerator()->ConvertToNinjaPath(input.c_str());
+
+ // Get the output file location.
+ std::string output = macdir;
+ output += "/";
+ output += cmSystemTools::GetFilenameName(input);
+ output =
+ this->Generator->GetLocalGenerator()->ConvertToNinjaPath(output.c_str());
+
+ // Write a build statement to copy the content into the bundle.
+ this->Generator->GetGlobalGenerator()->WriteMacOSXContentBuild(input,
+ output);
+
+ // Add as a dependency of all target so that it gets called.
+ this->Generator->GetGlobalGenerator()->AddDependencyToAll(output);
+}
diff --git a/Source/cmNinjaTargetGenerator.h b/Source/cmNinjaTargetGenerator.h
index af43a8b..84573ce 100644
--- a/Source/cmNinjaTargetGenerator.h
+++ b/Source/cmNinjaTargetGenerator.h
@@ -16,6 +16,7 @@
#include "cmStandardIncludes.h"
#include "cmNinjaTypes.h"
#include "cmLocalNinjaGenerator.h"
+#include "cmOSXBundleGenerator.h"
class cmTarget;
class cmGlobalNinjaGenerator;
@@ -114,6 +115,27 @@ protected:
void EnsureDirectoryExists(const std::string& dir);
void EnsureParentDirectoryExists(const std::string& path);
+ // write rules for Mac OS X Application Bundle content.
+ struct MacOSXContentGeneratorType :
+ cmOSXBundleGenerator::MacOSXContentGeneratorType
+ {
+ MacOSXContentGeneratorType(cmNinjaTargetGenerator* g) :
+ Generator(g) {}
+
+ void operator()(cmSourceFile& source, const char* pkgloc);
+
+ private:
+ cmNinjaTargetGenerator* Generator;
+ };
+ friend struct MacOSXContentGeneratorType;
+
+protected:
+ MacOSXContentGeneratorType* MacOSXContentGenerator;
+ // Properly initialized by sub-classes.
+ cmOSXBundleGenerator* OSXBundleGenerator;
+ std::set<cmStdString> MacContentFolders;
+
+
private:
cmTarget* Target;
cmGeneratorTarget* GeneratorTarget;
diff --git a/Source/cmOSXBundleGenerator.cxx b/Source/cmOSXBundleGenerator.cxx
new file mode 100644
index 0000000..42fad07
--- /dev/null
+++ b/Source/cmOSXBundleGenerator.cxx
@@ -0,0 +1,236 @@
+/*============================================================================
+ CMake - Cross Platform Makefile Generator
+ Copyright 2012 Nicolas Despres <nicolas.despres@gmail.com>
+
+ Distributed under the OSI-approved BSD License (the "License");
+ see accompanying file Copyright.txt for details.
+
+ This software is distributed WITHOUT ANY WARRANTY; without even the
+ implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ See the License for more information.
+============================================================================*/
+#include "cmOSXBundleGenerator.h"
+#include "cmMakefile.h"
+#include "cmTarget.h"
+#include "cmLocalGenerator.h"
+
+#include <cassert>
+
+void cmOSXBundleGenerator::PrepareTargetProperties(cmTarget* target)
+{
+ if(target->IsCFBundleOnApple())
+ {
+ target->SetProperty("PREFIX", "");
+ target->SetProperty("SUFFIX", "");
+ }
+}
+
+//----------------------------------------------------------------------------
+cmOSXBundleGenerator::
+cmOSXBundleGenerator(cmTarget* target,
+ std::string targetNameOut,
+ const char* configName)
+ : Target(target)
+ , Makefile(target->GetMakefile())
+ , LocalGenerator(Makefile->GetLocalGenerator())
+ , TargetNameOut(targetNameOut)
+ , ConfigName(configName)
+ , MacContentDirectory()
+ , FrameworkVersion()
+ , MacContentFolders(0)
+{
+ if (this->MustSkip())
+ return;
+
+ this->MacContentDirectory =
+ this->Target->GetMacContentDirectory(this->ConfigName,
+ /*implib*/ false,
+ /*includeMacOS*/ false);
+ if(this->Target->IsFrameworkOnApple())
+ this->FrameworkVersion = this->Target->GetFrameworkVersion();
+}
+
+//----------------------------------------------------------------------------
+bool cmOSXBundleGenerator::MustSkip()
+{
+ return !this->Target->HaveWellDefinedOutputFiles();
+}
+
+//----------------------------------------------------------------------------
+void cmOSXBundleGenerator::CreateAppBundle(std::string& targetName,
+ std::string& outpath)
+{
+ if (this->MustSkip())
+ return;
+
+ // Compute bundle directory names.
+ outpath = this->MacContentDirectory;
+ outpath += "MacOS";
+ cmSystemTools::MakeDirectory(outpath.c_str());
+ outpath += "/";
+ this->Makefile->AddCMakeOutputFile(outpath.c_str());
+
+ // Configure the Info.plist file. Note that it needs the executable name
+ // to be set.
+ std::string plist = this->MacContentDirectory + "Info.plist";
+ this->LocalGenerator->GenerateAppleInfoPList(this->Target,
+ targetName.c_str(),
+ plist.c_str());
+ this->Makefile->AddCMakeOutputFile(plist.c_str());
+}
+
+//----------------------------------------------------------------------------
+void cmOSXBundleGenerator::CreateFramework(std::string const& targetName)
+{
+ if (this->MustSkip())
+ return;
+
+ assert(this->MacContentFolders);
+
+ // Configure the Info.plist file into the Resources directory.
+ this->MacContentFolders->insert("Resources");
+ std::string plist = this->MacContentDirectory + "Resources/Info.plist";
+ this->LocalGenerator->GenerateFrameworkInfoPList(this->Target,
+ targetName.c_str(),
+ plist.c_str());
+
+ // TODO: Use the cmMakefileTargetGenerator::ExtraFiles vector to
+ // drive rules to create these files at build time.
+ std::string oldName;
+ std::string newName;
+
+ // Compute the location of the top-level foo.framework directory.
+ std::string top = this->Target->GetDirectory(this->ConfigName);
+ top += "/";
+ top += this->TargetNameOut;
+ top += ".framework/";
+
+ // Make foo.framework/Versions
+ std::string versions = top;
+ versions += "Versions";
+ cmSystemTools::MakeDirectory(versions.c_str());
+
+ // Make foo.framework/Versions/version
+ std::string version = versions;
+ version += "/";
+ version += this->FrameworkVersion;
+ cmSystemTools::MakeDirectory(version.c_str());
+
+ // Current -> version
+ oldName = this->FrameworkVersion;
+ newName = versions;
+ newName += "/Current";
+ cmSystemTools::RemoveFile(newName.c_str());
+ cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
+ this->Makefile->AddCMakeOutputFile(newName.c_str());
+
+ // foo -> Versions/Current/foo
+ oldName = "Versions/Current/";
+ oldName += this->TargetNameOut;
+ newName = top;
+ newName += this->TargetNameOut;
+ cmSystemTools::RemoveFile(newName.c_str());
+ cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
+ this->Makefile->AddCMakeOutputFile(newName.c_str());
+
+ // Resources -> Versions/Current/Resources
+ if(this->MacContentFolders->find("Resources") !=
+ this->MacContentFolders->end())
+ {
+ oldName = "Versions/Current/Resources";
+ newName = top;
+ newName += "Resources";
+ cmSystemTools::RemoveFile(newName.c_str());
+ cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
+ this->Makefile->AddCMakeOutputFile(newName.c_str());
+ }
+
+ // Headers -> Versions/Current/Headers
+ if(this->MacContentFolders->find("Headers") !=
+ this->MacContentFolders->end())
+ {
+ oldName = "Versions/Current/Headers";
+ newName = top;
+ newName += "Headers";
+ cmSystemTools::RemoveFile(newName.c_str());
+ cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
+ this->Makefile->AddCMakeOutputFile(newName.c_str());
+ }
+
+ // PrivateHeaders -> Versions/Current/PrivateHeaders
+ if(this->MacContentFolders->find("PrivateHeaders") !=
+ this->MacContentFolders->end())
+ {
+ oldName = "Versions/Current/PrivateHeaders";
+ newName = top;
+ newName += "PrivateHeaders";
+ cmSystemTools::RemoveFile(newName.c_str());
+ cmSystemTools::CreateSymlink(oldName.c_str(), newName.c_str());
+ this->Makefile->AddCMakeOutputFile(newName.c_str());
+ }
+}
+
+//----------------------------------------------------------------------------
+void cmOSXBundleGenerator::CreateCFBundle(std::string& targetName,
+ std::string& outpath)
+{
+ if (this->MustSkip())
+ return;
+
+ // Compute bundle directory names.
+ outpath = this->MacContentDirectory;
+ outpath += "MacOS";
+ cmSystemTools::MakeDirectory(outpath.c_str());
+ outpath += "/";
+ this->Makefile->AddCMakeOutputFile(outpath.c_str());
+
+ // Configure the Info.plist file. Note that it needs the executable name
+ // to be set.
+ std::string plist = this->MacContentDirectory;
+ plist += "Info.plist";
+ this->LocalGenerator->GenerateAppleInfoPList(this->Target,
+ targetName.c_str(),
+ plist.c_str());
+ this->Makefile->AddCMakeOutputFile(plist.c_str());
+}
+
+//----------------------------------------------------------------------------
+void
+cmOSXBundleGenerator::
+GenerateMacOSXContentStatements(std::vector<cmSourceFile*> const& sources,
+ MacOSXContentGeneratorType* generator)
+{
+ if (this->MustSkip())
+ return;
+
+ for(std::vector<cmSourceFile*>::const_iterator
+ si = sources.begin(); si != sources.end(); ++si)
+ {
+ cmTarget::SourceFileFlags tsFlags =
+ this->Target->GetTargetSourceFileFlags(*si);
+ if(tsFlags.Type != cmTarget::SourceFileTypeNormal)
+ {
+ (*generator)(**si, tsFlags.MacFolder);
+ }
+ }
+}
+
+//----------------------------------------------------------------------------
+std::string
+cmOSXBundleGenerator::InitMacOSXContentDirectory(const char* pkgloc)
+{
+ // Construct the full path to the content subdirectory.
+ std::string macdir = this->MacContentDirectory;
+ macdir += pkgloc;
+ cmSystemTools::MakeDirectory(macdir.c_str());
+
+ // Record use of this content location. Only the first level
+ // directory is needed.
+ {
+ std::string loc = pkgloc;
+ loc = loc.substr(0, loc.find('/'));
+ this->MacContentFolders->insert(loc);
+ }
+
+ return macdir;
+}
diff --git a/Source/cmOSXBundleGenerator.h b/Source/cmOSXBundleGenerator.h
new file mode 100644
index 0000000..01e3cbe
--- /dev/null
+++ b/Source/cmOSXBundleGenerator.h
@@ -0,0 +1,71 @@
+/*============================================================================
+ CMake - Cross Platform Makefile Generator
+ Copyright 2012 Nicolas Despres <nicolas.despres@gmail.com>
+
+ Distributed under the OSI-approved BSD License (the "License");
+ see accompanying file Copyright.txt for details.
+
+ This software is distributed WITHOUT ANY WARRANTY; without even the
+ implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ See the License for more information.
+============================================================================*/
+#ifndef cmOSXBundleGenerator_h
+#define cmOSXBundleGenerator_h
+
+#include "cmStandardIncludes.h"
+#include "cmSourceFile.h"
+
+#include <string>
+#include <set>
+
+class cmTarget;
+class cmMakefile;
+class cmLocalGenerator;
+
+class cmOSXBundleGenerator
+{
+public:
+ static void PrepareTargetProperties(cmTarget* target);
+
+ cmOSXBundleGenerator(cmTarget* target,
+ std::string targetNameOut,
+ const char* configName);
+
+ void CreateAppBundle(std::string& targetName, std::string& outpath);
+ void CreateFramework(std::string const& targetName);
+ void CreateCFBundle(std::string& targetName, std::string& outpath);
+
+ struct MacOSXContentGeneratorType
+ {
+ virtual ~MacOSXContentGeneratorType() {}
+ virtual void operator()(cmSourceFile& source, const char* pkgloc) = 0;
+ };
+
+ void GenerateMacOSXContentStatements(
+ std::vector<cmSourceFile*> const& sources,
+ MacOSXContentGeneratorType* generator);
+ std::string InitMacOSXContentDirectory(const char* pkgloc);
+
+ std::string GetMacContentDirectory() const
+ { return this->MacContentDirectory; }
+ std::string GetFrameworkVersion() const
+ { return this->FrameworkVersion; }
+ void SetMacContentFolders(std::set<cmStdString>* macContentFolders)
+ { this->MacContentFolders = macContentFolders; }
+
+private:
+ bool MustSkip();
+
+private:
+ cmTarget* Target;
+ cmMakefile* Makefile;
+ cmLocalGenerator* LocalGenerator;
+ std::string TargetNameOut;
+ const char* ConfigName;
+ std::string MacContentDirectory;
+ std::string FrameworkVersion;
+ std::set<cmStdString>* MacContentFolders;
+};
+
+
+#endif
diff --git a/Source/cmTarget.cxx b/Source/cmTarget.cxx
index 4f3f2c5..775662c 100644
--- a/Source/cmTarget.cxx
+++ b/Source/cmTarget.cxx
@@ -2483,6 +2483,16 @@ void cmTarget::MarkAsImported()
}
//----------------------------------------------------------------------------
+bool cmTarget::HaveWellDefinedOutputFiles()
+{
+ return
+ this->GetType() == cmTarget::STATIC_LIBRARY ||
+ this->GetType() == cmTarget::SHARED_LIBRARY ||
+ this->GetType() == cmTarget::MODULE_LIBRARY ||
+ this->GetType() == cmTarget::EXECUTABLE;
+}
+
+//----------------------------------------------------------------------------
cmTarget::OutputInfo const* cmTarget::GetOutputInfo(const char* config)
{
// There is no output information for imported targets.
@@ -2492,10 +2502,7 @@ cmTarget::OutputInfo const* cmTarget::GetOutputInfo(const char* config)
}
// Only libraries and executables have well-defined output files.
- if(this->GetType() != cmTarget::STATIC_LIBRARY &&
- this->GetType() != cmTarget::SHARED_LIBRARY &&
- this->GetType() != cmTarget::MODULE_LIBRARY &&
- this->GetType() != cmTarget::EXECUTABLE)
+ if(!this->HaveWellDefinedOutputFiles())
{
std::string msg = "cmTarget::GetOutputInfo called for ";
msg += this->GetName();
@@ -2586,18 +2593,7 @@ const char* cmTarget::NormalGetLocation(const char* config)
this->Location += cfgid;
this->Location += "/";
}
- if(this->IsAppBundleOnApple())
- {
- this->Location += this->GetFullName(config, false);
- this->Location += ".app/Contents/MacOS/";
- }
- if(this->IsFrameworkOnApple())
- {
- this->Location += this->GetFullName(config, false);
- this->Location += ".framework/Versions/";
- this->Location += this->GetFrameworkVersion();
- this->Location += "/";
- }
+ this->Location = this->BuildMacContentDirectory(this->Location, config);
this->Location += this->GetFullName(config, false);
return this->Location.c_str();
}
@@ -3169,22 +3165,7 @@ std::string cmTarget::GetFullPath(const char* config, bool implib,
std::string cmTarget::NormalGetFullPath(const char* config, bool implib,
bool realname)
{
- // Start with the output directory for the target.
- std::string fpath = this->GetDirectory(config, implib);
- fpath += "/";
-
- if(this->IsAppBundleOnApple())
- {
- fpath += this->GetFullName(config, false);
- fpath += ".app/Contents/MacOS/";
- }
- if(this->IsFrameworkOnApple())
- {
- fpath += this->GetFullName(config, false);
- fpath += ".framework/Versions/";
- fpath += this->GetFrameworkVersion();
- fpath += "/";
- }
+ std::string fpath = this->GetMacContentDirectory(config, implib);
// Add the full name of the target.
if(implib)
@@ -3707,10 +3688,7 @@ std::string cmTarget::GetInstallNameDirForBuildTree(const char* config,
dir += "/";
if(this->IsFrameworkOnApple() && !for_xcode)
{
- dir += this->GetFullName(config, false);
- dir += ".framework/Versions/";
- dir += this->GetFrameworkVersion();
- dir += "/";
+ dir += this->GetFrameworkDirectory(config);
}
return dir;
}
@@ -3741,10 +3719,7 @@ std::string cmTarget::GetInstallNameDirForInstallTree(const char* config,
if(this->IsFrameworkOnApple() && !for_xcode)
{
- dir += this->GetFullName(config, false);
- dir += ".framework/Versions/";
- dir += this->GetFrameworkVersion();
- dir += "/";
+ dir += this->GetFrameworkDirectory(config);
}
return dir;
@@ -4734,6 +4709,63 @@ std::vector<std::string> cmTarget::GetIncludeDirectories()
}
//----------------------------------------------------------------------------
+std::string cmTarget::GetFrameworkDirectory(const char* config)
+{
+ std::string fpath;
+ fpath += this->GetFullName(config, false);
+ fpath += ".framework/Versions/";
+ fpath += this->GetFrameworkVersion();
+ fpath += "/";
+ return fpath;
+}
+
+//----------------------------------------------------------------------------
+std::string cmTarget::BuildMacContentDirectory(const std::string& base,
+ const char* config,
+ bool includeMacOS)
+{
+ std::string fpath = base;
+ if(this->IsAppBundleOnApple())
+ {
+ fpath += this->GetFullName(config, false);
+ fpath += ".app/Contents/";
+ if(includeMacOS)
+ fpath += "MacOS/";
+ }
+ if(this->IsFrameworkOnApple())
+ {
+ fpath += this->GetFrameworkDirectory(config);
+ }
+ if(this->IsCFBundleOnApple())
+ {
+ fpath += this->GetFullName(config, false);
+ fpath += ".";
+ const char *ext = this->GetProperty("BUNDLE_EXTENSION");
+ if (!ext)
+ {
+ ext = "bundle";
+ }
+ fpath += ext;
+ fpath += "/Contents/";
+ if(includeMacOS)
+ fpath += "MacOS/";
+ }
+ return fpath;
+}
+
+//----------------------------------------------------------------------------
+std::string cmTarget::GetMacContentDirectory(const char* config,
+ bool implib,
+ bool includeMacOS)
+{
+ // Start with the output directory for the target.
+ std::string fpath = this->GetDirectory(config, implib);
+ fpath += "/";
+ fpath = this->BuildMacContentDirectory(fpath, config, includeMacOS);
+ return fpath;
+}
+
+//----------------------------------------------------------------------------
cmTargetLinkInformationMap
::cmTargetLinkInformationMap(cmTargetLinkInformationMap const& r): derived()
{
diff --git a/Source/cmTarget.h b/Source/cmTarget.h
index d70cacd..a89c5d9 100644
--- a/Source/cmTarget.h
+++ b/Source/cmTarget.h
@@ -465,6 +465,22 @@ public:
/** Get the include directories for this target. */
std::vector<std::string> GetIncludeDirectories();
+ /** Append to @a base the mac content directory and return it. */
+ std::string BuildMacContentDirectory(const std::string& base,
+ const char* config = 0,
+ bool includeMacOS = true);
+
+ /** @return the mac content directory for this target. */
+ std::string GetMacContentDirectory(const char* config = 0,
+ bool implib = false,
+ bool includeMacOS = true);
+
+ /** @return whether this target have a well defined output file name. */
+ bool HaveWellDefinedOutputFiles();
+
+ /** @return the Mac framework directory without the base. */
+ std::string GetFrameworkDirectory(const char* config = 0);
+
private:
/**
* A list of direct dependencies. Use in conjunction with DependencyMap.
diff --git a/Source/cmake.cxx b/Source/cmake.cxx
index 451aec8..fdc42fa 100644
--- a/Source/cmake.cxx
+++ b/Source/cmake.cxx
@@ -84,10 +84,8 @@
#else
#endif
#include "cmGlobalUnixMakefileGenerator3.h"
+#include "cmGlobalNinjaGenerator.h"
-#ifdef CMAKE_USE_NINJA
-# include "cmGlobalNinjaGenerator.h"
-#endif
#if defined(CMAKE_HAVE_VS_GENERATORS)
#include "cmCallVisualStudioMacro.h"
@@ -2600,10 +2598,8 @@ void cmake::AddDefaultGenerators()
#endif
this->Generators[cmGlobalUnixMakefileGenerator3::GetActualName()] =
&cmGlobalUnixMakefileGenerator3::New;
-#ifdef CMAKE_USE_NINJA
this->Generators[cmGlobalNinjaGenerator::GetActualName()] =
&cmGlobalNinjaGenerator::New;
-#endif
#ifdef CMAKE_USE_XCODE
this->Generators[cmGlobalXCodeGenerator::GetActualName()] =
&cmGlobalXCodeGenerator::New;
diff --git a/Tests/CMakeLists.txt b/Tests/CMakeLists.txt
index 80ab362..27ae3a0 100644
--- a/Tests/CMakeLists.txt
+++ b/Tests/CMakeLists.txt
@@ -1408,42 +1408,44 @@ ${CMake_BINARY_DIR}/bin/cmake -DVERSION=master -P ${CMake_SOURCE_DIR}/Utilities/
LIST(APPEND TEST_BUILD_DIRS "${CMake_BINARY_DIR}/Tests/VSMidl")
ENDIF(${CMAKE_TEST_GENERATOR} MATCHES "Visual Studio")
- IF (APPLE AND CMAKE_COMPILER_IS_GNUCXX)
- SET(BundleTestInstallDir
- "${CMake_BINARY_DIR}/Tests/BundleTest/InstallDirectory")
- ADD_TEST(BundleTest ${CMAKE_CTEST_COMMAND}
- --build-and-test
- "${CMake_SOURCE_DIR}/Tests/BundleTest"
- "${CMake_BINARY_DIR}/Tests/BundleTest"
- --build-two-config
- --build-generator ${CMAKE_TEST_GENERATOR}
- --build-makeprogram ${CMAKE_TEST_MAKEPROGRAM}
- --build-project BundleTest
- --build-target install
-# --build-target package
- --build-options "-DCMAKE_INSTALL_PREFIX:PATH=${BundleTestInstallDir}"
- "-DCMake_SOURCE_DIR:PATH=${CMake_SOURCE_DIR}"
- --test-command
- ${BundleTestInstallDir}/Applications/SecondBundleExe.app/Contents/MacOS/SecondBundleExe)
- LIST(APPEND TEST_BUILD_DIRS "${CMake_BINARY_DIR}/Tests/BundleTest")
-
- ADD_TEST(CFBundleTest ${CMAKE_CTEST_COMMAND}
- --build-and-test
- "${CMake_SOURCE_DIR}/Tests/CFBundleTest"
- "${CMake_BINARY_DIR}/Tests/CFBundleTest"
- --build-two-config
- --build-generator ${CMAKE_TEST_GENERATOR}
- --build-makeprogram ${CMAKE_TEST_MAKEPROGRAM}
- --build-project CFBundleTest
- --test-command
- ${CMAKE_CMAKE_COMMAND} -DCTEST_CONFIGURATION_TYPE=\${CTEST_CONFIGURATION_TYPE}
+ IF (APPLE)
+ if (CMAKE_COMPILER_IS_GNUCXX OR "${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")
+ SET(BundleTestInstallDir
+ "${CMake_BINARY_DIR}/Tests/BundleTest/InstallDirectory")
+ ADD_TEST(BundleTest ${CMAKE_CTEST_COMMAND}
+ --build-and-test
+ "${CMake_SOURCE_DIR}/Tests/BundleTest"
+ "${CMake_BINARY_DIR}/Tests/BundleTest"
+ --build-two-config
+ --build-generator ${CMAKE_TEST_GENERATOR}
+ --build-makeprogram ${CMAKE_TEST_MAKEPROGRAM}
+ --build-project BundleTest
+ --build-target install
+# --build-target package
+ --build-options "-DCMAKE_INSTALL_PREFIX:PATH=${BundleTestInstallDir}"
+ "-DCMake_SOURCE_DIR:PATH=${CMake_SOURCE_DIR}"
+ --test-command
+ ${BundleTestInstallDir}/Applications/SecondBundleExe.app/Contents/MacOS/SecondBundleExe)
+ LIST(APPEND TEST_BUILD_DIRS "${CMake_BINARY_DIR}/Tests/BundleTest")
+
+ ADD_TEST(CFBundleTest ${CMAKE_CTEST_COMMAND}
+ --build-and-test
+ "${CMake_SOURCE_DIR}/Tests/CFBundleTest"
+ "${CMake_BINARY_DIR}/Tests/CFBundleTest"
+ --build-two-config
+ --build-generator ${CMAKE_TEST_GENERATOR}
+ --build-makeprogram ${CMAKE_TEST_MAKEPROGRAM}
+ --build-project CFBundleTest
+ --test-command
+ ${CMAKE_CMAKE_COMMAND} -DCTEST_CONFIGURATION_TYPE=\${CTEST_CONFIGURATION_TYPE}
-Ddir=${CMake_BINARY_DIR}/Tests/CFBundleTest
-Dgen=${CMAKE_TEST_GENERATOR}
-P ${CMake_SOURCE_DIR}/Tests/CFBundleTest/VerifyResult.cmake)
- LIST(APPEND TEST_BUILD_DIRS "${CMake_BINARY_DIR}/Tests/CFBundleTest")
+ LIST(APPEND TEST_BUILD_DIRS "${CMake_BINARY_DIR}/Tests/CFBundleTest")
- ADD_TEST_MACRO(ObjC++ ObjC++)
- ENDIF (APPLE AND CMAKE_COMPILER_IS_GNUCXX)
+ ADD_TEST_MACRO(ObjC++ ObjC++)
+ ENDIF (CMAKE_COMPILER_IS_GNUCXX OR "${CMAKE_CXX_COMPILER_ID}" MATCHES "Clang")
+ ENDIF (APPLE)
IF(APPLE AND CTEST_TEST_CPACK)
ADD_TEST(BundleGeneratorTest ${CMAKE_CTEST_COMMAND}
diff --git a/bootstrap b/bootstrap
index 9d98f47..801882d 100755
--- a/bootstrap
+++ b/bootstrap
@@ -72,14 +72,14 @@ else
cmake_system_darwin=false
fi
-# Determine whether this is BeOS
+# Determine whether this is BeOS
if echo "${cmake_system}" | grep BeOS >/dev/null 2>&1; then
cmake_system_beos=true
else
cmake_system_beos=false
fi
-# Determine whether this is Haiku
+# Determine whether this is Haiku
if echo "${cmake_system}" | grep Haiku >/dev/null 2>&1; then
cmake_system_haiku=true
else
@@ -220,6 +220,7 @@ CMAKE_CXX_SOURCES="\
cmMakefileLibraryTargetGenerator \
cmMakefileTargetGenerator \
cmMakefileUtilityTargetGenerator \
+ cmOSXBundleGenerator \
cmNewLineStyle \
cmBootstrapCommands \
cmCommands \
@@ -238,6 +239,11 @@ CMAKE_CXX_SOURCES="\
cmExprLexer \
cmExprParser \
cmExprParserHelper \
+ cmGlobalNinjaGenerator \
+ cmLocalNinjaGenerator \
+ cmNinjaTargetGenerator \
+ cmNinjaNormalTargetGenerator \
+ cmNinjaUtilityTargetGenerator \
"
if ${cmake_system_mingw}; then
@@ -351,7 +357,7 @@ cmake_error()
res=$1
shift 1
echo "---------------------------------------------"
- echo "Error when bootstrapping CMake:"
+ echo "Error when bootstrapping CMake:"
echo "$*"
echo "---------------------------------------------"
if [ -f cmake_bootstrap.log ]; then
@@ -370,7 +376,7 @@ cmake_replace_string ()
SEARCHFOR="$3"
REPLACEWITH="$4"
if [ -f "${INFILE}" ] || ${cmake_system_openvms}; then
- cat "${INFILE}" |
+ cat "${INFILE}" |
sed "s/\@${SEARCHFOR}\@/${REPLACEWITH}/g" > "${OUTFILE}${_tmp}"
if [ -f "${OUTFILE}${_tmp}" ]; then
if "${_diff}" "${OUTFILE}" "${OUTFILE}${_tmp}" > /dev/null 2> /dev/null ; then
@@ -393,7 +399,7 @@ cmake_kwsys_config_replace_string ()
APPEND="$*"
if [ -f "${INFILE}" ] || ${cmake_system_openvms}; then
echo "${APPEND}" > "${OUTFILE}${_tmp}"
- cat "${INFILE}" |
+ cat "${INFILE}" |
sed "/./ {s/\@KWSYS_NAMESPACE\@/cmsys/g;
s/@KWSYS_BUILD_SHARED@/${KWSYS_BUILD_SHARED}/g;
s/@KWSYS_LFS_AVAILABLE@/${KWSYS_LFS_AVAILABLE}/g;
@@ -797,7 +803,7 @@ echo '
# include <iostream.h>
#endif
-class NeedCXX
+class NeedCXX
{
public:
NeedCXX() { this->Foo = 1; }
@@ -1387,12 +1393,12 @@ cmake_kwsys_config_replace_string \
"${cmake_bootstrap_dir}/cmsys/Configure.h" \
"${cmake_compiler_settings_comment}"
-for a in ${KWSYS_FILES}; do
+for a in ${KWSYS_FILES}; do
cmake_replace_string "${cmake_source_dir}/Source/kwsys/${a}.in" \
"${cmake_bootstrap_dir}/cmsys/${a}" KWSYS_NAMESPACE cmsys
done
-for a in ${KWSYS_IOS_FILES}; do
+for a in ${KWSYS_IOS_FILES}; do
cmake_replace_string "${cmake_source_dir}/Source/kwsys/kwsys_ios_${a}.h.in" \
"${cmake_bootstrap_dir}/cmsys/ios/${a}" KWSYS_NAMESPACE cmsys
done