diff options
Diffstat (limited to 'deps/v8/src/mips64/full-codegen-mips64.cc')
-rw-r--r-- | deps/v8/src/mips64/full-codegen-mips64.cc | 171 |
1 files changed, 101 insertions, 70 deletions
diff --git a/deps/v8/src/mips64/full-codegen-mips64.cc b/deps/v8/src/mips64/full-codegen-mips64.cc index 91d374a2c0..d2eb9dcec2 100644 --- a/deps/v8/src/mips64/full-codegen-mips64.cc +++ b/deps/v8/src/mips64/full-codegen-mips64.cc @@ -21,7 +21,6 @@ #include "src/debug.h" #include "src/full-codegen.h" #include "src/ic/ic.h" -#include "src/isolate-inl.h" #include "src/parser.h" #include "src/scopes.h" @@ -135,7 +134,8 @@ void FullCodeGenerator::Generate() { // Sloppy mode functions and builtins need to replace the receiver with the // global proxy when called as functions (without an explicit receiver // object). - if (is_sloppy(info->language_mode()) && !info->is_native()) { + if (is_sloppy(info->language_mode()) && !info->is_native() && + info->MayUseThis()) { Label ok; int receiver_offset = info->scope()->num_parameters() * kPointerSize; __ ld(at, MemOperand(sp, receiver_offset)); @@ -952,37 +952,6 @@ void FullCodeGenerator::VisitFunctionDeclaration( } -void FullCodeGenerator::VisitModuleDeclaration(ModuleDeclaration* declaration) { - Variable* variable = declaration->proxy()->var(); - ModuleDescriptor* descriptor = declaration->module()->descriptor(); - DCHECK(variable->location() == Variable::CONTEXT); - DCHECK(descriptor->IsFrozen()); - Comment cmnt(masm_, "[ ModuleDeclaration"); - EmitDebugCheckDeclarationContext(variable); - - // Load instance object. - __ LoadContext(a1, scope_->ContextChainLength(scope_->ScriptScope())); - __ ld(a1, ContextOperand(a1, descriptor->Index())); - __ ld(a1, ContextOperand(a1, Context::EXTENSION_INDEX)); - - // Assign it. - __ sd(a1, ContextOperand(cp, variable->index())); - // We know that we have written a module, which is not a smi. - __ RecordWriteContextSlot(cp, - Context::SlotOffset(variable->index()), - a1, - a3, - kRAHasBeenSaved, - kDontSaveFPRegs, - EMIT_REMEMBERED_SET, - OMIT_SMI_CHECK); - PrepareForBailoutForId(declaration->proxy()->id(), NO_REGISTERS); - - // Traverse into body. - Visit(declaration->module()); -} - - void FullCodeGenerator::VisitImportDeclaration(ImportDeclaration* declaration) { VariableProxy* proxy = declaration->proxy(); Variable* variable = proxy->var(); @@ -1269,6 +1238,7 @@ void FullCodeGenerator::VisitForInStatement(ForInStatement* stmt) { // just skip it. __ Push(a1, a3); // Enumerable and current entry. __ InvokeBuiltin(Builtins::FILTER_KEY, CALL_FUNCTION); + PrepareForBailoutForId(stmt->FilterId(), TOS_REG); __ mov(a3, result_register()); __ Branch(loop_statement.continue_label(), eq, a3, Operand(zero_reg)); @@ -2457,7 +2427,8 @@ void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr, patch_site.EmitJumpIfSmi(scratch1, &smi_case); __ bind(&stub_call); - Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), op).code(); + Handle<Code> code = CodeFactory::BinaryOpIC( + isolate(), op, language_mode()).code(); CallIC(code, expr->BinaryOperationFeedbackId()); patch_site.EmitPatchInfo(); __ jmp(&done); @@ -2599,7 +2570,8 @@ void FullCodeGenerator::EmitClassDefineProperties(ClassLiteral* lit) { void FullCodeGenerator::EmitBinaryOp(BinaryOperation* expr, Token::Value op) { __ mov(a0, result_register()); __ pop(a1); - Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), op).code(); + Handle<Code> code = CodeFactory::BinaryOpIC( + isolate(), op, language_mode()).code(); JumpPatchSite patch_site(masm_); // unbound, signals no inlined smi code. CallIC(code, expr->BinaryOperationFeedbackId()); patch_site.EmitPatchInfo(); @@ -3090,6 +3062,22 @@ void FullCodeGenerator::EmitLoadSuperConstructor() { } +void FullCodeGenerator::EmitInitializeThisAfterSuper( + SuperReference* super_ref) { + Variable* this_var = super_ref->this_var()->var(); + GetVar(a1, this_var); + __ LoadRoot(at, Heap::kTheHoleValueRootIndex); + Label uninitialized_this; + __ Branch(&uninitialized_this, eq, a1, Operand(at)); + __ li(a0, Operand(this_var->name())); + __ Push(a0); + __ CallRuntime(Runtime::kThrowReferenceError, 1); + __ bind(&uninitialized_this); + + EmitVariableAssignment(this_var, Token::INIT_CONST); +} + + void FullCodeGenerator::VisitCall(Call* expr) { #ifdef DEBUG // We want to verify that RecordJSReturnSite gets called on all paths @@ -3311,18 +3299,7 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) { RecordJSReturnSite(expr); - SuperReference* super_ref = expr->expression()->AsSuperReference(); - Variable* this_var = super_ref->this_var()->var(); - GetVar(a1, this_var); - __ LoadRoot(at, Heap::kTheHoleValueRootIndex); - Label uninitialized_this; - __ Branch(&uninitialized_this, eq, a1, Operand(at)); - __ li(a0, Operand(this_var->name())); - __ Push(a0); - __ CallRuntime(Runtime::kThrowReferenceError, 1); - __ bind(&uninitialized_this); - - EmitVariableAssignment(this_var, Token::INIT_CONST); + EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference()); context()->Plug(v0); } @@ -4614,27 +4591,81 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) { } +void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) { + // Assert: expr === CallRuntime("ReflectConstruct") + CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime(); + ZoneList<Expression*>* args = call->arguments(); + DCHECK_EQ(3, args->length()); + + SuperReference* super_reference = args->at(0)->AsSuperReference(); + + // Load ReflectConstruct function + EmitLoadJSRuntimeFunction(call); + + // Push the target function under the receiver. + __ ld(at, MemOperand(sp, 0)); + __ push(at); + __ sd(v0, MemOperand(sp, kPointerSize)); + + // Push super + EmitLoadSuperConstructor(); + __ Push(result_register()); + + // Push arguments array + VisitForStackValue(args->at(1)); + + // Push NewTarget + DCHECK(args->at(2)->IsVariableProxy()); + VisitForStackValue(args->at(2)); + + EmitCallJSRuntimeFunction(call); + + // Restore context register. + __ ld(cp, MemOperand(fp, StandardFrameConstants::kContextOffset)); + context()->DropAndPlug(1, v0); + + EmitInitializeThisAfterSuper(super_reference); +} + + +void FullCodeGenerator::EmitLoadJSRuntimeFunction(CallRuntime* expr) { + // Push the builtins object as the receiver. + Register receiver = LoadDescriptor::ReceiverRegister(); + __ ld(receiver, GlobalObjectOperand()); + __ ld(receiver, FieldMemOperand(receiver, GlobalObject::kBuiltinsOffset)); + __ push(receiver); + + // Load the function from the receiver. + __ li(LoadDescriptor::NameRegister(), Operand(expr->name())); + if (FLAG_vector_ics) { + __ li(VectorLoadICDescriptor::SlotRegister(), + Operand(SmiFromSlot(expr->CallRuntimeFeedbackSlot()))); + CallLoadIC(NOT_CONTEXTUAL); + } else { + CallLoadIC(NOT_CONTEXTUAL, expr->CallRuntimeFeedbackId()); + } +} + + +void FullCodeGenerator::EmitCallJSRuntimeFunction(CallRuntime* expr) { + ZoneList<Expression*>* args = expr->arguments(); + int arg_count = args->length(); + + // Record source position of the IC call. + SetSourcePosition(expr->position()); + CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); + __ ld(a1, MemOperand(sp, (arg_count + 1) * kPointerSize)); + __ CallStub(&stub); +} + + void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { ZoneList<Expression*>* args = expr->arguments(); int arg_count = args->length(); if (expr->is_jsruntime()) { Comment cmnt(masm_, "[ CallRuntime"); - // Push the builtins object as the receiver. - Register receiver = LoadDescriptor::ReceiverRegister(); - __ ld(receiver, GlobalObjectOperand()); - __ ld(receiver, FieldMemOperand(receiver, GlobalObject::kBuiltinsOffset)); - __ push(receiver); - - // Load the function from the receiver. - __ li(LoadDescriptor::NameRegister(), Operand(expr->name())); - if (FLAG_vector_ics) { - __ li(VectorLoadICDescriptor::SlotRegister(), - Operand(SmiFromSlot(expr->CallRuntimeFeedbackSlot()))); - CallLoadIC(NOT_CONTEXTUAL); - } else { - CallLoadIC(NOT_CONTEXTUAL, expr->CallRuntimeFeedbackId()); - } + EmitLoadJSRuntimeFunction(expr); // Push the target function under the receiver. __ ld(at, MemOperand(sp, 0)); @@ -4646,11 +4677,7 @@ void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { VisitForStackValue(args->at(i)); } - // Record source position of the IC call. - SetSourcePosition(expr->position()); - CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); - __ ld(a1, MemOperand(sp, (arg_count + 1) * kPointerSize)); - __ CallStub(&stub); + EmitCallJSRuntimeFunction(expr); // Restore context register. __ ld(cp, MemOperand(fp, StandardFrameConstants::kContextOffset)); @@ -4778,10 +4805,13 @@ void FullCodeGenerator::VisitUnaryOperation(UnaryOperation* expr) { case Token::TYPEOF: { Comment cmnt(masm_, "[ UnaryOperation (TYPEOF)"); - { StackValueContext context(this); + { + AccumulatorValueContext context(this); VisitForTypeofValue(expr->expression()); } - __ CallRuntime(Runtime::kTypeof, 1); + __ mov(a3, v0); + TypeofStub typeof_stub(isolate()); + __ CallStub(&typeof_stub); context()->Plug(v0); break; } @@ -4952,7 +4982,8 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) { // Record position before stub call. SetSourcePosition(expr->position()); - Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), Token::ADD).code(); + Handle<Code> code = CodeFactory::BinaryOpIC( + isolate(), Token::ADD, language_mode()).code(); CallIC(code, expr->CountBinOpFeedbackId()); patch_site.EmitPatchInfo(); __ bind(&done); |