summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorPeter Collingbourne <peter@pcc.me.uk>2011-08-27 01:25:57 (GMT)
committerPeter Collingbourne <peter@pcc.me.uk>2011-09-03 22:05:35 (GMT)
commit85740c2ddbb2aa0d523c997187442385a191fb64 (patch)
tree505687e9f44d3a0a1d29d979c1d51e555906fdc0 /src
parent769bb7d69bfd4bd120732bc6807e6f03bacfac16 (diff)
downloadNinja-85740c2ddbb2aa0d523c997187442385a191fb64.zip
Ninja-85740c2ddbb2aa0d523c997187442385a191fb64.tar.gz
Ninja-85740c2ddbb2aa0d523c997187442385a191fb64.tar.bz2
Support for rebuilding and reloading manifest files
This introduces support for rebuilding the top-level manifest file using a provided build statement, and reloading it before building the user-requested targets.
Diffstat (limited to 'src')
-rw-r--r--src/build_log.h1
-rw-r--r--src/ninja.cc29
2 files changed, 30 insertions, 0 deletions
diff --git a/src/build_log.h b/src/build_log.h
index 81a745f..f45cbde 100644
--- a/src/build_log.h
+++ b/src/build_log.h
@@ -32,6 +32,7 @@ struct Edge;
/// from it
struct BuildLog {
BuildLog();
+ ~BuildLog() { Close(); }
void SetConfig(BuildConfig* config) { config_ = config; }
bool OpenForWrite(const string& path, string* err);
diff --git a/src/ninja.cc b/src/ninja.cc
index 8f972f3..cdaab3a 100644
--- a/src/ninja.cc
+++ b/src/ninja.cc
@@ -109,6 +109,21 @@ struct RealFileReader : public ManifestParser::FileReader {
}
};
+bool RebuildManifest(State* state, const BuildConfig& config,
+ const char* input_file, string* err) {
+ string path = input_file;
+ CanonicalizePath(&path);
+ Node* node = state->LookupNode(path);
+ if (!node)
+ return false;
+
+ Builder manifest_builder(state, config);
+ if (!manifest_builder.AddTarget(node, err))
+ return false;
+
+ return manifest_builder.Build(err);
+}
+
bool CollectTargetsFromArgs(State* state, int argc, char* argv[],
vector<Node*>* targets, string* err) {
if (argc == 0) {
@@ -398,6 +413,9 @@ int main(int argc, char** argv) {
}
}
+ bool rebuilt_manifest = false;
+
+reload:
State state;
RealFileReader file_reader;
ManifestParser parser(&state, &file_reader);
@@ -450,6 +468,17 @@ int main(int argc, char** argv) {
return 1;
}
+ if (!rebuilt_manifest) { // Don't get caught in an infinite loop by a rebuild
+ // target that is never up to date.
+ if (RebuildManifest(&state, config, input_file, &err)) {
+ rebuilt_manifest = true;
+ goto reload;
+ } else if (!err.empty()) {
+ Error("rebuilding '%s': %s", input_file, err.c_str());
+ return 1;
+ }
+ }
+
vector<Node*> targets;
if (!CollectTargetsFromArgs(&state, argc, argv, &targets, &err)) {
Error("%s", err.c_str());