예제 #1
0
static KidsHash *
HashChildren(Shape *kid1, Shape *kid2)
{
    void *mem = js_malloc(sizeof(KidsHash));
    if (!mem)
        return NULL;

    KidsHash *hash = new (mem) KidsHash();
    if (!hash->init(2)) {
        js_free(hash);
        return NULL;
    }

    KidsHash::AddPtr addPtr = hash->lookupForAdd(kid1);
    JS_ALWAYS_TRUE(hash->add(addPtr, kid1));

    addPtr = hash->lookupForAdd(kid2);
    JS_ASSERT(!addPtr.found());
    JS_ALWAYS_TRUE(hash->add(addPtr, kid2));

    return hash;
}
예제 #2
0
bool
PropertyTree::insertChild(JSContext *cx, Shape *parent, Shape *child)
{
    JS_ASSERT(!parent->inDictionary());
    JS_ASSERT(!child->parent);
    JS_ASSERT(!child->inDictionary());
    JS_ASSERT(!JSID_IS_VOID(parent->id));
    JS_ASSERT(!JSID_IS_VOID(child->id));
    JS_ASSERT(cx->compartment == compartment);
    JS_ASSERT(child->compartment == parent->compartment);

    KidsPointer *kidp = &parent->kids;

    if (kidp->isNull()) {
        child->setParent(parent);
        kidp->setShape(child);
        return true;
    }

    if (kidp->isShape()) {
        Shape *shape = kidp->toShape();
        JS_ASSERT(shape != child);
        JS_ASSERT(!shape->matches(child));

        KidsHash *hash = HashChildren(shape, child);
        if (!hash) {
            JS_ReportOutOfMemory(cx);
            return false;
        }
        kidp->setHash(hash);
        child->setParent(parent);
        return true;
    }

    KidsHash *hash = kidp->toHash();
    KidsHash::AddPtr addPtr = hash->lookupForAdd(child);
    JS_ASSERT(!addPtr.found());
    if (!hash->add(addPtr, child)) {
        JS_ReportOutOfMemory(cx);
        return false;
    }
    child->setParent(parent);
    return true;
}