blob: 6905ef589ff56c11b18ac6717969d726aee56577 [file] [log] [blame]
Ben Murdochb8a8cc12014-11-26 15:28:44 +00001// Copyright 2013 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Ben Murdoch4a90d5f2016-03-22 12:00:34 +00005#include "src/compiler/control-builders.h"
Ben Murdochb8a8cc12014-11-26 15:28:44 +00006
7namespace v8 {
8namespace internal {
9namespace compiler {
10
11
Emily Bernierd0a1eb72015-03-24 16:35:39 -040012void IfBuilder::If(Node* condition, BranchHint hint) {
13 builder_->NewBranch(condition, hint);
Ben Murdochb8a8cc12014-11-26 15:28:44 +000014 else_environment_ = environment()->CopyForConditional();
15}
16
17
18void IfBuilder::Then() { builder_->NewIfTrue(); }
19
20
21void IfBuilder::Else() {
22 builder_->NewMerge();
23 then_environment_ = environment();
24 set_environment(else_environment_);
25 builder_->NewIfFalse();
26}
27
28
29void IfBuilder::End() {
30 then_environment_->Merge(environment());
31 set_environment(then_environment_);
32}
33
34
Ben Murdoch4a90d5f2016-03-22 12:00:34 +000035void LoopBuilder::BeginLoop(BitVector* assigned, bool is_osr) {
36 loop_environment_ = environment()->CopyForLoop(assigned, is_osr);
Ben Murdochb8a8cc12014-11-26 15:28:44 +000037 continue_environment_ = environment()->CopyAsUnreachable();
38 break_environment_ = environment()->CopyAsUnreachable();
39}
40
41
42void LoopBuilder::Continue() {
43 continue_environment_->Merge(environment());
44 environment()->MarkAsUnreachable();
45}
46
47
48void LoopBuilder::Break() {
49 break_environment_->Merge(environment());
50 environment()->MarkAsUnreachable();
51}
52
53
54void LoopBuilder::EndBody() {
55 continue_environment_->Merge(environment());
56 set_environment(continue_environment_);
57}
58
59
60void LoopBuilder::EndLoop() {
61 loop_environment_->Merge(environment());
62 set_environment(break_environment_);
63}
64
65
66void LoopBuilder::BreakUnless(Node* condition) {
67 IfBuilder control_if(builder_);
68 control_if.If(condition);
69 control_if.Then();
70 control_if.Else();
71 Break();
72 control_if.End();
73}
74
75
Ben Murdoch4a90d5f2016-03-22 12:00:34 +000076void LoopBuilder::BreakWhen(Node* condition) {
77 IfBuilder control_if(builder_);
78 control_if.If(condition);
79 control_if.Then();
80 Break();
81 control_if.Else();
82 control_if.End();
83}
84
85
Ben Murdochb8a8cc12014-11-26 15:28:44 +000086void SwitchBuilder::BeginSwitch() {
87 body_environment_ = environment()->CopyAsUnreachable();
88 label_environment_ = environment()->CopyAsUnreachable();
89 break_environment_ = environment()->CopyAsUnreachable();
Ben Murdochb8a8cc12014-11-26 15:28:44 +000090}
91
92
93void SwitchBuilder::BeginLabel(int index, Node* condition) {
94 builder_->NewBranch(condition);
95 label_environment_ = environment()->CopyForConditional();
96 builder_->NewIfTrue();
97 body_environments_[index] = environment();
98}
99
100
101void SwitchBuilder::EndLabel() {
102 set_environment(label_environment_);
103 builder_->NewIfFalse();
104}
105
106
107void SwitchBuilder::DefaultAt(int index) {
108 label_environment_ = environment()->CopyAsUnreachable();
109 body_environments_[index] = environment();
110}
111
112
113void SwitchBuilder::BeginCase(int index) {
114 set_environment(body_environments_[index]);
115 environment()->Merge(body_environment_);
116}
117
118
119void SwitchBuilder::Break() {
120 break_environment_->Merge(environment());
121 environment()->MarkAsUnreachable();
122}
123
124
125void SwitchBuilder::EndCase() { body_environment_ = environment(); }
126
127
128void SwitchBuilder::EndSwitch() {
129 break_environment_->Merge(label_environment_);
130 break_environment_->Merge(environment());
131 set_environment(break_environment_);
132}
133
134
135void BlockBuilder::BeginBlock() {
136 break_environment_ = environment()->CopyAsUnreachable();
137}
138
139
140void BlockBuilder::Break() {
141 break_environment_->Merge(environment());
142 environment()->MarkAsUnreachable();
143}
144
145
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000146void BlockBuilder::BreakWhen(Node* condition, BranchHint hint) {
147 IfBuilder control_if(builder_);
148 control_if.If(condition, hint);
149 control_if.Then();
150 Break();
151 control_if.Else();
152 control_if.End();
153}
154
155
156void BlockBuilder::BreakUnless(Node* condition, BranchHint hint) {
157 IfBuilder control_if(builder_);
158 control_if.If(condition, hint);
159 control_if.Then();
160 control_if.Else();
161 Break();
162 control_if.End();
163}
164
165
Ben Murdochb8a8cc12014-11-26 15:28:44 +0000166void BlockBuilder::EndBlock() {
167 break_environment_->Merge(environment());
168 set_environment(break_environment_);
169}
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000170
171
172void TryCatchBuilder::BeginTry() {
173 exit_environment_ = environment()->CopyAsUnreachable();
174 catch_environment_ = environment()->CopyAsUnreachable();
175 catch_environment_->Push(the_hole());
Ben Murdochb8a8cc12014-11-26 15:28:44 +0000176}
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000177
178
179void TryCatchBuilder::Throw(Node* exception) {
180 environment()->Push(exception);
181 catch_environment_->Merge(environment());
182 environment()->Pop();
183 environment()->MarkAsUnreachable();
Ben Murdochb8a8cc12014-11-26 15:28:44 +0000184}
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000185
186
187void TryCatchBuilder::EndTry() {
188 exit_environment_->Merge(environment());
189 exception_node_ = catch_environment_->Pop();
190 set_environment(catch_environment_);
191}
192
193
194void TryCatchBuilder::EndCatch() {
195 exit_environment_->Merge(environment());
196 set_environment(exit_environment_);
197}
198
199
200void TryFinallyBuilder::BeginTry() {
201 finally_environment_ = environment()->CopyAsUnreachable();
202 finally_environment_->Push(the_hole());
203 finally_environment_->Push(the_hole());
204}
205
206
207void TryFinallyBuilder::LeaveTry(Node* token, Node* value) {
208 environment()->Push(value);
209 environment()->Push(token);
210 finally_environment_->Merge(environment());
211 environment()->Drop(2);
212}
213
214
215void TryFinallyBuilder::EndTry(Node* fallthrough_token, Node* value) {
216 environment()->Push(value);
217 environment()->Push(fallthrough_token);
218 finally_environment_->Merge(environment());
219 environment()->Drop(2);
220 token_node_ = finally_environment_->Pop();
221 value_node_ = finally_environment_->Pop();
222 set_environment(finally_environment_);
223}
224
225
226void TryFinallyBuilder::EndFinally() {
227 // Nothing to be done here.
228}
229
230} // namespace compiler
231} // namespace internal
232} // namespace v8