diff --git a/src/state.cc b/src/state.cc index b5d2622f21..cd43e0d484 100644 --- a/src/state.cc +++ b/src/state.cc @@ -35,23 +35,25 @@ void Pool::EdgeFinished(const Edge& edge) { void Pool::DelayEdge(Edge* edge) { assert(depth_ != 0); - delayed_.push_back(edge); + delayed_.insert(edge); } void Pool::RetrieveReadyEdges(set* ready_queue) { - while (!delayed_.empty()) { - Edge* edge = delayed_.front(); + set::iterator it = delayed_.begin(); + while (it != delayed_.end()) { + Edge* edge = *it; if (current_use_ + edge->weight() > depth_) break; - delayed_.pop_front(); ready_queue->insert(edge); EdgeScheduled(*edge); + ++it; } + delayed_.erase(delayed_.begin(), it); } void Pool::Dump() const { printf("%s (%d/%d) ->\n", name_.c_str(), current_use_, depth_); - for (deque::const_iterator it = delayed_.begin(); + for (set::const_iterator it = delayed_.begin(); it != delayed_.end(); ++it) { printf("\t"); @@ -59,6 +61,13 @@ void Pool::Dump() const { } } +bool Pool::WeightedEdgeCmp(const Edge* a, const Edge* b) { + if (!a) return b; + if (!b) return false; + int weight_diff = a->weight() - b->weight(); + return ((weight_diff < 0) || (weight_diff == 0 && a < b)); +} + Pool State::kDefaultPool("", 0); const Rule State::kPhonyRule("phony"); diff --git a/src/state.h b/src/state.h index 0a2e890967..279a64a5bd 100644 --- a/src/state.h +++ b/src/state.h @@ -39,7 +39,7 @@ struct Rule; /// completes). struct Pool { explicit Pool(const string& name, int depth) - : name_(name), current_use_(0), depth_(depth) { } + : name_(name), current_use_(0), depth_(depth), delayed_(&WeightedEdgeCmp) { } // A depth of 0 is infinite bool is_valid() const { return depth_ >= 0; } @@ -74,7 +74,9 @@ struct Pool { int current_use_; int depth_; - deque delayed_; + static bool WeightedEdgeCmp(const Edge* a, const Edge* b); + + set delayed_; }; /// Global state (file status, loaded rules) for a single run.