add util.cpp/.h changes

This commit is contained in:
Joshua Warner 2014-06-28 14:41:27 -06:00 committed by Joshua Warner
parent 51368651dc
commit 6a0502bbfe
9 changed files with 224 additions and 211 deletions

View File

@ -1916,6 +1916,19 @@ set(Thread* t, object target, unsigned offset, object value)
mark(t, target, offset);
}
inline void
set(Thread* t, GcObject* target, unsigned offset, GcObject* value)
{
fieldAtOffset<GcObject*>(target, offset) = value;
mark(t, reinterpret_cast<object>(target), offset);
}
inline void
setObject(Thread* t, GcObject* target, unsigned offset, GcObject* value)
{
set(t, target, offset, value);
}
inline void
setObjectClass(Thread*, object o, GcClass* c)
{
@ -3808,8 +3821,8 @@ resolveMethod(Thread* t, GcMethod* method, unsigned index, bool throw_ = true)
(t, reinterpret_cast<object>(method->class_()->loader()), method, index, throw_);
}
object
vectorAppend(Thread*, object, object);
GcVector*
vectorAppend(Thread*, GcVector*, object);
inline object
getClassRuntimeDataIfExists(Thread* t, object c)
@ -3833,8 +3846,8 @@ getClassRuntimeData(Thread* t, GcClass* c)
if (c->runtimeDataIndex() == 0) {
object runtimeData = reinterpret_cast<object>(makeClassRuntimeData(t, 0, 0, 0, 0));
setRoot(t, Machine::ClassRuntimeDataTable, vectorAppend
(t, root(t, Machine::ClassRuntimeDataTable), runtimeData));
setRoot(t, Machine::ClassRuntimeDataTable, reinterpret_cast<object>(vectorAppend
(t, cast<GcVector>(t, root(t, Machine::ClassRuntimeDataTable)), runtimeData)));
c->runtimeDataIndex() = vectorSize
(t, root(t, Machine::ClassRuntimeDataTable));
@ -3860,8 +3873,8 @@ getMethodRuntimeData(Thread* t, GcMethod* method)
if (method->runtimeDataIndex() == 0) {
object runtimeData = reinterpret_cast<object>(makeMethodRuntimeData(t, 0));
setRoot(t, Machine::MethodRuntimeDataTable, vectorAppend
(t, root(t, Machine::MethodRuntimeDataTable), runtimeData));
setRoot(t, Machine::MethodRuntimeDataTable, reinterpret_cast<object>(vectorAppend
(t, cast<GcVector>(t, root(t, Machine::MethodRuntimeDataTable)), runtimeData)));
storeStoreMemoryBarrier();

View File

@ -16,7 +16,7 @@
namespace vm {
object
GcTriple*
hashMapFindNode(Thread* t, GcHashMap* map, object key,
uint32_t (*hash)(Thread*, object),
bool (*equal)(Thread*, object, object));
@ -26,8 +26,8 @@ hashMapFind(Thread* t, GcHashMap* map, object key,
uint32_t (*hash)(Thread*, object),
bool (*equal)(Thread*, object, object))
{
object n = hashMapFindNode(t, map, key, hash, equal);
return (n ? tripleSecond(t, n) : 0);
GcTriple* n = hashMapFindNode(t, map, key, hash, equal);
return (n ? n->second() : 0);
}
void
@ -43,12 +43,12 @@ hashMapInsertOrReplace(Thread* t, GcHashMap* map, object key, object value,
uint32_t (*hash)(Thread*, object),
bool (*equal)(Thread*, object, object))
{
object n = hashMapFindNode(t, map, key, hash, equal);
GcTriple* n = hashMapFindNode(t, map, key, hash, equal);
if (n == 0) {
hashMapInsert(t, map, key, value, hash);
return true;
} else {
set(t, n, TripleSecond, value);
set(t, reinterpret_cast<object>(n), TripleSecond, value);
return false;
}
}
@ -58,7 +58,7 @@ hashMapInsertMaybe(Thread* t, GcHashMap* map, object key, object value,
uint32_t (*hash)(Thread*, object),
bool (*equal)(Thread*, object, object))
{
object n = hashMapFindNode(t, map, key, hash, equal);
GcTriple* n = hashMapFindNode(t, map, key, hash, equal);
if (n == 0) {
hashMapInsert(t, map, key, value, hash);
return true;
@ -79,25 +79,25 @@ object
hashMapIteratorNext(Thread* t, object it);
void
listAppend(Thread* t, object list, object value);
listAppend(Thread* t, GcList* list, object value);
object
vectorAppend(Thread* t, object vector, object value);
GcVector*
vectorAppend(Thread* t, GcVector* vector, object value);
object
growArray(Thread* t, object array);
object
treeQuery(Thread* t, object tree, intptr_t key, object sentinal,
treeQuery(Thread* t, GcTreeNode* tree, intptr_t key, GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b));
object
treeInsert(Thread* t, Zone* zone, object tree, intptr_t key, object value,
object sentinal,
GcTreeNode*
treeInsert(Thread* t, Zone* zone, GcTreeNode* tree, intptr_t key, object value,
GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b));
void
treeUpdate(Thread* t, object tree, intptr_t key, object value, object sentinal,
treeUpdate(Thread* t, GcTreeNode* tree, intptr_t key, object value, GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b));
class HashMapIterator: public Thread::Protector {
@ -109,11 +109,11 @@ class HashMapIterator: public Thread::Protector {
}
void find() {
object array = map->array();
GcArray* array = map->array();
if (array) {
for (unsigned i = index; i < arrayLength(t, array); ++i) {
if (arrayBody(t, array, i)) {
node = arrayBody(t, array, i);
for (unsigned i = index; i < array->length(); ++i) {
if (array->body()[i]) {
node = cast<GcTriple>(t, array->body()[i]);
index = i + 1;
return;
}
@ -126,11 +126,11 @@ class HashMapIterator: public Thread::Protector {
return node != 0;
}
object next() {
GcTriple* next() {
if (node) {
object n = node;
if (tripleThird(t, node)) {
node = tripleThird(t, node);
GcTriple* n = node;
if (node->third()) {
node = cast<GcTriple>(t, node->third());
} else {
find();
}
@ -146,7 +146,7 @@ class HashMapIterator: public Thread::Protector {
}
GcHashMap* map;
object node;
GcTriple* node;
unsigned index;
};

View File

@ -412,8 +412,8 @@ methodForIp(MyThread* t, void* ip)
// compile(MyThread*, FixedAllocator*, BootContext*, object)):
loadMemoryBarrier();
return cast<GcMethod>(t, treeQuery(t, root(t, MethodTree), reinterpret_cast<intptr_t>(ip),
root(t, MethodTreeSentinal), compareIpToMethodBounds));
return cast<GcMethod>(t, treeQuery(t, cast<GcTreeNode>(t, root(t, MethodTree)), reinterpret_cast<intptr_t>(ip),
cast<GcTreeNode>(t, root(t, MethodTreeSentinal)), compareIpToMethodBounds));
}
unsigned
@ -5751,7 +5751,7 @@ compile(MyThread* t, Frame* initialFrame, unsigned initialIp,
value);
} else {
c->call(
c->constant(getThunk(t, setThunk), ir::Type::iptr()),
c->constant(getThunk(t, setObjectThunk), ir::Type::iptr()),
0,
0,
ir::Type::void_(),
@ -9261,7 +9261,7 @@ GcHashMap*
makeClassMap(Thread* t, unsigned* table, unsigned count,
uintptr_t* heap)
{
object array = reinterpret_cast<object>(makeArray(t, nextPowerOfTwo(count)));
GcArray* array = makeArray(t, nextPowerOfTwo(count));
GcHashMap* map = makeHashMap(t, 0, array);
PROTECT(t, map);
@ -9295,7 +9295,7 @@ makeStaticTableArray(Thread* t, unsigned* bootTable, unsigned bootCount,
GcWeakHashMap*
makeStringMap(Thread* t, unsigned* table, unsigned count, uintptr_t* heap)
{
object array = reinterpret_cast<object>(makeArray(t, nextPowerOfTwo(count)));
GcArray* array = makeArray(t, nextPowerOfTwo(count));
GcWeakHashMap* map = makeWeakHashMap(t, 0, array);
PROTECT(t, map);
@ -9400,7 +9400,7 @@ void
resetRuntimeState(Thread* t, GcHashMap* map, uintptr_t* heap, unsigned heapSize)
{
for (HashMapIterator it(t, map); it.hasMore();) {
resetClassRuntimeState(t, tripleSecond(t, it.next()), heap, heapSize);
resetClassRuntimeState(t, it.next()->second(), heap, heapSize);
}
}
@ -9408,7 +9408,7 @@ void
fixupMethods(Thread* t, GcHashMap* map, BootImage* image UNUSED, uint8_t* code)
{
for (HashMapIterator it(t, map); it.hasMore();) {
object c = tripleSecond(t, it.next());
object c = it.next()->second();
if (classMethodTable(t, c)) {
for (unsigned i = 0; i < arrayLength(t, classMethodTable(t, c)); ++i) {
@ -10020,13 +10020,13 @@ compile(MyThread* t, FixedAllocator* allocator, BootContext* bootContext,
setRoot(t,
MethodTree,
treeInsert(t,
reinterpret_cast<object>(treeInsert(t,
&(context.zone),
root(t, MethodTree),
cast<GcTreeNode>(t, root(t, MethodTree)),
methodCompiled(t, clone),
reinterpret_cast<object>(clone),
root(t, MethodTreeSentinal),
compareIpToMethodBounds));
cast<GcTreeNode>(t, root(t, MethodTreeSentinal)),
compareIpToMethodBounds)));
storeStoreMemoryBarrier();
@ -10042,8 +10042,8 @@ compile(MyThread* t, FixedAllocator* allocator, BootContext* bootContext,
// when we dispose of the context:
context.executableAllocator = 0;
treeUpdate(t, root(t, MethodTree), methodCompiled(t, clone),
reinterpret_cast<object>(method), root(t, MethodTreeSentinal), compareIpToMethodBounds);
treeUpdate(t, cast<GcTreeNode>(t, root(t, MethodTree)), methodCompiled(t, clone),
reinterpret_cast<object>(method), cast<GcTreeNode>(t, root(t, MethodTreeSentinal)), compareIpToMethodBounds);
}
object&

View File

@ -544,8 +544,8 @@ methodID(Thread* t, GcMethod* method)
ACQUIRE(t, t->m->referenceLock);
if (method->nativeID() == 0) {
setRoot(t, Machine::JNIMethodTable, vectorAppend
(t, root(t, Machine::JNIMethodTable), reinterpret_cast<object>(method)));
setRoot(t, Machine::JNIMethodTable, reinterpret_cast<object>(vectorAppend
(t, cast<GcVector>(t, root(t, Machine::JNIMethodTable)), reinterpret_cast<object>(method))));
storeStoreMemoryBarrier();
@ -1497,8 +1497,8 @@ fieldID(Thread* t, object field)
ACQUIRE(t, t->m->referenceLock);
if (fieldNativeID(t, field) == 0) {
setRoot(t, Machine::JNIFieldTable, vectorAppend
(t, root(t, Machine::JNIFieldTable), field));
setRoot(t, Machine::JNIFieldTable, reinterpret_cast<object>(vectorAppend
(t, cast<GcVector>(t, root(t, Machine::JNIFieldTable)), field)));
storeStoreMemoryBarrier();

View File

@ -893,10 +893,10 @@ internByteArray(Thread* t, object array)
ACQUIRE(t, t->m->referenceLock);
object n = hashMapFindNode
GcTriple* n = hashMapFindNode
(t, cast<GcHashMap>(t, root(t, Machine::ByteArrayMap)), array, byteArrayHash, byteArrayEqual);
if (n) {
return jreferenceTarget(t, tripleFirst(t, n));
return jreferenceTarget(t, n->first());
} else {
hashMapInsert(t, cast<GcHashMap>(t, root(t, Machine::ByteArrayMap)), array, 0, byteArrayHash);
addFinalizer(t, array, removeByteArray);
@ -1275,7 +1275,7 @@ parseInterfaceTable(Thread* t, Stream& s, GcClass* class_, GcSingleton* pool,
unsigned i = 0;
for (HashMapIterator it(t, map); it.hasMore();) {
GcClass* interface = cast<GcClass>(t, tripleSecond(t, it.next()));
GcClass* interface = cast<GcClass>(t, it.next()->second());
set(t, interfaceTable, ArrayBody + (i * BytesPerWord), reinterpret_cast<object>(interface));
++ i;
@ -1987,7 +1987,7 @@ addInterfaceMethods(Thread* t, GcClass* class_, GcHashMap* virtualMap,
if (vtable) {
for (unsigned j = 0; j < arrayLength(t, vtable); ++j) {
method = cast<GcMethod>(t, arrayBody(t, vtable, j));
object n = hashMapFindNode
GcTriple* n = hashMapFindNode
(t, virtualMap, reinterpret_cast<object>(method), methodHash, methodEqual);
if (n == 0) {
method = makeMethod
@ -2016,7 +2016,7 @@ addInterfaceMethods(Thread* t, GcClass* class_, GcHashMap* virtualMap,
if (list == 0) {
list = reinterpret_cast<object>(vm::makeList(t, 0, 0, 0));
}
listAppend(t, list, reinterpret_cast<object>(method));
listAppend(t, cast<GcList>(t, list), reinterpret_cast<object>(method));
}
}
}
@ -2193,17 +2193,17 @@ parseMethodTable(Thread* t, Stream& s, GcClass* class_, GcSingleton* pool)
if (methodVirtual(t, method)) {
++ declaredVirtualCount;
object p = hashMapFindNode
GcTriple* p = hashMapFindNode
(t, virtualMap, reinterpret_cast<object>(method), methodHash, methodEqual);
if (p) {
method->offset() = methodOffset(t, tripleFirst(t, p));
method->offset() = methodOffset(t, p->first());
set(t, p, TripleSecond, reinterpret_cast<object>(method));
set(t, reinterpret_cast<object>(p), TripleSecond, reinterpret_cast<object>(method));
} else {
method->offset() = virtualCount++;
listAppend(t, newVirtuals, reinterpret_cast<object>(method));
listAppend(t, cast<GcList>(t, newVirtuals), reinterpret_cast<object>(method));
hashMapInsert(t, virtualMap, reinterpret_cast<object>(method), reinterpret_cast<object>(method), methodHash);
}
@ -2284,7 +2284,7 @@ parseMethodTable(Thread* t, Stream& s, GcClass* class_, GcSingleton* pool)
PROTECT(t, vtable);
for (HashMapIterator it(t, virtualMap); it.hasMore();) {
object method = tripleFirst(t, it.next());
object method = it.next()->first();
assertT(t, arrayBody(t, vtable, methodOffset(t, method)) == 0);
set(t, vtable, ArrayBody + (methodOffset(t, method) * BytesPerWord),
method);
@ -4933,11 +4933,11 @@ intern(Thread* t, object s)
ACQUIRE(t, t->m->referenceLock);
object n = hashMapFindNode
GcTriple* n = hashMapFindNode
(t, cast<GcHashMap>(t, root(t, Machine::StringMap)), s, stringHash, stringEqual);
if (n) {
return jreferenceTarget(t, tripleFirst(t, n));
return jreferenceTarget(t, n->first());
} else {
hashMapInsert(t, cast<GcHashMap>(t, root(t, Machine::StringMap)), s, 0, stringHash);
addFinalizer(t, s, removeString);

View File

@ -66,7 +66,7 @@ THUNK(instanceOfFromReference)
THUNK(makeNewGeneral64)
THUNK(makeNew64)
THUNK(makeNewFromReference)
THUNK(set)
THUNK(setObject)
THUNK(getJClass64)
THUNK(getJClassFromReference)
THUNK(gcIfNecessary)

View File

@ -200,13 +200,13 @@ getNonStaticFields(Thread* t, GcHashMap* typeMaps, object c, object fields,
if ((fieldFlags(t, field) & ACC_STATIC) == 0) {
++ (*count);
fields = vectorAppend(t, fields, field);
fields = reinterpret_cast<object>(vectorAppend(t, cast<GcVector>(t, fields), field));
}
}
}
}
return vectorAppend(t, fields, 0);
return reinterpret_cast<object>(vectorAppend(t, cast<GcVector>(t, fields), 0));
}
object
@ -239,7 +239,7 @@ allFields(Thread* t, GcHashMap* typeMaps, object c, unsigned* count, object* arr
if (includeMembers or (fieldFlags(t, field) & ACC_STATIC)) {
++ (*count);
fields = vectorAppend(t, fields, field);
fields = reinterpret_cast<object>(vectorAppend(t, cast<GcVector>(t, fields), field));
}
}
}
@ -707,7 +707,7 @@ visitRoots(Thread* t, BootImage* image, HeapWalker* w, object constants)
for (HashMapIterator it(t, cast<GcHashMap>(t, classLoaderMap(t, root(t, Machine::BootLoader))));
it.hasMore();)
{
w->visitRoot(tripleSecond(t, it.next()));
w->visitRoot(it.next()->second());
}
image->bootLoader = w->visitRoot(root(t, Machine::BootLoader));
@ -1572,7 +1572,7 @@ writeBootImage2(Thread* t, OutputStream* bootimageOutput, OutputStream* codeOutp
it.hasMore();)
{
bootClassTable[i++] = targetVW
(heapWalker->map()->find(tripleSecond(t, it.next())));
(heapWalker->map()->find(it.next()->second()));
}
}
@ -1588,7 +1588,7 @@ writeBootImage2(Thread* t, OutputStream* bootimageOutput, OutputStream* codeOutp
it.hasMore();)
{
appClassTable[i++] = targetVW
(heapWalker->map()->find(tripleSecond(t, it.next())));
(heapWalker->map()->find(it.next()->second()));
}
}
@ -1600,7 +1600,7 @@ writeBootImage2(Thread* t, OutputStream* bootimageOutput, OutputStream* codeOutp
for (HashMapIterator it(t, cast<GcHashMap>(t, root(t, Machine::StringMap))); it.hasMore();) {
stringTable[i++] = targetVW
(heapWalker->map()->find
(jreferenceTarget(t, tripleFirst(t, it.next()))));
(jreferenceTarget(t, it.next()->first())));
}
}

View File

@ -105,13 +105,6 @@
(object queueTarget)
(object queueNext))
(type hashMap
(uint32_t size)
(object array))
(type weakHashMap
(extends hashMap))
(type list
(uint32_t size)
(object front)
@ -127,8 +120,8 @@
(type treeNode
(object value)
(object left)
(object right))
(treeNode left)
(treeNode right))
(type callNode
(intptr_t address)
@ -142,6 +135,13 @@
(type array
(noassert array object body))
(type hashMap
(uint32_t size)
(field array array))
(type weakHashMap
(extends hashMap))
(type pair
(object first)
(object second))

View File

@ -28,7 +28,7 @@ class TreeContext {
v->visit(&(context->root));
v->visit(&(context->node));
for (List<object>* p = context->ancestors; p; p = p->next) {
for (List<GcTreeNode*>* p = context->ancestors; p; p = p->next) {
v->visit(&(p->item));
}
}
@ -42,44 +42,44 @@ class TreeContext {
{ }
Zone* zone;
object root;
object node;
List<object>* ancestors;
GcTreeNode* root;
GcTreeNode* node;
List<GcTreeNode*>* ancestors;
MyProtector protector;
bool fresh;
};
List<object>*
path(TreeContext* c, object node, List<object>* next)
List<GcTreeNode*>*
path(TreeContext* c, GcTreeNode* node, List<GcTreeNode*>* next)
{
return new(c->zone) List<object>(node, next);
return new(c->zone) List<GcTreeNode*>(node, next);
}
inline object
getTreeNodeValue(Thread*, object n)
getTreeNodeValue(Thread*, GcTreeNode* n)
{
return reinterpret_cast<object>
(alias(n, TreeNodeValue) & PointerMask);
}
inline void
setTreeNodeValue(Thread* t, object n, object value)
setTreeNodeValue(Thread* t, GcTreeNode* n, object value)
{
intptr_t red = alias(n, TreeNodeValue) & (~PointerMask);
set(t, n, TreeNodeValue, value);
set(t, reinterpret_cast<object>(n), TreeNodeValue, value);
alias(n, TreeNodeValue) |= red;
}
inline bool
treeNodeRed(Thread*, object n)
treeNodeRed(Thread*, GcTreeNode* n)
{
return (alias(n, TreeNodeValue) & (~PointerMask)) == 1;
}
inline void
setTreeNodeRed(Thread*, object n, bool red)
setTreeNodeRed(Thread*, GcTreeNode* n, bool red)
{
if (red) {
alias(n, TreeNodeValue) |= 1;
@ -88,28 +88,28 @@ setTreeNodeRed(Thread*, object n, bool red)
}
}
inline object
cloneTreeNode(Thread* t, object n)
inline GcTreeNode*
cloneTreeNode(Thread* t, GcTreeNode* n)
{
PROTECT(t, n);
object newNode = reinterpret_cast<object>(makeTreeNode
(t, getTreeNodeValue(t, n), treeNodeLeft(t, n), treeNodeRight(t, n)));
GcTreeNode* newNode = makeTreeNode
(t, getTreeNodeValue(t, n), n->left(), n->right());
setTreeNodeRed(t, newNode, treeNodeRed(t, n));
return newNode;
}
object
treeFind(Thread* t, object tree, intptr_t key, object sentinal,
GcTreeNode*
treeFind(Thread* t, GcTreeNode* tree, intptr_t key, GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b))
{
object node = tree;
GcTreeNode* node = tree;
while (node != sentinal) {
intptr_t difference = compare(t, key, getTreeNodeValue(t, node));
if (difference < 0) {
node = treeNodeLeft(t, node);
node = node->left();
} else if (difference > 0) {
node = treeNodeRight(t, node);
node = node->right();
} else {
return node;
}
@ -119,18 +119,18 @@ treeFind(Thread* t, object tree, intptr_t key, object sentinal,
}
void
treeFind(Thread* t, TreeContext* c, object old, intptr_t key, object node,
object sentinal,
treeFind(Thread* t, TreeContext* c, GcTreeNode* old, intptr_t key, GcTreeNode* node,
GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b))
{
PROTECT(t, old);
PROTECT(t, node);
PROTECT(t, sentinal);
object newRoot = cloneTreeNode(t, old);
GcTreeNode* newRoot = cloneTreeNode(t, old);
PROTECT(t, newRoot);
object new_ = newRoot;
GcTreeNode* new_ = newRoot;
PROTECT(t, new_);
int count = 0;
@ -140,13 +140,13 @@ treeFind(Thread* t, TreeContext* c, object old, intptr_t key, object node,
intptr_t difference = compare(t, key, getTreeNodeValue(t, old));
if (difference < 0) {
old = treeNodeLeft(t, old);
object n = cloneTreeNode(t, old);
old = old->left();
GcTreeNode* n = cloneTreeNode(t, old);
set(t, new_, TreeNodeLeft, n);
new_ = n;
} else if (difference > 0) {
old = treeNodeRight(t, old);
object n = cloneTreeNode(t, old);
old = old->right();
GcTreeNode* n = cloneTreeNode(t, old);
set(t, new_, TreeNodeRight, n);
new_ = n;
} else {
@ -173,67 +173,67 @@ treeFind(Thread* t, TreeContext* c, object old, intptr_t key, object node,
c->ancestors = c->ancestors;
}
object
leftRotate(Thread* t, object n)
GcTreeNode*
leftRotate(Thread* t, GcTreeNode* n)
{
PROTECT(t, n);
object child = cloneTreeNode(t, treeNodeRight(t, n));
set(t, n, TreeNodeRight, treeNodeLeft(t, child));
GcTreeNode* child = cloneTreeNode(t, n->right());
set(t, n, TreeNodeRight, child->left());
set(t, child, TreeNodeLeft, n);
return child;
}
object
rightRotate(Thread* t, object n)
GcTreeNode*
rightRotate(Thread* t, GcTreeNode* n)
{
PROTECT(t, n);
object child = cloneTreeNode(t, treeNodeLeft(t, n));
set(t, n, TreeNodeLeft, treeNodeRight(t, child));
GcTreeNode* child = cloneTreeNode(t, n->left());
set(t, n, TreeNodeLeft, child->right());
set(t, child, TreeNodeRight, n);
return child;
}
object
GcTreeNode*
treeAdd(Thread* t, TreeContext* c)
{
object new_ = c->node;
GcTreeNode* new_ = c->node;
PROTECT(t, new_);
object newRoot = c->root;
GcTreeNode* newRoot = c->root;
PROTECT(t, newRoot);
// rebalance
setTreeNodeRed(t, new_, true);
while (c->ancestors != 0 and treeNodeRed(t, c->ancestors->item)) {
if (c->ancestors->item
== treeNodeLeft(t, c->ancestors->next->item))
== c->ancestors->next->item->left())
{
if (treeNodeRed
(t, treeNodeRight(t, c->ancestors->next->item)))
(t, c->ancestors->next->item->right()))
{
setTreeNodeRed(t, c->ancestors->item, false);
object n = cloneTreeNode
(t, treeNodeRight(t, c->ancestors->next->item));
GcTreeNode* n = cloneTreeNode
(t, c->ancestors->next->item->right());
set(t, c->ancestors->next->item, TreeNodeRight, n);
setTreeNodeRed(t, treeNodeRight(t, c->ancestors->next->item), false);
setTreeNodeRed(t, c->ancestors->next->item->right(), false);
setTreeNodeRed(t, c->ancestors->next->item, true);
new_ = c->ancestors->next->item;
c->ancestors = c->ancestors->next->next;
} else {
if (new_ == treeNodeRight(t, c->ancestors->item)) {
if (new_ == c->ancestors->item->right()) {
new_ = c->ancestors->item;
c->ancestors = c->ancestors->next;
object n = leftRotate(t, new_);
GcTreeNode* n = leftRotate(t, new_);
if (new_ == treeNodeRight(t, c->ancestors->item)) {
if (new_ == c->ancestors->item->right()) {
set(t, c->ancestors->item, TreeNodeRight, n);
} else {
set(t, c->ancestors->item, TreeNodeLeft, n);
@ -243,10 +243,10 @@ treeAdd(Thread* t, TreeContext* c)
setTreeNodeRed(t, c->ancestors->item, false);
setTreeNodeRed(t, c->ancestors->next->item, true);
object n = rightRotate(t, c->ancestors->next->item);
GcTreeNode* n = rightRotate(t, c->ancestors->next->item);
if (c->ancestors->next->next == 0) {
newRoot = n;
} else if (treeNodeRight(t, c->ancestors->next->next->item)
} else if (c->ancestors->next->next->item->right()
== c->ancestors->next->item)
{
set(t, c->ancestors->next->next->item, TreeNodeRight, n);
@ -258,29 +258,29 @@ treeAdd(Thread* t, TreeContext* c)
} else { // this is just the reverse of the code above (right and
// left swapped):
if (treeNodeRed
(t, treeNodeLeft(t, c->ancestors->next->item)))
(t, c->ancestors->next->item->left()))
{
setTreeNodeRed(t, c->ancestors->item, false);
object n = cloneTreeNode
(t, treeNodeLeft(t, c->ancestors->next->item));
GcTreeNode* n = cloneTreeNode
(t, c->ancestors->next->item->left());
set(t, c->ancestors->next->item, TreeNodeLeft, n);
setTreeNodeRed(t, treeNodeLeft(t, c->ancestors->next->item), false);
setTreeNodeRed(t, c->ancestors->next->item->left(), false);
setTreeNodeRed(t, c->ancestors->next->item, true);
new_ = c->ancestors->next->item;
c->ancestors = c->ancestors->next->next;
} else {
if (new_ == treeNodeLeft(t, c->ancestors->item)) {
if (new_ == c->ancestors->item->left()) {
new_ = c->ancestors->item;
c->ancestors = c->ancestors->next;
object n = rightRotate(t, new_);
GcTreeNode* n = rightRotate(t, new_);
if (new_ == treeNodeLeft(t, c->ancestors->item)) {
if (new_ == c->ancestors->item->left()) {
set(t, c->ancestors->item, TreeNodeLeft, n);
} else {
set(t, c->ancestors->item, TreeNodeRight, n);
@ -290,10 +290,10 @@ treeAdd(Thread* t, TreeContext* c)
setTreeNodeRed(t, c->ancestors->item, false);
setTreeNodeRed(t, c->ancestors->next->item, true);
object n = leftRotate(t, c->ancestors->next->item);
GcTreeNode* n = leftRotate(t, c->ancestors->next->item);
if (c->ancestors->next->next == 0) {
newRoot = n;
} else if (treeNodeLeft(t, c->ancestors->next->next->item)
} else if (c->ancestors->next->next->item->left()
== c->ancestors->next->item)
{
set(t, c->ancestors->next->next->item, TreeNodeLeft, n);
@ -314,20 +314,20 @@ treeAdd(Thread* t, TreeContext* c)
namespace vm {
object
GcTriple*
hashMapFindNode(Thread* t, GcHashMap* map, object key,
uint32_t (*hash)(Thread*, object),
bool (*equal)(Thread*, object, object))
{
bool weak = objectClass(t, map) == type(t, GcWeakHashMap::Type);
object array = map->array();
GcArray* array = map->array();
if (array) {
unsigned index = hash(t, key) & (arrayLength(t, array) - 1);
for (object n = arrayBody(t, array, index); n; n = tripleThird(t, n)) {
object k = tripleFirst(t, n);
unsigned index = hash(t, key) & (array->length() - 1);
for (GcTriple* n = cast<GcTriple>(t, array->body()[index]); n; n = cast<GcTriple>(t, n->third())) {
object k = n->first();
if (weak) {
k = jreferenceTarget(t, k);
k = reinterpret_cast<object>(cast<GcJreference>(t, k)->target());
if (k == 0) {
continue;
}
@ -347,18 +347,18 @@ hashMapResize(Thread* t, GcHashMap* map, uint32_t (*hash)(Thread*, object),
{
PROTECT(t, map);
object newArray = 0;
GcArray* newArray = 0;
if (size) {
object oldArray = map->array();
GcArray* oldArray = map->array();
PROTECT(t, oldArray);
unsigned newLength = nextPowerOfTwo(size);
if (oldArray and arrayLength(t, oldArray) == newLength) {
if (oldArray and oldArray->length() == newLength) {
return;
}
newArray = reinterpret_cast<object>(makeArray(t, newLength));
newArray = makeArray(t, newLength);
if (oldArray != map->array()) {
// a resize was performed during a GC via the makeArray call
@ -368,14 +368,14 @@ hashMapResize(Thread* t, GcHashMap* map, uint32_t (*hash)(Thread*, object),
if (oldArray) {
bool weak = objectClass(t, map) == type(t, GcWeakHashMap::Type);
for (unsigned i = 0; i < arrayLength(t, oldArray); ++i) {
object next;
for (object p = arrayBody(t, oldArray, i); p; p = next) {
next = tripleThird(t, p);
for (unsigned i = 0; i < oldArray->length(); ++i) {
GcTriple* next;
for (GcTriple* p = cast<GcTriple>(t, oldArray->body()[i]); p; p = next) {
next = cast<GcTriple>(t, p->third());
object k = tripleFirst(t, p);
object k = p->first();
if (weak) {
k = jreferenceTarget(t, k);
k = reinterpret_cast<object>(cast<GcJreference>(t, k)->target());
if (k == 0) {
continue;
}
@ -383,14 +383,14 @@ hashMapResize(Thread* t, GcHashMap* map, uint32_t (*hash)(Thread*, object),
unsigned index = hash(t, k) & (newLength - 1);
set(t, p, TripleThird, arrayBody(t, newArray, index));
set(t, reinterpret_cast<object>(p), TripleThird, newArray->body()[index]);
set(t, newArray, ArrayBody + (index * BytesPerWord), p);
}
}
}
}
set(t, reinterpret_cast<object>(map), HashMapArray, newArray);
set(t, map, HashMapArray, newArray);
}
void
@ -407,15 +407,15 @@ hashMapInsert(Thread* t, GcHashMap* map, object key, object value,
bool weak = objectClass(t, map) == type(t, GcWeakHashMap::Type);
object array = map->array();
GcArray* array = map->array();
++ map->size();
if (array == 0 or map->size() >= arrayLength(t, array) * 2) {
if (array == 0 or map->size() >= array->length() * 2) {
PROTECT(t, key);
PROTECT(t, value);
hashMapResize(t, map, hash, array ? arrayLength(t, array) * 2 : 16);
hashMapResize(t, map, hash, array ? array->length() * 2 : 16);
array = map->array();
}
@ -426,39 +426,39 @@ hashMapInsert(Thread* t, GcHashMap* map, object key, object value,
PROTECT(t, key);
PROTECT(t, value);
object r = reinterpret_cast<object>(makeWeakReference(t, 0, 0, 0, 0));
jreferenceTarget(t, r) = key;
jreferenceVmNext(t, r) = t->m->weakReferences;
t->m->weakReferences = r;
k = r;
GcWeakReference* r = makeWeakReference(t, 0, 0, 0, 0);
r->target() = key;
r->vmNext() = t->m->weakReferences;
t->m->weakReferences = reinterpret_cast<object>(r);
k = reinterpret_cast<object>(r);
array = map->array();
}
object n = reinterpret_cast<object>(makeTriple(t, k, value, 0));
GcTriple* n = makeTriple(t, k, value, 0);
array = map->array();
unsigned index = h & (arrayLength(t, array) - 1);
unsigned index = h & (array->length() - 1);
set(t, n, TripleThird, arrayBody(t, array, index));
set(t, reinterpret_cast<object>(n), TripleThird, array->body()[index]);
set(t, array, ArrayBody + (index * BytesPerWord), n);
if (map->size() <= arrayLength(t, array) / 3) {
if (map->size() <= array->length() / 3) {
// this might happen if nodes were removed during GC in which case
// we weren't able to resize at the time
hashMapResize(t, map, hash, arrayLength(t, array) / 2);
hashMapResize(t, map, hash, array->length() / 2);
}
}
object
hashMapRemoveNode(Thread* t, GcHashMap* map, unsigned index, object p, object n)
GcTriple*
hashMapRemoveNode(Thread* t, GcHashMap* map, unsigned index, object p, GcTriple* n)
{
if (p) {
set(t, p, TripleThird, tripleThird(t, n));
set(t, p, TripleThird, n->third());
} else {
set(t, map->array(), ArrayBody + (index * BytesPerWord),
tripleThird(t, n));
set(t, reinterpret_cast<object>(map->array()), ArrayBody + (index * BytesPerWord),
n->third());
}
-- map->size();
return n;
@ -471,35 +471,35 @@ hashMapRemove(Thread* t, GcHashMap* map, object key,
{
bool weak = objectClass(t, map) == type(t, GcWeakHashMap::Type);
object array = map->array();
GcArray* array = map->array();
object o = 0;
if (array) {
unsigned index = hash(t, key) & (arrayLength(t, array) - 1);
unsigned index = hash(t, key) & (array->length() - 1);
object p = 0;
for (object n = arrayBody(t, array, index); n;) {
object k = tripleFirst(t, n);
for (GcTriple* n = cast<GcTriple>(t, array->body()[index]); n;) {
object k = n->first();
if (weak) {
k = jreferenceTarget(t, k);
k = reinterpret_cast<object>(cast<GcJreference>(t, k)->target());
if (k == 0) {
n = tripleThird(t, hashMapRemoveNode(t, map, index, p, n));
n = cast<GcTriple>(t, hashMapRemoveNode(t, map, index, p, n)->third());
continue;
}
}
if (equal(t, key, k)) {
o = tripleSecond(t, hashMapRemoveNode(t, map, index, p, n));
o = hashMapRemoveNode(t, map, index, p, n)->second();
break;
} else {
p = n;
n = tripleThird(t, n);
p = reinterpret_cast<object>(n);
n = cast<GcTriple>(t, n->third());
}
}
if ((not t->m->collecting)
and map->size() <= arrayLength(t, array) / 3)
and map->size() <= array->length() / 3)
{
PROTECT(t, o);
hashMapResize(t, map, hash, arrayLength(t, array) / 2);
hashMapResize(t, map, hash, array->length() / 2);
}
}
@ -507,78 +507,78 @@ hashMapRemove(Thread* t, GcHashMap* map, object key,
}
void
listAppend(Thread* t, object list, object value)
listAppend(Thread* t, GcList* list, object value)
{
PROTECT(t, list);
++ listSize(t, list);
++ list->size();
object p = reinterpret_cast<object>(makePair(t, value, 0));
if (listFront(t, list)) {
set(t, listRear(t, list), PairSecond, p);
if (list->front()) {
set(t, list->rear(), PairSecond, p);
} else {
set(t, list, ListFront, p);
set(t, reinterpret_cast<object>(list), ListFront, p);
}
set(t, list, ListRear, p);
set(t, reinterpret_cast<object>(list), ListRear, p);
}
object
vectorAppend(Thread* t, object vector, object value)
GcVector*
vectorAppend(Thread* t, GcVector* vector, object value)
{
if (vectorLength(t, vector) == vectorSize(t, vector)) {
if (vector->length() == vector->size()) {
PROTECT(t, vector);
PROTECT(t, value);
object newVector = reinterpret_cast<object>(makeVector
(t, vectorSize(t, vector), max(16, vectorSize(t, vector) * 2)));
GcVector* newVector = makeVector
(t, vector->size(), max(16, vector->size() * 2));
if (vectorSize(t, vector)) {
memcpy(&vectorBody(t, newVector, 0),
&vectorBody(t, vector, 0),
vectorSize(t, vector) * BytesPerWord);
if (vector->size()) {
memcpy(newVector->body().begin(),
vector->body().begin(),
vector->size() * BytesPerWord);
}
vector = newVector;
}
set(t, vector, VectorBody + (vectorSize(t, vector) * BytesPerWord), value);
++ vectorSize(t, vector);
set(t, reinterpret_cast<object>(vector), VectorBody + (vector->size() * BytesPerWord), value);
++ vector->size();
return vector;
}
object
growArray(Thread* t, object array)
GcArray*
growArray(Thread* t, GcArray* array)
{
PROTECT(t, array);
object newArray = reinterpret_cast<object>(makeArray
(t, array == 0 ? 16 : (arrayLength(t, array) * 2)));
GcArray* newArray = makeArray
(t, array == 0 ? 16 : (array->length() * 2));
if (array) {
memcpy(&arrayBody(t, newArray, 0), &arrayBody(t, array, 0),
arrayLength(t, array));
memcpy(newArray->body().begin(), array->body().begin(),
array->length());
}
return newArray;
}
object
treeQuery(Thread* t, object tree, intptr_t key, object sentinal,
treeQuery(Thread* t, GcTreeNode* tree, intptr_t key, GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b))
{
object node = treeFind(t, tree, key, sentinal, compare);
GcTreeNode* node = treeFind(t, tree, key, sentinal, compare);
return (node ? getTreeNodeValue(t, node) : 0);
}
object
treeInsert(Thread* t, Zone* zone, object tree, intptr_t key, object value,
object sentinal,
GcTreeNode*
treeInsert(Thread* t, Zone* zone, GcTreeNode* tree, intptr_t key, object value,
GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b))
{
PROTECT(t, tree);
PROTECT(t, sentinal);
object node = reinterpret_cast<object>(makeTreeNode(t, value, sentinal, sentinal));
GcTreeNode* node = makeTreeNode(t, value, sentinal, sentinal);
TreeContext c(t, zone);
treeFind(t, &c, tree, key, node, sentinal, compare);
@ -588,7 +588,7 @@ treeInsert(Thread* t, Zone* zone, object tree, intptr_t key, object value,
}
void
treeUpdate(Thread* t, object tree, intptr_t key, object value, object sentinal,
treeUpdate(Thread* t, GcTreeNode* tree, intptr_t key, object value, GcTreeNode* sentinal,
intptr_t (*compare)(Thread* t, intptr_t key, object b))
{
setTreeNodeValue(t, treeFind(t, tree, key, sentinal, compare), value);