Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(61)

Side by Side Diff: src/compiler/bytecode-loop-analysis.cc

Issue 2254493002: [interpreter] Use VisitForTest for loop conditions (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: rebase(line) golden file Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/compiler/bytecode-loop-analysis.h ('k') | src/interpreter/bytecode-generator.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 the V8 project authors. All rights reserved. 1 // Copyright 2016 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/compiler/bytecode-loop-analysis.h" 5 #include "src/compiler/bytecode-loop-analysis.h"
6 6
7 #include "src/compiler/bytecode-branch-analysis.h" 7 #include "src/compiler/bytecode-branch-analysis.h"
8 #include "src/interpreter/bytecode-array-iterator.h" 8 #include "src/interpreter/bytecode-array-iterator.h"
9 #include "src/objects-inl.h" 9 #include "src/objects-inl.h"
10 10
11 namespace v8 { 11 namespace v8 {
12 namespace internal { 12 namespace internal {
13 namespace compiler { 13 namespace compiler {
14 14
15 BytecodeLoopAnalysis::BytecodeLoopAnalysis( 15 BytecodeLoopAnalysis::BytecodeLoopAnalysis(
16 Handle<BytecodeArray> bytecode_array, 16 Handle<BytecodeArray> bytecode_array,
17 const BytecodeBranchAnalysis* branch_analysis, Zone* zone) 17 const BytecodeBranchAnalysis* branch_analysis, Zone* zone)
18 : bytecode_array_(bytecode_array), 18 : bytecode_array_(bytecode_array),
19 branch_analysis_(branch_analysis), 19 branch_analysis_(branch_analysis),
20 zone_(zone), 20 zone_(zone),
21 current_loop_offset_(-1),
22 found_current_backedge_(false),
21 backedge_to_header_(zone), 23 backedge_to_header_(zone),
22 loop_header_to_parent_(zone) {} 24 loop_header_to_parent_(zone) {}
23 25
24 void BytecodeLoopAnalysis::Analyze() { 26 void BytecodeLoopAnalysis::Analyze() {
25 current_loop_offset_ = -1; 27 current_loop_offset_ = -1;
28 found_current_backedge_ = false;
26 interpreter::BytecodeArrayIterator iterator(bytecode_array()); 29 interpreter::BytecodeArrayIterator iterator(bytecode_array());
27 while (!iterator.done()) { 30 while (!iterator.done()) {
28 interpreter::Bytecode bytecode = iterator.current_bytecode(); 31 interpreter::Bytecode bytecode = iterator.current_bytecode();
29 int current_offset = iterator.current_offset(); 32 int current_offset = iterator.current_offset();
30 if (branch_analysis_->backward_branches_target(current_offset)) { 33 if (branch_analysis_->backward_branches_target(current_offset)) {
31 AddLoopEntry(current_offset); 34 AddLoopEntry(current_offset);
32 } else if (interpreter::Bytecodes::IsJump(bytecode)) { 35 } else if (interpreter::Bytecodes::IsJump(bytecode)) {
33 AddBranch(current_offset, iterator.GetJumpTargetOffset()); 36 AddBranch(current_offset, iterator.GetJumpTargetOffset());
34 } 37 }
35 iterator.Advance(); 38 iterator.Advance();
36 } 39 }
37 } 40 }
38 41
39 void BytecodeLoopAnalysis::AddLoopEntry(int entry_offset) { 42 void BytecodeLoopAnalysis::AddLoopEntry(int entry_offset) {
43 if (found_current_backedge_) {
44 // We assume that all backedges of a loop must occur together and before
45 // another loop entry or an outer loop backedge.
46 // This is guaranteed by the invariants from AddBranch, such that every
47 // backedge must either go to the current loop or be the first of the
48 // backedges to the parent loop.
49 // Thus here, the current loop actually ended before and we have a loop
50 // with the same parent.
51 current_loop_offset_ = loop_header_to_parent_[current_loop_offset_];
52 found_current_backedge_ = false;
53 }
40 loop_header_to_parent_[entry_offset] = current_loop_offset_; 54 loop_header_to_parent_[entry_offset] = current_loop_offset_;
41 current_loop_offset_ = entry_offset; 55 current_loop_offset_ = entry_offset;
42 } 56 }
43 57
44 void BytecodeLoopAnalysis::AddBranch(int origin_offset, int target_offset) { 58 void BytecodeLoopAnalysis::AddBranch(int origin_offset, int target_offset) {
45 // If this is a backedge, record it and update the current loop to the parent. 59 // If this is a backedge, record it.
46 if (target_offset < origin_offset) { 60 if (target_offset < origin_offset) {
47 backedge_to_header_[origin_offset] = target_offset; 61 backedge_to_header_[origin_offset] = target_offset;
48 // Check that we are finishing the current loop. This assumes that 62 // Check whether this is actually a backedge of the outer loop and we have
49 // there is one backedge for each loop. 63 // already finished the current loop.
50 DCHECK_EQ(target_offset, current_loop_offset_); 64 if (target_offset < current_loop_offset_) {
51 current_loop_offset_ = loop_header_to_parent_[target_offset]; 65 DCHECK(found_current_backedge_);
66 int parent_offset = loop_header_to_parent_[current_loop_offset_];
67 DCHECK_EQ(target_offset, parent_offset);
68 current_loop_offset_ = parent_offset;
69 } else {
70 DCHECK_EQ(target_offset, current_loop_offset_);
71 found_current_backedge_ = true;
72 }
52 } 73 }
53 } 74 }
54 75
55 int BytecodeLoopAnalysis::GetLoopOffsetFor(int offset) const { 76 int BytecodeLoopAnalysis::GetLoopOffsetFor(int offset) const {
56 auto next_backedge = backedge_to_header_.lower_bound(offset); 77 auto next_backedge = backedge_to_header_.lower_bound(offset);
57 // If there is no next backedge => offset is not in a loop. 78 // If there is no next backedge => offset is not in a loop.
58 if (next_backedge == backedge_to_header_.end()) { 79 if (next_backedge == backedge_to_header_.end()) {
59 return -1; 80 return -1;
60 } 81 }
61 // If the header preceeds the offset, it is the backedge of the containing 82 // If the header preceeds the offset, it is the backedge of the containing
62 // loop. 83 // loop.
63 if (next_backedge->second <= offset) { 84 if (next_backedge->second <= offset) {
64 return next_backedge->second; 85 return next_backedge->second;
65 } 86 }
66 // Otherwise there is a nested loop after this offset. We just return the 87 // Otherwise there is a nested loop after this offset. We just return the
67 // parent of the next nested loop. 88 // parent of the next nested loop.
68 return loop_header_to_parent_.upper_bound(offset)->second; 89 return loop_header_to_parent_.upper_bound(offset)->second;
69 } 90 }
70 91
71 int BytecodeLoopAnalysis::GetParentLoopFor(int header_offset) const { 92 int BytecodeLoopAnalysis::GetParentLoopFor(int header_offset) const {
72 auto parent = loop_header_to_parent_.find(header_offset); 93 auto parent = loop_header_to_parent_.find(header_offset);
73 DCHECK(parent != loop_header_to_parent_.end()); 94 DCHECK(parent != loop_header_to_parent_.end());
74 return parent->second; 95 return parent->second;
75 } 96 }
76 97
77 } // namespace compiler 98 } // namespace compiler
78 } // namespace internal 99 } // namespace internal
79 } // namespace v8 100 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/bytecode-loop-analysis.h ('k') | src/interpreter/bytecode-generator.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698