blob: b39f7f1f0cb32617408fcef5ac09e5cadecadb35 [file] [log] [blame]
Ben Murdoch4a90d5f2016-03-22 12:00:34 +00001// Copyright 2015 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
5#include "src/ast/ast.h"
6#include "src/ast/ast-expression-rewriter.h"
7
8namespace v8 {
9namespace internal {
10
11// ----------------------------------------------------------------------------
12// Implementation of AstExpressionRewriter
13// The AST is traversed but no actual rewriting takes place, unless the
14// Visit methods are overriden in subclasses.
15
16#define REWRITE_THIS(node) \
17 do { \
18 if (!RewriteExpression(node)) return; \
19 } while (false)
20#define NOTHING() DCHECK_NULL(replacement_)
21
22
23void AstExpressionRewriter::VisitDeclarations(
24 ZoneList<Declaration*>* declarations) {
25 for (int i = 0; i < declarations->length(); i++) {
26 AST_REWRITE_LIST_ELEMENT(Declaration, declarations, i);
27 }
28}
29
30
31void AstExpressionRewriter::VisitStatements(ZoneList<Statement*>* statements) {
32 for (int i = 0; i < statements->length(); i++) {
33 AST_REWRITE_LIST_ELEMENT(Statement, statements, i);
34 // Not stopping when a jump statement is found.
35 }
36}
37
38
39void AstExpressionRewriter::VisitExpressions(
40 ZoneList<Expression*>* expressions) {
41 for (int i = 0; i < expressions->length(); i++) {
42 // The variable statement visiting code may pass NULL expressions
43 // to this code. Maybe this should be handled by introducing an
44 // undefined expression or literal? Revisit this code if this
45 // changes
46 if (expressions->at(i) != nullptr) {
47 AST_REWRITE_LIST_ELEMENT(Expression, expressions, i);
48 }
49 }
50}
51
52
53void AstExpressionRewriter::VisitVariableDeclaration(
54 VariableDeclaration* node) {
55 // Not visiting `proxy_`.
56 NOTHING();
57}
58
59
60void AstExpressionRewriter::VisitFunctionDeclaration(
61 FunctionDeclaration* node) {
62 // Not visiting `proxy_`.
63 AST_REWRITE_PROPERTY(FunctionLiteral, node, fun);
64}
65
66
67void AstExpressionRewriter::VisitImportDeclaration(ImportDeclaration* node) {
68 // Not visiting `proxy_`.
69 NOTHING();
70}
71
72
73void AstExpressionRewriter::VisitExportDeclaration(ExportDeclaration* node) {
74 // Not visiting `proxy_`.
75 NOTHING();
76}
77
78
79void AstExpressionRewriter::VisitBlock(Block* node) {
80 VisitStatements(node->statements());
81}
82
83
84void AstExpressionRewriter::VisitExpressionStatement(
85 ExpressionStatement* node) {
86 AST_REWRITE_PROPERTY(Expression, node, expression);
87}
88
89
90void AstExpressionRewriter::VisitEmptyStatement(EmptyStatement* node) {
91 NOTHING();
92}
93
94
95void AstExpressionRewriter::VisitSloppyBlockFunctionStatement(
96 SloppyBlockFunctionStatement* node) {
97 AST_REWRITE_PROPERTY(Statement, node, statement);
98}
99
100
101void AstExpressionRewriter::VisitIfStatement(IfStatement* node) {
102 AST_REWRITE_PROPERTY(Expression, node, condition);
103 AST_REWRITE_PROPERTY(Statement, node, then_statement);
104 AST_REWRITE_PROPERTY(Statement, node, else_statement);
105}
106
107
108void AstExpressionRewriter::VisitContinueStatement(ContinueStatement* node) {
109 NOTHING();
110}
111
112
113void AstExpressionRewriter::VisitBreakStatement(BreakStatement* node) {
114 NOTHING();
115}
116
117
118void AstExpressionRewriter::VisitReturnStatement(ReturnStatement* node) {
119 AST_REWRITE_PROPERTY(Expression, node, expression);
120}
121
122
123void AstExpressionRewriter::VisitWithStatement(WithStatement* node) {
124 AST_REWRITE_PROPERTY(Expression, node, expression);
125 AST_REWRITE_PROPERTY(Statement, node, statement);
126}
127
128
129void AstExpressionRewriter::VisitSwitchStatement(SwitchStatement* node) {
130 AST_REWRITE_PROPERTY(Expression, node, tag);
131 ZoneList<CaseClause*>* clauses = node->cases();
132 for (int i = 0; i < clauses->length(); i++) {
133 AST_REWRITE_LIST_ELEMENT(CaseClause, clauses, i);
134 }
135}
136
137
138void AstExpressionRewriter::VisitDoWhileStatement(DoWhileStatement* node) {
139 AST_REWRITE_PROPERTY(Expression, node, cond);
140 AST_REWRITE_PROPERTY(Statement, node, body);
141}
142
143
144void AstExpressionRewriter::VisitWhileStatement(WhileStatement* node) {
145 AST_REWRITE_PROPERTY(Expression, node, cond);
146 AST_REWRITE_PROPERTY(Statement, node, body);
147}
148
149
150void AstExpressionRewriter::VisitForStatement(ForStatement* node) {
151 if (node->init() != nullptr) {
152 AST_REWRITE_PROPERTY(Statement, node, init);
153 }
154 if (node->cond() != nullptr) {
155 AST_REWRITE_PROPERTY(Expression, node, cond);
156 }
157 if (node->next() != nullptr) {
158 AST_REWRITE_PROPERTY(Statement, node, next);
159 }
160 AST_REWRITE_PROPERTY(Statement, node, body);
161}
162
163
164void AstExpressionRewriter::VisitForInStatement(ForInStatement* node) {
165 AST_REWRITE_PROPERTY(Expression, node, each);
166 AST_REWRITE_PROPERTY(Expression, node, subject);
167 AST_REWRITE_PROPERTY(Statement, node, body);
168}
169
170
171void AstExpressionRewriter::VisitForOfStatement(ForOfStatement* node) {
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000172 AST_REWRITE_PROPERTY(Expression, node, assign_iterator);
173 AST_REWRITE_PROPERTY(Expression, node, next_result);
174 AST_REWRITE_PROPERTY(Expression, node, result_done);
175 AST_REWRITE_PROPERTY(Expression, node, assign_each);
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000176 AST_REWRITE_PROPERTY(Statement, node, body);
177}
178
179
180void AstExpressionRewriter::VisitTryCatchStatement(TryCatchStatement* node) {
181 AST_REWRITE_PROPERTY(Block, node, try_block);
182 // Not visiting the variable.
183 AST_REWRITE_PROPERTY(Block, node, catch_block);
184}
185
186
187void AstExpressionRewriter::VisitTryFinallyStatement(
188 TryFinallyStatement* node) {
189 AST_REWRITE_PROPERTY(Block, node, try_block);
190 AST_REWRITE_PROPERTY(Block, node, finally_block);
191}
192
193
194void AstExpressionRewriter::VisitDebuggerStatement(DebuggerStatement* node) {
195 NOTHING();
196}
197
198
199void AstExpressionRewriter::VisitFunctionLiteral(FunctionLiteral* node) {
200 REWRITE_THIS(node);
201 VisitDeclarations(node->scope()->declarations());
202 ZoneList<Statement*>* body = node->body();
203 if (body != nullptr) VisitStatements(body);
204}
205
206
207void AstExpressionRewriter::VisitClassLiteral(ClassLiteral* node) {
208 REWRITE_THIS(node);
209 // Not visiting `class_variable_proxy_`.
210 if (node->extends() != nullptr) {
211 AST_REWRITE_PROPERTY(Expression, node, extends);
212 }
213 AST_REWRITE_PROPERTY(FunctionLiteral, node, constructor);
214 ZoneList<typename ClassLiteral::Property*>* properties = node->properties();
215 for (int i = 0; i < properties->length(); i++) {
216 VisitObjectLiteralProperty(properties->at(i));
217 }
218}
219
220
221void AstExpressionRewriter::VisitNativeFunctionLiteral(
222 NativeFunctionLiteral* node) {
223 REWRITE_THIS(node);
224 NOTHING();
225}
226
227
228void AstExpressionRewriter::VisitConditional(Conditional* node) {
229 REWRITE_THIS(node);
230 AST_REWRITE_PROPERTY(Expression, node, condition);
231 AST_REWRITE_PROPERTY(Expression, node, then_expression);
232 AST_REWRITE_PROPERTY(Expression, node, else_expression);
233}
234
235
236void AstExpressionRewriter::VisitVariableProxy(VariableProxy* node) {
237 REWRITE_THIS(node);
238 NOTHING();
239}
240
241
242void AstExpressionRewriter::VisitLiteral(Literal* node) {
243 REWRITE_THIS(node);
244 NOTHING();
245}
246
247
248void AstExpressionRewriter::VisitRegExpLiteral(RegExpLiteral* node) {
249 REWRITE_THIS(node);
250 NOTHING();
251}
252
253
254void AstExpressionRewriter::VisitObjectLiteral(ObjectLiteral* node) {
255 REWRITE_THIS(node);
256 ZoneList<typename ObjectLiteral::Property*>* properties = node->properties();
257 for (int i = 0; i < properties->length(); i++) {
258 VisitObjectLiteralProperty(properties->at(i));
259 }
260}
261
262
263void AstExpressionRewriter::VisitObjectLiteralProperty(
264 ObjectLiteralProperty* property) {
265 if (property == nullptr) return;
266 AST_REWRITE_PROPERTY(Expression, property, key);
267 AST_REWRITE_PROPERTY(Expression, property, value);
268}
269
270
271void AstExpressionRewriter::VisitArrayLiteral(ArrayLiteral* node) {
272 REWRITE_THIS(node);
273 VisitExpressions(node->values());
274}
275
276
277void AstExpressionRewriter::VisitAssignment(Assignment* node) {
278 REWRITE_THIS(node);
279 AST_REWRITE_PROPERTY(Expression, node, target);
280 AST_REWRITE_PROPERTY(Expression, node, value);
281}
282
283
284void AstExpressionRewriter::VisitYield(Yield* node) {
285 REWRITE_THIS(node);
286 AST_REWRITE_PROPERTY(Expression, node, generator_object);
287 AST_REWRITE_PROPERTY(Expression, node, expression);
288}
289
290
291void AstExpressionRewriter::VisitThrow(Throw* node) {
292 REWRITE_THIS(node);
293 AST_REWRITE_PROPERTY(Expression, node, exception);
294}
295
296
297void AstExpressionRewriter::VisitProperty(Property* node) {
298 REWRITE_THIS(node);
299 if (node == nullptr) return;
300 AST_REWRITE_PROPERTY(Expression, node, obj);
301 AST_REWRITE_PROPERTY(Expression, node, key);
302}
303
304
305void AstExpressionRewriter::VisitCall(Call* node) {
306 REWRITE_THIS(node);
307 AST_REWRITE_PROPERTY(Expression, node, expression);
308 VisitExpressions(node->arguments());
309}
310
311
312void AstExpressionRewriter::VisitCallNew(CallNew* node) {
313 REWRITE_THIS(node);
314 AST_REWRITE_PROPERTY(Expression, node, expression);
315 VisitExpressions(node->arguments());
316}
317
318
319void AstExpressionRewriter::VisitCallRuntime(CallRuntime* node) {
320 REWRITE_THIS(node);
321 VisitExpressions(node->arguments());
322}
323
324
325void AstExpressionRewriter::VisitUnaryOperation(UnaryOperation* node) {
326 REWRITE_THIS(node);
327 AST_REWRITE_PROPERTY(Expression, node, expression);
328}
329
330
331void AstExpressionRewriter::VisitCountOperation(CountOperation* node) {
332 REWRITE_THIS(node);
333 AST_REWRITE_PROPERTY(Expression, node, expression);
334}
335
336
337void AstExpressionRewriter::VisitBinaryOperation(BinaryOperation* node) {
338 REWRITE_THIS(node);
339 AST_REWRITE_PROPERTY(Expression, node, left);
340 AST_REWRITE_PROPERTY(Expression, node, right);
341}
342
343
344void AstExpressionRewriter::VisitCompareOperation(CompareOperation* node) {
345 REWRITE_THIS(node);
346 AST_REWRITE_PROPERTY(Expression, node, left);
347 AST_REWRITE_PROPERTY(Expression, node, right);
348}
349
350
351void AstExpressionRewriter::VisitSpread(Spread* node) {
352 REWRITE_THIS(node);
353 AST_REWRITE_PROPERTY(Expression, node, expression);
354}
355
356
357void AstExpressionRewriter::VisitThisFunction(ThisFunction* node) {
358 REWRITE_THIS(node);
359 NOTHING();
360}
361
362
363void AstExpressionRewriter::VisitSuperPropertyReference(
364 SuperPropertyReference* node) {
365 REWRITE_THIS(node);
366 AST_REWRITE_PROPERTY(VariableProxy, node, this_var);
367 AST_REWRITE_PROPERTY(Expression, node, home_object);
368}
369
370
371void AstExpressionRewriter::VisitSuperCallReference(SuperCallReference* node) {
372 REWRITE_THIS(node);
373 AST_REWRITE_PROPERTY(VariableProxy, node, this_var);
374 AST_REWRITE_PROPERTY(VariableProxy, node, new_target_var);
375 AST_REWRITE_PROPERTY(VariableProxy, node, this_function_var);
376}
377
378
379void AstExpressionRewriter::VisitCaseClause(CaseClause* node) {
380 if (!node->is_default()) {
381 AST_REWRITE_PROPERTY(Expression, node, label);
382 }
383 VisitStatements(node->statements());
384}
385
386
387void AstExpressionRewriter::VisitEmptyParentheses(EmptyParentheses* node) {
388 NOTHING();
389}
390
391
392void AstExpressionRewriter::VisitDoExpression(DoExpression* node) {
393 REWRITE_THIS(node);
394 AST_REWRITE_PROPERTY(Block, node, block);
395 AST_REWRITE_PROPERTY(VariableProxy, node, result);
396}
397
398
Ben Murdoch097c5b22016-05-18 11:27:45 +0100399void AstExpressionRewriter::VisitRewritableExpression(
400 RewritableExpression* node) {
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000401 REWRITE_THIS(node);
Ben Murdoch097c5b22016-05-18 11:27:45 +0100402 AST_REWRITE(Expression, node->expression(), node->Rewrite(replacement));
Ben Murdoch4a90d5f2016-03-22 12:00:34 +0000403}
404
405
406} // namespace internal
407} // namespace v8