| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/flow_graph_optimizer.h" | 5 #include "vm/flow_graph_optimizer.h" |
| 6 | 6 |
| 7 #include "vm/bit_vector.h" | 7 #include "vm/bit_vector.h" |
| 8 #include "vm/cha.h" | 8 #include "vm/cha.h" |
| 9 #include "vm/cpu.h" | 9 #include "vm/cpu.h" |
| 10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
| (...skipping 4713 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4724 | 4724 |
| 4725 #if defined(TARGET_ARCH_ARM) || defined(TARGET_ARCH_IA32) | 4725 #if defined(TARGET_ARCH_ARM) || defined(TARGET_ARCH_IA32) |
| 4726 // Smi widening pass is only meaningful on platforms where Smi | 4726 // Smi widening pass is only meaningful on platforms where Smi |
| 4727 // is smaller than 32bit. For now only support it on ARM and ia32. | 4727 // is smaller than 32bit. For now only support it on ARM and ia32. |
| 4728 | 4728 |
| 4729 class DefinitionWorklist : public ValueObject { | 4729 class DefinitionWorklist : public ValueObject { |
| 4730 public: | 4730 public: |
| 4731 DefinitionWorklist(FlowGraph* flow_graph, | 4731 DefinitionWorklist(FlowGraph* flow_graph, |
| 4732 intptr_t initial_capacity) | 4732 intptr_t initial_capacity) |
| 4733 : defs_(initial_capacity), | 4733 : defs_(initial_capacity), |
| 4734 contains_vector_(new BitVector(flow_graph->current_ssa_temp_index())) { | 4734 contains_vector_(new(flow_graph->isolate()) BitVector( |
| 4735 flow_graph->isolate(), flow_graph->current_ssa_temp_index())) { |
| 4735 } | 4736 } |
| 4736 | 4737 |
| 4737 void Add(Definition* defn) { | 4738 void Add(Definition* defn) { |
| 4738 if (!Contains(defn)) { | 4739 if (!Contains(defn)) { |
| 4739 defs_.Add(defn); | 4740 defs_.Add(defn); |
| 4740 contains_vector_->Add(defn->ssa_temp_index()); | 4741 contains_vector_->Add(defn->ssa_temp_index()); |
| 4741 } | 4742 } |
| 4742 } | 4743 } |
| 4743 | 4744 |
| 4744 bool Contains(Definition* defn) const { | 4745 bool Contains(Definition* defn) const { |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4829 } | 4830 } |
| 4830 | 4831 |
| 4831 // Step 3. For each candidate transitively collect all other BinarySmiOpInstr | 4832 // Step 3. For each candidate transitively collect all other BinarySmiOpInstr |
| 4832 // and PhiInstr that depend on it and that it depends on and count amount of | 4833 // and PhiInstr that depend on it and that it depends on and count amount of |
| 4833 // untagging operations that we save in assumption that this whole graph of | 4834 // untagging operations that we save in assumption that this whole graph of |
| 4834 // values is using kUnboxedInt32 representation instead of kTagged. | 4835 // values is using kUnboxedInt32 representation instead of kTagged. |
| 4835 // Convert those graphs that have positive gain to kUnboxedInt32. | 4836 // Convert those graphs that have positive gain to kUnboxedInt32. |
| 4836 | 4837 |
| 4837 // BitVector containing SSA indexes of all processed definitions. Used to skip | 4838 // BitVector containing SSA indexes of all processed definitions. Used to skip |
| 4838 // those candidates that belong to dependency graph of another candidate. | 4839 // those candidates that belong to dependency graph of another candidate. |
| 4839 BitVector* processed = new BitVector(flow_graph_->current_ssa_temp_index()); | 4840 BitVector* processed = |
| 4841 new(I) BitVector(I, flow_graph_->current_ssa_temp_index()); |
| 4840 | 4842 |
| 4841 // Worklist used to collect dependency graph. | 4843 // Worklist used to collect dependency graph. |
| 4842 DefinitionWorklist worklist(flow_graph_, candidates.length()); | 4844 DefinitionWorklist worklist(flow_graph_, candidates.length()); |
| 4843 for (intptr_t i = 0; i < candidates.length(); i++) { | 4845 for (intptr_t i = 0; i < candidates.length(); i++) { |
| 4844 BinarySmiOpInstr* op = candidates[i]; | 4846 BinarySmiOpInstr* op = candidates[i]; |
| 4845 if (op->WasEliminated() || processed->Contains(op->ssa_temp_index())) { | 4847 if (op->WasEliminated() || processed->Contains(op->ssa_temp_index())) { |
| 4846 continue; | 4848 continue; |
| 4847 } | 4849 } |
| 4848 | 4850 |
| 4849 if (FLAG_trace_smi_widening) { | 4851 if (FLAG_trace_smi_widening) { |
| (...skipping 846 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5696 AliasedSet(Isolate* isolate, | 5698 AliasedSet(Isolate* isolate, |
| 5697 ZoneGrowableArray<Place*>* places, | 5699 ZoneGrowableArray<Place*>* places, |
| 5698 PhiPlaceMoves* phi_moves) | 5700 PhiPlaceMoves* phi_moves) |
| 5699 : isolate_(isolate), | 5701 : isolate_(isolate), |
| 5700 places_(*places), | 5702 places_(*places), |
| 5701 phi_moves_(phi_moves), | 5703 phi_moves_(phi_moves), |
| 5702 aliases_(5), | 5704 aliases_(5), |
| 5703 aliases_map_(), | 5705 aliases_map_(), |
| 5704 representatives_(), | 5706 representatives_(), |
| 5705 killed_(), | 5707 killed_(), |
| 5706 aliased_by_effects_(new(isolate) BitVector(places->length())) { | 5708 aliased_by_effects_(new(isolate) BitVector(isolate, places->length())) { |
| 5707 InsertAlias(Place::CreateAnyInstanceAnyIndexAlias(isolate_, | 5709 InsertAlias(Place::CreateAnyInstanceAnyIndexAlias(isolate_, |
| 5708 kAnyInstanceAnyIndexAlias)); | 5710 kAnyInstanceAnyIndexAlias)); |
| 5709 for (intptr_t i = 0; i < places_.length(); i++) { | 5711 for (intptr_t i = 0; i < places_.length(); i++) { |
| 5710 AddRepresentative(places_[i]); | 5712 AddRepresentative(places_[i]); |
| 5711 } | 5713 } |
| 5712 ComputeKillSets(); | 5714 ComputeKillSets(); |
| 5713 } | 5715 } |
| 5714 | 5716 |
| 5715 intptr_t LookupAliasId(const Place& alias) { | 5717 intptr_t LookupAliasId(const Place& alias) { |
| 5716 const Place* result = aliases_map_.Lookup(&alias); | 5718 const Place* result = aliases_map_.Lookup(&alias); |
| (...skipping 154 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5871 } | 5873 } |
| 5872 | 5874 |
| 5873 BitVector* EnsureSet(GrowableArray<BitVector*>* sets, | 5875 BitVector* EnsureSet(GrowableArray<BitVector*>* sets, |
| 5874 intptr_t alias) { | 5876 intptr_t alias) { |
| 5875 while (sets->length() <= alias) { | 5877 while (sets->length() <= alias) { |
| 5876 sets->Add(NULL); | 5878 sets->Add(NULL); |
| 5877 } | 5879 } |
| 5878 | 5880 |
| 5879 BitVector* set = (*sets)[alias]; | 5881 BitVector* set = (*sets)[alias]; |
| 5880 if (set == NULL) { | 5882 if (set == NULL) { |
| 5881 (*sets)[alias] = set = new(isolate_) BitVector(max_place_id()); | 5883 (*sets)[alias] = set = new(isolate_) BitVector(isolate_, max_place_id()); |
| 5882 } | 5884 } |
| 5883 return set; | 5885 return set; |
| 5884 } | 5886 } |
| 5885 | 5887 |
| 5886 void AddAllRepresentatives(const Place* to, intptr_t from) { | 5888 void AddAllRepresentatives(const Place* to, intptr_t from) { |
| 5887 AddAllRepresentatives(to->id(), from); | 5889 AddAllRepresentatives(to->id(), from); |
| 5888 } | 5890 } |
| 5889 | 5891 |
| 5890 void AddAllRepresentatives(intptr_t to, intptr_t from) { | 5892 void AddAllRepresentatives(intptr_t to, intptr_t from) { |
| 5891 BitVector* from_set = GetRepresentativesSet(from); | 5893 BitVector* from_set = GetRepresentativesSet(from); |
| (...skipping 405 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6297 exposed_values_(graph_->preorder().length()), | 6299 exposed_values_(graph_->preorder().length()), |
| 6298 out_values_(graph_->preorder().length()), | 6300 out_values_(graph_->preorder().length()), |
| 6299 phis_(5), | 6301 phis_(5), |
| 6300 worklist_(5), | 6302 worklist_(5), |
| 6301 congruency_worklist_(6), | 6303 congruency_worklist_(6), |
| 6302 in_worklist_(NULL), | 6304 in_worklist_(NULL), |
| 6303 forwarded_(false) { | 6305 forwarded_(false) { |
| 6304 const intptr_t num_blocks = graph_->preorder().length(); | 6306 const intptr_t num_blocks = graph_->preorder().length(); |
| 6305 for (intptr_t i = 0; i < num_blocks; i++) { | 6307 for (intptr_t i = 0; i < num_blocks; i++) { |
| 6306 out_.Add(NULL); | 6308 out_.Add(NULL); |
| 6307 gen_.Add(new(I) BitVector(aliased_set_->max_place_id())); | 6309 gen_.Add(new(I) BitVector(I, aliased_set_->max_place_id())); |
| 6308 kill_.Add(new(I) BitVector(aliased_set_->max_place_id())); | 6310 kill_.Add(new(I) BitVector(I, aliased_set_->max_place_id())); |
| 6309 in_.Add(new(I) BitVector(aliased_set_->max_place_id())); | 6311 in_.Add(new(I) BitVector(I, aliased_set_->max_place_id())); |
| 6310 | 6312 |
| 6311 exposed_values_.Add(NULL); | 6313 exposed_values_.Add(NULL); |
| 6312 out_values_.Add(NULL); | 6314 out_values_.Add(NULL); |
| 6313 } | 6315 } |
| 6314 } | 6316 } |
| 6315 | 6317 |
| 6316 ~LoadOptimizer() { | 6318 ~LoadOptimizer() { |
| 6317 aliased_set_->RollbackAliasedIdentites(); | 6319 aliased_set_->RollbackAliasedIdentites(); |
| 6318 } | 6320 } |
| 6319 | 6321 |
| (...skipping 227 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6547 | 6549 |
| 6548 out->Remove(to); | 6550 out->Remove(to); |
| 6549 } | 6551 } |
| 6550 | 6552 |
| 6551 out->AddAll(forwarded_loads); | 6553 out->AddAll(forwarded_loads); |
| 6552 } | 6554 } |
| 6553 | 6555 |
| 6554 // Compute OUT sets by propagating them iteratively until fix point | 6556 // Compute OUT sets by propagating them iteratively until fix point |
| 6555 // is reached. | 6557 // is reached. |
| 6556 void ComputeOutSets() { | 6558 void ComputeOutSets() { |
| 6557 BitVector* temp = new(I) BitVector(aliased_set_->max_place_id()); | 6559 BitVector* temp = new(I) BitVector(I, aliased_set_->max_place_id()); |
| 6558 BitVector* forwarded_loads = new(I) BitVector(aliased_set_->max_place_id()); | 6560 BitVector* forwarded_loads = |
| 6559 BitVector* temp_out = new(I) BitVector(aliased_set_->max_place_id()); | 6561 new(I) BitVector(I, aliased_set_->max_place_id()); |
| 6562 BitVector* temp_out = new(I) BitVector(I, aliased_set_->max_place_id()); |
| 6560 | 6563 |
| 6561 bool changed = true; | 6564 bool changed = true; |
| 6562 while (changed) { | 6565 while (changed) { |
| 6563 changed = false; | 6566 changed = false; |
| 6564 | 6567 |
| 6565 for (BlockIterator block_it = graph_->reverse_postorder_iterator(); | 6568 for (BlockIterator block_it = graph_->reverse_postorder_iterator(); |
| 6566 !block_it.Done(); | 6569 !block_it.Done(); |
| 6567 block_it.Advance()) { | 6570 block_it.Advance()) { |
| 6568 BlockEntryInstr* block = block_it.Current(); | 6571 BlockEntryInstr* block = block_it.Current(); |
| 6569 | 6572 |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6601 if (!temp->Equals(*block_in) || (block_out == NULL)) { | 6604 if (!temp->Equals(*block_in) || (block_out == NULL)) { |
| 6602 // If IN set has changed propagate the change to OUT set. | 6605 // If IN set has changed propagate the change to OUT set. |
| 6603 block_in->CopyFrom(temp); | 6606 block_in->CopyFrom(temp); |
| 6604 | 6607 |
| 6605 temp->RemoveAll(block_kill); | 6608 temp->RemoveAll(block_kill); |
| 6606 temp->AddAll(block_gen); | 6609 temp->AddAll(block_gen); |
| 6607 | 6610 |
| 6608 if ((block_out == NULL) || !block_out->Equals(*temp)) { | 6611 if ((block_out == NULL) || !block_out->Equals(*temp)) { |
| 6609 if (block_out == NULL) { | 6612 if (block_out == NULL) { |
| 6610 block_out = out_[preorder_number] = | 6613 block_out = out_[preorder_number] = |
| 6611 new(I) BitVector(aliased_set_->max_place_id()); | 6614 new(I) BitVector(I, aliased_set_->max_place_id()); |
| 6612 } | 6615 } |
| 6613 block_out->CopyFrom(temp); | 6616 block_out->CopyFrom(temp); |
| 6614 changed = true; | 6617 changed = true; |
| 6615 } | 6618 } |
| 6616 } | 6619 } |
| 6617 } | 6620 } |
| 6618 } | 6621 } |
| 6619 } | 6622 } |
| 6620 | 6623 |
| 6621 // Compute out_values mappings by propagating them in reverse postorder once | 6624 // Compute out_values mappings by propagating them in reverse postorder once |
| (...skipping 116 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6738 new(I) ZoneGrowableArray<BitVector*>(loop_headers.length()); | 6741 new(I) ZoneGrowableArray<BitVector*>(loop_headers.length()); |
| 6739 | 6742 |
| 6740 for (intptr_t i = 0; i < loop_headers.length(); i++) { | 6743 for (intptr_t i = 0; i < loop_headers.length(); i++) { |
| 6741 BlockEntryInstr* header = loop_headers[i]; | 6744 BlockEntryInstr* header = loop_headers[i]; |
| 6742 BlockEntryInstr* pre_header = FindPreHeader(header); | 6745 BlockEntryInstr* pre_header = FindPreHeader(header); |
| 6743 if (pre_header == NULL) { | 6746 if (pre_header == NULL) { |
| 6744 invariant_loads->Add(NULL); | 6747 invariant_loads->Add(NULL); |
| 6745 continue; | 6748 continue; |
| 6746 } | 6749 } |
| 6747 | 6750 |
| 6748 BitVector* loop_gen = new(I) BitVector(aliased_set_->max_place_id()); | 6751 BitVector* loop_gen = new(I) BitVector(I, aliased_set_->max_place_id()); |
| 6749 for (BitVector::Iterator loop_it(header->loop_info()); | 6752 for (BitVector::Iterator loop_it(header->loop_info()); |
| 6750 !loop_it.Done(); | 6753 !loop_it.Done(); |
| 6751 loop_it.Advance()) { | 6754 loop_it.Advance()) { |
| 6752 const intptr_t preorder_number = loop_it.Current(); | 6755 const intptr_t preorder_number = loop_it.Current(); |
| 6753 loop_gen->AddAll(gen_[preorder_number]); | 6756 loop_gen->AddAll(gen_[preorder_number]); |
| 6754 } | 6757 } |
| 6755 | 6758 |
| 6756 for (BitVector::Iterator loop_it(header->loop_info()); | 6759 for (BitVector::Iterator loop_it(header->loop_info()); |
| 6757 !loop_it.Done(); | 6760 !loop_it.Done(); |
| 6758 loop_it.Advance()) { | 6761 loop_it.Advance()) { |
| (...skipping 131 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6890 // Eliminate it as redundant if this is the case. | 6893 // Eliminate it as redundant if this is the case. |
| 6891 // When analyzing phi operands assumes that only generated during | 6894 // When analyzing phi operands assumes that only generated during |
| 6892 // this load phase can be redundant. They can be distinguished because | 6895 // this load phase can be redundant. They can be distinguished because |
| 6893 // they are not marked alive. | 6896 // they are not marked alive. |
| 6894 // TODO(vegorov): move this into a separate phase over all phis. | 6897 // TODO(vegorov): move this into a separate phase over all phis. |
| 6895 bool EliminateRedundantPhi(PhiInstr* phi) { | 6898 bool EliminateRedundantPhi(PhiInstr* phi) { |
| 6896 Definition* value = NULL; // Possible value of this phi. | 6899 Definition* value = NULL; // Possible value of this phi. |
| 6897 | 6900 |
| 6898 worklist_.Clear(); | 6901 worklist_.Clear(); |
| 6899 if (in_worklist_ == NULL) { | 6902 if (in_worklist_ == NULL) { |
| 6900 in_worklist_ = new(I) BitVector(graph_->current_ssa_temp_index()); | 6903 in_worklist_ = new(I) BitVector(I, graph_->current_ssa_temp_index()); |
| 6901 } else { | 6904 } else { |
| 6902 in_worklist_->Clear(); | 6905 in_worklist_->Clear(); |
| 6903 } | 6906 } |
| 6904 | 6907 |
| 6905 worklist_.Add(phi); | 6908 worklist_.Add(phi); |
| 6906 in_worklist_->Add(phi->ssa_temp_index()); | 6909 in_worklist_->Add(phi->ssa_temp_index()); |
| 6907 | 6910 |
| 6908 for (intptr_t i = 0; i < worklist_.length(); i++) { | 6911 for (intptr_t i = 0; i < worklist_.length(); i++) { |
| 6909 PhiInstr* phi = worklist_[i]; | 6912 PhiInstr* phi = worklist_[i]; |
| 6910 | 6913 |
| (...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7013 } | 7016 } |
| 7014 | 7017 |
| 7015 // Replace the given phi with another if they are congruent. | 7018 // Replace the given phi with another if they are congruent. |
| 7016 // Returns true if succeeds. | 7019 // Returns true if succeeds. |
| 7017 bool ReplacePhiWith(PhiInstr* phi, PhiInstr* replacement) { | 7020 bool ReplacePhiWith(PhiInstr* phi, PhiInstr* replacement) { |
| 7018 ASSERT(phi->InputCount() == replacement->InputCount()); | 7021 ASSERT(phi->InputCount() == replacement->InputCount()); |
| 7019 ASSERT(phi->block() == replacement->block()); | 7022 ASSERT(phi->block() == replacement->block()); |
| 7020 | 7023 |
| 7021 congruency_worklist_.Clear(); | 7024 congruency_worklist_.Clear(); |
| 7022 if (in_worklist_ == NULL) { | 7025 if (in_worklist_ == NULL) { |
| 7023 in_worklist_ = new(I) BitVector(graph_->current_ssa_temp_index()); | 7026 in_worklist_ = new(I) BitVector(I, graph_->current_ssa_temp_index()); |
| 7024 } else { | 7027 } else { |
| 7025 in_worklist_->Clear(); | 7028 in_worklist_->Clear(); |
| 7026 } | 7029 } |
| 7027 | 7030 |
| 7028 // During the comparison worklist contains pairs of definitions to be | 7031 // During the comparison worklist contains pairs of definitions to be |
| 7029 // compared. | 7032 // compared. |
| 7030 if (!AddPairToCongruencyWorklist(phi, replacement)) { | 7033 if (!AddPairToCongruencyWorklist(phi, replacement)) { |
| 7031 return false; | 7034 return false; |
| 7032 } | 7035 } |
| 7033 | 7036 |
| (...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7225 case Instruction::kStoreStaticField: | 7228 case Instruction::kStoreStaticField: |
| 7226 return true; | 7229 return true; |
| 7227 default: | 7230 default: |
| 7228 UNREACHABLE(); | 7231 UNREACHABLE(); |
| 7229 return false; | 7232 return false; |
| 7230 } | 7233 } |
| 7231 } | 7234 } |
| 7232 | 7235 |
| 7233 virtual void ComputeInitialSets() { | 7236 virtual void ComputeInitialSets() { |
| 7234 Isolate* isolate = graph_->isolate(); | 7237 Isolate* isolate = graph_->isolate(); |
| 7235 BitVector* all_places = new(isolate) BitVector( | 7238 BitVector* all_places = new(isolate) BitVector(isolate, |
| 7236 aliased_set_->max_place_id()); | 7239 aliased_set_->max_place_id()); |
| 7237 all_places->SetAll(); | 7240 all_places->SetAll(); |
| 7238 for (BlockIterator block_it = graph_->postorder_iterator(); | 7241 for (BlockIterator block_it = graph_->postorder_iterator(); |
| 7239 !block_it.Done(); | 7242 !block_it.Done(); |
| 7240 block_it.Advance()) { | 7243 block_it.Advance()) { |
| 7241 BlockEntryInstr* block = block_it.Current(); | 7244 BlockEntryInstr* block = block_it.Current(); |
| 7242 const intptr_t postorder_number = block->postorder_number(); | 7245 const intptr_t postorder_number = block->postorder_number(); |
| 7243 | 7246 |
| 7244 BitVector* kill = kill_[postorder_number]; | 7247 BitVector* kill = kill_[postorder_number]; |
| 7245 BitVector* live_in = live_in_[postorder_number]; | 7248 BitVector* live_in = live_in_[postorder_number]; |
| (...skipping 321 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7567 } | 7570 } |
| 7568 | 7571 |
| 7569 | 7572 |
| 7570 ConstantPropagator::ConstantPropagator( | 7573 ConstantPropagator::ConstantPropagator( |
| 7571 FlowGraph* graph, | 7574 FlowGraph* graph, |
| 7572 const GrowableArray<BlockEntryInstr*>& ignored) | 7575 const GrowableArray<BlockEntryInstr*>& ignored) |
| 7573 : FlowGraphVisitor(ignored), | 7576 : FlowGraphVisitor(ignored), |
| 7574 graph_(graph), | 7577 graph_(graph), |
| 7575 unknown_(Object::unknown_constant()), | 7578 unknown_(Object::unknown_constant()), |
| 7576 non_constant_(Object::non_constant()), | 7579 non_constant_(Object::non_constant()), |
| 7577 reachable_(new(graph->isolate()) BitVector(graph->preorder().length())), | 7580 reachable_(new(graph->isolate()) BitVector( |
| 7581 graph->isolate(), graph->preorder().length())), |
| 7578 definition_marks_(new(graph->isolate()) BitVector( | 7582 definition_marks_(new(graph->isolate()) BitVector( |
| 7579 graph->max_virtual_register_number())), | 7583 graph->isolate(), graph->max_virtual_register_number())), |
| 7580 block_worklist_(), | 7584 block_worklist_(), |
| 7581 definition_worklist_() {} | 7585 definition_worklist_() {} |
| 7582 | 7586 |
| 7583 | 7587 |
| 7584 void ConstantPropagator::Optimize(FlowGraph* graph) { | 7588 void ConstantPropagator::Optimize(FlowGraph* graph) { |
| 7585 GrowableArray<BlockEntryInstr*> ignored; | 7589 GrowableArray<BlockEntryInstr*> ignored; |
| 7586 ConstantPropagator cp(graph, ignored); | 7590 ConstantPropagator cp(graph, ignored); |
| 7587 cp.Analyze(); | 7591 cp.Analyze(); |
| 7588 cp.Transform(); | 7592 cp.Transform(); |
| 7589 } | 7593 } |
| (...skipping 1359 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 8949 current = current->next()->AsGoto()->successor(); | 8953 current = current->next()->AsGoto()->successor(); |
| 8950 } | 8954 } |
| 8951 return current; | 8955 return current; |
| 8952 } | 8956 } |
| 8953 | 8957 |
| 8954 | 8958 |
| 8955 void ConstantPropagator::EliminateRedundantBranches() { | 8959 void ConstantPropagator::EliminateRedundantBranches() { |
| 8956 // Canonicalize branches that have no side-effects and where true- and | 8960 // Canonicalize branches that have no side-effects and where true- and |
| 8957 // false-targets are the same. | 8961 // false-targets are the same. |
| 8958 bool changed = false; | 8962 bool changed = false; |
| 8959 BitVector* empty_blocks = new(I) BitVector(graph_->preorder().length()); | 8963 BitVector* empty_blocks = new(I) BitVector(I, graph_->preorder().length()); |
| 8960 for (BlockIterator b = graph_->postorder_iterator(); | 8964 for (BlockIterator b = graph_->postorder_iterator(); |
| 8961 !b.Done(); | 8965 !b.Done(); |
| 8962 b.Advance()) { | 8966 b.Advance()) { |
| 8963 BlockEntryInstr* block = b.Current(); | 8967 BlockEntryInstr* block = b.Current(); |
| 8964 BranchInstr* branch = block->last_instruction()->AsBranch(); | 8968 BranchInstr* branch = block->last_instruction()->AsBranch(); |
| 8965 empty_blocks->Clear(); | 8969 empty_blocks->Clear(); |
| 8966 if ((branch != NULL) && branch->Effects().IsNone()) { | 8970 if ((branch != NULL) && branch->Effects().IsNone()) { |
| 8967 ASSERT(branch->previous() != NULL); // Not already eliminated. | 8971 ASSERT(branch->previous() != NULL); // Not already eliminated. |
| 8968 BlockEntryInstr* if_true = | 8972 BlockEntryInstr* if_true = |
| 8969 FindFirstNonEmptySuccessor(branch->true_successor(), empty_blocks); | 8973 FindFirstNonEmptySuccessor(branch->true_successor(), empty_blocks); |
| (...skipping 1146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 10116 | 10120 |
| 10117 // Insert materializations at environment uses. | 10121 // Insert materializations at environment uses. |
| 10118 for (intptr_t i = 0; i < exits_collector_.exits().length(); i++) { | 10122 for (intptr_t i = 0; i < exits_collector_.exits().length(); i++) { |
| 10119 CreateMaterializationAt( | 10123 CreateMaterializationAt( |
| 10120 exits_collector_.exits()[i], alloc, alloc->cls(), *slots); | 10124 exits_collector_.exits()[i], alloc, alloc->cls(), *slots); |
| 10121 } | 10125 } |
| 10122 } | 10126 } |
| 10123 | 10127 |
| 10124 | 10128 |
| 10125 } // namespace dart | 10129 } // namespace dart |
| OLD | NEW |