Line data Source code
1 : // Copyright 2018 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/source-range-ast-visitor.h"
6 :
7 : #include "src/ast/ast-source-ranges.h"
8 :
9 : namespace v8 {
10 : namespace internal {
11 :
12 676 : SourceRangeAstVisitor::SourceRangeAstVisitor(uintptr_t stack_limit,
13 : Expression* root,
14 : SourceRangeMap* source_range_map)
15 : : AstTraversalVisitor(stack_limit, root),
16 1352 : source_range_map_(source_range_map) {}
17 :
18 1280 : void SourceRangeAstVisitor::VisitBlock(Block* stmt) {
19 1280 : AstTraversalVisitor::VisitBlock(stmt);
20 : ZonePtrList<Statement>* stmts = stmt->statements();
21 1280 : AstNodeSourceRanges* enclosingSourceRanges = source_range_map_->Find(stmt);
22 1280 : if (enclosingSourceRanges != nullptr) {
23 600 : CHECK(enclosingSourceRanges->HasRange(SourceRangeKind::kContinuation));
24 600 : MaybeRemoveLastContinuationRange(stmts);
25 : }
26 1280 : }
27 :
28 0 : void SourceRangeAstVisitor::VisitFunctionLiteral(FunctionLiteral* expr) {
29 1212 : AstTraversalVisitor::VisitFunctionLiteral(expr);
30 : ZonePtrList<Statement>* stmts = expr->body();
31 1212 : MaybeRemoveLastContinuationRange(stmts);
32 0 : }
33 :
34 17136 : bool SourceRangeAstVisitor::VisitNode(AstNode* node) {
35 17136 : AstNodeSourceRanges* range = source_range_map_->Find(node);
36 :
37 17136 : if (range == nullptr) return true;
38 2440 : if (!range->HasRange(SourceRangeKind::kContinuation)) return true;
39 :
40 : // Called in pre-order. In case of conflicting continuation ranges, only the
41 : // outermost range may survive.
42 :
43 2128 : SourceRange continuation = range->GetRange(SourceRangeKind::kContinuation);
44 2128 : if (continuation_positions_.find(continuation.start) !=
45 : continuation_positions_.end()) {
46 688 : range->RemoveContinuationRange();
47 : } else {
48 : continuation_positions_.emplace(continuation.start);
49 : }
50 :
51 : return true;
52 : }
53 :
54 1812 : void SourceRangeAstVisitor::MaybeRemoveLastContinuationRange(
55 : ZonePtrList<Statement>* statements) {
56 1812 : if (statements->is_empty()) return;
57 :
58 1324 : Statement* last_statement = statements->last();
59 : AstNodeSourceRanges* last_range = nullptr;
60 :
61 1972 : if (last_statement->IsExpressionStatement() &&
62 648 : last_statement->AsExpressionStatement()->expression()->IsThrow()) {
63 : // For ThrowStatement, source range is tied to Throw expression not
64 : // ExpressionStatement.
65 32 : last_range = source_range_map_->Find(
66 32 : last_statement->AsExpressionStatement()->expression());
67 : } else {
68 1292 : last_range = source_range_map_->Find(last_statement);
69 : }
70 :
71 1324 : if (last_range == nullptr) return;
72 :
73 580 : if (last_range->HasRange(SourceRangeKind::kContinuation)) {
74 580 : last_range->RemoveContinuationRange();
75 : }
76 : }
77 :
78 : } // namespace internal
79 122004 : } // namespace v8
|