diff options
author | Erik Verbruggen <erik.verbruggen@digia.com> | 2016-09-09 15:37:57 +0200 |
---|---|---|
committer | Erik Verbruggen <erik.verbruggen@qt.io> | 2016-10-06 11:44:08 +0000 |
commit | 3b14e2ffdd8eb4b7f7f4508768b75f2acc399370 (patch) | |
tree | 7943f293bf2d0d376d5dc620448bab1a2b58027d /src/qml/jsruntime/qv4objectiterator_p.h | |
parent | 1b90dc4482d001512f09a5785d4cbd8030879d82 (diff) |
QML: Make Heap::Object and all subclasses trivial
GCC6 might dead-store-eliminate out our secret write to Base::mmdata,
because it expects all memory content to be "undefined" before
constructor calls. Clang might take the same approach if the constructor
of Heap::Object is removed.
By making these structs trivial, it also makes them memcpy-able.
Change-Id: I055b2ad28311b997fbe059849ebda4d5894eaa9b
Reviewed-by: Simon Hausmann <simon.hausmann@qt.io>
Diffstat (limited to 'src/qml/jsruntime/qv4objectiterator_p.h')
-rw-r--r-- | src/qml/jsruntime/qv4objectiterator_p.h | 51 |
1 files changed, 42 insertions, 9 deletions
diff --git a/src/qml/jsruntime/qv4objectiterator_p.h b/src/qml/jsruntime/qv4objectiterator_p.h index 6bef703a4d..98e94a95ea 100644 --- a/src/qml/jsruntime/qv4objectiterator_p.h +++ b/src/qml/jsruntime/qv4objectiterator_p.h @@ -57,7 +57,7 @@ QT_BEGIN_NAMESPACE namespace QV4 { -struct Q_QML_EXPORT ObjectIterator +struct Q_QML_EXPORT ObjectIteratorData { enum Flags { NoFlags = 0, @@ -72,21 +72,52 @@ struct Q_QML_EXPORT ObjectIterator uint arrayIndex; uint memberIndex; uint flags; +}; +V4_ASSERT_IS_TRIVIAL(ObjectIteratorData) + +struct Q_QML_EXPORT ObjectIterator: ObjectIteratorData +{ + ObjectIterator(ExecutionEngine *e, Value *scratch1, Value *scratch2, Object *o, uint flags) + { + engine = e; + object = scratch1; + current = scratch2; + arrayNode = nullptr; + arrayIndex = 0; + memberIndex = 0; + this->flags = flags; + init(o); + } + + ObjectIterator(Scope &scope, const Object *o, uint flags) + { + engine = scope.engine; + object = scope.alloc(1); + current = scope.alloc(1); + arrayNode = nullptr; + arrayIndex = 0; + memberIndex = 0; + this->flags = flags; + init(o); + } - ObjectIterator(ExecutionEngine *e, Value *scratch1, Value *scratch2, Object *o, uint flags); - ObjectIterator(Scope &scope, const Object *o, uint flags); - void init(const Object *o); void next(Value *name, uint *index, Property *pd, PropertyAttributes *attributes = 0); ReturnedValue nextPropertyName(Value *value); ReturnedValue nextPropertyNameAsString(Value *value); ReturnedValue nextPropertyNameAsString(); + +private: + void init(const Object *o); }; namespace Heap { struct ForEachIteratorObject : Object { - ForEachIteratorObject(QV4::Object *o); - ObjectIterator it; + void init(QV4::Object *o); + ObjectIterator &it() { return *reinterpret_cast<ObjectIterator*>(&itData); } Value workArea[2]; + +private: + ObjectIteratorData itData; }; } @@ -95,16 +126,18 @@ struct ForEachIteratorObject: Object { V4_OBJECT2(ForEachIteratorObject, Object) Q_MANAGED_TYPE(ForeachIteratorObject) - ReturnedValue nextPropertyName() { return d()->it.nextPropertyNameAsString(); } + ReturnedValue nextPropertyName() { return d()->it().nextPropertyNameAsString(); } protected: static void markObjects(Heap::Base *that, ExecutionEngine *e); }; inline -Heap::ForEachIteratorObject::ForEachIteratorObject(QV4::Object *o) - : it(internalClass->engine, workArea, workArea + 1, o, ObjectIterator::EnumerableOnly|ObjectIterator::WithProtoChain) +void Heap::ForEachIteratorObject::init(QV4::Object *o) { + Object::init(); + it() = ObjectIterator(internalClass->engine, workArea, workArea + 1, o, + ObjectIterator::EnumerableOnly | ObjectIterator::WithProtoChain); } |