|
@@ -679,6 +679,7 @@ void cmGlobalXCodeGenerator::ClearXCodeObjects()
|
|
|
this->FileRefs.clear();
|
|
this->FileRefs.clear();
|
|
|
this->ExternalLibRefs.clear();
|
|
this->ExternalLibRefs.clear();
|
|
|
this->FileRefToBuildFileMap.clear();
|
|
this->FileRefToBuildFileMap.clear();
|
|
|
|
|
+ this->CommandsVisited.clear();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
void cmGlobalXCodeGenerator::addObject(std::unique_ptr<cmXCodeObject> obj)
|
|
void cmGlobalXCodeGenerator::addObject(std::unique_ptr<cmXCodeObject> obj)
|
|
@@ -1271,6 +1272,16 @@ bool cmGlobalXCodeGenerator::CreateXCodeTarget(
|
|
|
return true;
|
|
return true;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ auto& gtgt_visited = this->CommandsVisited[gtgt];
|
|
|
|
|
+ auto& deps = this->GetTargetDirectDepends(gtgt);
|
|
|
|
|
+ for (auto& d : deps) {
|
|
|
|
|
+ // Take the union of visited source files of custom commands so far.
|
|
|
|
|
+ // ComputeTargetOrder ensures our dependencies already visited their
|
|
|
|
|
+ // custom commands and updated CommandsVisited.
|
|
|
|
|
+ auto& dep_visited = this->CommandsVisited[d];
|
|
|
|
|
+ gtgt_visited.insert(dep_visited.begin(), dep_visited.end());
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
if (gtgt->GetType() == cmStateEnums::UTILITY ||
|
|
if (gtgt->GetType() == cmStateEnums::UTILITY ||
|
|
|
gtgt->GetType() == cmStateEnums::INTERFACE_LIBRARY ||
|
|
gtgt->GetType() == cmStateEnums::INTERFACE_LIBRARY ||
|
|
|
gtgt->GetType() == cmStateEnums::GLOBAL_TARGET) {
|
|
gtgt->GetType() == cmStateEnums::GLOBAL_TARGET) {
|
|
@@ -1628,8 +1639,9 @@ void cmGlobalXCodeGenerator::CreateCustomCommands(
|
|
|
}
|
|
}
|
|
|
// add all the sources
|
|
// add all the sources
|
|
|
std::vector<cmCustomCommand> commands;
|
|
std::vector<cmCustomCommand> commands;
|
|
|
|
|
+ auto& visited = this->CommandsVisited[gtgt];
|
|
|
for (auto sourceFile : classes) {
|
|
for (auto sourceFile : classes) {
|
|
|
- if (sourceFile->GetCustomCommand()) {
|
|
|
|
|
|
|
+ if (sourceFile->GetCustomCommand() && visited.insert(sourceFile).second) {
|
|
|
commands.push_back(*sourceFile->GetCustomCommand());
|
|
commands.push_back(*sourceFile->GetCustomCommand());
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
@@ -1839,6 +1851,15 @@ void cmGlobalXCodeGenerator::CreateCustomRulesMakefile(
|
|
|
for (auto const& command : commands) {
|
|
for (auto const& command : commands) {
|
|
|
cmCustomCommandGenerator ccg(command, configName,
|
|
cmCustomCommandGenerator ccg(command, configName,
|
|
|
this->CurrentLocalGenerator);
|
|
this->CurrentLocalGenerator);
|
|
|
|
|
+ std::vector<std::string> realDepends;
|
|
|
|
|
+ realDepends.reserve(ccg.GetDepends().size());
|
|
|
|
|
+ for (auto const& d : ccg.GetDepends()) {
|
|
|
|
|
+ std::string dep;
|
|
|
|
|
+ if (this->CurrentLocalGenerator->GetRealDependency(d, configName, dep)) {
|
|
|
|
|
+ realDepends.emplace_back(std::move(dep));
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
if (ccg.GetNumberOfCommands() > 0) {
|
|
if (ccg.GetNumberOfCommands() > 0) {
|
|
|
makefileStream << "\n";
|
|
makefileStream << "\n";
|
|
|
const std::vector<std::string>& outputs = ccg.GetOutputs();
|
|
const std::vector<std::string>& outputs = ccg.GetOutputs();
|
|
@@ -1854,12 +1875,8 @@ void cmGlobalXCodeGenerator::CreateCustomRulesMakefile(
|
|
|
// There are no outputs. Use the generated force rule name.
|
|
// There are no outputs. Use the generated force rule name.
|
|
|
makefileStream << tname[&ccg.GetCC()] << ": ";
|
|
makefileStream << tname[&ccg.GetCC()] << ": ";
|
|
|
}
|
|
}
|
|
|
- for (auto const& d : ccg.GetDepends()) {
|
|
|
|
|
- std::string dep;
|
|
|
|
|
- if (this->CurrentLocalGenerator->GetRealDependency(d, configName,
|
|
|
|
|
- dep)) {
|
|
|
|
|
- makefileStream << "\\\n" << this->ConvertToRelativeForMake(dep);
|
|
|
|
|
- }
|
|
|
|
|
|
|
+ for (auto const& dep : realDepends) {
|
|
|
|
|
+ makefileStream << "\\\n" << this->ConvertToRelativeForMake(dep);
|
|
|
}
|
|
}
|
|
|
makefileStream << "\n";
|
|
makefileStream << "\n";
|
|
|
|
|
|
|
@@ -1888,6 +1905,17 @@ void cmGlobalXCodeGenerator::CreateCustomRulesMakefile(
|
|
|
ccg.AppendArguments(c, cmd);
|
|
ccg.AppendArguments(c, cmd);
|
|
|
makefileStream << "\t" << cmd << "\n";
|
|
makefileStream << "\t" << cmd << "\n";
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+ // Symbolic inputs are not expected to exist, so add dummy rules.
|
|
|
|
|
+ for (auto const& dep : realDepends) {
|
|
|
|
|
+ if (cmSourceFile* dsf =
|
|
|
|
|
+ target->GetLocalGenerator()->GetMakefile()->GetSource(
|
|
|
|
|
+ dep, cmSourceFileLocationKind::Known)) {
|
|
|
|
|
+ if (dsf->GetPropertyAsBool("SYMBOLIC")) {
|
|
|
|
|
+ makefileStream << this->ConvertToRelativeForMake(dep) << ":\n";
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|