| Index: runtime/vm/flow_graph_optimizer.cc
|
| diff --git a/runtime/vm/flow_graph_optimizer.cc b/runtime/vm/flow_graph_optimizer.cc
|
| index 3d2d5479bd006545976fbaa3afae9591bfbc201a..d54972523febe22e51d2421d237a71259879af16 100644
|
| --- a/runtime/vm/flow_graph_optimizer.cc
|
| +++ b/runtime/vm/flow_graph_optimizer.cc
|
| @@ -5616,9 +5616,11 @@ class PhiPlaceMoves : public ZoneAllocated {
|
| class AliasedSet : public ZoneAllocated {
|
| public:
|
| AliasedSet(Isolate* isolate,
|
| + DirectChainedHashMap<PointerKeyValueTrait<Place> >* places_map,
|
| ZoneGrowableArray<Place*>* places,
|
| PhiPlaceMoves* phi_moves)
|
| : isolate_(isolate),
|
| + places_map_(places_map),
|
| places_(*places),
|
| phi_moves_(phi_moves),
|
| aliases_(5),
|
| @@ -5667,6 +5669,12 @@ class AliasedSet : public ZoneAllocated {
|
| *killed = GetKilledSet(
|
| LookupAliasId(places_[instr->place_id()]->ToAlias()));
|
| }
|
| + } else if (is_load && (place.kind() != Place::kNone)) {
|
| + const Place* canonical = LookupCanonical(&place);
|
| + if ((canonical != NULL) &&
|
| + (canonical->id() != instr->AsDefinition()->place_id())) {
|
| + instr->AsDefinition()->set_place_id(canonical->id());
|
| + }
|
| }
|
| return is_store;
|
| }
|
| @@ -5684,6 +5692,10 @@ class AliasedSet : public ZoneAllocated {
|
| return places_;
|
| }
|
|
|
| + Place* LookupCanonical(Place* place) const {
|
| + return places_map_->Lookup(place);
|
| + }
|
| +
|
| void PrintSet(BitVector* set) {
|
| bool comma = false;
|
| for (BitVector::Iterator it(set);
|
| @@ -6055,6 +6067,8 @@ class AliasedSet : public ZoneAllocated {
|
|
|
| Isolate* isolate_;
|
|
|
| + DirectChainedHashMap<PointerKeyValueTrait<Place> >* places_map_;
|
| +
|
| const ZoneGrowableArray<Place*>& places_;
|
|
|
| const PhiPlaceMoves* phi_moves_;
|
| @@ -6224,17 +6238,14 @@ static AliasedSet* NumberPlaces(
|
| PhiPlaceMoves* phi_moves = ComputePhiMoves(map, places);
|
|
|
| // Build aliasing sets mapping aliases to loads.
|
| - return new(isolate) AliasedSet(isolate, places, phi_moves);
|
| + return new(isolate) AliasedSet(isolate, map, places, phi_moves);
|
| }
|
|
|
|
|
| class LoadOptimizer : public ValueObject {
|
| public:
|
| - LoadOptimizer(FlowGraph* graph,
|
| - AliasedSet* aliased_set,
|
| - DirectChainedHashMap<PointerKeyValueTrait<Place> >* map)
|
| + LoadOptimizer(FlowGraph* graph, AliasedSet* aliased_set)
|
| : graph_(graph),
|
| - map_(map),
|
| aliased_set_(aliased_set),
|
| in_(graph_->preorder().length()),
|
| out_(graph_->preorder().length()),
|
| @@ -6280,7 +6291,7 @@ class LoadOptimizer : public ValueObject {
|
| // as loads from loaded context.
|
| // TODO(vegorov): renumber newly discovered congruences during the
|
| // forwarding to forward chains without running whole pass twice.
|
| - LoadOptimizer load_optimizer(graph, aliased_set, &map);
|
| + LoadOptimizer load_optimizer(graph, aliased_set);
|
| return load_optimizer.Optimize();
|
| }
|
| return false;
|
| @@ -6350,7 +6361,7 @@ class LoadOptimizer : public ValueObject {
|
| bool is_load = false, is_store = false;
|
| Place store_place(instr, &is_load, &is_store);
|
| ASSERT(!is_load && is_store);
|
| - Place* place = map_->Lookup(&store_place);
|
| + Place* place = aliased_set_->LookupCanonical(&store_place);
|
| if (place != NULL) {
|
| // Store has a corresponding numbered place that might have a
|
| // load. Try forwarding stored value to it.
|
|
|