Revert of [es6] Super call in arrows and eval (patchset #5 id:100001 of https://codereview.chromium.org/1146863007/)

Reason for revert:
Fails

http://build.chromium.org/p/client.v8/builders/V8%20Linux%20-%20nosnap%20-%20debug%20-%201/builds/579/steps/Check/logs/super

Original issue's description:
> [es6] Super call in arrows and eval
>
> This splits the SuperReference AST node into SuperPropertyReference and
> SuperCallReference. The super call reference node consists of three
> unresolved vars to this, new.target and this_function. These gets
> declared when the right function is entered and if it is in use. The
> variables gets assigned in FullCodeGenerator::Generate.
>
> BUG=v8:3768
> LOG=N
> R=wingo@igalia.com, adamk@chromium.org
>
> Committed: https://crrev.com/673c0516ab96f24343bbb26e0afc2846b5a679df
> Cr-Commit-Position: refs/heads/master@{#28731}

TBR=wingo@igalia.com,adamk@chromium.org
NOPRESUBMIT=true
NOTREECHECKS=true
NOTRY=true
BUG=v8:3768

Review URL: https://codereview.chromium.org/1161243005

Cr-Commit-Position: refs/heads/master@{#28735}
This commit is contained in:
arv 2015-06-01 09:10:08 -07:00 committed by Commit bot
parent 710baad489
commit 88b1c9170a
26 changed files with 342 additions and 743 deletions

View File

@ -242,24 +242,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, r1, r0, r2);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset = 2 * kPointerSize +
(info_->scope()->num_parameters() + 1) * kPointerSize;
__ ldr(r0, MemOperand(fp, offset));
SetVar(new_target_var, r0, r2, r3);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ Push(r1);
@ -2020,10 +2002,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
if (expr->is_compound()) {
const Register scratch = r1;
@ -2033,10 +2014,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case KEYED_SUPER_PROPERTY:
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(property->key());
__ Push(result_register());
if (expr->is_compound()) {
@ -2679,9 +2659,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ Push(r0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; r0: home_object
Register scratch = r2;
Register scratch2 = r3;
@ -2696,9 +2676,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ Push(r0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = r2;
Register scratch2 = r3;
@ -2922,9 +2901,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::ReceiverRegister(), r0);
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2935,9 +2913,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ pop(LoadDescriptor::ReceiverRegister());
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -3002,7 +2979,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
DCHECK(!key->value()->IsSmi());
// Load the function from the receiver.
const Register scratch = r1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(r0);
@ -3062,7 +3039,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
SetSourcePosition(prop->position());
// Load the function from the receiver.
const Register scratch = r1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(r0);
@ -3144,8 +3121,15 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ ldr(r0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset));
__ Push(r0);
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_ref, FeedbackVectorICSlot slot) {
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(r1, this_var);
__ CompareRoot(r1, Heap::kTheHoleValueRootIndex);
@ -3305,7 +3289,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3341,14 +3325,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3386,7 +3367,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(r0);
}
@ -4247,15 +4229,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ Push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4648,14 +4626,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr === CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4665,8 +4640,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ push(ip);
__ str(r0, MemOperand(sp, kPointerSize));
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4683,7 +4658,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, r0);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4908,9 +4883,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
const Register scratch = r1;
__ ldr(scratch, MemOperand(sp, kPointerSize));
@ -4921,9 +4896,8 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
__ Push(result_register());
const Register scratch = r1;

View File

@ -243,24 +243,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, x1, x0, x2);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset =
2 * kXRegSize + (info_->scope()->num_parameters() + 1) * kPointerSize;
__ Ldr(x0, MemOperand(fp, offset));
SetVar(new_target_var, x0, x2, x3);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ Push(x1);
@ -1988,10 +1970,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
if (expr->is_compound()) {
const Register scratch = x10;
@ -2000,10 +1981,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case KEYED_SUPER_PROPERTY:
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(property->key());
__ Push(result_register());
if (expr->is_compound()) {
@ -2360,9 +2340,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ Push(x0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; x0: home_object
Register scratch = x10;
Register scratch2 = x11;
@ -2377,9 +2357,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ Push(x0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = x10;
Register scratch2 = x11;
@ -2605,9 +2584,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::ReceiverRegister(), x0);
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2618,9 +2596,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Pop(LoadDescriptor::ReceiverRegister());
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -2688,8 +2665,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
// Load the function from the receiver.
const Register scratch = x10;
SuperPropertyReference* super_ref =
callee->AsProperty()->obj()->AsSuperPropertyReference();
SuperReference* super_ref = callee->AsProperty()->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(x0);
@ -2748,8 +2724,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
// Load the function from the receiver.
const Register scratch = x10;
SuperPropertyReference* super_ref =
callee->AsProperty()->obj()->AsSuperPropertyReference();
SuperReference* super_ref = callee->AsProperty()->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(x0);
@ -2830,8 +2805,15 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ ldr(x0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset));
__ Push(x0);
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_ref, FeedbackVectorICSlot slot) {
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(x1, this_var);
Label uninitialized_this;
@ -2991,7 +2973,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3027,14 +3009,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3072,7 +3051,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(x0);
}
@ -3952,15 +3932,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ Push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4333,14 +4309,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr === CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4349,8 +4322,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ Pop(x10);
__ Push(x0, x10);
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4367,7 +4340,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, x0);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4589,9 +4562,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
const Register scratch = x10;
__ Peek(scratch, kPointerSize);
@ -4601,9 +4574,8 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
__ Push(result_register());
const Register scratch1 = x10;

View File

@ -168,26 +168,15 @@ void AstNumberingVisitor::VisitThisFunction(ThisFunction* node) {
}
void AstNumberingVisitor::VisitSuperPropertyReference(
SuperPropertyReference* node) {
void AstNumberingVisitor::VisitSuperReference(SuperReference* node) {
IncrementNodeCount();
DisableOptimization(kSuperReference);
node->set_base_id(ReserveIdRange(SuperPropertyReference::num_ids()));
node->set_base_id(ReserveIdRange(SuperReference::num_ids()));
Visit(node->this_var());
Visit(node->home_object_var());
}
void AstNumberingVisitor::VisitSuperCallReference(SuperCallReference* node) {
IncrementNodeCount();
DisableOptimization(kSuperReference);
node->set_base_id(ReserveIdRange(SuperCallReference::num_ids()));
Visit(node->this_var());
Visit(node->new_target_var());
Visit(node->this_function_var());
}
void AstNumberingVisitor::VisitImportDeclaration(ImportDeclaration* node) {
IncrementNodeCount();
DisableOptimization(kImportDeclaration);

View File

@ -267,7 +267,6 @@ class AstValue : public ZoneObject {
F(spread_arguments, "$spreadArguments") \
F(spread_iterable, "$spreadIterable") \
F(this, "this") \
F(this_function, ".this_function") \
F(throw_iterator_result_not_an_object, "ThrowIteratorResultNotAnObject") \
F(to_string, "$toString") \
F(undefined, "undefined") \

View File

@ -734,7 +734,7 @@ Call::CallType Call::GetCallType(Isolate* isolate) const {
}
}
if (expression()->IsSuperCallReference()) return SUPER_CALL;
if (expression()->AsSuperReference() != NULL) return SUPER_CALL;
Property* property = expression()->AsProperty();
return property != NULL ? PROPERTY_CALL : OTHER_CALL;

View File

@ -87,8 +87,7 @@ namespace internal {
V(CompareOperation) \
V(Spread) \
V(ThisFunction) \
V(SuperPropertyReference) \
V(SuperCallReference) \
V(SuperReference) \
V(CaseClause)
#define AST_NODE_LIST(V) \
@ -1761,7 +1760,9 @@ class Property final : public Expression {
}
bool is_for_call() const { return IsForCallField::decode(bit_field_); }
bool IsSuperAccess() { return obj()->IsSuperPropertyReference(); }
bool IsSuperAccess() {
return obj()->IsSuperReference();
}
virtual FeedbackVectorRequirements ComputeFeedbackRequirements(
Isolate* isolate, const ICSlotCache* cache) override {
@ -2790,16 +2791,16 @@ class ThisFunction final : public Expression {
};
class SuperPropertyReference final : public Expression {
class SuperReference final : public Expression {
public:
DECLARE_NODE_TYPE(SuperPropertyReference)
DECLARE_NODE_TYPE(SuperReference)
VariableProxy* this_var() const { return this_var_; }
VariableProxy* home_object_var() const { return home_object_var_; }
protected:
SuperPropertyReference(Zone* zone, VariableProxy* this_var,
VariableProxy* home_object_var, int pos)
SuperReference(Zone* zone, VariableProxy* this_var,
VariableProxy* home_object_var, int pos)
: Expression(zone, pos),
this_var_(this_var),
home_object_var_(home_object_var) {
@ -2813,34 +2814,6 @@ class SuperPropertyReference final : public Expression {
};
class SuperCallReference final : public Expression {
public:
DECLARE_NODE_TYPE(SuperCallReference)
VariableProxy* this_var() const { return this_var_; }
VariableProxy* new_target_var() const { return new_target_var_; }
VariableProxy* this_function_var() const { return this_function_var_; }
protected:
SuperCallReference(Zone* zone, VariableProxy* this_var,
VariableProxy* new_target_var,
VariableProxy* this_function_var, int pos)
: Expression(zone, pos),
this_var_(this_var),
new_target_var_(new_target_var),
this_function_var_(this_function_var) {
DCHECK(this_var->is_this());
DCHECK(new_target_var->raw_name()->IsOneByteEqualTo("new.target"));
DCHECK(this_function_var->raw_name()->IsOneByteEqualTo(".this_function"));
}
private:
VariableProxy* this_var_;
VariableProxy* new_target_var_;
VariableProxy* this_function_var_;
};
#undef DECLARE_NODE_TYPE
@ -3608,18 +3581,9 @@ class AstNodeFactory final BASE_EMBEDDED {
return new (zone_) ThisFunction(zone_, pos);
}
SuperPropertyReference* NewSuperPropertyReference(
VariableProxy* this_var, VariableProxy* home_object_var, int pos) {
return new (zone_)
SuperPropertyReference(zone_, this_var, home_object_var, pos);
}
SuperCallReference* NewSuperCallReference(VariableProxy* this_var,
VariableProxy* new_target_var,
VariableProxy* this_function_var,
int pos) {
return new (zone_) SuperCallReference(zone_, this_var, new_target_var,
this_function_var, pos);
SuperReference* NewSuperReference(VariableProxy* this_var,
VariableProxy* home_object_var, int pos) {
return new (zone_) SuperReference(zone_, this_var, home_object_var, pos);
}
private:

View File

@ -2590,15 +2590,7 @@ void AstGraphBuilder::VisitThisFunction(ThisFunction* expr) {
}
void AstGraphBuilder::VisitSuperPropertyReference(
SuperPropertyReference* expr) {
// TODO(turbofan): Implement super here.
SetStackOverflow();
ast_context()->ProduceValue(jsgraph()->UndefinedConstant());
}
void AstGraphBuilder::VisitSuperCallReference(SuperCallReference* expr) {
void AstGraphBuilder::VisitSuperReference(SuperReference* expr) {
// TODO(turbofan): Implement super here.
SetStackOverflow();
ast_context()->ProduceValue(jsgraph()->UndefinedConstant());

View File

@ -67,8 +67,7 @@ void ALAA::VisitVariableProxy(VariableProxy* leaf) {}
void ALAA::VisitLiteral(Literal* leaf) {}
void ALAA::VisitRegExpLiteral(RegExpLiteral* leaf) {}
void ALAA::VisitThisFunction(ThisFunction* leaf) {}
void ALAA::VisitSuperPropertyReference(SuperPropertyReference* leaf) {}
void ALAA::VisitSuperCallReference(SuperCallReference* leaf) {}
void ALAA::VisitSuperReference(SuperReference* leaf) {}
// ---------------------------------------------------------------------------

View File

@ -276,12 +276,7 @@ void BreakableStatementChecker::VisitThisFunction(ThisFunction* expr) {
}
void BreakableStatementChecker::VisitSuperPropertyReference(
SuperPropertyReference* expr) {}
void BreakableStatementChecker::VisitSuperCallReference(
SuperCallReference* expr) {}
void BreakableStatementChecker::VisitSuperReference(SuperReference* expr) {}
#define __ ACCESS_MASM(masm())
@ -673,13 +668,7 @@ void FullCodeGenerator::SetStatementPosition(Statement* stmt) {
}
void FullCodeGenerator::VisitSuperPropertyReference(
SuperPropertyReference* super) {
__ CallRuntime(Runtime::kThrowUnsupportedSuperError, 0);
}
void FullCodeGenerator::VisitSuperCallReference(SuperCallReference* super) {
void FullCodeGenerator::VisitSuperReference(SuperReference* super) {
__ CallRuntime(Runtime::kThrowUnsupportedSuperError, 0);
}
@ -989,12 +978,6 @@ void FullCodeGenerator::EmitPropertyKey(ObjectLiteralProperty* property,
}
void FullCodeGenerator::EmitLoadSuperConstructor(SuperCallReference* ref) {
VisitForStackValue(ref->this_function_var());
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::VisitReturnStatement(ReturnStatement* stmt) {
Comment cmnt(masm_, "[ ReturnStatement");
SetStatementPosition(stmt);

View File

@ -672,9 +672,9 @@ class FullCodeGenerator: public AstVisitor {
Expression* initializer, int offset,
FeedbackVectorICSlot slot = FeedbackVectorICSlot::Invalid());
void EmitLoadSuperConstructor(SuperCallReference* super_call_ref);
void EmitLoadSuperConstructor();
void EmitInitializeThisAfterSuper(
SuperCallReference* super_call_ref,
SuperReference* super_ref,
FeedbackVectorICSlot slot = FeedbackVectorICSlot::Invalid());
void CallIC(Handle<Code> code,

View File

@ -11568,16 +11568,7 @@ void HOptimizedGraphBuilder::VisitThisFunction(ThisFunction* expr) {
}
void HOptimizedGraphBuilder::VisitSuperPropertyReference(
SuperPropertyReference* expr) {
DCHECK(!HasStackOverflow());
DCHECK(current_block() != NULL);
DCHECK(current_block()->HasPredecessor());
return Bailout(kSuperReference);
}
void HOptimizedGraphBuilder::VisitSuperCallReference(SuperCallReference* expr) {
void HOptimizedGraphBuilder::VisitSuperReference(SuperReference* expr) {
DCHECK(!HasStackOverflow());
DCHECK(current_block() != NULL);
DCHECK(current_block()->HasPredecessor());

View File

@ -238,24 +238,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, edi, ebx, edx);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset = 2 * kPointerSize + kFPOnStackSize + kPCOnStackSize +
(info_->scope()->num_parameters() - 1) * kPointerSize;
__ mov(eax, Operand(ebp, offset));
SetVar(new_target_var, eax, ebx, edx);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ push(edi);
@ -1938,10 +1920,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
// Nothing to do here.
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ push(result_register());
if (expr->is_compound()) {
__ push(MemOperand(esp, kPointerSize));
@ -1958,10 +1939,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case KEYED_SUPER_PROPERTY:
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(property->key());
__ Push(result_register());
if (expr->is_compound()) {
@ -2585,9 +2565,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ push(eax);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; eax: home_object
Register scratch = ecx;
Register scratch2 = edx;
@ -2602,9 +2582,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ push(eax);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = ecx;
Register scratch2 = edx;
@ -2826,9 +2805,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::ReceiverRegister(), result_register());
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2839,9 +2817,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::NameRegister(), result_register()); // Key.
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -2899,7 +2876,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
Literal* key = prop->key()->AsLiteral();
DCHECK(!key->value()->IsSmi());
// Load the function from the receiver.
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = callee->AsProperty()->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ push(eax);
@ -2955,7 +2932,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
SetSourcePosition(prop->position());
// Load the function from the receiver.
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = callee->AsProperty()->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ push(eax);
@ -3033,9 +3010,15 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ push(Operand(ebp, JavaScriptFrameConstants::kFunctionOffset));
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_call_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_call_ref->this_var()->var();
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(ecx, this_var);
__ cmp(ecx, isolate()->factory()->the_hole_value());
Label uninitialized_this;
@ -3184,7 +3167,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3220,14 +3203,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(eax, new_target_var);
__ push(eax);
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3265,7 +3245,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(eax);
}
@ -4142,15 +4123,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(eax, new_target_var);
__ push(eax);
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4573,14 +4550,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr == CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4589,8 +4563,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ push(Operand(esp, 0));
__ mov(Operand(esp, kPointerSize), eax);
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4607,7 +4581,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, eax);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4832,9 +4806,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ push(result_register());
__ push(MemOperand(esp, kPointerSize));
__ push(result_register());
@ -4843,9 +4817,8 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
__ push(result_register());
__ push(MemOperand(esp, 2 * kPointerSize));

View File

@ -251,24 +251,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, a1, a2, a3);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset = 2 * kPointerSize +
(info_->scope()->num_parameters() + 1) * kPointerSize;
__ lw(v0, MemOperand(fp, offset));
SetVar(new_target_var, v0, a2, a3);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ Push(a1);
@ -2006,10 +1988,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
if (expr->is_compound()) {
const Register scratch = a1;
@ -2019,10 +2000,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
break;
case KEYED_SUPER_PROPERTY: {
const Register scratch = a1;
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Move(scratch, result_register());
VisitForAccumulatorValue(property->key());
__ Push(scratch, result_register());
@ -2656,9 +2636,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ Push(v0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; v0: home_object
Register scratch = a2;
Register scratch2 = a3;
@ -2673,9 +2653,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ Push(v0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = a2;
Register scratch2 = a3;
@ -2904,9 +2883,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::ReceiverRegister(), v0);
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2917,9 +2895,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ pop(LoadDescriptor::ReceiverRegister());
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -2981,7 +2958,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
DCHECK(!key->value()->IsSmi());
// Load the function from the receiver.
const Register scratch = a1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForAccumulatorValue(super_ref->home_object_var());
__ mov(scratch, v0);
VisitForAccumulatorValue(super_ref->this_var());
@ -3039,7 +3016,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
SetSourcePosition(prop->position());
// Load the function from the receiver.
const Register scratch = a1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForAccumulatorValue(super_ref->home_object_var());
__ Move(scratch, v0);
VisitForAccumulatorValue(super_ref->this_var());
@ -3119,8 +3096,15 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ lw(a0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset));
__ Push(a0);
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_ref, FeedbackVectorICSlot slot) {
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(a1, this_var);
__ LoadRoot(at, Heap::kTheHoleValueRootIndex);
@ -3278,7 +3262,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3314,14 +3298,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3359,7 +3340,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(v0);
}
@ -4245,15 +4227,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ Push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4655,14 +4633,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr == CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4672,8 +4647,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ push(at);
__ sw(v0, MemOperand(sp, kPointerSize));
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4690,7 +4665,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, v0);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4915,9 +4890,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
const Register scratch = a1;
__ lw(scratch, MemOperand(sp, kPointerSize));
@ -4927,9 +4902,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
const Register scratch = a1;
const Register scratch1 = t0;
__ Move(scratch, result_register());

View File

@ -248,24 +248,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, a1, a2, a3);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset = 2 * kPointerSize +
(info_->scope()->num_parameters() + 1) * kPointerSize;
__ lw(v0, MemOperand(fp, offset));
SetVar(new_target_var, v0, a2, a3);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ Push(a1);
@ -2005,10 +1987,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
if (expr->is_compound()) {
const Register scratch = a1;
@ -2018,10 +1999,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
break;
case KEYED_SUPER_PROPERTY: {
const Register scratch = a1;
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Move(scratch, result_register());
VisitForAccumulatorValue(property->key());
__ Push(scratch, result_register());
@ -2655,9 +2635,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ Push(v0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; v0: home_object
Register scratch = a2;
Register scratch2 = a3;
@ -2672,9 +2652,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ Push(v0);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = a2;
Register scratch2 = a3;
@ -2907,9 +2886,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Move(LoadDescriptor::ReceiverRegister(), v0);
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2920,9 +2898,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ pop(LoadDescriptor::ReceiverRegister());
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -2984,7 +2961,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
DCHECK(!key->value()->IsSmi());
// Load the function from the receiver.
const Register scratch = a1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForAccumulatorValue(super_ref->home_object_var());
__ mov(scratch, v0);
VisitForAccumulatorValue(super_ref->this_var());
@ -3042,7 +3019,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
SetSourcePosition(prop->position());
// Load the function from the receiver.
const Register scratch = a1;
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForAccumulatorValue(super_ref->home_object_var());
__ Move(scratch, v0);
VisitForAccumulatorValue(super_ref->this_var());
@ -3121,8 +3098,15 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ ld(a0, MemOperand(fp, JavaScriptFrameConstants::kFunctionOffset));
__ Push(a0);
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_ref, FeedbackVectorICSlot slot) {
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(a1, this_var);
__ LoadRoot(at, Heap::kTheHoleValueRootIndex);
@ -3280,7 +3264,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3316,14 +3300,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3361,7 +3342,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(v0);
}
@ -4249,15 +4231,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ Push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4659,14 +4637,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr === CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4676,8 +4651,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ push(at);
__ sd(v0, MemOperand(sp, kPointerSize));
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4694,7 +4669,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, v0);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4918,9 +4893,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
const Register scratch = a1;
__ ld(scratch, MemOperand(sp, kPointerSize));
@ -4930,9 +4905,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
const Register scratch = a1;
const Register scratch1 = a4;
__ Move(scratch, result_register());

View File

@ -359,17 +359,8 @@ FunctionLiteral* Parser::DefaultConstructor(bool call_super, Scope* scope,
body = new (zone()) ZoneList<Statement*>(call_super ? 2 : 1, zone());
AddAssertIsConstruct(body, pos);
if (call_super) {
// %_DefaultConstructorCallSuper(new.target, .this_function)
ZoneList<Expression*>* args =
new (zone()) ZoneList<Expression*>(2, zone());
VariableProxy* new_target_proxy = scope_->NewUnresolved(
factory(), ast_value_factory()->new_target_string(), Variable::NORMAL,
pos);
args->Add(new_target_proxy, zone());
VariableProxy* this_function_proxy = scope_->NewUnresolved(
factory(), ast_value_factory()->this_function_string(),
Variable::NORMAL, pos);
args->Add(this_function_proxy, zone());
new (zone()) ZoneList<Expression*>(0, zone());
CallRuntime* call = factory()->NewCallRuntime(
ast_value_factory()->empty_string(),
Runtime::FunctionForId(Runtime::kInlineDefaultConstructorCallSuper),
@ -756,32 +747,19 @@ Expression* ParserTraits::ThisExpression(Scope* scope, AstNodeFactory* factory,
Variable::THIS, pos, pos + 4);
}
Expression* ParserTraits::SuperPropertyReference(Scope* scope,
AstNodeFactory* factory,
int pos) {
Expression* ParserTraits::SuperReference(Scope* scope, AstNodeFactory* factory,
int pos) {
// TODO(arv): Split into SuperProperty and SuperCall?
VariableProxy* home_object_proxy = scope->NewUnresolved(
factory, parser_->ast_value_factory()->home_object_string(),
Variable::NORMAL, pos);
return factory->NewSuperPropertyReference(
return factory->NewSuperReference(
ThisExpression(scope, factory, pos)->AsVariableProxy(), home_object_proxy,
pos);
}
Expression* ParserTraits::SuperCallReference(Scope* scope,
AstNodeFactory* factory, int pos) {
VariableProxy* new_target_proxy = scope->NewUnresolved(
factory, parser_->ast_value_factory()->new_target_string(),
Variable::NORMAL, pos);
VariableProxy* this_function_proxy = scope->NewUnresolved(
factory, parser_->ast_value_factory()->this_function_string(),
Variable::NORMAL, pos);
return factory->NewSuperCallReference(
ThisExpression(scope, factory, pos)->AsVariableProxy(), new_target_proxy,
this_function_proxy, pos);
}
Expression* ParserTraits::DefaultConstructor(bool call_super, Scope* scope,
int pos, int end_pos) {
return parser_->DefaultConstructor(call_super, scope, pos, end_pos);
@ -5766,14 +5744,13 @@ ZoneList<v8::internal::Expression*>* Parser::PrepareSpreadArguments(
Expression* Parser::SpreadCall(Expression* function,
ZoneList<v8::internal::Expression*>* args,
int pos) {
if (function->IsSuperCallReference()) {
if (function->IsSuperReference()) {
// Super calls
// %_CallSuperWithSpread(%ReflectConstruct(<super>, args, new.target))
args->InsertAt(0, function, zone());
args->Add(function->AsSuperCallReference()->new_target_var(), zone());
args->Add(factory()->NewVariableProxy(scope_->new_target_var()), zone());
Expression* result = factory()->NewCallRuntime(
ast_value_factory()->reflect_construct_string(), NULL, args, pos);
args = new (zone()) ZoneList<Expression*>(1, zone());
args = new (zone()) ZoneList<Expression*>(0, zone());
args->Add(result, zone());
return factory()->NewCallRuntime(
ast_value_factory()->empty_string(),

View File

@ -724,10 +724,7 @@ class ParserTraits {
Expression* ThisExpression(Scope* scope, AstNodeFactory* factory,
int pos = RelocInfo::kNoPosition);
Expression* SuperPropertyReference(Scope* scope, AstNodeFactory* factory,
int pos);
Expression* SuperCallReference(Scope* scope, AstNodeFactory* factory,
int pos);
Expression* SuperReference(Scope* scope, AstNodeFactory* factory, int pos);
Expression* DefaultConstructor(bool call_super, Scope* scope, int pos,
int end_pos);
Literal* ExpressionFromLiteral(Token::Value token, int pos, Scanner* scanner,

View File

@ -404,8 +404,7 @@ NOT_A_PATTERN(NativeFunctionLiteral)
NOT_A_PATTERN(Property)
NOT_A_PATTERN(RegExpLiteral)
NOT_A_PATTERN(ReturnStatement)
NOT_A_PATTERN(SuperPropertyReference)
NOT_A_PATTERN(SuperCallReference)
NOT_A_PATTERN(SuperReference)
NOT_A_PATTERN(SwitchStatement)
NOT_A_PATTERN(ThisFunction)
NOT_A_PATTERN(Throw)

View File

@ -1715,15 +1715,9 @@ class PreParserTraits {
return PreParserExpression::This();
}
static PreParserExpression SuperPropertyReference(Scope* scope,
PreParserFactory* factory,
int pos) {
return PreParserExpression::Default();
}
static PreParserExpression SuperCallReference(Scope* scope,
PreParserFactory* factory,
int pos) {
static PreParserExpression SuperReference(Scope* scope,
PreParserFactory* factory,
int pos) {
return PreParserExpression::Default();
}
@ -3521,7 +3515,7 @@ ParserBase<Traits>::ParseStrongSuperCallExpression(
Consume(Token::SUPER);
int pos = position();
Scanner::Location super_loc = scanner()->location();
ExpressionT expr = this->SuperCallReference(scope_, factory(), pos);
ExpressionT expr = this->SuperReference(scope_, factory(), pos);
if (peek() != Token::LPAREN) {
ReportMessage(MessageTemplate::kStrongConstructorSuper);
@ -3586,7 +3580,7 @@ ParserBase<Traits>::ParseSuperExpression(bool is_new,
i::IsConstructor(kind)) {
if (peek() == Token::PERIOD || peek() == Token::LBRACK) {
scope->RecordSuperPropertyUsage();
return this->SuperPropertyReference(scope_, factory(), pos);
return this->SuperReference(scope_, factory(), pos);
}
// new super() is never allowed.
// super() is only allowed in derived constructor
@ -3601,7 +3595,7 @@ ParserBase<Traits>::ParseSuperExpression(bool is_new,
// TODO(rossberg): This might not be the correct FunctionState for the
// method here.
function_state_->set_super_location(scanner()->location());
return this->SuperCallReference(scope_, factory(), pos);
return this->SuperReference(scope_, factory(), pos);
}
}

View File

@ -364,10 +364,7 @@ void CallPrinter::VisitSpread(Spread* node) {
void CallPrinter::VisitThisFunction(ThisFunction* node) {}
void CallPrinter::VisitSuperPropertyReference(SuperPropertyReference* node) {}
void CallPrinter::VisitSuperCallReference(SuperCallReference* node) {}
void CallPrinter::VisitSuperReference(SuperReference* node) {}
void CallPrinter::FindStatements(ZoneList<Statement*>* statements) {
@ -838,13 +835,8 @@ void PrettyPrinter::VisitThisFunction(ThisFunction* node) {
}
void PrettyPrinter::VisitSuperPropertyReference(SuperPropertyReference* node) {
Print("<super-property-reference>");
}
void PrettyPrinter::VisitSuperCallReference(SuperCallReference* node) {
Print("<super-call-reference>");
void PrettyPrinter::VisitSuperReference(SuperReference* node) {
Print("<super-reference>");
}
@ -1535,16 +1527,10 @@ void AstPrinter::VisitThisFunction(ThisFunction* node) {
}
void AstPrinter::VisitSuperPropertyReference(SuperPropertyReference* node) {
IndentedScope indent(this, "SUPER-PROPERTY-REFERENCE");
void AstPrinter::VisitSuperReference(SuperReference* node) {
IndentedScope indent(this, "SUPER-REFERENCE");
}
void AstPrinter::VisitSuperCallReference(SuperCallReference* node) {
IndentedScope indent(this, "SUPER-CALL-REFERENCE");
}
#endif // DEBUG
} } // namespace v8::internal

View File

@ -72,8 +72,8 @@ namespace internal {
F(StoreKeyedToSuper_Strict, 4, 1) \
F(StoreKeyedToSuper_Sloppy, 4, 1) \
F(HandleStepInForDerivedConstructors, 1, 1) \
F(DefaultConstructorCallSuper, 2, 1) \
F(CallSuperWithSpread, 1, 1)
F(DefaultConstructorCallSuper, 0, 1) \
F(CallSuperWithSpread, 0, 1)
#define FOR_EACH_INTRINSIC_COLLECTIONS(F) \

View File

@ -160,7 +160,6 @@ void Scope::SetDefaults(ScopeType scope_type, Scope* outer_scope,
function_ = nullptr;
arguments_ = nullptr;
home_object_ = nullptr;
this_function_ = nullptr;
illegal_redecl_ = nullptr;
scope_inside_with_ = false;
scope_contains_with_ = false;
@ -309,44 +308,45 @@ void Scope::Initialize() {
}
// Declare convenience variables and the receiver.
if (is_declaration_scope() && has_this_declaration()) {
Variable* var = variables_.Declare(
this, ast_value_factory_->this_string(),
subclass_constructor ? CONST : VAR, Variable::THIS,
subclass_constructor ? kNeedsInitialization : kCreatedInitialized);
receiver_ = var;
}
if (is_function_scope()) {
if (!is_arrow_scope()) {
// Declare 'arguments' variable which exists in all non arrow functions.
// Note that it might never be accessed, in which case it won't be
// allocated during variable allocation.
variables_.Declare(this, ast_value_factory_->arguments_string(), VAR,
Variable::ARGUMENTS, kCreatedInitialized);
if (is_declaration_scope()) {
DCHECK(!subclass_constructor || is_function_scope());
if (has_this_declaration()) {
Variable* var = variables_.Declare(
this, ast_value_factory_->this_string(),
subclass_constructor ? CONST : VAR, Variable::THIS,
subclass_constructor ? kNeedsInitialization : kCreatedInitialized);
receiver_ = var;
}
if (subclass_constructor) {
DCHECK(!is_arrow_scope());
variables_.Declare(this, ast_value_factory_->new_target_string(), CONST,
Variable::NORMAL, kCreatedInitialized);
new_target_ =
variables_.Declare(this, ast_value_factory_->new_target_string(),
CONST, Variable::NEW_TARGET, kCreatedInitialized);
new_target_->AllocateTo(Variable::PARAMETER, -2);
new_target_->set_is_used();
}
}
if (IsConciseMethod(function_kind_) || IsConstructor(function_kind_) ||
IsAccessorFunction(function_kind_)) {
DCHECK(!is_arrow_scope());
// Declare '.home_object' variable which exists in all methods.
// Note that it might never be accessed, in which case it won't be
// allocated during variable allocation.
variables_.Declare(this, ast_value_factory_->home_object_string(), CONST,
Variable::NORMAL, kCreatedInitialized);
}
if (is_function_scope() && !is_arrow_scope()) {
// Declare 'arguments' variable which exists in all non arrow functions.
// Note that it might never be accessed, in which case it won't be
// allocated during variable allocation.
variables_.Declare(this,
ast_value_factory_->arguments_string(),
VAR,
Variable::ARGUMENTS,
kCreatedInitialized);
}
if (IsSubclassConstructor(function_kind_)) {
DCHECK(!is_arrow_scope());
variables_.Declare(this, ast_value_factory_->this_function_string(),
CONST, Variable::NORMAL, kCreatedInitialized);
}
if (is_function_scope() &&
(IsConciseMethod(function_kind_) || IsConstructor(function_kind_) ||
IsAccessorFunction(function_kind_))) {
DCHECK(!is_arrow_scope());
// Declare '.home_object' variable which exists in all methods.
// Note that it might never be accessed, in which case it won't be
// allocated during variable allocation.
variables_.Declare(this, ast_value_factory_->home_object_string(), VAR,
Variable::NORMAL, kCreatedInitialized);
}
}
@ -1311,7 +1311,7 @@ bool Scope::MustAllocate(Variable* var) {
// Give var a read/write use if there is a chance it might be accessed
// via an eval() call. This is only possible if the variable has a
// visible name.
if ((var->is_this() || !var->raw_name()->IsEmpty()) &&
if ((var->is_this() || var->is_new_target() || !var->raw_name()->IsEmpty()) &&
(var->has_forced_context_allocation() || scope_calls_eval_ ||
inner_scope_calls_eval_ || scope_contains_with_ || is_catch_scope() ||
is_block_scope() || is_module_scope() || is_script_scope())) {
@ -1403,6 +1403,18 @@ void Scope::AllocateParameterLocals(Isolate* isolate) {
rest_parameter_ = NULL;
}
Variable* home_object_var =
LookupLocal(ast_value_factory_->home_object_string());
if (home_object_var != nullptr && uses_super_property() &&
MustAllocate(home_object_var)) {
// TODO(arv): super() uses a SuperReference so it generates a VariableProxy
// for the .home_object which makes it look like we need to allocate the
// home_object_var.
// Consider splitting the AST node into 2 different nodes since the
// semantics is just so different.
home_object_ = home_object_var;
}
// The same parameter may occur multiple times in the parameters_ list.
// If it does, and if it is not copied into the context object, it must
// receive the highest parameter index for that parameter; thus iteration
@ -1491,31 +1503,13 @@ void Scope::AllocateNonParameterLocals(Isolate* isolate) {
// allocated in the context, it must be the last slot in the context,
// because of the current ScopeInfo implementation (see
// ScopeInfo::ScopeInfo(FunctionScope* scope) constructor).
if (function_ != nullptr) {
if (function_ != NULL) {
AllocateNonParameterLocal(isolate, function_->proxy()->var());
}
if (rest_parameter_ != nullptr) {
if (rest_parameter_) {
AllocateNonParameterLocal(isolate, rest_parameter_);
}
Variable* home_object_var =
LookupLocal(ast_value_factory_->home_object_string());
if (home_object_var != nullptr && MustAllocate(home_object_var)) {
home_object_ = home_object_var;
}
Variable* new_target_var =
LookupLocal(ast_value_factory_->new_target_string());
if (new_target_var != nullptr && MustAllocate(new_target_var)) {
new_target_ = new_target_var;
}
Variable* this_function_var =
LookupLocal(ast_value_factory_->this_function_string());
if (this_function_var != nullptr && MustAllocate(this_function_var)) {
this_function_ = this_function_var;
}
}

View File

@ -419,13 +419,6 @@ class Scope: public ZoneObject {
return home_object_;
}
Variable* this_function_var() const {
// This is only used in derived constructors atm.
DCHECK(this_function_ == nullptr ||
(is_function_scope() && IsSubclassConstructor(function_kind())));
return this_function_;
}
// Declarations list.
ZoneList<Declaration*>* declarations() { return &decls_; }
@ -586,8 +579,6 @@ class Scope: public ZoneObject {
Variable* arguments_;
// Convenience variable; method scopes only.
Variable* home_object_;
// Convenience variable; Subclass constructor only
Variable* this_function_;
// Module descriptor; module scopes only.
ModuleDescriptor* module_descriptor_;

View File

@ -761,10 +761,7 @@ void AstTyper::VisitThisFunction(ThisFunction* expr) {
}
void AstTyper::VisitSuperPropertyReference(SuperPropertyReference* expr) {}
void AstTyper::VisitSuperCallReference(SuperCallReference* expr) {}
void AstTyper::VisitSuperReference(SuperReference* expr) {}
void AstTyper::VisitDeclarations(ZoneList<Declaration*>* decls) {

View File

@ -20,7 +20,7 @@ class ClassVariable;
class Variable: public ZoneObject {
public:
enum Kind { NORMAL, FUNCTION, CLASS, THIS, ARGUMENTS };
enum Kind { NORMAL, FUNCTION, CLASS, THIS, NEW_TARGET, ARGUMENTS };
enum Location {
// Before and during variable allocation, a variable whose location is
@ -103,6 +103,7 @@ class Variable: public ZoneObject {
bool is_function() const { return kind_ == FUNCTION; }
bool is_class() const { return kind_ == CLASS; }
bool is_this() const { return kind_ == THIS; }
bool is_new_target() const { return kind_ == NEW_TARGET; }
bool is_arguments() const { return kind_ == ARGUMENTS; }
ClassVariable* AsClassVariable() {

View File

@ -234,24 +234,6 @@ void FullCodeGenerator::Generate() {
}
}
// Possibly set up a local binding to the this function which is used in
// derived constructors with super calls.
Variable* this_function_var = scope()->this_function_var();
if (this_function_var != nullptr) {
Comment cmnt(masm_, "[ This function");
SetVar(this_function_var, rdi, rbx, rdx);
}
Variable* new_target_var = scope()->new_target_var();
if (new_target_var != nullptr) {
Comment cmnt(masm_, "[ new.target");
// new.target is parameter -2.
int offset = 2 * kPointerSize + kFPOnStackSize + kPCOnStackSize +
(info_->scope()->num_parameters() - 1) * kPointerSize;
__ movp(rax, Operand(rbp, offset));
SetVar(new_target_var, rax, rbx, rdx);
}
Variable* home_object_var = scope()->home_object_var();
if (home_object_var != nullptr) {
__ Push(rdi);
@ -1977,10 +1959,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case NAMED_SUPER_PROPERTY:
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
if (expr->is_compound()) {
__ Push(MemOperand(rsp, kPointerSize));
@ -1988,10 +1969,9 @@ void FullCodeGenerator::VisitAssignment(Assignment* expr) {
}
break;
case KEYED_SUPER_PROPERTY:
VisitForStackValue(property->obj()->AsSuperReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
property->obj()->AsSuperPropertyReference()->home_object_var());
property->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(property->key());
__ Push(result_register());
if (expr->is_compound()) {
@ -2583,9 +2563,9 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case NAMED_SUPER_PROPERTY: {
__ Push(rax);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
// stack: value, this; rax: home_object
Register scratch = rcx;
Register scratch2 = rdx;
@ -2600,9 +2580,8 @@ void FullCodeGenerator::EmitAssignment(Expression* expr,
}
case KEYED_SUPER_PROPERTY: {
__ Push(rax);
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
Register scratch = rcx;
Register scratch2 = rdx;
@ -2821,9 +2800,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ movp(LoadDescriptor::ReceiverRegister(), rax);
EmitNamedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
EmitNamedSuperPropertyLoad(expr);
}
} else {
@ -2834,9 +2812,8 @@ void FullCodeGenerator::VisitProperty(Property* expr) {
__ Pop(LoadDescriptor::ReceiverRegister());
EmitKeyedPropertyLoad(expr);
} else {
VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
expr->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(expr->obj()->AsSuperReference()->this_var());
VisitForStackValue(expr->obj()->AsSuperReference()->home_object_var());
VisitForStackValue(expr->key());
EmitKeyedSuperPropertyLoad(expr);
}
@ -2894,7 +2871,7 @@ void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
Literal* key = prop->key()->AsLiteral();
DCHECK(!key->value()->IsSmi());
// Load the function from the receiver.
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(rax);
@ -2951,7 +2928,7 @@ void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
SetSourcePosition(prop->position());
// Load the function from the receiver.
SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
SuperReference* super_ref = prop->obj()->AsSuperReference();
VisitForStackValue(super_ref->home_object_var());
VisitForAccumulatorValue(super_ref->this_var());
__ Push(rax);
@ -3032,8 +3009,14 @@ void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
}
void FullCodeGenerator::EmitLoadSuperConstructor() {
__ Push(Operand(rbp, JavaScriptFrameConstants::kFunctionOffset));
__ CallRuntime(Runtime::kGetPrototype, 1);
}
void FullCodeGenerator::EmitInitializeThisAfterSuper(
SuperCallReference* super_ref, FeedbackVectorICSlot slot) {
SuperReference* super_ref, FeedbackVectorICSlot slot) {
Variable* this_var = super_ref->this_var()->var();
GetVar(rcx, this_var);
__ CompareRoot(rcx, Heap::kTheHoleValueRootIndex);
@ -3183,7 +3166,7 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
// Push constructor on the stack. If it's not a function it's used as
// receiver for CALL_NON_FUNCTION, otherwise the value on the stack is
// ignored.
DCHECK(!expr->expression()->IsSuperPropertyReference());
DCHECK(!expr->expression()->IsSuperReference());
VisitForStackValue(expr->expression());
// Push the arguments ("left-to-right") on the stack.
@ -3219,14 +3202,11 @@ void FullCodeGenerator::VisitCallNew(CallNew* expr) {
void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
SuperCallReference* super_call_ref =
expr->expression()->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
VariableProxy* new_target_proxy = super_call_ref->new_target_var();
VisitForStackValue(new_target_proxy);
EmitLoadSuperConstructor(super_call_ref);
EmitLoadSuperConstructor();
__ Push(result_register());
// Push the arguments ("left-to-right") on the stack.
@ -3264,7 +3244,8 @@ void FullCodeGenerator::EmitSuperConstructorCall(Call* expr) {
RecordJSReturnSite(expr);
EmitInitializeThisAfterSuper(super_call_ref, expr->CallFeedbackICSlot());
EmitInitializeThisAfterSuper(expr->expression()->AsSuperReference(),
expr->CallFeedbackICSlot());
context()->Plug(rax);
}
@ -4131,15 +4112,11 @@ void FullCodeGenerator::EmitCallFunction(CallRuntime* expr) {
void FullCodeGenerator::EmitDefaultConstructorCallSuper(CallRuntime* expr) {
ZoneList<Expression*>* args = expr->arguments();
DCHECK(args->length() == 2);
Variable* new_target_var = scope()->DeclarationScope()->new_target_var();
GetVar(result_register(), new_target_var);
__ Push(result_register());
// new.target
VisitForStackValue(args->at(0));
// .this_function
VisitForStackValue(args->at(1));
__ CallRuntime(Runtime::kGetPrototype, 1);
EmitLoadSuperConstructor();
__ Push(result_register());
// Check if the calling frame is an arguments adaptor frame.
@ -4591,14 +4568,11 @@ void FullCodeGenerator::EmitDebugIsActive(CallRuntime* expr) {
void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
// Assert: expr === CallRuntime("ReflectConstruct")
DCHECK_EQ(1, expr->arguments()->length());
CallRuntime* call = expr->arguments()->at(0)->AsCallRuntime();
ZoneList<Expression*>* args = call->arguments();
DCHECK_EQ(3, args->length());
SuperCallReference* super_call_ref = args->at(0)->AsSuperCallReference();
DCHECK_NOT_NULL(super_call_ref);
SuperReference* super_reference = args->at(0)->AsSuperReference();
// Load ReflectConstruct function
EmitLoadJSRuntimeFunction(call);
@ -4607,8 +4581,8 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
__ Push(Operand(rsp, 0));
__ movp(Operand(rsp, kPointerSize), rax);
// Push super constructor
EmitLoadSuperConstructor(super_call_ref);
// Push super
EmitLoadSuperConstructor();
__ Push(result_register());
// Push arguments array
@ -4625,7 +4599,7 @@ void FullCodeGenerator::EmitCallSuperWithSpread(CallRuntime* expr) {
context()->DropAndPlug(1, rax);
// TODO(mvstanton): with FLAG_vector_stores this needs a slot id.
EmitInitializeThisAfterSuper(super_call_ref);
EmitInitializeThisAfterSuper(super_reference);
}
@ -4850,9 +4824,9 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case NAMED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForAccumulatorValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
prop->obj()->AsSuperReference()->home_object_var());
__ Push(result_register());
__ Push(MemOperand(rsp, kPointerSize));
__ Push(result_register());
@ -4861,9 +4835,8 @@ void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
}
case KEYED_SUPER_PROPERTY: {
VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
VisitForStackValue(
prop->obj()->AsSuperPropertyReference()->home_object_var());
VisitForStackValue(prop->obj()->AsSuperReference()->this_var());
VisitForStackValue(prop->obj()->AsSuperReference()->home_object_var());
VisitForAccumulatorValue(prop->key());
__ Push(result_register());
__ Push(MemOperand(rsp, 2 * kPointerSize));

View File

@ -3,7 +3,7 @@
// found in the LICENSE file.
// Flags: --harmony-classes --harmony-arrow-functions --allow-natives-syntax
// Flags: --harmony-spreadcalls
(function TestSuperNamedLoads() {
function Base() { }
@ -2107,99 +2107,3 @@ TestKeyedSetterCreatingOwnPropertiesNonConfigurable(42, 43, 44);
let d = new Derived();
assertSame(1, d.arrow());
})();
(function TestSuperCallInEval() {
'use strict';
class Base {
constructor(x) {
this.x = x;
}
}
class Derived extends Base {
constructor(x) {
eval('super(x)');
}
}
let d = new Derived(42);
assertSame(42, d.x);
})();
(function TestSuperCallInArrow() {
'use strict';
class Base {
constructor(x) {
this.x = x;
}
}
class Derived extends Base {
constructor(x) {
(() => super(x))();
}
}
let d = new Derived(42);
assertSame(42, d.x);
})();
(function TestSuperCallEscapes() {
'use strict';
class Base {
constructor(x) {
this.x = x;
}
}
let f;
class Derived extends Base {
constructor() {
f = () => super(2);
}
}
assertThrows(function() {
new Derived();
}, ReferenceError);
let o = f();
assertEquals(2, o.x);
assertInstanceof(o, Derived);
assertThrows(function() {
f();
}, ReferenceError);
})();
(function TestSuperCallSpreadInEval() {
'use strict';
class Base {
constructor(x) {
this.x = x;
}
}
class Derived extends Base {
constructor(x) {
eval('super(...[x])');
}
}
let d = new Derived(42);
assertSame(42, d.x);
})();
(function TestSuperCallSpreadInArrow() {
'use strict';
class Base {
constructor(x) {
this.x = x;
}
}
class Derived extends Base {
constructor(x) {
(() => super(...[x]))();
}
}
let d = new Derived(42);
assertSame(42, d.x);
})();