| Index: src/compiler/ast-graph-builder.cc
|
| diff --git a/src/compiler/ast-graph-builder.cc b/src/compiler/ast-graph-builder.cc
|
| index ec2af52ec4d5b605c335b2d4a15a56fa73359920..3f8d40cd8f2882dd51a6ee25639c495480d57e9d 100644
|
| --- a/src/compiler/ast-graph-builder.cc
|
| +++ b/src/compiler/ast-graph-builder.cc
|
| @@ -40,14 +40,14 @@
|
|
|
| // Plug a node into this expression context. Call this function in tail
|
| // position in the Visit functions for expressions.
|
| - virtual void ProduceValue(Node* value) = 0;
|
| + virtual void ProduceValue(Expression* expr, Node* value) = 0;
|
|
|
| // Unplugs a node from this expression context. Call this to retrieve the
|
| // result of another Visit function that already plugged the context.
|
| virtual Node* ConsumeValue() = 0;
|
|
|
| // Shortcut for "context->ProduceValue(context->ConsumeValue())".
|
| - void ReplaceValue() { ProduceValue(ConsumeValue()); }
|
| + void ReplaceValue(Expression* expr) { ProduceValue(expr, ConsumeValue()); }
|
|
|
| protected:
|
| AstContext(AstGraphBuilder* owner, Expression::Context kind);
|
| @@ -75,7 +75,7 @@
|
| explicit AstEffectContext(AstGraphBuilder* owner)
|
| : AstContext(owner, Expression::kEffect) {}
|
| ~AstEffectContext() final;
|
| - void ProduceValue(Node* value) final;
|
| + void ProduceValue(Expression* expr, Node* value) final;
|
| Node* ConsumeValue() final;
|
| };
|
|
|
| @@ -86,7 +86,7 @@
|
| explicit AstValueContext(AstGraphBuilder* owner)
|
| : AstContext(owner, Expression::kValue) {}
|
| ~AstValueContext() final;
|
| - void ProduceValue(Node* value) final;
|
| + void ProduceValue(Expression* expr, Node* value) final;
|
| Node* ConsumeValue() final;
|
| };
|
|
|
| @@ -97,7 +97,7 @@
|
| AstTestContext(AstGraphBuilder* owner, TypeFeedbackId feedback_id)
|
| : AstContext(owner, Expression::kTest), feedback_id_(feedback_id) {}
|
| ~AstTestContext() final;
|
| - void ProduceValue(Node* value) final;
|
| + void ProduceValue(Expression* expr, Node* value) final;
|
| Node* ConsumeValue() final;
|
|
|
| private:
|
| @@ -968,19 +968,22 @@
|
| DCHECK(environment()->stack_height() == original_height_ + 1);
|
| }
|
|
|
| -
|
| -void AstGraphBuilder::AstEffectContext::ProduceValue(Node* value) {
|
| +void AstGraphBuilder::AstEffectContext::ProduceValue(Expression* expr,
|
| + Node* value) {
|
| // The value is ignored.
|
| -}
|
| -
|
| -
|
| -void AstGraphBuilder::AstValueContext::ProduceValue(Node* value) {
|
| + owner()->PrepareEagerCheckpoint(expr->id());
|
| +}
|
| +
|
| +void AstGraphBuilder::AstValueContext::ProduceValue(Expression* expr,
|
| + Node* value) {
|
| environment()->Push(value);
|
| -}
|
| -
|
| -
|
| -void AstGraphBuilder::AstTestContext::ProduceValue(Node* value) {
|
| + owner()->PrepareEagerCheckpoint(expr->id());
|
| +}
|
| +
|
| +void AstGraphBuilder::AstTestContext::ProduceValue(Expression* expr,
|
| + Node* value) {
|
| environment()->Push(owner()->BuildToBoolean(value, feedback_id_));
|
| + owner()->PrepareEagerCheckpoint(expr->id());
|
| }
|
|
|
|
|
| @@ -1071,7 +1074,7 @@
|
| if (!CheckStackOverflow()) {
|
| expr->Accept(this);
|
| } else {
|
| - ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
|
| + ast_context()->ProduceValue(expr, jsgraph()->UndefinedConstant());
|
| }
|
| }
|
|
|
| @@ -1081,7 +1084,7 @@
|
| if (!CheckStackOverflow()) {
|
| expr->Accept(this);
|
| } else {
|
| - ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
|
| + ast_context()->ProduceValue(expr, jsgraph()->UndefinedConstant());
|
| }
|
| }
|
|
|
| @@ -1091,7 +1094,7 @@
|
| if (!CheckStackOverflow()) {
|
| expr->Accept(this);
|
| } else {
|
| - ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
|
| + ast_context()->ProduceValue(expr, jsgraph()->UndefinedConstant());
|
| }
|
| }
|
|
|
| @@ -1101,7 +1104,7 @@
|
| if (!CheckStackOverflow()) {
|
| expr->Accept(this);
|
| } else {
|
| - ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
|
| + ast_context()->ProduceValue(expr, jsgraph()->UndefinedConstant());
|
| }
|
| }
|
|
|
| @@ -1438,10 +1441,13 @@
|
| test_value.Then();
|
| test_value.Else();
|
| {
|
| + environment()->Push(value);
|
| + PrepareEagerCheckpoint(stmt->FilterId());
|
| + value = environment()->Pop();
|
| // Bind value and do loop body.
|
| VectorSlotPair feedback =
|
| CreateVectorSlotPair(stmt->EachFeedbackSlot());
|
| - VisitForInAssignment(stmt->each(), value, feedback, stmt->FilterId(),
|
| + VisitForInAssignment(stmt->each(), value, feedback,
|
| stmt->AssignmentId());
|
| VisitIterationBody(stmt, &for_loop);
|
| }
|
| @@ -1589,7 +1595,7 @@
|
| PretenureFlag pretenure = expr->pretenure() ? TENURED : NOT_TENURED;
|
| const Operator* op = javascript()->CreateClosure(shared_info, pretenure);
|
| Node* value = NewNode(op);
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -1704,7 +1710,7 @@
|
| BuildVariableAssignment(var, literal, Token::INIT, feedback,
|
| BailoutId::None());
|
| }
|
| - ast_context()->ProduceValue(literal);
|
| + ast_context()->ProduceValue(expr, literal);
|
| }
|
|
|
|
|
| @@ -1716,7 +1722,7 @@
|
| void AstGraphBuilder::VisitDoExpression(DoExpression* expr) {
|
| VisitBlock(expr->block());
|
| VisitVariableProxy(expr->result());
|
| - ast_context()->ReplaceValue();
|
| + ast_context()->ReplaceValue(expr);
|
| }
|
|
|
|
|
| @@ -1730,7 +1736,11 @@
|
| compare_if.Else();
|
| Visit(expr->else_expression());
|
| compare_if.End();
|
| - ast_context()->ReplaceValue();
|
| + // Skip plugging AST evaluation contexts of the test kind. This is to stay in
|
| + // sync with full codegen which doesn't prepare the proper bailout point (see
|
| + // the implementation of FullCodeGenerator::VisitForControl).
|
| + if (ast_context()->IsTest()) return;
|
| + ast_context()->ReplaceValue(expr);
|
| }
|
|
|
|
|
| @@ -1739,13 +1749,13 @@
|
| PrepareEagerCheckpoint(BeforeId(expr));
|
| Node* value = BuildVariableLoad(expr->var(), expr->id(), pair,
|
| ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitLiteral(Literal* expr) {
|
| Node* value = jsgraph()->Constant(expr->value());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -1757,7 +1767,7 @@
|
| expr->pattern(), expr->flags(), expr->literal_index());
|
| Node* literal = NewNode(op, closure);
|
| PrepareFrameState(literal, expr->id(), ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(literal);
|
| + ast_context()->ProduceValue(expr, literal);
|
| }
|
|
|
|
|
| @@ -1797,7 +1807,6 @@
|
| if (key->value()->IsInternalizedString()) {
|
| if (property->emit_store()) {
|
| VisitForValue(property->value());
|
| - PrepareEagerCheckpoint(property->value()->id());
|
| Node* value = environment()->Pop();
|
| Node* literal = environment()->Top();
|
| Handle<Name> name = key->AsPropertyName();
|
| @@ -1943,7 +1952,7 @@
|
| }
|
| }
|
|
|
| - ast_context()->ProduceValue(environment()->Pop());
|
| + ast_context()->ProduceValue(expr, environment()->Pop());
|
| }
|
|
|
|
|
| @@ -1982,16 +1991,13 @@
|
| if (CompileTimeValue::IsCompileTimeValue(subexpr)) continue;
|
|
|
| VisitForValue(subexpr);
|
| - {
|
| - PrepareEagerCheckpoint(subexpr->id());
|
| - VectorSlotPair pair = CreateVectorSlotPair(expr->LiteralFeedbackSlot());
|
| - Node* value = environment()->Pop();
|
| - Node* index = jsgraph()->Constant(array_index);
|
| - Node* literal = environment()->Top();
|
| - Node* store = BuildKeyedStore(literal, index, value, pair);
|
| - PrepareFrameState(store, expr->GetIdForElement(array_index),
|
| - OutputFrameStateCombine::Ignore());
|
| - }
|
| + VectorSlotPair pair = CreateVectorSlotPair(expr->LiteralFeedbackSlot());
|
| + Node* value = environment()->Pop();
|
| + Node* index = jsgraph()->Constant(array_index);
|
| + Node* literal = environment()->Top();
|
| + Node* store = BuildKeyedStore(literal, index, value, pair);
|
| + PrepareFrameState(store, expr->GetIdForElement(array_index),
|
| + OutputFrameStateCombine::Ignore());
|
| }
|
|
|
| // In case the array literal contains spread expressions it has two parts. The
|
| @@ -2014,14 +2020,12 @@
|
| }
|
| }
|
|
|
| - ast_context()->ProduceValue(environment()->Pop());
|
| -}
|
| -
|
| + ast_context()->ProduceValue(expr, environment()->Pop());
|
| +}
|
|
|
| void AstGraphBuilder::VisitForInAssignment(Expression* expr, Node* value,
|
| const VectorSlotPair& feedback,
|
| - BailoutId bailout_id_before,
|
| - BailoutId bailout_id_after) {
|
| + BailoutId bailout_id) {
|
| DCHECK(expr->IsValidReferenceExpressionOrThis());
|
|
|
| // Left-hand side can only be a property, a global or a variable slot.
|
| @@ -2032,50 +2036,40 @@
|
| switch (assign_type) {
|
| case VARIABLE: {
|
| Variable* var = expr->AsVariableProxy()->var();
|
| - environment()->Push(value);
|
| - PrepareEagerCheckpoint(bailout_id_before);
|
| - value = environment()->Pop();
|
| - BuildVariableAssignment(var, value, Token::ASSIGN, feedback,
|
| - bailout_id_after);
|
| + BuildVariableAssignment(var, value, Token::ASSIGN, feedback, bailout_id);
|
| break;
|
| }
|
| case NAMED_PROPERTY: {
|
| environment()->Push(value);
|
| VisitForValue(property->obj());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Node* object = environment()->Pop();
|
| value = environment()->Pop();
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| Node* store = BuildNamedStore(object, name, value, feedback);
|
| - PrepareFrameState(store, bailout_id_after,
|
| - OutputFrameStateCombine::Ignore());
|
| + PrepareFrameState(store, bailout_id, OutputFrameStateCombine::Ignore());
|
| break;
|
| }
|
| case KEYED_PROPERTY: {
|
| environment()->Push(value);
|
| VisitForValue(property->obj());
|
| VisitForValue(property->key());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| Node* key = environment()->Pop();
|
| Node* object = environment()->Pop();
|
| value = environment()->Pop();
|
| Node* store = BuildKeyedStore(object, key, value, feedback);
|
| - PrepareFrameState(store, bailout_id_after,
|
| - OutputFrameStateCombine::Ignore());
|
| + PrepareFrameState(store, bailout_id, OutputFrameStateCombine::Ignore());
|
| break;
|
| }
|
| case NAMED_SUPER_PROPERTY: {
|
| environment()->Push(value);
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->home_object());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Node* home_object = environment()->Pop();
|
| Node* receiver = environment()->Pop();
|
| value = environment()->Pop();
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| Node* store = BuildNamedSuperStore(receiver, home_object, name, value);
|
| - PrepareFrameState(store, bailout_id_after,
|
| - OutputFrameStateCombine::Ignore());
|
| + PrepareFrameState(store, bailout_id, OutputFrameStateCombine::Ignore());
|
| break;
|
| }
|
| case KEYED_SUPER_PROPERTY: {
|
| @@ -2083,14 +2077,12 @@
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->home_object());
|
| VisitForValue(property->key());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| Node* key = environment()->Pop();
|
| Node* home_object = environment()->Pop();
|
| Node* receiver = environment()->Pop();
|
| value = environment()->Pop();
|
| Node* store = BuildKeyedSuperStore(receiver, home_object, key, value);
|
| - PrepareFrameState(store, bailout_id_after,
|
| - OutputFrameStateCombine::Ignore());
|
| + PrepareFrameState(store, bailout_id, OutputFrameStateCombine::Ignore());
|
| break;
|
| }
|
| }
|
| @@ -2134,7 +2126,6 @@
|
| break;
|
| }
|
|
|
| - BailoutId before_store_id = BailoutId::None();
|
| // Evaluate the value and potentially handle compound assignments by loading
|
| // the left-hand side value and performing a binary operation.
|
| if (expr->is_compound()) {
|
| @@ -2154,7 +2145,6 @@
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| VectorSlotPair pair =
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| old_value = BuildNamedLoad(object, name, pair);
|
| PrepareFrameState(old_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2165,7 +2155,6 @@
|
| Node* object = environment()->Peek(1);
|
| VectorSlotPair pair =
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| old_value = BuildKeyedLoad(object, key, pair);
|
| PrepareFrameState(old_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2177,7 +2166,6 @@
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| VectorSlotPair pair =
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| old_value = BuildNamedSuperLoad(receiver, home_object, name, pair);
|
| PrepareFrameState(old_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2189,7 +2177,6 @@
|
| Node* receiver = environment()->Peek(2);
|
| VectorSlotPair pair =
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| old_value = BuildKeyedSuperLoad(receiver, home_object, key, pair);
|
| PrepareFrameState(old_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2211,17 +2198,13 @@
|
| }
|
| environment()->Push(value);
|
| if (needs_frame_state_before) {
|
| - before_store_id = expr->binary_operation()->id();
|
| + PrepareEagerCheckpoint(expr->binary_operation()->id());
|
| }
|
| } else {
|
| VisitForValue(expr->value());
|
| - if (needs_frame_state_before) {
|
| - before_store_id = expr->value()->id();
|
| - }
|
| }
|
|
|
| // Store the value.
|
| - PrepareEagerCheckpoint(before_store_id);
|
| Node* value = environment()->Pop();
|
| VectorSlotPair feedback = CreateVectorSlotPair(expr->AssignmentSlot());
|
| switch (assign_type) {
|
| @@ -2263,14 +2246,14 @@
|
| }
|
| }
|
|
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitYield(Yield* expr) {
|
| // Generator functions are supported only by going through Ignition first.
|
| SetStackOverflow();
|
| - ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
|
| + ast_context()->ProduceValue(expr, jsgraph()->UndefinedConstant());
|
| }
|
|
|
|
|
| @@ -2278,7 +2261,7 @@
|
| VisitForValue(expr->exception());
|
| Node* exception = environment()->Pop();
|
| Node* value = BuildThrowError(exception, expr->id());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2292,7 +2275,6 @@
|
| break;
|
| case NAMED_PROPERTY: {
|
| VisitForValue(expr->obj());
|
| - PrepareEagerCheckpoint(expr->obj()->id());
|
| Node* object = environment()->Pop();
|
| Handle<Name> name = expr->key()->AsLiteral()->AsPropertyName();
|
| value = BuildNamedLoad(object, name, pair);
|
| @@ -2302,7 +2284,6 @@
|
| case KEYED_PROPERTY: {
|
| VisitForValue(expr->obj());
|
| VisitForValue(expr->key());
|
| - PrepareEagerCheckpoint(expr->key()->id());
|
| Node* key = environment()->Pop();
|
| Node* object = environment()->Pop();
|
| value = BuildKeyedLoad(object, key, pair);
|
| @@ -2312,7 +2293,6 @@
|
| case NAMED_SUPER_PROPERTY: {
|
| VisitForValue(expr->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(expr->obj()->AsSuperPropertyReference()->home_object());
|
| - PrepareEagerCheckpoint(expr->obj()->id());
|
| Node* home_object = environment()->Pop();
|
| Node* receiver = environment()->Pop();
|
| Handle<Name> name = expr->key()->AsLiteral()->AsPropertyName();
|
| @@ -2324,7 +2304,6 @@
|
| VisitForValue(expr->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(expr->obj()->AsSuperPropertyReference()->home_object());
|
| VisitForValue(expr->key());
|
| - PrepareEagerCheckpoint(expr->key()->id());
|
| Node* key = environment()->Pop();
|
| Node* home_object = environment()->Pop();
|
| Node* receiver = environment()->Pop();
|
| @@ -2333,7 +2312,7 @@
|
| break;
|
| }
|
| }
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2376,7 +2355,6 @@
|
| VectorSlotPair feedback =
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| VisitForValue(property->obj());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| Node* object = environment()->Top();
|
| callee_value = BuildNamedLoad(object, name, feedback);
|
| @@ -2395,7 +2373,6 @@
|
| CreateVectorSlotPair(property->PropertyFeedbackSlot());
|
| VisitForValue(property->obj());
|
| VisitForValue(property->key());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| Node* key = environment()->Pop();
|
| Node* object = environment()->Top();
|
| callee_value = BuildKeyedLoad(object, key, feedback);
|
| @@ -2417,7 +2394,6 @@
|
| Node* home = environment()->Peek(1);
|
| Node* object = environment()->Top();
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| callee_value = BuildNamedSuperLoad(object, home, name, VectorSlotPair());
|
| PrepareFrameState(callee_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2440,7 +2416,6 @@
|
| Node* key = environment()->Pop();
|
| Node* home = environment()->Pop();
|
| Node* object = environment()->Pop();
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| callee_value = BuildKeyedSuperLoad(object, home, key, VectorSlotPair());
|
| PrepareFrameState(callee_value, property->LoadId(),
|
| OutputFrameStateCombine::Push());
|
| @@ -2516,12 +2491,12 @@
|
| VectorSlotPair feedback = CreateVectorSlotPair(expr->CallFeedbackICSlot());
|
| const Operator* call = javascript()->CallFunction(
|
| args->length() + 2, feedback, receiver_hint, expr->tail_call_mode());
|
| - PrepareEagerCheckpoint(expr->CallId());
|
| + PrepareEagerCheckpoint(possibly_eval ? expr->EvalId() : expr->CallId());
|
| Node* value = ProcessArguments(call, args->length() + 2);
|
| environment()->Push(value->InputAt(0)); // The callee passed to the call.
|
| PrepareFrameState(value, expr->ReturnId(), OutputFrameStateCombine::Push());
|
| environment()->Drop(1);
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2547,10 +2522,9 @@
|
| // Create node to perform the super call.
|
| const Operator* call =
|
| javascript()->CallConstruct(args->length() + 2, VectorSlotPair());
|
| - PrepareEagerCheckpoint(super->new_target_var()->id());
|
| Node* value = ProcessArguments(call, args->length() + 2);
|
| PrepareFrameState(value, expr->ReturnId(), OutputFrameStateCombine::Push());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2560,11 +2534,6 @@
|
| // Evaluate all arguments to the construct call.
|
| ZoneList<Expression*>* args = expr->arguments();
|
| VisitForValues(args);
|
| -
|
| - // The baseline compiler doesn't push the new.target, so we need to record
|
| - // the frame state before the push.
|
| - PrepareEagerCheckpoint(args->is_empty() ? expr->expression()->id()
|
| - : args->last()->id());
|
|
|
| // The new target is the same as the callee.
|
| environment()->Push(environment()->Peek(args->length()));
|
| @@ -2575,7 +2544,7 @@
|
| javascript()->CallConstruct(args->length() + 2, feedback);
|
| Node* value = ProcessArguments(call, args->length() + 2);
|
| PrepareFrameState(value, expr->ReturnId(), OutputFrameStateCombine::Push());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2597,7 +2566,7 @@
|
| PrepareEagerCheckpoint(expr->CallId());
|
| Node* value = ProcessArguments(call, args->length() + 2);
|
| PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2615,10 +2584,13 @@
|
| // Create node to perform the runtime call.
|
| Runtime::FunctionId functionId = expr->function()->function_id;
|
| const Operator* call = javascript()->CallRuntime(functionId, args->length());
|
| - PrepareEagerCheckpoint(expr->CallId());
|
| + if (expr->function()->intrinsic_type == Runtime::IntrinsicType::RUNTIME ||
|
| + expr->function()->function_id == Runtime::kInlineCall) {
|
| + PrepareEagerCheckpoint(expr->CallId());
|
| + }
|
| Node* value = ProcessArguments(call, args->length());
|
| PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2666,7 +2638,6 @@
|
| }
|
| case NAMED_PROPERTY: {
|
| VisitForValue(property->obj());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Node* object = environment()->Top();
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| VectorSlotPair pair =
|
| @@ -2680,7 +2651,6 @@
|
| case KEYED_PROPERTY: {
|
| VisitForValue(property->obj());
|
| VisitForValue(property->key());
|
| - PrepareEagerCheckpoint(property->key()->id());
|
| Node* key = environment()->Top();
|
| Node* object = environment()->Peek(1);
|
| VectorSlotPair pair =
|
| @@ -2694,7 +2664,6 @@
|
| case NAMED_SUPER_PROPERTY: {
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->home_object());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Node* home_object = environment()->Top();
|
| Node* receiver = environment()->Peek(1);
|
| Handle<Name> name = property->key()->AsLiteral()->AsPropertyName();
|
| @@ -2710,7 +2679,6 @@
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->this_var());
|
| VisitForValue(property->obj()->AsSuperPropertyReference()->home_object());
|
| VisitForValue(property->key());
|
| - PrepareEagerCheckpoint(property->obj()->id());
|
| Node* key = environment()->Top();
|
| Node* home_object = environment()->Peek(1);
|
| Node* receiver = environment()->Peek(2);
|
| @@ -2809,7 +2777,7 @@
|
| // Restore old value for postfix expressions.
|
| if (is_postfix) value = environment()->Pop();
|
|
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2829,7 +2797,7 @@
|
| Node* value = BuildBinaryOp(left, right, expr->op(),
|
| expr->BinaryOperationFeedbackId());
|
| states.AddToNode(value, expr->id(), ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
| }
|
| }
|
| @@ -2849,23 +2817,21 @@
|
| UNREACHABLE();
|
| }
|
| VisitForValue(sub_expr);
|
| - PrepareEagerCheckpoint(sub_expr->id());
|
| Node* value_to_compare = environment()->Pop();
|
| Node* value = NewNode(op, value_to_compare, nil_value);
|
| PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
|
| - return ast_context()->ProduceValue(value);
|
| + return ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
| void AstGraphBuilder::VisitLiteralCompareTypeof(CompareOperation* expr,
|
| Expression* sub_expr,
|
| Handle<String> check) {
|
| VisitTypeofExpression(sub_expr);
|
| - PrepareEagerCheckpoint(sub_expr->id());
|
| Node* typeof_arg = NewNode(javascript()->TypeOf(), environment()->Pop());
|
| Node* value = NewNode(javascript()->StrictEqual(CompareOperationHints::Any()),
|
| typeof_arg, jsgraph()->Constant(check));
|
| PrepareFrameState(value, expr->id(), ast_context()->GetStateCombine());
|
| - return ast_context()->ProduceValue(value);
|
| + return ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
| void AstGraphBuilder::VisitCompareOperation(CompareOperation* expr) {
|
| @@ -2935,7 +2901,7 @@
|
| Node* left = environment()->Pop();
|
| Node* value = NewNode(op, left, right);
|
| states.AddToNode(value, expr->id(), ast_context()->GetStateCombine());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -2953,14 +2919,14 @@
|
|
|
| void AstGraphBuilder::VisitThisFunction(ThisFunction* expr) {
|
| Node* value = GetFunctionClosure();
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitSuperPropertyReference(
|
| SuperPropertyReference* expr) {
|
| Node* value = BuildThrowUnsupportedSuperError(expr->id());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| @@ -3041,14 +3007,14 @@
|
| VisitForEffect(expr->expression());
|
| value = jsgraph()->TrueConstant();
|
| }
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitVoid(UnaryOperation* expr) {
|
| VisitForEffect(expr->expression());
|
| Node* value = jsgraph()->UndefinedConstant();
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
| void AstGraphBuilder::VisitTypeofExpression(Expression* expr) {
|
| @@ -3070,33 +3036,46 @@
|
| void AstGraphBuilder::VisitTypeof(UnaryOperation* expr) {
|
| VisitTypeofExpression(expr->expression());
|
| Node* value = NewNode(javascript()->TypeOf(), environment()->Pop());
|
| - ast_context()->ProduceValue(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitNot(UnaryOperation* expr) {
|
| - VisitForValue(expr->expression());
|
| - Node* operand = environment()->Pop();
|
| - Node* input = BuildToBoolean(operand, expr->expression()->test_id());
|
| + VisitForTest(expr->expression());
|
| + Node* input = environment()->Pop();
|
| Node* value = NewNode(common()->Select(MachineRepresentation::kTagged), input,
|
| jsgraph()->FalseConstant(), jsgraph()->TrueConstant());
|
| - ast_context()->ProduceValue(value);
|
| + // Skip plugging AST evaluation contexts of the test kind. This is to stay in
|
| + // sync with full codegen which doesn't prepare the proper bailout point (see
|
| + // the implementation of FullCodeGenerator::VisitForControl).
|
| + if (ast_context()->IsTest()) return environment()->Push(value);
|
| + ast_context()->ProduceValue(expr, value);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitComma(BinaryOperation* expr) {
|
| VisitForEffect(expr->left());
|
| Visit(expr->right());
|
| - ast_context()->ReplaceValue();
|
| + ast_context()->ReplaceValue(expr);
|
| }
|
|
|
|
|
| void AstGraphBuilder::VisitLogicalExpression(BinaryOperation* expr) {
|
| bool is_logical_and = expr->op() == Token::AND;
|
| IfBuilder compare_if(this);
|
| - VisitForValue(expr->left());
|
| - Node* condition = environment()->Top();
|
| - compare_if.If(BuildToBoolean(condition, expr->left()->test_id()));
|
| + // Only use an AST evaluation context of the value kind when this expression
|
| + // is evaluated as value as well. Otherwise stick to a test context which is
|
| + // in sync with full codegen (see FullCodeGenerator::VisitLogicalExpression).
|
| + Node* condition = nullptr;
|
| + if (ast_context()->IsValue()) {
|
| + VisitForValue(expr->left());
|
| + Node* left = environment()->Top();
|
| + condition = BuildToBoolean(left, expr->left()->test_id());
|
| + } else {
|
| + VisitForTest(expr->left());
|
| + condition = environment()->Top();
|
| + }
|
| + compare_if.If(condition);
|
| compare_if.Then();
|
| if (is_logical_and) {
|
| environment()->Pop();
|
| @@ -3116,7 +3095,11 @@
|
| environment()->Poke(0, jsgraph()->FalseConstant());
|
| }
|
| compare_if.End();
|
| - ast_context()->ReplaceValue();
|
| + // Skip plugging AST evaluation contexts of the test kind. This is to stay in
|
| + // sync with full codegen which doesn't prepare the proper bailout point (see
|
| + // the implementation of FullCodeGenerator::VisitForControl).
|
| + if (ast_context()->IsTest()) return;
|
| + ast_context()->ReplaceValue(expr);
|
| }
|
|
|
|
|
| @@ -4077,6 +4060,7 @@
|
| return;
|
| }
|
| if (ast_id != BailoutId::None()) {
|
| + DCHECK(info()->shared_info()->VerifyBailoutId(ast_id));
|
| Node* node = NewNode(common()->Checkpoint());
|
| DCHECK_EQ(IrOpcode::kDead,
|
| NodeProperties::GetFrameStateInput(node, 0)->opcode());
|
|
|