Move readonly accessors into Heap::ArrayData

these methods don't modify the object, so it's safe to have them
there and this simplifies quite a bit of the code.

Change-Id: I2f591758efba9cb8d17b956bc7c02e2d7a468ea4
Reviewed-by: Simon Hausmann <simon.hausmann@digia.com>
This commit is contained in:
Lars Knoll 2014-11-17 21:08:13 +01:00 committed by Simon Hausmann
parent d5b43dc847
commit 2e6e49f829
2 changed files with 70 additions and 57 deletions

View File

@ -64,7 +64,6 @@ const ArrayVTable SimpleArrayData::static_vtbl =
SimpleArrayData::putArray, SimpleArrayData::putArray,
SimpleArrayData::del, SimpleArrayData::del,
SimpleArrayData::setAttribute, SimpleArrayData::setAttribute,
SimpleArrayData::attribute,
SimpleArrayData::push_front, SimpleArrayData::push_front,
SimpleArrayData::pop_front, SimpleArrayData::pop_front,
SimpleArrayData::truncate, SimpleArrayData::truncate,
@ -81,7 +80,6 @@ const ArrayVTable SparseArrayData::static_vtbl =
SparseArrayData::putArray, SparseArrayData::putArray,
SparseArrayData::del, SparseArrayData::del,
SparseArrayData::setAttribute, SparseArrayData::setAttribute,
SparseArrayData::attribute,
SparseArrayData::push_front, SparseArrayData::push_front,
SparseArrayData::pop_front, SparseArrayData::pop_front,
SparseArrayData::truncate, SparseArrayData::truncate,
@ -222,10 +220,10 @@ void SimpleArrayData::markObjects(Heap::Base *d, ExecutionEngine *e)
dd->arrayData[i].mark(e); dd->arrayData[i].mark(e);
} }
ReturnedValue SimpleArrayData::get(const ArrayData *d, uint index) ReturnedValue SimpleArrayData::get(const Heap::ArrayData *d, uint index)
{ {
const SimpleArrayData *dd = static_cast<const SimpleArrayData *>(d); const Heap::SimpleArrayData *dd = static_cast<const Heap::SimpleArrayData *>(d);
if (index >= dd->len()) if (index >= dd->len)
return Primitive::emptyValue().asReturnedValue(); return Primitive::emptyValue().asReturnedValue();
return dd->data(index).asReturnedValue(); return dd->data(index).asReturnedValue();
} }
@ -266,11 +264,6 @@ void SimpleArrayData::setAttribute(Object *o, uint index, PropertyAttributes att
o->arrayData()->attrs()[index] = attrs; o->arrayData()->attrs()[index] = attrs;
} }
PropertyAttributes SimpleArrayData::attribute(const ArrayData *d, uint index)
{
return d->attrs()[index];
}
void SimpleArrayData::push_front(Object *o, Value *values, uint n) void SimpleArrayData::push_front(Object *o, Value *values, uint n)
{ {
Heap::SimpleArrayData *dd = static_cast<Heap::SimpleArrayData *>(o->d()->arrayData); Heap::SimpleArrayData *dd = static_cast<Heap::SimpleArrayData *>(o->d()->arrayData);
@ -412,9 +405,9 @@ uint SparseArrayData::allocate(Object *o, bool doubleSlot)
} }
} }
ReturnedValue SparseArrayData::get(const ArrayData *d, uint index) ReturnedValue SparseArrayData::get(const Heap::ArrayData *d, uint index)
{ {
const Heap::SparseArrayData *s = static_cast<const SparseArrayData *>(d)->d(); const Heap::SparseArrayData *s = static_cast<const Heap::SparseArrayData *>(d);
index = s->mappedIndex(index); index = s->mappedIndex(index);
if (index == UINT_MAX) if (index == UINT_MAX)
return Primitive::emptyValue().asReturnedValue(); return Primitive::emptyValue().asReturnedValue();
@ -491,14 +484,6 @@ void SparseArrayData::setAttribute(Object *o, uint index, PropertyAttributes att
d->attrs[n->value] = attrs; d->attrs[n->value] = attrs;
} }
PropertyAttributes SparseArrayData::attribute(const ArrayData *d, uint index)
{
SparseArrayNode *n = d->d()->sparse->findNode(index);
if (!n)
return PropertyAttributes();
return d->d()->attrs[n->value];
}
void SparseArrayData::push_front(Object *o, Value *values, uint n) void SparseArrayData::push_front(Object *o, Value *values, uint n)
{ {
Heap::SparseArrayData *d = static_cast<Heap::SparseArrayData *>(o->d()->arrayData); Heap::SparseArrayData *d = static_cast<Heap::SparseArrayData *>(o->d()->arrayData);

View File

@ -59,12 +59,11 @@ struct ArrayVTable
ManagedVTable managedVTable; ManagedVTable managedVTable;
uint type; uint type;
ArrayData *(*reallocate)(Object *o, uint n, bool enforceAttributes); ArrayData *(*reallocate)(Object *o, uint n, bool enforceAttributes);
ReturnedValue (*get)(const ArrayData *d, uint index); ReturnedValue (*get)(const Heap::ArrayData *d, uint index);
bool (*put)(Object *o, uint index, ValueRef value); bool (*put)(Object *o, uint index, ValueRef value);
bool (*putArray)(Object *o, uint index, Value *values, uint n); bool (*putArray)(Object *o, uint index, Value *values, uint n);
bool (*del)(Object *o, uint index); bool (*del)(Object *o, uint index);
void (*setAttribute)(Object *o, uint index, PropertyAttributes attrs); void (*setAttribute)(Object *o, uint index, PropertyAttributes attrs);
PropertyAttributes (*attribute)(const ArrayData *d, uint index);
void (*push_front)(Object *o, Value *values, uint n); void (*push_front)(Object *o, Value *values, uint n);
ReturnedValue (*pop_front)(Object *o); ReturnedValue (*pop_front)(Object *o);
uint (*truncate)(Object *o, uint newLen); uint (*truncate)(Object *o, uint newLen);
@ -96,6 +95,21 @@ struct ArrayData : public Base {
SparseArray *sparse; SparseArray *sparse;
}; };
Value arrayData[1]; Value arrayData[1];
bool isSparse() const { return type == Sparse; }
const ArrayVTable *vtable() const { return reinterpret_cast<const ArrayVTable *>(internalClass->vtable); }
inline ReturnedValue get(uint i) const {
return vtable()->get(this, i);
}
inline Property *getProperty(uint index);
inline PropertyAttributes attributes(uint i) const;
bool isEmpty(uint i) const {
return get(i) == Primitive::emptyValue().asReturnedValue();
}
}; };
struct SimpleArrayData : public ArrayData { struct SimpleArrayData : public ArrayData {
@ -106,6 +120,19 @@ struct SimpleArrayData : public ArrayData {
uint mappedIndex(uint index) const { return (index + offset) % alloc; } uint mappedIndex(uint index) const { return (index + offset) % alloc; }
Value data(uint index) const { return arrayData[mappedIndex(index)]; } Value data(uint index) const { return arrayData[mappedIndex(index)]; }
Value &data(uint index) { return arrayData[mappedIndex(index)]; } Value &data(uint index) { return arrayData[mappedIndex(index)]; }
Property *getProperty(uint index) {
if (index >= len)
return 0;
index = mappedIndex(index);
if (arrayData[index].isEmpty())
return 0;
return reinterpret_cast<Property *>(arrayData + index);
}
PropertyAttributes attributes(uint i) const {
return attrs ? attrs[i] : Attr_Data;
}
}; };
struct SparseArrayData : public ArrayData { struct SparseArrayData : public ArrayData {
@ -118,6 +145,20 @@ struct SparseArrayData : public ArrayData {
return UINT_MAX; return UINT_MAX;
return n->value; return n->value;
} }
Property *getProperty(uint index) {
SparseArrayNode *n = sparse->findNode(index);
if (!n)
return 0;
return reinterpret_cast<Property *>(arrayData + n->value);
}
PropertyAttributes attributes(uint i) const {
if (!attrs)
return Attr_Data;
uint index = mappedIndex(i);
return index < UINT_MAX ? attrs[index] : Attr_Data;
}
}; };
} }
@ -147,19 +188,20 @@ struct Q_QML_EXPORT ArrayData : public Managed
bool hasAttributes() const { bool hasAttributes() const {
return attrs(); return attrs();
} }
PropertyAttributes attributes(int i) const { PropertyAttributes attributes(uint i) const {
Q_ASSERT(this); return d()->attributes(i);
return attrs() ? vtable()->attribute(this, i) : Attr_Data;
} }
bool isEmpty(uint i) const { bool isEmpty(uint i) const {
return (vtable()->get(this, i) == Primitive::emptyValue().asReturnedValue()); return d()->isEmpty(i);
} }
ReturnedValue get(uint i) const { ReturnedValue get(uint i) const {
return vtable()->get(this, i); return d()->get(i);
}
inline Property *getProperty(uint index) {
return d()->getProperty(index);
} }
inline Property *getProperty(uint index);
static void ensureAttributes(Object *o); static void ensureAttributes(Object *o);
static void realloc(Object *o, Type newType, uint alloc, bool enforceAttributes); static void realloc(Object *o, Type newType, uint alloc, bool enforceAttributes);
@ -177,15 +219,6 @@ struct Q_QML_EXPORT SimpleArrayData : public ArrayData
Value data(uint index) const { return d()->data(index); } Value data(uint index) const { return d()->data(index); }
Value &data(uint index) { return d()->data(index); } Value &data(uint index) { return d()->data(index); }
Property *getProperty(uint index) {
if (index >= len())
return 0;
index = mappedIndex(index);
if (d()->arrayData[index].isEmpty())
return 0;
return reinterpret_cast<Property *>(d()->arrayData + index);
}
uint &len() { return d()->len; } uint &len() { return d()->len; }
uint len() const { return d()->len; } uint len() const { return d()->len; }
@ -193,12 +226,11 @@ struct Q_QML_EXPORT SimpleArrayData : public ArrayData
static void markObjects(Heap::Base *d, ExecutionEngine *e); static void markObjects(Heap::Base *d, ExecutionEngine *e);
static ReturnedValue get(const ArrayData *d, uint index); static ReturnedValue get(const Heap::ArrayData *d, uint index);
static bool put(Object *o, uint index, ValueRef value); static bool put(Object *o, uint index, ValueRef value);
static bool putArray(Object *o, uint index, Value *values, uint n); static bool putArray(Object *o, uint index, Value *values, uint n);
static bool del(Object *o, uint index); static bool del(Object *o, uint index);
static void setAttribute(Object *o, uint index, PropertyAttributes attrs); static void setAttribute(Object *o, uint index, PropertyAttributes attrs);
static PropertyAttributes attribute(const ArrayData *d, uint index);
static void push_front(Object *o, Value *values, uint n); static void push_front(Object *o, Value *values, uint n);
static ReturnedValue pop_front(Object *o); static ReturnedValue pop_front(Object *o);
static uint truncate(Object *o, uint newLen); static uint truncate(Object *o, uint newLen);
@ -218,24 +250,16 @@ struct Q_QML_EXPORT SparseArrayData : public ArrayData
static uint allocate(Object *o, bool doubleSlot = false); static uint allocate(Object *o, bool doubleSlot = false);
static void free(ArrayData *d, uint idx); static void free(ArrayData *d, uint idx);
Property *getProperty(uint index) {
SparseArrayNode *n = sparse()->findNode(index);
if (!n)
return 0;
return reinterpret_cast<Property *>(arrayData() + n->value);
}
uint mappedIndex(uint index) const { return d()->mappedIndex(index); } uint mappedIndex(uint index) const { return d()->mappedIndex(index); }
static void markObjects(Heap::Base *d, ExecutionEngine *e); static void markObjects(Heap::Base *d, ExecutionEngine *e);
static ArrayData *reallocate(Object *o, uint n, bool enforceAttributes); static ArrayData *reallocate(Object *o, uint n, bool enforceAttributes);
static ReturnedValue get(const ArrayData *d, uint index); static ReturnedValue get(const Heap::ArrayData *d, uint index);
static bool put(Object *o, uint index, ValueRef value); static bool put(Object *o, uint index, ValueRef value);
static bool putArray(Object *o, uint index, Value *values, uint n); static bool putArray(Object *o, uint index, Value *values, uint n);
static bool del(Object *o, uint index); static bool del(Object *o, uint index);
static void setAttribute(Object *o, uint index, PropertyAttributes attrs); static void setAttribute(Object *o, uint index, PropertyAttributes attrs);
static PropertyAttributes attribute(const ArrayData *d, uint index);
static void push_front(Object *o, Value *values, uint n); static void push_front(Object *o, Value *values, uint n);
static ReturnedValue pop_front(Object *o); static ReturnedValue pop_front(Object *o);
static uint truncate(Object *o, uint newLen); static uint truncate(Object *o, uint newLen);
@ -254,17 +278,21 @@ inline SparseArrayData::~SparseArrayData()
delete sparse; delete sparse;
} }
}
inline Property *ArrayData::getProperty(uint index) inline Property *ArrayData::getProperty(uint index)
{ {
if (type() != Heap::ArrayData::Sparse) { if (isSparse())
SimpleArrayData *that = static_cast<SimpleArrayData *>(this); return static_cast<SparseArrayData *>(this)->getProperty(index);
return that->getProperty(index); return static_cast<SimpleArrayData *>(this)->getProperty(index);
} else { }
SparseArrayData *that = static_cast<SparseArrayData *>(this);
return that->getProperty(index); inline PropertyAttributes ArrayData::attributes(uint i) const
} {
if (isSparse())
return static_cast<const SparseArrayData *>(this)->attributes(i);
return static_cast<const SimpleArrayData *>(this)->attributes(i);
}
} }
} }