diff options
author | Lars Knoll <lars.knoll@qt.io> | 2018-06-22 12:32:13 +0200 |
---|---|---|
committer | Lars Knoll <lars.knoll@qt.io> | 2018-06-26 10:04:18 +0000 |
commit | eae4756f74d70de46d9345ece54345f597bc1929 (patch) | |
tree | 3bd9de778a4a035a79595ed160c7b474a03695ec /src/qml/jsruntime/qv4functionobject.cpp | |
parent | e9b3bdb96e008060a0e78815a3995015e5e4598d (diff) |
Add a MemberFunction function object
Member functions in ES7 can not be called as constructors and
will throw a type error when trying.
Some more fixes are needed here, as they also do not have a
prototype property.
Change-Id: Ieb920163acaa68d4ff0ff73ae4c1015e883b406f
Reviewed-by: Simon Hausmann <simon.hausmann@qt.io>
Diffstat (limited to 'src/qml/jsruntime/qv4functionobject.cpp')
-rw-r--r-- | src/qml/jsruntime/qv4functionobject.cpp | 35 |
1 files changed, 26 insertions, 9 deletions
diff --git a/src/qml/jsruntime/qv4functionobject.cpp b/src/qml/jsruntime/qv4functionobject.cpp index 589ed8fded..f73d6eef43 100644 --- a/src/qml/jsruntime/qv4functionobject.cpp +++ b/src/qml/jsruntime/qv4functionobject.cpp @@ -145,20 +145,25 @@ void FunctionObject::init(String *n, bool createProto) Scope s(internalClass()->engine); ScopedValue protectThis(s, this); - Q_ASSERT(internalClass() && internalClass()->find(s.engine->id_prototype()->identifier()) == Heap::FunctionObject::Index_Prototype); - if (createProto) { - ScopedObject proto(s, s.engine->newObject(s.engine->internalClasses(EngineBase::Class_ObjectProto))); - Q_ASSERT(s.engine->internalClasses(EngineBase::Class_ObjectProto)->find(s.engine->id_constructor()->identifier()) == Heap::FunctionObject::Index_ProtoConstructor); - proto->setProperty(Heap::FunctionObject::Index_ProtoConstructor, d()); - setProperty(Heap::FunctionObject::Index_Prototype, proto); - } else { - setProperty(Heap::FunctionObject::Index_Prototype, Primitive::undefinedValue()); - } + if (createProto) + createDefaultPrototypeProperty(); if (n) defineReadonlyConfigurableProperty(s.engine->id_name(), *n); } +void FunctionObject::createDefaultPrototypeProperty() +{ + Scope s(this); + + Q_ASSERT(internalClass() && internalClass()->find(s.engine->id_prototype()->identifier()) == Heap::FunctionObject::Index_Prototype); + Q_ASSERT(s.engine->internalClasses(EngineBase::Class_ObjectProto)->find(s.engine->id_constructor()->identifier()) == Heap::FunctionObject::Index_ProtoConstructor); + + ScopedObject proto(s, s.engine->newObject(s.engine->internalClasses(EngineBase::Class_ObjectProto))); + proto->setProperty(Heap::FunctionObject::Index_ProtoConstructor, d()); + setProperty(Heap::FunctionObject::Index_Prototype, proto); +} + ReturnedValue FunctionObject::name() const { return get(scope()->internalClass->engine->id_name()); @@ -184,6 +189,11 @@ Heap::FunctionObject *FunctionObject::createConstructorFunction(ExecutionContext return scope->engine()->memoryManager->allocate<ConstructorFunction>(scope, function); } +Heap::FunctionObject *FunctionObject::createMemberFunction(ExecutionContext *scope, Function *function) +{ + return scope->engine()->memoryManager->allocate<MemberFunction>(scope, function); +} + Heap::FunctionObject *FunctionObject::createBuiltinFunction(ExecutionEngine *engine, StringOrSymbol *nameOrSymbol, jsCallFunction code, int argumentCount) { Scope scope(engine); @@ -502,6 +512,13 @@ ReturnedValue ConstructorFunction::call(const FunctionObject *f, const Value *, return f->engine()->throwTypeError(QStringLiteral("Cannot call a class constructor without |new|")); } +DEFINE_OBJECT_VTABLE(MemberFunction); + +ReturnedValue MemberFunction::callAsConstructor(const FunctionObject *f, const Value *, int) +{ + return f->engine()->throwTypeError(QStringLiteral("Function is not a constructor.")); +} + DEFINE_OBJECT_VTABLE(DefaultClassConstructorFunction); ReturnedValue DefaultClassConstructorFunction::callAsConstructor(const FunctionObject *f, const Value *, int) |