OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 3874 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3885 } | 3885 } |
3886 | 3886 |
3887 | 3887 |
3888 void HOptimizedGraphBuilder::VisitForTypeOf(Expression* expr) { | 3888 void HOptimizedGraphBuilder::VisitForTypeOf(Expression* expr) { |
3889 ValueContext for_value(this, ARGUMENTS_NOT_ALLOWED); | 3889 ValueContext for_value(this, ARGUMENTS_NOT_ALLOWED); |
3890 for_value.set_for_typeof(true); | 3890 for_value.set_for_typeof(true); |
3891 Visit(expr); | 3891 Visit(expr); |
3892 } | 3892 } |
3893 | 3893 |
3894 | 3894 |
3895 | |
3896 void HOptimizedGraphBuilder::VisitForControl(Expression* expr, | 3895 void HOptimizedGraphBuilder::VisitForControl(Expression* expr, |
3897 HBasicBlock* true_block, | 3896 HBasicBlock* true_block, |
3898 HBasicBlock* false_block) { | 3897 HBasicBlock* false_block) { |
3899 TestContext for_test(this, expr, true_block, false_block); | 3898 TestContext for_test(this, expr, true_block, false_block); |
3900 Visit(expr); | 3899 Visit(expr); |
3901 } | 3900 } |
3902 | 3901 |
3903 | 3902 |
3904 void HOptimizedGraphBuilder::VisitArgument(Expression* expr) { | |
3905 CHECK_ALIVE(VisitForValue(expr)); | |
3906 Push(Add<HPushArgument>(Pop())); | |
3907 } | |
3908 | |
3909 | |
3910 void HOptimizedGraphBuilder::VisitArgumentList( | |
3911 ZoneList<Expression*>* arguments) { | |
3912 for (int i = 0; i < arguments->length(); i++) { | |
3913 CHECK_ALIVE(VisitArgument(arguments->at(i))); | |
3914 } | |
3915 } | |
3916 | |
3917 | |
3918 void HOptimizedGraphBuilder::VisitExpressions( | 3903 void HOptimizedGraphBuilder::VisitExpressions( |
3919 ZoneList<Expression*>* exprs) { | 3904 ZoneList<Expression*>* exprs) { |
3920 for (int i = 0; i < exprs->length(); ++i) { | 3905 for (int i = 0; i < exprs->length(); ++i) { |
3921 CHECK_ALIVE(VisitForValue(exprs->at(i))); | 3906 CHECK_ALIVE(VisitForValue(exprs->at(i))); |
3922 } | 3907 } |
3923 } | 3908 } |
3924 | 3909 |
3925 | 3910 |
3926 bool HOptimizedGraphBuilder::BuildGraph() { | 3911 bool HOptimizedGraphBuilder::BuildGraph() { |
3927 if (current_info()->function()->is_generator()) { | 3912 if (current_info()->function()->is_generator()) { |
(...skipping 4120 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
8048 call = New<HCallFunction>(function, argument_count, flags); | 8033 call = New<HCallFunction>(function, argument_count, flags); |
8049 } | 8034 } |
8050 PushArgumentsFromEnvironment(argument_count); | 8035 PushArgumentsFromEnvironment(argument_count); |
8051 | 8036 |
8052 } else { | 8037 } else { |
8053 VariableProxy* proxy = expr->expression()->AsVariableProxy(); | 8038 VariableProxy* proxy = expr->expression()->AsVariableProxy(); |
8054 if (proxy != NULL && proxy->var()->is_possibly_eval(isolate())) { | 8039 if (proxy != NULL && proxy->var()->is_possibly_eval(isolate())) { |
8055 return Bailout(kPossibleDirectCallToEval); | 8040 return Bailout(kPossibleDirectCallToEval); |
8056 } | 8041 } |
8057 | 8042 |
| 8043 // The function is on the stack in the unoptimized code during |
| 8044 // evaluation of the arguments. |
| 8045 CHECK_ALIVE(VisitForValue(expr->expression())); |
| 8046 HValue* function = Top(); |
8058 bool global_call = proxy != NULL && proxy->var()->IsUnallocated(); | 8047 bool global_call = proxy != NULL && proxy->var()->IsUnallocated(); |
8059 if (global_call) { | 8048 if (global_call) { |
8060 Variable* var = proxy->var(); | 8049 Variable* var = proxy->var(); |
8061 bool known_global_function = false; | 8050 bool known_global_function = false; |
8062 // If there is a global property cell for the name at compile time and | 8051 // If there is a global property cell for the name at compile time and |
8063 // access check is not enabled we assume that the function will not change | 8052 // access check is not enabled we assume that the function will not change |
8064 // and generate optimized code for calling the function. | 8053 // and generate optimized code for calling the function. |
8065 LookupResult lookup(isolate()); | 8054 LookupResult lookup(isolate()); |
8066 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, LOAD); | 8055 GlobalPropertyAccess type = LookupGlobalProperty(var, &lookup, LOAD); |
8067 if (type == kUseCell && | 8056 if (type == kUseCell && |
8068 !current_info()->global_object()->IsAccessCheckNeeded()) { | 8057 !current_info()->global_object()->IsAccessCheckNeeded()) { |
8069 Handle<GlobalObject> global(current_info()->global_object()); | 8058 Handle<GlobalObject> global(current_info()->global_object()); |
8070 known_global_function = expr->ComputeGlobalTarget(global, &lookup); | 8059 known_global_function = expr->ComputeGlobalTarget(global, &lookup); |
8071 } | 8060 } |
8072 CHECK_ALIVE(VisitForValue(expr->expression())); | |
8073 HValue* function = Top(); | |
8074 if (known_global_function) { | 8061 if (known_global_function) { |
8075 Add<HCheckValue>(function, expr->target()); | 8062 Add<HCheckValue>(function, expr->target()); |
8076 | 8063 |
8077 // Placeholder for the receiver. | 8064 // Placeholder for the receiver. |
8078 Push(graph()->GetConstantUndefined()); | 8065 Push(graph()->GetConstantUndefined()); |
8079 CHECK_ALIVE(VisitExpressions(expr->arguments())); | 8066 CHECK_ALIVE(VisitExpressions(expr->arguments())); |
8080 | 8067 |
8081 // Patch the global object on the stack by the expected receiver. | 8068 // Patch the global object on the stack by the expected receiver. |
8082 HValue* receiver = ImplicitReceiverFor(function, expr->target()); | 8069 HValue* receiver = ImplicitReceiverFor(function, expr->target()); |
8083 const int receiver_index = argument_count - 1; | 8070 const int receiver_index = argument_count - 1; |
8084 environment()->SetExpressionStackAt(receiver_index, receiver); | 8071 environment()->SetExpressionStackAt(receiver_index, receiver); |
8085 | 8072 |
8086 if (TryInlineBuiltinFunctionCall(expr)) { | 8073 if (TryInlineBuiltinFunctionCall(expr)) { |
8087 if (FLAG_trace_inlining) { | 8074 if (FLAG_trace_inlining) { |
8088 PrintF("Inlining builtin "); | 8075 PrintF("Inlining builtin "); |
8089 expr->target()->ShortPrint(); | 8076 expr->target()->ShortPrint(); |
8090 PrintF("\n"); | 8077 PrintF("\n"); |
8091 } | 8078 } |
8092 return; | 8079 return; |
8093 } | 8080 } |
8094 if (TryInlineApiFunctionCall(expr, receiver)) return; | 8081 if (TryInlineApiFunctionCall(expr, receiver)) return; |
8095 if (TryInlineCall(expr)) return; | 8082 if (TryInlineCall(expr)) return; |
8096 | 8083 |
8097 PushArgumentsFromEnvironment(argument_count); | 8084 PushArgumentsFromEnvironment(argument_count); |
8098 call = BuildCallConstantFunction(expr->target(), argument_count); | 8085 call = BuildCallConstantFunction(expr->target(), argument_count); |
8099 } else { | 8086 } else { |
8100 Push(Add<HPushArgument>(graph()->GetConstantUndefined())); | 8087 Push(graph()->GetConstantUndefined()); |
8101 CHECK_ALIVE(VisitArgumentList(expr->arguments())); | 8088 CHECK_ALIVE(VisitExpressions(expr->arguments())); |
| 8089 PushArgumentsFromEnvironment(argument_count); |
8102 call = New<HCallFunction>(function, argument_count); | 8090 call = New<HCallFunction>(function, argument_count); |
8103 Drop(argument_count); | |
8104 } | 8091 } |
8105 | 8092 |
8106 } else if (expr->IsMonomorphic()) { | 8093 } else if (expr->IsMonomorphic()) { |
8107 // The function is on the stack in the unoptimized code during | |
8108 // evaluation of the arguments. | |
8109 CHECK_ALIVE(VisitForValue(expr->expression())); | |
8110 HValue* function = Top(); | |
8111 | |
8112 Add<HCheckValue>(function, expr->target()); | 8094 Add<HCheckValue>(function, expr->target()); |
8113 | 8095 |
8114 Push(graph()->GetConstantUndefined()); | 8096 Push(graph()->GetConstantUndefined()); |
8115 CHECK_ALIVE(VisitExpressions(expr->arguments())); | 8097 CHECK_ALIVE(VisitExpressions(expr->arguments())); |
8116 | 8098 |
8117 HValue* receiver = ImplicitReceiverFor(function, expr->target()); | 8099 HValue* receiver = ImplicitReceiverFor(function, expr->target()); |
8118 const int receiver_index = argument_count - 1; | 8100 const int receiver_index = argument_count - 1; |
8119 environment()->SetExpressionStackAt(receiver_index, receiver); | 8101 environment()->SetExpressionStackAt(receiver_index, receiver); |
8120 | 8102 |
8121 if (TryInlineBuiltinFunctionCall(expr)) { | 8103 if (TryInlineBuiltinFunctionCall(expr)) { |
8122 if (FLAG_trace_inlining) { | 8104 if (FLAG_trace_inlining) { |
8123 PrintF("Inlining builtin "); | 8105 PrintF("Inlining builtin "); |
8124 expr->target()->ShortPrint(); | 8106 expr->target()->ShortPrint(); |
8125 PrintF("\n"); | 8107 PrintF("\n"); |
8126 } | 8108 } |
8127 return; | 8109 return; |
8128 } | 8110 } |
8129 if (TryInlineApiFunctionCall(expr, receiver)) return; | 8111 if (TryInlineApiFunctionCall(expr, receiver)) return; |
8130 | 8112 |
8131 if (TryInlineCall(expr)) return; | 8113 if (TryInlineCall(expr)) return; |
8132 | 8114 |
8133 call = PreProcessCall(New<HInvokeFunction>( | 8115 call = PreProcessCall(New<HInvokeFunction>( |
8134 function, expr->target(), argument_count)); | 8116 function, expr->target(), argument_count)); |
8135 | 8117 |
8136 } else { | 8118 } else { |
8137 CHECK_ALIVE(VisitForValue(expr->expression())); | 8119 Push(graph()->GetConstantUndefined()); |
8138 HValue* function = Top(); | 8120 CHECK_ALIVE(VisitExpressions(expr->arguments())); |
8139 HValue* receiver = graph()->GetConstantUndefined(); | 8121 PushArgumentsFromEnvironment(argument_count); |
8140 Push(Add<HPushArgument>(receiver)); | |
8141 CHECK_ALIVE(VisitArgumentList(expr->arguments())); | |
8142 call = New<HCallFunction>(function, argument_count); | 8122 call = New<HCallFunction>(function, argument_count); |
8143 Drop(argument_count); | |
8144 } | 8123 } |
8145 } | 8124 } |
8146 | 8125 |
8147 Drop(1); // Drop the function. | 8126 Drop(1); // Drop the function. |
8148 return ast_context()->ReturnInstruction(call, expr->id()); | 8127 return ast_context()->ReturnInstruction(call, expr->id()); |
8149 } | 8128 } |
8150 | 8129 |
8151 | 8130 |
8152 void HOptimizedGraphBuilder::BuildInlinedCallNewArray(CallNew* expr) { | 8131 void HOptimizedGraphBuilder::BuildInlinedCallNewArray(CallNew* expr) { |
8153 NoObservableSideEffectsScope no_effects(this); | 8132 NoObservableSideEffectsScope no_effects(this); |
(...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
8573 Add<HStoreNamedField>(elements, | 8552 Add<HStoreNamedField>(elements, |
8574 HObjectAccess::ForFixedArrayLength(), | 8553 HObjectAccess::ForFixedArrayLength(), |
8575 length); | 8554 length); |
8576 Add<HStoreNamedField>( | 8555 Add<HStoreNamedField>( |
8577 obj, HObjectAccess::ForElementsPointer(), elements); | 8556 obj, HObjectAccess::ForElementsPointer(), elements); |
8578 } | 8557 } |
8579 | 8558 |
8580 if (!is_zero_byte_offset) { | 8559 if (!is_zero_byte_offset) { |
8581 byte_offset_smi.Else(); | 8560 byte_offset_smi.Else(); |
8582 { // byte_offset is not Smi. | 8561 { // byte_offset is not Smi. |
8583 Push(Add<HPushArgument>(obj)); | 8562 Push(obj); |
8584 VisitArgument(arguments->at(kArrayIdArg)); | 8563 CHECK_ALIVE(VisitForValue(arguments->at(kArrayIdArg))); |
8585 Push(Add<HPushArgument>(buffer)); | 8564 Push(buffer); |
8586 Push(Add<HPushArgument>(byte_offset)); | 8565 Push(byte_offset); |
8587 Push(Add<HPushArgument>(byte_length)); | 8566 Push(byte_length); |
| 8567 PushArgumentsFromEnvironment(kArgsLength); |
8588 Add<HCallRuntime>(expr->name(), expr->function(), kArgsLength); | 8568 Add<HCallRuntime>(expr->name(), expr->function(), kArgsLength); |
8589 Drop(kArgsLength); | |
8590 } | 8569 } |
8591 } | 8570 } |
8592 byte_offset_smi.End(); | 8571 byte_offset_smi.End(); |
8593 } | 8572 } |
8594 | 8573 |
8595 | 8574 |
8596 void HOptimizedGraphBuilder::VisitCallRuntime(CallRuntime* expr) { | 8575 void HOptimizedGraphBuilder::VisitCallRuntime(CallRuntime* expr) { |
8597 ASSERT(!HasStackOverflow()); | 8576 ASSERT(!HasStackOverflow()); |
8598 ASSERT(current_block() != NULL); | 8577 ASSERT(current_block() != NULL); |
8599 ASSERT(current_block()->HasPredecessor()); | 8578 ASSERT(current_block()->HasPredecessor()); |
(...skipping 26 matching lines...) Expand all Loading... |
8626 static_cast<int>(Runtime::kFirstInlineFunction); | 8605 static_cast<int>(Runtime::kFirstInlineFunction); |
8627 ASSERT(lookup_index >= 0); | 8606 ASSERT(lookup_index >= 0); |
8628 ASSERT(static_cast<size_t>(lookup_index) < | 8607 ASSERT(static_cast<size_t>(lookup_index) < |
8629 ARRAY_SIZE(kInlineFunctionGenerators)); | 8608 ARRAY_SIZE(kInlineFunctionGenerators)); |
8630 InlineFunctionGenerator generator = kInlineFunctionGenerators[lookup_index]; | 8609 InlineFunctionGenerator generator = kInlineFunctionGenerators[lookup_index]; |
8631 | 8610 |
8632 // Call the inline code generator using the pointer-to-member. | 8611 // Call the inline code generator using the pointer-to-member. |
8633 (this->*generator)(expr); | 8612 (this->*generator)(expr); |
8634 } else { | 8613 } else { |
8635 ASSERT(function->intrinsic_type == Runtime::RUNTIME); | 8614 ASSERT(function->intrinsic_type == Runtime::RUNTIME); |
8636 CHECK_ALIVE(VisitArgumentList(expr->arguments())); | |
8637 | |
8638 Handle<String> name = expr->name(); | 8615 Handle<String> name = expr->name(); |
8639 int argument_count = expr->arguments()->length(); | 8616 int argument_count = expr->arguments()->length(); |
| 8617 CHECK_ALIVE(VisitExpressions(expr->arguments())); |
| 8618 PushArgumentsFromEnvironment(argument_count); |
8640 HCallRuntime* call = New<HCallRuntime>(name, function, | 8619 HCallRuntime* call = New<HCallRuntime>(name, function, |
8641 argument_count); | 8620 argument_count); |
8642 Drop(argument_count); | |
8643 return ast_context()->ReturnInstruction(call, expr->id()); | 8621 return ast_context()->ReturnInstruction(call, expr->id()); |
8644 } | 8622 } |
8645 } | 8623 } |
8646 | 8624 |
8647 | 8625 |
8648 void HOptimizedGraphBuilder::VisitUnaryOperation(UnaryOperation* expr) { | 8626 void HOptimizedGraphBuilder::VisitUnaryOperation(UnaryOperation* expr) { |
8649 ASSERT(!HasStackOverflow()); | 8627 ASSERT(!HasStackOverflow()); |
8650 ASSERT(current_block() != NULL); | 8628 ASSERT(current_block() != NULL); |
8651 ASSERT(current_block()->HasPredecessor()); | 8629 ASSERT(current_block()->HasPredecessor()); |
8652 switch (expr->op()) { | 8630 switch (expr->op()) { |
(...skipping 1844 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
10497 HValue* right = Pop(); | 10475 HValue* right = Pop(); |
10498 HValue* left = Pop(); | 10476 HValue* left = Pop(); |
10499 HInstruction* result = NewUncasted<HStringAdd>(left, right); | 10477 HInstruction* result = NewUncasted<HStringAdd>(left, right); |
10500 return ast_context()->ReturnInstruction(result, call->id()); | 10478 return ast_context()->ReturnInstruction(result, call->id()); |
10501 } | 10479 } |
10502 | 10480 |
10503 | 10481 |
10504 // Fast support for SubString. | 10482 // Fast support for SubString. |
10505 void HOptimizedGraphBuilder::GenerateSubString(CallRuntime* call) { | 10483 void HOptimizedGraphBuilder::GenerateSubString(CallRuntime* call) { |
10506 ASSERT_EQ(3, call->arguments()->length()); | 10484 ASSERT_EQ(3, call->arguments()->length()); |
10507 CHECK_ALIVE(VisitArgumentList(call->arguments())); | 10485 CHECK_ALIVE(VisitExpressions(call->arguments())); |
| 10486 PushArgumentsFromEnvironment(call->arguments()->length()); |
10508 HCallStub* result = New<HCallStub>(CodeStub::SubString, 3); | 10487 HCallStub* result = New<HCallStub>(CodeStub::SubString, 3); |
10509 Drop(3); | |
10510 return ast_context()->ReturnInstruction(result, call->id()); | 10488 return ast_context()->ReturnInstruction(result, call->id()); |
10511 } | 10489 } |
10512 | 10490 |
10513 | 10491 |
10514 // Fast support for StringCompare. | 10492 // Fast support for StringCompare. |
10515 void HOptimizedGraphBuilder::GenerateStringCompare(CallRuntime* call) { | 10493 void HOptimizedGraphBuilder::GenerateStringCompare(CallRuntime* call) { |
10516 ASSERT_EQ(2, call->arguments()->length()); | 10494 ASSERT_EQ(2, call->arguments()->length()); |
10517 CHECK_ALIVE(VisitArgumentList(call->arguments())); | 10495 CHECK_ALIVE(VisitExpressions(call->arguments())); |
| 10496 PushArgumentsFromEnvironment(call->arguments()->length()); |
10518 HCallStub* result = New<HCallStub>(CodeStub::StringCompare, 2); | 10497 HCallStub* result = New<HCallStub>(CodeStub::StringCompare, 2); |
10519 Drop(2); | |
10520 return ast_context()->ReturnInstruction(result, call->id()); | 10498 return ast_context()->ReturnInstruction(result, call->id()); |
10521 } | 10499 } |
10522 | 10500 |
10523 | 10501 |
10524 // Support for direct calls from JavaScript to native RegExp code. | 10502 // Support for direct calls from JavaScript to native RegExp code. |
10525 void HOptimizedGraphBuilder::GenerateRegExpExec(CallRuntime* call) { | 10503 void HOptimizedGraphBuilder::GenerateRegExpExec(CallRuntime* call) { |
10526 ASSERT_EQ(4, call->arguments()->length()); | 10504 ASSERT_EQ(4, call->arguments()->length()); |
10527 CHECK_ALIVE(VisitArgumentList(call->arguments())); | 10505 CHECK_ALIVE(VisitExpressions(call->arguments())); |
| 10506 PushArgumentsFromEnvironment(call->arguments()->length()); |
10528 HCallStub* result = New<HCallStub>(CodeStub::RegExpExec, 4); | 10507 HCallStub* result = New<HCallStub>(CodeStub::RegExpExec, 4); |
10529 Drop(4); | |
10530 return ast_context()->ReturnInstruction(result, call->id()); | 10508 return ast_context()->ReturnInstruction(result, call->id()); |
10531 } | 10509 } |
10532 | 10510 |
10533 | 10511 |
10534 // Construct a RegExp exec result with two in-object properties. | 10512 // Construct a RegExp exec result with two in-object properties. |
10535 void HOptimizedGraphBuilder::GenerateRegExpConstructResult(CallRuntime* call) { | 10513 void HOptimizedGraphBuilder::GenerateRegExpConstructResult(CallRuntime* call) { |
10536 ASSERT_EQ(3, call->arguments()->length()); | 10514 ASSERT_EQ(3, call->arguments()->length()); |
10537 CHECK_ALIVE(VisitForValue(call->arguments()->at(0))); | 10515 CHECK_ALIVE(VisitForValue(call->arguments()->at(0))); |
10538 CHECK_ALIVE(VisitForValue(call->arguments()->at(1))); | 10516 CHECK_ALIVE(VisitForValue(call->arguments()->at(1))); |
10539 CHECK_ALIVE(VisitForValue(call->arguments()->at(2))); | 10517 CHECK_ALIVE(VisitForValue(call->arguments()->at(2))); |
(...skipping 20 matching lines...) Expand all Loading... |
10560 return ast_context()->ReturnValue(result); | 10538 return ast_context()->ReturnValue(result); |
10561 } | 10539 } |
10562 | 10540 |
10563 | 10541 |
10564 // Fast call for custom callbacks. | 10542 // Fast call for custom callbacks. |
10565 void HOptimizedGraphBuilder::GenerateCallFunction(CallRuntime* call) { | 10543 void HOptimizedGraphBuilder::GenerateCallFunction(CallRuntime* call) { |
10566 // 1 ~ The function to call is not itself an argument to the call. | 10544 // 1 ~ The function to call is not itself an argument to the call. |
10567 int arg_count = call->arguments()->length() - 1; | 10545 int arg_count = call->arguments()->length() - 1; |
10568 ASSERT(arg_count >= 1); // There's always at least a receiver. | 10546 ASSERT(arg_count >= 1); // There's always at least a receiver. |
10569 | 10547 |
10570 for (int i = 0; i < arg_count; ++i) { | 10548 CHECK_ALIVE(VisitExpressions(call->arguments())); |
10571 CHECK_ALIVE(VisitArgument(call->arguments()->at(i))); | 10549 // The function is the last argument |
10572 } | |
10573 CHECK_ALIVE(VisitForValue(call->arguments()->last())); | |
10574 | |
10575 HValue* function = Pop(); | 10550 HValue* function = Pop(); |
| 10551 // Push the arguments to the stack |
| 10552 PushArgumentsFromEnvironment(arg_count); |
10576 | 10553 |
10577 IfBuilder if_is_jsfunction(this); | 10554 IfBuilder if_is_jsfunction(this); |
10578 if_is_jsfunction.If<HHasInstanceTypeAndBranch>(function, JS_FUNCTION_TYPE); | 10555 if_is_jsfunction.If<HHasInstanceTypeAndBranch>(function, JS_FUNCTION_TYPE); |
10579 | 10556 |
10580 if_is_jsfunction.Then(); | 10557 if_is_jsfunction.Then(); |
10581 { | 10558 { |
10582 HInstruction* invoke_result = | 10559 HInstruction* invoke_result = |
10583 Add<HInvokeFunction>(function, arg_count); | 10560 Add<HInvokeFunction>(function, arg_count); |
10584 Drop(arg_count); | |
10585 if (!ast_context()->IsEffect()) { | 10561 if (!ast_context()->IsEffect()) { |
10586 Push(invoke_result); | 10562 Push(invoke_result); |
10587 } | 10563 } |
10588 Add<HSimulate>(call->id(), FIXED_SIMULATE); | 10564 Add<HSimulate>(call->id(), FIXED_SIMULATE); |
10589 } | 10565 } |
10590 | 10566 |
10591 if_is_jsfunction.Else(); | 10567 if_is_jsfunction.Else(); |
10592 { | 10568 { |
10593 HInstruction* call_result = | 10569 HInstruction* call_result = |
10594 Add<HCallFunction>(function, arg_count); | 10570 Add<HCallFunction>(function, arg_count); |
10595 Drop(arg_count); | |
10596 if (!ast_context()->IsEffect()) { | 10571 if (!ast_context()->IsEffect()) { |
10597 Push(call_result); | 10572 Push(call_result); |
10598 } | 10573 } |
10599 Add<HSimulate>(call->id(), FIXED_SIMULATE); | 10574 Add<HSimulate>(call->id(), FIXED_SIMULATE); |
10600 } | 10575 } |
10601 if_is_jsfunction.End(); | 10576 if_is_jsfunction.End(); |
10602 | 10577 |
10603 if (ast_context()->IsEffect()) { | 10578 if (ast_context()->IsEffect()) { |
10604 // EffectContext::ReturnValue ignores the value, so we can just pass | 10579 // EffectContext::ReturnValue ignores the value, so we can just pass |
10605 // 'undefined' (as we do not have the call result anymore). | 10580 // 'undefined' (as we do not have the call result anymore). |
(...skipping 692 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
11298 if (ShouldProduceTraceOutput()) { | 11273 if (ShouldProduceTraceOutput()) { |
11299 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); | 11274 isolate()->GetHTracer()->TraceHydrogen(name(), graph_); |
11300 } | 11275 } |
11301 | 11276 |
11302 #ifdef DEBUG | 11277 #ifdef DEBUG |
11303 graph_->Verify(false); // No full verify. | 11278 graph_->Verify(false); // No full verify. |
11304 #endif | 11279 #endif |
11305 } | 11280 } |
11306 | 11281 |
11307 } } // namespace v8::internal | 11282 } } // namespace v8::internal |
OLD | NEW |