|
|
@@ -249,51 +249,17 @@ void cmMakefileTargetGenerator::WriteCommonCodeRules()
|
|
|
}
|
|
|
|
|
|
//----------------------------------------------------------------------------
|
|
|
-void cmMakefileTargetGenerator::WriteTargetLanguageFlags()
|
|
|
+std::string cmMakefileTargetGenerator::GetFlags(const std::string &l)
|
|
|
{
|
|
|
- // write language flags for target
|
|
|
- std::set<cmStdString> languages;
|
|
|
- this->Target->GetLanguages(languages);
|
|
|
- // put the compiler in the rules.make file so that if it changes
|
|
|
- // things rebuild
|
|
|
- for(std::set<cmStdString>::const_iterator l = languages.begin();
|
|
|
- l != languages.end(); ++l)
|
|
|
- {
|
|
|
- cmStdString compiler = "CMAKE_";
|
|
|
- compiler += *l;
|
|
|
- compiler += "_COMPILER";
|
|
|
- *this->FlagFileStream << "# compile " << l->c_str() << " with " <<
|
|
|
- this->Makefile->GetSafeDefinition(compiler.c_str()) << "\n";
|
|
|
- }
|
|
|
-
|
|
|
- for(std::set<cmStdString>::const_iterator l = languages.begin();
|
|
|
- l != languages.end(); ++l)
|
|
|
+ ByLanguageMap::iterator i = this->FlagsByLanguage.find(l);
|
|
|
+ if (i == this->FlagsByLanguage.end())
|
|
|
{
|
|
|
- const char *lang = l->c_str();
|
|
|
std::string flags;
|
|
|
- std::string defines;
|
|
|
+ const char *lang = l.c_str();
|
|
|
+
|
|
|
bool shared = ((this->Target->GetType() == cmTarget::SHARED_LIBRARY) ||
|
|
|
(this->Target->GetType() == cmTarget::MODULE_LIBRARY));
|
|
|
|
|
|
- // Add the export symbol definition for shared library objects.
|
|
|
- if(const char* exportMacro = this->Target->GetExportMacro())
|
|
|
- {
|
|
|
- this->LocalGenerator->AppendDefines(defines, exportMacro, lang);
|
|
|
- }
|
|
|
-
|
|
|
- // Add preprocessor definitions for this target and configuration.
|
|
|
- this->LocalGenerator->AppendDefines
|
|
|
- (defines, this->Makefile->GetProperty("COMPILE_DEFINITIONS"), lang);
|
|
|
- this->LocalGenerator->AppendDefines
|
|
|
- (defines, this->Target->GetProperty("COMPILE_DEFINITIONS"), lang);
|
|
|
- std::string defPropName = "COMPILE_DEFINITIONS_";
|
|
|
- defPropName +=
|
|
|
- cmSystemTools::UpperCase(this->LocalGenerator->ConfigurationName);
|
|
|
- this->LocalGenerator->AppendDefines
|
|
|
- (defines, this->Makefile->GetProperty(defPropName.c_str()), lang);
|
|
|
- this->LocalGenerator->AppendDefines
|
|
|
- (defines, this->Target->GetProperty(defPropName.c_str()), lang);
|
|
|
-
|
|
|
// Add language feature flags.
|
|
|
this->AddFeatureFlags(flags, lang);
|
|
|
|
|
|
@@ -301,7 +267,7 @@ void cmMakefileTargetGenerator::WriteTargetLanguageFlags()
|
|
|
lang, this->ConfigName);
|
|
|
|
|
|
// Fortran-specific flags computed for this target.
|
|
|
- if(*l == "Fortran")
|
|
|
+ if(l == "Fortran")
|
|
|
{
|
|
|
this->AddFortranFlags(flags);
|
|
|
}
|
|
|
@@ -320,14 +286,73 @@ void cmMakefileTargetGenerator::WriteTargetLanguageFlags()
|
|
|
this->LocalGenerator->
|
|
|
AppendFlags(flags,this->GetFrameworkFlags().c_str());
|
|
|
|
|
|
- *this->FlagFileStream << lang << "_FLAGS = " << flags << "\n\n";
|
|
|
- *this->FlagFileStream << lang << "_DEFINES = " << defines << "\n\n";
|
|
|
+ ByLanguageMap::value_type entry(l, flags);
|
|
|
+ i = this->FlagsByLanguage.insert(entry).first;
|
|
|
+ }
|
|
|
+ return i->second;
|
|
|
+}
|
|
|
+
|
|
|
+std::string cmMakefileTargetGenerator::GetDefines(const std::string &l)
|
|
|
+{
|
|
|
+ ByLanguageMap::iterator i = this->DefinesByLanguage.find(l);
|
|
|
+ if (i == this->DefinesByLanguage.end())
|
|
|
+ {
|
|
|
+ std::string defines;
|
|
|
+ const char *lang = l.c_str();
|
|
|
+ // Add the export symbol definition for shared library objects.
|
|
|
+ if(const char* exportMacro = this->Target->GetExportMacro())
|
|
|
+ {
|
|
|
+ this->LocalGenerator->AppendDefines(defines, exportMacro, lang);
|
|
|
+ }
|
|
|
+
|
|
|
+ // Add preprocessor definitions for this target and configuration.
|
|
|
+ this->LocalGenerator->AppendDefines
|
|
|
+ (defines, this->Makefile->GetProperty("COMPILE_DEFINITIONS"), lang);
|
|
|
+ this->LocalGenerator->AppendDefines
|
|
|
+ (defines, this->Target->GetProperty("COMPILE_DEFINITIONS"), lang);
|
|
|
+ std::string defPropName = "COMPILE_DEFINITIONS_";
|
|
|
+ defPropName +=
|
|
|
+ cmSystemTools::UpperCase(this->LocalGenerator->ConfigurationName);
|
|
|
+ this->LocalGenerator->AppendDefines
|
|
|
+ (defines, this->Makefile->GetProperty(defPropName.c_str()), lang);
|
|
|
+ this->LocalGenerator->AppendDefines
|
|
|
+ (defines, this->Target->GetProperty(defPropName.c_str()), lang);
|
|
|
+
|
|
|
+ ByLanguageMap::value_type entry(l, defines);
|
|
|
+ i = this->DefinesByLanguage.insert(entry).first;
|
|
|
+ }
|
|
|
+ return i->second;
|
|
|
+}
|
|
|
+
|
|
|
+void cmMakefileTargetGenerator::WriteTargetLanguageFlags()
|
|
|
+{
|
|
|
+ // write language flags for target
|
|
|
+ std::set<cmStdString> languages;
|
|
|
+ this->Target->GetLanguages(languages);
|
|
|
+ // put the compiler in the rules.make file so that if it changes
|
|
|
+ // things rebuild
|
|
|
+ for(std::set<cmStdString>::const_iterator l = languages.begin();
|
|
|
+ l != languages.end(); ++l)
|
|
|
+ {
|
|
|
+ cmStdString compiler = "CMAKE_";
|
|
|
+ compiler += *l;
|
|
|
+ compiler += "_COMPILER";
|
|
|
+ *this->FlagFileStream << "# compile " << l->c_str() << " with " <<
|
|
|
+ this->Makefile->GetSafeDefinition(compiler.c_str()) << "\n";
|
|
|
+ }
|
|
|
+
|
|
|
+ for(std::set<cmStdString>::const_iterator l = languages.begin();
|
|
|
+ l != languages.end(); ++l)
|
|
|
+ {
|
|
|
+ *this->FlagFileStream << *l << "_FLAGS = " << this->GetFlags(*l) << "\n\n";
|
|
|
+ *this->FlagFileStream << *l << "_DEFINES = " << this->GetDefines(*l) <<
|
|
|
+ "\n\n";
|
|
|
}
|
|
|
|
|
|
// Add target-specific flags.
|
|
|
if(this->Target->GetProperty("COMPILE_FLAGS"))
|
|
|
{
|
|
|
- std::string flags;
|
|
|
+ std::string flags;
|
|
|
this->LocalGenerator->AppendFlags
|
|
|
(flags, this->Target->GetProperty("COMPILE_FLAGS"));
|
|
|
*this->FlagFileStream << "# TARGET_FLAGS = " << flags << "\n\n";
|
|
|
@@ -641,6 +666,9 @@ cmMakefileTargetGenerator
|
|
|
vars.Flags = flags.c_str();
|
|
|
vars.Defines = defines.c_str();
|
|
|
|
|
|
+ bool lang_is_c_or_cxx = ((strcmp(lang, "C") == 0) ||
|
|
|
+ (strcmp(lang, "CXX") == 0));
|
|
|
+
|
|
|
// Construct the compile rules.
|
|
|
{
|
|
|
std::string compileRuleVar = "CMAKE_";
|
|
|
@@ -651,6 +679,23 @@ cmMakefileTargetGenerator
|
|
|
std::vector<std::string> compileCommands;
|
|
|
cmSystemTools::ExpandListArgument(compileRule, compileCommands);
|
|
|
|
|
|
+ if (this->Makefile->IsOn("CMAKE_EXPORT_COMPILE_COMMANDS") &&
|
|
|
+ lang_is_c_or_cxx && compileCommands.size() == 1)
|
|
|
+ {
|
|
|
+ std::string compileCommand = compileCommands[0];
|
|
|
+ this->LocalGenerator->ExpandRuleVariables(compileCommand, vars);
|
|
|
+ std::string workingDirectory =
|
|
|
+ this->LocalGenerator->Convert(
|
|
|
+ this->Makefile->GetStartOutputDirectory(), cmLocalGenerator::FULL);
|
|
|
+ compileCommand.replace(compileCommand.find(langFlags),
|
|
|
+ langFlags.size(), this->GetFlags(lang));
|
|
|
+ std::string langDefines = std::string("$(") + lang + "_DEFINES)";
|
|
|
+ compileCommand.replace(compileCommand.find(langDefines),
|
|
|
+ langDefines.size(), this->GetDefines(lang));
|
|
|
+ this->GlobalGenerator->AddCXXCompileCommand(
|
|
|
+ source.GetFullPath(), workingDirectory, compileCommand);
|
|
|
+ }
|
|
|
+
|
|
|
// Expand placeholders in the commands.
|
|
|
for(std::vector<std::string>::iterator i = compileCommands.begin();
|
|
|
i != compileCommands.end(); ++i)
|
|
|
@@ -691,8 +736,6 @@ cmMakefileTargetGenerator
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- bool lang_is_c_or_cxx = ((strcmp(lang, "C") == 0) ||
|
|
|
- (strcmp(lang, "CXX") == 0));
|
|
|
bool do_preprocess_rules = lang_is_c_or_cxx &&
|
|
|
this->LocalGenerator->GetCreatePreprocessedSourceRules();
|
|
|
bool do_assembly_rules = lang_is_c_or_cxx &&
|