aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/qml/jsruntime/qv4booleanobject_p.h1
-rw-r--r--src/qml/jsruntime/qv4context_p.h1
-rw-r--r--src/qml/jsruntime/qv4dateobject_p.h2
-rw-r--r--src/qml/jsruntime/qv4engine.cpp40
-rw-r--r--src/qml/jsruntime/qv4enginebase_p.h4
-rw-r--r--src/qml/jsruntime/qv4errorobject.cpp2
-rw-r--r--src/qml/jsruntime/qv4errorobject_p.h4
-rw-r--r--src/qml/jsruntime/qv4internalclass.cpp13
-rw-r--r--src/qml/jsruntime/qv4internalclass_p.h2
-rw-r--r--src/qml/jsruntime/qv4managed_p.h2
-rw-r--r--src/qml/jsruntime/qv4numberobject_p.h1
-rw-r--r--src/qml/jsruntime/qv4object.cpp1
-rw-r--r--src/qml/jsruntime/qv4object_p.h2
-rw-r--r--src/qml/jsruntime/qv4qmlcontext.cpp2
-rw-r--r--src/qml/jsruntime/qv4qobjectwrapper.cpp1
-rw-r--r--src/qml/jsruntime/qv4regexp_p.h1
-rw-r--r--src/qml/jsruntime/qv4sequenceobject_p.h1
-rw-r--r--src/qml/jsruntime/qv4string_p.h2
-rw-r--r--src/qml/jsruntime/qv4typedarray.cpp3
-rw-r--r--src/qml/jsruntime/qv4typedarray_p.h1
-rw-r--r--src/qml/jsruntime/qv4variantobject_p.h1
-rw-r--r--src/qml/memory/qv4heap_p.h10
-rw-r--r--src/qml/memory/qv4mm.cpp3
-rw-r--r--src/qml/memory/qv4mm_p.h17
24 files changed, 81 insertions, 36 deletions
diff --git a/src/qml/jsruntime/qv4booleanobject_p.h b/src/qml/jsruntime/qv4booleanobject_p.h
index 9c8b1d67f1..ca2cf7d17a 100644
--- a/src/qml/jsruntime/qv4booleanobject_p.h
+++ b/src/qml/jsruntime/qv4booleanobject_p.h
@@ -76,6 +76,7 @@ struct BooleanCtor: FunctionObject
struct BooleanPrototype: BooleanObject
{
+ V4_PROTOTYPE(objectPrototype)
void init(ExecutionEngine *engine, Object *ctor);
static void method_toString(const BuiltinFunction *, Scope &scope, CallData *callData);
diff --git a/src/qml/jsruntime/qv4context_p.h b/src/qml/jsruntime/qv4context_p.h
index c769dcd142..c742df7b97 100644
--- a/src/qml/jsruntime/qv4context_p.h
+++ b/src/qml/jsruntime/qv4context_p.h
@@ -228,6 +228,7 @@ struct Q_QML_EXPORT ExecutionContext : public Managed
V4_MANAGED(ExecutionContext, Managed)
Q_MANAGED_TYPE(ExecutionContext)
+ V4_INTERNALCLASS(ExecutionContext)
ExecutionEngine *engine() const { return d()->engine; }
diff --git a/src/qml/jsruntime/qv4dateobject_p.h b/src/qml/jsruntime/qv4dateobject_p.h
index a56d17f9b1..ecd57bcd8d 100644
--- a/src/qml/jsruntime/qv4dateobject_p.h
+++ b/src/qml/jsruntime/qv4dateobject_p.h
@@ -114,6 +114,8 @@ struct DateCtor: FunctionObject
struct DatePrototype: DateObject
{
+ V4_PROTOTYPE(objectPrototype)
+
void init(ExecutionEngine *engine, Object *ctor);
static double getThisDate(Scope &scope, CallData *callData);
diff --git a/src/qml/jsruntime/qv4engine.cpp b/src/qml/jsruntime/qv4engine.cpp
index 982db33092..6b05d9a05c 100644
--- a/src/qml/jsruntime/qv4engine.cpp
+++ b/src/qml/jsruntime/qv4engine.cpp
@@ -213,12 +213,12 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
classPool = new InternalClassPool;
internalClasses[Class_Empty] = new (classPool) InternalClass(this);
- internalClasses[Class_Object] = internalClasses[Class_Empty];
-
+ internalClasses[Class_Object] = internalClasses[Class_Empty]->changeVTable(QV4::Object::staticVTable());
internalClasses[Class_String] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::String::staticVTable());
internalClasses[Class_MemberData] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::MemberData::staticVTable());
internalClasses[Class_SimpleArrayData] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::SimpleArrayData::staticVTable());
internalClasses[Class_SparseArrayData] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::SparseArrayData::staticVTable());
+ internalClasses[Class_ExecutionContext] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::ExecutionContext::staticVTable());
jsStrings[String_Empty] = newIdentifier(QString());
jsStrings[String_undefined] = newIdentifier(QStringLiteral("undefined"));
@@ -259,11 +259,13 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
jsObjects[ObjectProto] = memoryManager->allocObject<ObjectPrototype>(internalClasses[Class_Object]);
- internalClasses[Class_ArrayObject] = internalClasses[Class_Object]->addMember(id_length(), Attr_NotConfigurable|Attr_NotEnumerable);
+ internalClasses[Class_ArrayObject] = internalClasses[Class_Empty]->changeVTable(QV4::ArrayObject::staticVTable());
+ internalClasses[Class_ArrayObject] = internalClasses[Class_ArrayObject]->addMember(id_length(), Attr_NotConfigurable|Attr_NotEnumerable);
jsObjects[ArrayProto] = memoryManager->allocObject<ArrayPrototype>(internalClasses[Class_ArrayObject], objectPrototype());
jsObjects[PropertyListProto] = memoryManager->allocObject<PropertyListPrototype>();
- InternalClass *argsClass = internalClasses[Class_Object]->addMember(id_length(), Attr_NotEnumerable);
+ InternalClass *argsClass = internalClasses[Class_Empty]->changeVTable(QV4::ArgumentsObject::staticVTable())
+ ->addMember(id_length(), Attr_NotEnumerable);
internalClasses[EngineBase::Class_ArgumentsObject] = argsClass->addMember(id_callee(), Attr_Data|Attr_NotEnumerable);
argsClass = argsClass->addMember(id_callee(), Attr_Accessor|Attr_NotConfigurable|Attr_NotEnumerable);
internalClasses[EngineBase::Class_StrictArgumentsObject] = argsClass->addMember(id_caller(), Attr_Accessor|Attr_NotConfigurable|Attr_NotEnumerable);
@@ -272,15 +274,18 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
Q_ASSERT(globalObject->d()->vtable());
initRootContext();
- internalClasses[EngineBase::Class_StringObject] = internalClasses[Class_Object]->addMember(id_length(), Attr_ReadOnly);
+ internalClasses[Class_StringObject] = internalClasses[Class_Empty]->changeVTable(QV4::StringObject::staticVTable());
+ internalClasses[EngineBase::Class_StringObject] = internalClasses[Class_StringObject]->addMember(id_length(), Attr_ReadOnly);
Q_ASSERT(internalClasses[EngineBase::Class_StringObject]->find(id_length()) == Heap::StringObject::LengthPropertyIndex);
jsObjects[StringProto] = memoryManager->allocObject<StringPrototype>(internalClasses[EngineBase::Class_StringObject], objectPrototype());
- jsObjects[NumberProto] = memoryManager->allocObject<NumberPrototype>(internalClasses[Class_Object], objectPrototype());
- jsObjects[BooleanProto] = memoryManager->allocObject<BooleanPrototype>(internalClasses[Class_Object], objectPrototype());
- jsObjects[DateProto] = memoryManager->allocObject<DatePrototype>(internalClasses[Class_Object], objectPrototype());
+ jsObjects[NumberProto] = memoryManager->allocObject<NumberPrototype>();
+ jsObjects[BooleanProto] = memoryManager->allocObject<BooleanPrototype>();
+ jsObjects[DateProto] = memoryManager->allocObject<DatePrototype>();
uint index;
- InternalClass *functionProtoClass = internalClasses[Class_Object]->addMember(id_prototype(), Attr_NotEnumerable, &index);
+ InternalClass *functionProtoClass =
+ internalClasses[Class_Empty]->changeVTable(QV4::FunctionPrototype::staticVTable())
+ ->addMember(id_prototype(), Attr_NotEnumerable, &index);
Q_ASSERT(index == Heap::FunctionObject::Index_Prototype);
jsObjects[FunctionProto] = memoryManager->allocObject<FunctionPrototype>(functionProtoClass, objectPrototype());
internalClasses[EngineBase::Class_FunctionObject] = internalClasses[Class_Object]->addMember(id_prototype(), Attr_NotEnumerable|Attr_NotConfigurable, &index);
@@ -294,7 +299,10 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
Scope scope(this);
ScopedString str(scope);
- internalClasses[EngineBase::Class_RegExpObject] = internalClasses[Class_Object]->addMember(id_lastIndex(), Attr_NotEnumerable|Attr_NotConfigurable, &index);
+ internalClasses[Class_RegExp] = internalClasses[EngineBase::Class_Empty]->changeVTable(QV4::RegExp::staticVTable());
+ internalClasses[EngineBase::Class_RegExpObject] =
+ internalClasses[Class_Empty]->changeVTable(QV4::RegExpObject::staticVTable())
+ ->addMember(id_lastIndex(), Attr_NotEnumerable|Attr_NotConfigurable, &index);
Q_ASSERT(index == RegExpObject::Index_LastIndex);
internalClasses[EngineBase::Class_RegExpObject] = internalClasses[EngineBase::Class_RegExpObject]->addMember((str = newIdentifier(QStringLiteral("source"))), Attr_ReadOnly, &index);
Q_ASSERT(index == RegExpObject::Index_Source);
@@ -311,7 +319,9 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
internalClasses[EngineBase::Class_RegExpExecArray] = internalClasses[EngineBase::Class_RegExpExecArray]->addMember(id_input(), Attr_Data, &index);
Q_ASSERT(index == RegExpObject::Index_ArrayInput);
- internalClasses[EngineBase::Class_ErrorObject] = internalClasses[Class_Object]->addMember((str = newIdentifier(QStringLiteral("stack"))), Attr_Accessor|Attr_NotConfigurable|Attr_NotEnumerable, &index);
+ internalClasses[EngineBase::Class_ErrorObject] =
+ internalClasses[Class_Empty]->changeVTable(QV4::ErrorObject::staticVTable())
+ ->addMember((str = newIdentifier(QStringLiteral("stack"))), Attr_Accessor|Attr_NotConfigurable|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorObject::Index_Stack);
internalClasses[EngineBase::Class_ErrorObject] = internalClasses[EngineBase::Class_ErrorObject]->addMember((str = newIdentifier(QStringLiteral("fileName"))), Attr_Data|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorObject::Index_FileName);
@@ -319,7 +329,9 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
Q_ASSERT(index == ErrorObject::Index_LineNumber);
internalClasses[EngineBase::Class_ErrorObjectWithMessage] = internalClasses[EngineBase::Class_ErrorObject]->addMember((str = newIdentifier(QStringLiteral("message"))), Attr_Data|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorObject::Index_Message);
- internalClasses[EngineBase::Class_ErrorProto] = internalClasses[Class_Object]->addMember(id_constructor(), Attr_Data|Attr_NotEnumerable, &index);
+ internalClasses[EngineBase::Class_ErrorProto] =
+ internalClasses[Class_Empty]->changeVTable(QV4::ErrorPrototype::staticVTable())
+ ->addMember(id_constructor(), Attr_Data|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorPrototype::Index_Constructor);
internalClasses[EngineBase::Class_ErrorProto] = internalClasses[EngineBase::Class_ErrorProto]->addMember((str = newIdentifier(QStringLiteral("message"))), Attr_Data|Attr_NotEnumerable, &index);
Q_ASSERT(index == ErrorPrototype::Index_Message);
@@ -337,10 +349,10 @@ ExecutionEngine::ExecutionEngine(EvalISelFactory *factory)
jsObjects[TypeErrorProto] = memoryManager->allocObject<TypeErrorPrototype>(internalClasses[EngineBase::Class_ErrorProto], errorPrototype());
jsObjects[URIErrorProto] = memoryManager->allocObject<URIErrorPrototype>(internalClasses[EngineBase::Class_ErrorProto], errorPrototype());
- jsObjects[VariantProto] = memoryManager->allocObject<VariantPrototype>(internalClasses[Class_Object], objectPrototype());
+ jsObjects[VariantProto] = memoryManager->allocObject<VariantPrototype>();
Q_ASSERT(variantPrototype()->prototype() == objectPrototype()->d());
- jsObjects[SequenceProto] = ScopedValue(scope, memoryManager->allocObject<SequencePrototype>(internalClasses[Class_ArrayObject], arrayPrototype()));
+ jsObjects[SequenceProto] = ScopedValue(scope, memoryManager->allocObject<SequencePrototype>());
ExecutionContext *global = rootContext();
jsObjects[Object_Ctor] = memoryManager->allocObject<ObjectCtor>(global);
diff --git a/src/qml/jsruntime/qv4enginebase_p.h b/src/qml/jsruntime/qv4enginebase_p.h
index 783ddc5bd3..e124adb810 100644
--- a/src/qml/jsruntime/qv4enginebase_p.h
+++ b/src/qml/jsruntime/qv4enginebase_p.h
@@ -87,14 +87,16 @@ struct EngineBase {
Class_MemberData,
Class_SimpleArrayData,
Class_SparseArrayData,
+ Class_ExecutionContext,
Class_Object,
Class_ArrayObject,
Class_FunctionObject,
Class_StringObject,
Class_ScriptFunction,
Class_ObjectProto,
- Class_RegExpExecArray,
+ Class_RegExp,
Class_RegExpObject,
+ Class_RegExpExecArray,
Class_ArgumentsObject,
Class_StrictArgumentsObject,
Class_ErrorObject,
diff --git a/src/qml/jsruntime/qv4errorobject.cpp b/src/qml/jsruntime/qv4errorobject.cpp
index 63b778b56d..65507e2251 100644
--- a/src/qml/jsruntime/qv4errorobject.cpp
+++ b/src/qml/jsruntime/qv4errorobject.cpp
@@ -183,8 +183,6 @@ void ErrorObject::markObjects(Heap::Base *that, ExecutionEngine *e)
DEFINE_OBJECT_VTABLE(ErrorObject);
-DEFINE_OBJECT_VTABLE(SyntaxErrorObject);
-
void Heap::SyntaxErrorObject::init(const Value &msg)
{
Heap::ErrorObject::init(msg, SyntaxError);
diff --git a/src/qml/jsruntime/qv4errorobject_p.h b/src/qml/jsruntime/qv4errorobject_p.h
index 896b54da5e..34e4b4a682 100644
--- a/src/qml/jsruntime/qv4errorobject_p.h
+++ b/src/qml/jsruntime/qv4errorobject_p.h
@@ -203,8 +203,10 @@ struct ReferenceErrorObject: ErrorObject {
};
struct SyntaxErrorObject: ErrorObject {
- V4_OBJECT2(SyntaxErrorObject, ErrorObject)
+ typedef Heap::SyntaxErrorObject Data;
V4_PROTOTYPE(syntaxErrorPrototype)
+ const Data *d() const { return static_cast<const Data *>(ErrorObject::d()); }
+ Data *d() { return static_cast<Data *>(ErrorObject::d()); }
};
struct TypeErrorObject: ErrorObject {
diff --git a/src/qml/jsruntime/qv4internalclass.cpp b/src/qml/jsruntime/qv4internalclass.cpp
index e117da1a04..9a4087485f 100644
--- a/src/qml/jsruntime/qv4internalclass.cpp
+++ b/src/qml/jsruntime/qv4internalclass.cpp
@@ -249,8 +249,17 @@ InternalClass *InternalClass::changeVTableImpl(const VTable *vt)
// create a new class and add it to the tree
InternalClass *newClass;
- newClass = engine->newClass(*this);
- newClass->vtable = vt;
+ if (this == engine->internalClasses[EngineBase::Class_Empty]) {
+ newClass = engine->newClass(*this);
+ newClass->vtable = vt;
+ } else {
+ newClass = engine->internalClasses[EngineBase::Class_Empty]->changeVTable(vt);
+ newClass = newClass->changePrototype(prototype);
+ for (uint i = 0; i < size; ++i) {
+ if (!propertyData.at(i).isEmpty())
+ newClass = newClass->addMember(nameMap.at(i), propertyData.at(i));
+ }
+ }
t.lookup = newClass;
Q_ASSERT(t.lookup);
diff --git a/src/qml/jsruntime/qv4internalclass_p.h b/src/qml/jsruntime/qv4internalclass_p.h
index c68a6638e7..3c4e0838d9 100644
--- a/src/qml/jsruntime/qv4internalclass_p.h
+++ b/src/qml/jsruntime/qv4internalclass_p.h
@@ -280,7 +280,7 @@ struct InternalClass : public QQmlJS::Managed {
void destroy();
private:
- InternalClass *changeVTableImpl(const VTable *vt);
+ Q_QML_EXPORT InternalClass *changeVTableImpl(const VTable *vt);
InternalClass *addMemberImpl(Identifier *identifier, PropertyAttributes data, uint *index);
friend struct ExecutionEngine;
InternalClass(ExecutionEngine *engine);
diff --git a/src/qml/jsruntime/qv4managed_p.h b/src/qml/jsruntime/qv4managed_p.h
index 00bfad78dd..814755efe9 100644
--- a/src/qml/jsruntime/qv4managed_p.h
+++ b/src/qml/jsruntime/qv4managed_p.h
@@ -198,6 +198,8 @@ public:
};
Q_MANAGED_TYPE(Invalid)
+ InternalClass *internalClass() const { return d()->internalClass; }
+
bool isListType() const { return d()->vtable()->type == Type_QmlSequence; }
bool isArrayObject() const { return d()->vtable()->type == Type_ArrayObject; }
diff --git a/src/qml/jsruntime/qv4numberobject_p.h b/src/qml/jsruntime/qv4numberobject_p.h
index 364b866a16..85d306020c 100644
--- a/src/qml/jsruntime/qv4numberobject_p.h
+++ b/src/qml/jsruntime/qv4numberobject_p.h
@@ -85,6 +85,7 @@ struct NumberCtor: FunctionObject
struct NumberPrototype: NumberObject
{
+ V4_PROTOTYPE(objectPrototype)
void init(ExecutionEngine *engine, Object *ctor);
static void method_isFinite(const BuiltinFunction *, Scope &scope, CallData *callData);
diff --git a/src/qml/jsruntime/qv4object.cpp b/src/qml/jsruntime/qv4object.cpp
index f5dafa7914..838ae96c59 100644
--- a/src/qml/jsruntime/qv4object.cpp
+++ b/src/qml/jsruntime/qv4object.cpp
@@ -61,6 +61,7 @@ DEFINE_OBJECT_VTABLE(Object);
void Object::setInternalClass(InternalClass *ic)
{
d()->internalClass = ic;
+ Q_ASSERT(ic && ic->vtable);
uint nInline = d()->vtable()->nInlineProperties;
if (ic->size <= nInline)
return;
diff --git a/src/qml/jsruntime/qv4object_p.h b/src/qml/jsruntime/qv4object_p.h
index 78ee263c80..951659a4bc 100644
--- a/src/qml/jsruntime/qv4object_p.h
+++ b/src/qml/jsruntime/qv4object_p.h
@@ -95,7 +95,6 @@ struct Object : Base {
return memberData->data + index;
}
- InternalClass *internalClass;
Pointer<Object> prototype;
Pointer<MemberData> memberData;
Pointer<ArrayData> arrayData;
@@ -204,7 +203,6 @@ struct Q_QML_EXPORT Object: Managed {
SetterOffset = 1
};
- InternalClass *internalClass() const { return d()->internalClass; }
void setInternalClass(InternalClass *ic);
const Value *propertyData(uint index) const { return d()->propertyData(index); }
diff --git a/src/qml/jsruntime/qv4qmlcontext.cpp b/src/qml/jsruntime/qv4qmlcontext.cpp
index 889f4ea288..ef1a1c11ed 100644
--- a/src/qml/jsruntime/qv4qmlcontext.cpp
+++ b/src/qml/jsruntime/qv4qmlcontext.cpp
@@ -331,6 +331,7 @@ Heap::QmlContext *QmlContext::createWorkerContext(ExecutionContext *parent, cons
qml->setReadOnly(true);
Heap::QmlContext *c = parent->d()->engine->memoryManager->alloc<QmlContext>(parent, qml);
+ Q_ASSERT(c->vtable() == staticVTable());
return c;
}
@@ -340,6 +341,7 @@ Heap::QmlContext *QmlContext::create(ExecutionContext *parent, QQmlContextData *
Scoped<QmlContextWrapper> qml(scope, scope.engine->memoryManager->allocObject<QmlContextWrapper>(context, scopeObject));
Heap::QmlContext *c = parent->d()->engine->memoryManager->alloc<QmlContext>(parent, qml);
+ Q_ASSERT(c->vtable() == staticVTable());
return c;
}
diff --git a/src/qml/jsruntime/qv4qobjectwrapper.cpp b/src/qml/jsruntime/qv4qobjectwrapper.cpp
index 67b1356e65..f484d56040 100644
--- a/src/qml/jsruntime/qv4qobjectwrapper.cpp
+++ b/src/qml/jsruntime/qv4qobjectwrapper.cpp
@@ -997,7 +997,6 @@ void QObjectWrapper::destroyObject(bool lastCall)
}
}
- h->internalClass = 0;
h->~Data();
}
diff --git a/src/qml/jsruntime/qv4regexp_p.h b/src/qml/jsruntime/qv4regexp_p.h
index d3e63375a5..04cdb468bf 100644
--- a/src/qml/jsruntime/qv4regexp_p.h
+++ b/src/qml/jsruntime/qv4regexp_p.h
@@ -100,6 +100,7 @@ struct RegExp : public Managed
V4_MANAGED(RegExp, Managed)
Q_MANAGED_TYPE(RegExp)
V4_NEEDS_DESTROY
+ V4_INTERNALCLASS(RegExp)
QString pattern() const { return *d()->pattern; }
JSC::Yarr::BytecodePattern *byteCode() { return d()->byteCode; }
diff --git a/src/qml/jsruntime/qv4sequenceobject_p.h b/src/qml/jsruntime/qv4sequenceobject_p.h
index 6f96b9f760..0879f149fa 100644
--- a/src/qml/jsruntime/qv4sequenceobject_p.h
+++ b/src/qml/jsruntime/qv4sequenceobject_p.h
@@ -65,6 +65,7 @@ namespace QV4 {
struct SequencePrototype : public QV4::Object
{
+ V4_PROTOTYPE(arrayPrototype)
void init();
static void method_valueOf(const BuiltinFunction *, Scope &scope, CallData *callData)
diff --git a/src/qml/jsruntime/qv4string_p.h b/src/qml/jsruntime/qv4string_p.h
index bf8c48ceee..ad30165ce5 100644
--- a/src/qml/jsruntime/qv4string_p.h
+++ b/src/qml/jsruntime/qv4string_p.h
@@ -72,7 +72,6 @@ struct Q_QML_PRIVATE_EXPORT String : Base {
};
#ifndef V4_BOOTSTRAP
- V4_INTERNALCLASS(String)
void init(MemoryManager *mm, const QString &text);
void init(MemoryManager *mm, String *l, String *n);
void destroy();
@@ -140,6 +139,7 @@ struct Q_QML_PRIVATE_EXPORT String : public Managed {
#ifndef V4_BOOTSTRAP
V4_MANAGED(String, Managed)
Q_MANAGED_TYPE(String)
+ V4_INTERNALCLASS(String)
V4_NEEDS_DESTROY
enum {
IsString = true
diff --git a/src/qml/jsruntime/qv4typedarray.cpp b/src/qml/jsruntime/qv4typedarray.cpp
index 542460ee81..bb28a7683c 100644
--- a/src/qml/jsruntime/qv4typedarray.cpp
+++ b/src/qml/jsruntime/qv4typedarray.cpp
@@ -372,7 +372,8 @@ void Heap::TypedArray::init(Type t)
Heap::TypedArray *TypedArray::create(ExecutionEngine *e, Heap::TypedArray::Type t)
{
- return e->memoryManager->allocObject<TypedArray>(e->internalClasses[EngineBase::Class_Object], e->typedArrayPrototype + t, t);
+ QV4::InternalClass *ic = e->internalClasses[EngineBase::Class_Empty]->changeVTable(staticVTable());
+ return e->memoryManager->allocObject<TypedArray>(ic, e->typedArrayPrototype + t, t);
}
void TypedArray::markObjects(Heap::Base *that, ExecutionEngine *e)
diff --git a/src/qml/jsruntime/qv4typedarray_p.h b/src/qml/jsruntime/qv4typedarray_p.h
index eefed2db4b..a6a74e4b9b 100644
--- a/src/qml/jsruntime/qv4typedarray_p.h
+++ b/src/qml/jsruntime/qv4typedarray_p.h
@@ -148,6 +148,7 @@ struct TypedArrayCtor: FunctionObject
struct TypedArrayPrototype : Object
{
V4_OBJECT2(TypedArrayPrototype, Object)
+ V4_PROTOTYPE(objectPrototype)
void init(ExecutionEngine *engine, TypedArrayCtor *ctor);
diff --git a/src/qml/jsruntime/qv4variantobject_p.h b/src/qml/jsruntime/qv4variantobject_p.h
index ef51b6632d..dba14b13fb 100644
--- a/src/qml/jsruntime/qv4variantobject_p.h
+++ b/src/qml/jsruntime/qv4variantobject_p.h
@@ -105,6 +105,7 @@ struct VariantObject : Object
struct VariantPrototype : VariantObject
{
public:
+ V4_PROTOTYPE(objectPrototype)
void init();
static void method_preserve(const BuiltinFunction *, Scope &scope, CallData *callData);
diff --git a/src/qml/memory/qv4heap_p.h b/src/qml/memory/qv4heap_p.h
index cd0a6d9a81..a4e96b4c84 100644
--- a/src/qml/memory/qv4heap_p.h
+++ b/src/qml/memory/qv4heap_p.h
@@ -53,6 +53,7 @@
#include <QtCore/QString>
#include <private/qv4global_p.h>
#include <private/qv4mmdefs_p.h>
+#include <private/qv4internalclass_p.h>
#include <QSharedPointer>
// To check if Heap::Base::init is called (meaning, all subclasses did their init and called their
@@ -69,6 +70,8 @@ QT_BEGIN_NAMESPACE
namespace QV4 {
+struct InternalClass;
+
struct VTable
{
const VTable * const parent;
@@ -93,13 +96,12 @@ namespace Heap {
struct Q_QML_EXPORT Base {
void *operator new(size_t) = delete;
- const VTable *vt;
+ InternalClass *internalClass;
inline ReturnedValue asReturnedValue() const;
inline void mark(QV4::ExecutionEngine *engine);
- void setVtable(const VTable *v) { vt = v; }
- const VTable *vtable() const { return vt; }
+ const VTable *vtable() const { return internalClass->vtable; }
inline bool isMarked() const {
const HeapItem *h = reinterpret_cast<const HeapItem *>(this);
Chunk *c = h->chunk();
@@ -166,7 +168,7 @@ V4_ASSERT_IS_TRIVIAL(Base)
// for a size/offset translation when cross-compiling between 32- and
// 64-bit.
Q_STATIC_ASSERT(std::is_standard_layout<Base>::value);
-Q_STATIC_ASSERT(offsetof(Base, vt) == 0);
+Q_STATIC_ASSERT(offsetof(Base, internalClass) == 0);
Q_STATIC_ASSERT(sizeof(Base) == QT_POINTER_SIZE);
template <typename T>
diff --git a/src/qml/memory/qv4mm.cpp b/src/qml/memory/qv4mm.cpp
index ef36e62373..56f1254421 100644
--- a/src/qml/memory/qv4mm.cpp
+++ b/src/qml/memory/qv4mm.cpp
@@ -787,7 +787,8 @@ Heap::Object *MemoryManager::allocObjectWithMemberData(const QV4::VTable *vtable
m = *blockAllocator.allocate(memberSize, true);
memset(m, 0, memberSize);
o->memberData = static_cast<Heap::MemberData *>(m);
- o->memberData->setVtable(MemberData::staticVTable());
+ o->memberData->internalClass = engine->internalClasses[EngineBase::Class_MemberData];
+ Q_ASSERT(o->memberData->internalClass);
o->memberData->size = static_cast<uint>((memberSize - sizeof(Heap::MemberData) + sizeof(Value))/sizeof(Value));
o->memberData->init();
// qDebug() << " got" << o->memberData << o->memberData->size;
diff --git a/src/qml/memory/qv4mm_p.h b/src/qml/memory/qv4mm_p.h
index 9b4c2cd8df..8f12fa7cbd 100644
--- a/src/qml/memory/qv4mm_p.h
+++ b/src/qml/memory/qv4mm_p.h
@@ -210,7 +210,8 @@ public:
{
Heap::CallContext *ctxt = stackAllocator.allocate();
memset(ctxt, 0, sizeof(Heap::CallContext));
- ctxt->setVtable(QV4::CallContext::staticVTable());
+ ctxt->internalClass = CallContext::defaultInternalClass(engine);
+ Q_ASSERT(ctxt->internalClass && ctxt->internalClass->vtable);
ctxt->init(v4);
return ctxt;
@@ -224,7 +225,10 @@ public:
V4_ASSERT_IS_TRIVIAL(typename ManagedType::Data)
size = align(size);
Heap::Base *o = allocData(size);
- o->setVtable(ManagedType::staticVTable());
+ InternalClass *ic = ManagedType::defaultInternalClass(engine);
+ ic = ic->changeVTable(ManagedType::staticVTable());
+ o->internalClass = ic;
+ Q_ASSERT(o->internalClass && o->internalClass->vtable);
return static_cast<typename ManagedType::Data *>(o);
}
@@ -232,8 +236,9 @@ public:
typename ObjectType::Data *allocateObject(InternalClass *ic)
{
Heap::Object *o = allocObjectWithMemberData(ObjectType::staticVTable(), ic->size);
- o->setVtable(ObjectType::staticVTable());
o->internalClass = ic;
+ Q_ASSERT(o->internalClass && o->internalClass->vtable);
+ Q_ASSERT(ic->vtable == ObjectType::staticVTable());
return static_cast<typename ObjectType::Data *>(o);
}
@@ -241,10 +246,11 @@ public:
typename ObjectType::Data *allocateObject()
{
InternalClass *ic = ObjectType::defaultInternalClass(engine);
+ ic = ic->changeVTable(ObjectType::staticVTable());
Heap::Object *o = allocObjectWithMemberData(ObjectType::staticVTable(), ic->size);
- o->setVtable(ObjectType::staticVTable());
Object *prototype = ObjectType::defaultPrototype(engine);
o->internalClass = ic;
+ Q_ASSERT(o->internalClass && o->internalClass->vtable);
o->prototype = prototype->d();
return static_cast<typename ObjectType::Data *>(o);
}
@@ -253,7 +259,8 @@ public:
typename ManagedType::Data *allocWithStringData(std::size_t unmanagedSize, Arg1 arg1)
{
typename ManagedType::Data *o = reinterpret_cast<typename ManagedType::Data *>(allocString(unmanagedSize));
- o->setVtable(ManagedType::staticVTable());
+ o->internalClass = ManagedType::defaultInternalClass(engine);
+ Q_ASSERT(o->internalClass && o->internalClass->vtable);
o->init(this, arg1);
return o;
}