| OLD | NEW |
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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/ast-graph-builder.h" | 5 #include "src/compiler/ast-graph-builder.h" |
| 6 | 6 |
| 7 #include "src/compiler.h" | 7 #include "src/compiler.h" |
| 8 #include "src/compiler/ast-loop-assignment-analyzer.h" | 8 #include "src/compiler/ast-loop-assignment-analyzer.h" |
| 9 #include "src/compiler/control-builders.h" | 9 #include "src/compiler/control-builders.h" |
| 10 #include "src/compiler/linkage.h" | 10 #include "src/compiler/linkage.h" |
| (...skipping 2666 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2677 case Variable::PARAMETER: | 2677 case Variable::PARAMETER: |
| 2678 case Variable::LOCAL: | 2678 case Variable::LOCAL: |
| 2679 // Local var, const, or let variable. | 2679 // Local var, const, or let variable. |
| 2680 if (mode == CONST_LEGACY && op == Token::INIT_CONST_LEGACY) { | 2680 if (mode == CONST_LEGACY && op == Token::INIT_CONST_LEGACY) { |
| 2681 // Perform an initialization check for legacy const variables. | 2681 // Perform an initialization check for legacy const variables. |
| 2682 Node* current = environment()->Lookup(variable); | 2682 Node* current = environment()->Lookup(variable); |
| 2683 if (current->op() != the_hole->op()) { | 2683 if (current->op() != the_hole->op()) { |
| 2684 value = BuildHoleCheckSilent(current, value, current); | 2684 value = BuildHoleCheckSilent(current, value, current); |
| 2685 } | 2685 } |
| 2686 } else if (mode == CONST_LEGACY && op != Token::INIT_CONST_LEGACY) { | 2686 } else if (mode == CONST_LEGACY && op != Token::INIT_CONST_LEGACY) { |
| 2687 // Non-initializing assignments to legacy const is | 2687 // Non-initializing assignment to legacy const is |
| 2688 // - exception in strict mode. | 2688 // - exception in strict mode. |
| 2689 // - ignored in sloppy mode. | 2689 // - ignored in sloppy mode. |
| 2690 if (is_strict(language_mode())) { | 2690 if (is_strict(language_mode())) { |
| 2691 return BuildThrowConstAssignError(bailout_id); | 2691 return BuildThrowConstAssignError(bailout_id); |
| 2692 } | 2692 } |
| 2693 return value; | 2693 return value; |
| 2694 } else if (mode == LET && op != Token::INIT_LET) { | 2694 } else if (mode == LET && op != Token::INIT_LET) { |
| 2695 // Perform an initialization check for let declared variables. | 2695 // Perform an initialization check for let declared variables. |
| 2696 // Also note that the dynamic hole-check is only done to ensure that | 2696 // Also note that the dynamic hole-check is only done to ensure that |
| 2697 // this does not break in the presence of do-expressions within the | 2697 // this does not break in the presence of do-expressions within the |
| 2698 // temporal dead zone of a let declared variable. | 2698 // temporal dead zone of a let declared variable. |
| 2699 Node* current = environment()->Lookup(variable); | 2699 Node* current = environment()->Lookup(variable); |
| 2700 if (current->op() == the_hole->op()) { | 2700 if (current->op() == the_hole->op()) { |
| 2701 value = BuildThrowReferenceError(variable, bailout_id); | 2701 value = BuildThrowReferenceError(variable, bailout_id); |
| 2702 } else if (value->opcode() == IrOpcode::kPhi) { | 2702 } else if (value->opcode() == IrOpcode::kPhi) { |
| 2703 value = BuildHoleCheckThrow(current, variable, value, bailout_id); | 2703 value = BuildHoleCheckThrow(current, variable, value, bailout_id); |
| 2704 } | 2704 } |
| 2705 } else if (mode == CONST && op != Token::INIT_CONST) { | 2705 } else if (mode == CONST && op != Token::INIT_CONST) { |
| 2706 // Non-initializing assignments to const is exception in all modes. | 2706 // Assignment to const is exception in all modes. |
| 2707 Node* current = environment()->Lookup(variable); |
| 2708 if (current->op() == the_hole->op()) { |
| 2709 return BuildThrowReferenceError(variable, bailout_id); |
| 2710 } else if (value->opcode() == IrOpcode::kPhi) { |
| 2711 BuildHoleCheckThrow(current, variable, value, bailout_id); |
| 2712 } |
| 2707 return BuildThrowConstAssignError(bailout_id); | 2713 return BuildThrowConstAssignError(bailout_id); |
| 2708 } | 2714 } |
| 2709 environment()->Bind(variable, value); | 2715 environment()->Bind(variable, value); |
| 2710 return value; | 2716 return value; |
| 2711 case Variable::CONTEXT: { | 2717 case Variable::CONTEXT: { |
| 2712 // Context variable (potentially up the context chain). | 2718 // Context variable (potentially up the context chain). |
| 2713 int depth = current_scope()->ContextChainLength(variable->scope()); | 2719 int depth = current_scope()->ContextChainLength(variable->scope()); |
| 2714 if (mode == CONST_LEGACY && op == Token::INIT_CONST_LEGACY) { | 2720 if (mode == CONST_LEGACY && op == Token::INIT_CONST_LEGACY) { |
| 2715 // Perform an initialization check for legacy const variables. | 2721 // Perform an initialization check for legacy const variables. |
| 2716 const Operator* op = | 2722 const Operator* op = |
| 2717 javascript()->LoadContext(depth, variable->index(), false); | 2723 javascript()->LoadContext(depth, variable->index(), false); |
| 2718 Node* current = NewNode(op, current_context()); | 2724 Node* current = NewNode(op, current_context()); |
| 2719 value = BuildHoleCheckSilent(current, value, current); | 2725 value = BuildHoleCheckSilent(current, value, current); |
| 2720 } else if (mode == CONST_LEGACY && op != Token::INIT_CONST_LEGACY) { | 2726 } else if (mode == CONST_LEGACY && op != Token::INIT_CONST_LEGACY) { |
| 2721 // Non-initializing assignments to legacy const is | 2727 // Non-initializing assignment to legacy const is |
| 2722 // - exception in strict mode. | 2728 // - exception in strict mode. |
| 2723 // - ignored in sloppy mode. | 2729 // - ignored in sloppy mode. |
| 2724 if (is_strict(language_mode())) { | 2730 if (is_strict(language_mode())) { |
| 2725 return BuildThrowConstAssignError(bailout_id); | 2731 return BuildThrowConstAssignError(bailout_id); |
| 2726 } | 2732 } |
| 2727 return value; | 2733 return value; |
| 2728 } else if (mode == LET && op != Token::INIT_LET) { | 2734 } else if (mode == LET && op != Token::INIT_LET) { |
| 2729 // Perform an initialization check for let declared variables. | 2735 // Perform an initialization check for let declared variables. |
| 2730 const Operator* op = | 2736 const Operator* op = |
| 2731 javascript()->LoadContext(depth, variable->index(), false); | 2737 javascript()->LoadContext(depth, variable->index(), false); |
| 2732 Node* current = NewNode(op, current_context()); | 2738 Node* current = NewNode(op, current_context()); |
| 2733 value = BuildHoleCheckThrow(current, variable, value, bailout_id); | 2739 value = BuildHoleCheckThrow(current, variable, value, bailout_id); |
| 2734 } else if (mode == CONST && op != Token::INIT_CONST) { | 2740 } else if (mode == CONST && op != Token::INIT_CONST) { |
| 2735 // Non-initializing assignments to const is exception in all modes. | 2741 // Assignment to const is exception in all modes. |
| 2742 const Operator* op = |
| 2743 javascript()->LoadContext(depth, variable->index(), false); |
| 2744 Node* current = NewNode(op, current_context()); |
| 2745 BuildHoleCheckThrow(current, variable, value, bailout_id); |
| 2736 return BuildThrowConstAssignError(bailout_id); | 2746 return BuildThrowConstAssignError(bailout_id); |
| 2737 } | 2747 } |
| 2738 const Operator* op = javascript()->StoreContext(depth, variable->index()); | 2748 const Operator* op = javascript()->StoreContext(depth, variable->index()); |
| 2739 return NewNode(op, current_context(), value); | 2749 return NewNode(op, current_context(), value); |
| 2740 } | 2750 } |
| 2741 case Variable::LOOKUP: { | 2751 case Variable::LOOKUP: { |
| 2742 // Dynamic lookup of context variable (anywhere in the chain). | 2752 // Dynamic lookup of context variable (anywhere in the chain). |
| 2743 Node* name = jsgraph()->Constant(variable->name()); | 2753 Node* name = jsgraph()->Constant(variable->name()); |
| 2744 Node* language = jsgraph()->Constant(language_mode()); | 2754 Node* language = jsgraph()->Constant(language_mode()); |
| 2745 // TODO(mstarzinger): Use Runtime::kInitializeLegacyConstLookupSlot for | 2755 // TODO(mstarzinger): Use Runtime::kInitializeLegacyConstLookupSlot for |
| (...skipping 487 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3233 // Phi does not exist yet, introduce one. | 3243 // Phi does not exist yet, introduce one. |
| 3234 value = NewPhi(inputs, value, control); | 3244 value = NewPhi(inputs, value, control); |
| 3235 value->ReplaceInput(inputs - 1, other); | 3245 value->ReplaceInput(inputs - 1, other); |
| 3236 } | 3246 } |
| 3237 return value; | 3247 return value; |
| 3238 } | 3248 } |
| 3239 | 3249 |
| 3240 } // namespace compiler | 3250 } // namespace compiler |
| 3241 } // namespace internal | 3251 } // namespace internal |
| 3242 } // namespace v8 | 3252 } // namespace v8 |
| OLD | NEW |