aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFrank Meerkoetter <frank.meerkoetter@basyskom.com>2015-08-29 22:25:51 +0200
committerFrank Meerkoetter <frank.meerkoetter@basyskom.com>2015-09-05 11:52:44 +0000
commitcef14c0ff9a0caaa5b65ab89825534b3fcbd4764 (patch)
tree46cb93062822bcc7d8c59fe89cb7801954119678
parent217bca42934ecf9a5fab74bbddbfa852c9b1bfe6 (diff)
Allocate QML defined properties without extra room
QV4::MemberData is used to allocate storage for QML defined properties. QV4::MemberData::reallocate() is multiplying each allocation by two as a growth strategy. This is a waste of memory for QML defined properties. This commits extends the QV4::MemberData with an additional method to allow exactly sized allocations. Change-Id: I5c0a3a5a3852d39af9e1afb512380fb1400d2448 Reviewed-by: Simon Hausmann <simon.hausmann@theqtcompany.com>
-rw-r--r--src/qml/jsruntime/qv4memberdata.cpp28
-rw-r--r--src/qml/jsruntime/qv4memberdata_p.h3
-rw-r--r--src/qml/qml/qqmlvmemetaobject.cpp2
3 files changed, 22 insertions, 11 deletions
diff --git a/src/qml/jsruntime/qv4memberdata.cpp b/src/qml/jsruntime/qv4memberdata.cpp
index 5ec5cb1f58..20f8d9ec0f 100644
--- a/src/qml/jsruntime/qv4memberdata.cpp
+++ b/src/qml/jsruntime/qv4memberdata.cpp
@@ -46,20 +46,30 @@ void MemberData::markObjects(Heap::Base *that, ExecutionEngine *e)
m->data[i].mark(e);
}
-Heap::MemberData *MemberData::reallocate(ExecutionEngine *e, Heap::MemberData *old, uint idx)
+static Heap::MemberData *reallocateHelper(ExecutionEngine *e, Heap::MemberData *old, uint n)
{
- uint s = old ? old->size : 0;
- if (idx < s)
- return old;
-
- int newAlloc = qMax((uint)4, 2*idx);
- uint alloc = sizeof(Heap::MemberData) + (newAlloc)*sizeof(Value);
+ uint alloc = sizeof(Heap::MemberData) + (n)*sizeof(Value);
Scope scope(e);
Scoped<MemberData> newMemberData(scope, e->memoryManager->allocManaged<MemberData>(alloc));
if (old)
- memcpy(newMemberData->d(), old, sizeof(Heap::MemberData) + s*sizeof(Value));
+ memcpy(newMemberData->d(), old, sizeof(Heap::MemberData) + old->size * sizeof(Value));
else
new (newMemberData->d()) Heap::MemberData;
- newMemberData->d()->size = newAlloc;
+ newMemberData->d()->size = n;
return newMemberData->d();
}
+
+Heap::MemberData *MemberData::allocate(ExecutionEngine *e, uint n)
+{
+ return reallocateHelper(e, 0, n);
+}
+
+Heap::MemberData *MemberData::reallocate(ExecutionEngine *e, Heap::MemberData *old, uint n)
+{
+ uint s = old ? old->size : 0;
+ if (n < s)
+ return old;
+
+ // n is multiplied by two to leave room for growth
+ return reallocateHelper(e, old, qMax((uint)4, 2*n));
+}
diff --git a/src/qml/jsruntime/qv4memberdata_p.h b/src/qml/jsruntime/qv4memberdata_p.h
index 4c7cfa47cb..50b8ddb3d1 100644
--- a/src/qml/jsruntime/qv4memberdata_p.h
+++ b/src/qml/jsruntime/qv4memberdata_p.h
@@ -61,7 +61,8 @@ struct MemberData : Managed
Value *data() { return d()->data; }
inline uint size() const { return d()->size; }
- static Heap::MemberData *reallocate(QV4::ExecutionEngine *e, Heap::MemberData *old, uint idx);
+ static Heap::MemberData *allocate(QV4::ExecutionEngine *e, uint n);
+ static Heap::MemberData *reallocate(QV4::ExecutionEngine *e, Heap::MemberData *old, uint n);
static void markObjects(Heap::Base *that, ExecutionEngine *e);
};
diff --git a/src/qml/qml/qqmlvmemetaobject.cpp b/src/qml/qml/qqmlvmemetaobject.cpp
index 0ffeddbabc..4b19d1af04 100644
--- a/src/qml/qml/qqmlvmemetaobject.cpp
+++ b/src/qml/qml/qqmlvmemetaobject.cpp
@@ -1086,7 +1086,7 @@ void QQmlVMEMetaObject::allocateProperties()
{
Q_ASSERT(cache && cache->engine);
QV4::ExecutionEngine *v4 = cache->engine;
- QV4::Heap::MemberData *data = QV4::MemberData::reallocate(v4, 0, metaData->propertyCount);
+ QV4::Heap::MemberData *data = QV4::MemberData::allocate(v4, metaData->propertyCount);
properties.set(v4, data);
for (uint i = 0; i < data->size; ++i)
data->data[i] = QV4::Encode::undefined();