Exemplo n.º 1
0
void verify(void) {
    chkctx ctx;
    enum234 e;
    int i;
    void *p;

    ctx.treedepth = -1;                /* depth unknown yet */
    ctx.elemcount = 0;                 /* no elements seen yet */
    /*
     * Verify validity of tree properties.
     */
    if (tree->root)
        chknode(&ctx, 0, tree->root, NULL, NULL);
    printf("tree depth: %d\n", ctx.treedepth);
    /*
     * Enumerate the tree and ensure it matches up to the array.
     */
    for (i = 0, p = first234(tree, &e);
         p;
         i++, p = next234(&e)) {
        if (i >= arraylen)
            error("tree contains more than %d elements", arraylen);
        if (array[i] != p)
            error("enum at position %d: array says %s, tree says %s",
                   i, array[i], p);
    }
    if (i != ctx.elemcount) {
        error("tree really contains %d elements, enum gave %d",
               i, ctx.elemcount);
    }
    if (i < arraylen) {
        error("enum gave only %d elements, array has %d", i, arraylen);
    }
}
Exemplo n.º 2
0
void verify(void)
{
    chkctx ctx;
    int i;
    void *p;

    ctx.treedepth = -1;		       /* depth unknown yet */
    ctx.elemcount = 0;		       /* no elements seen yet */
    /*
     * Verify validity of tree properties.
     */
    if (tree->root) {
	if (tree->root->parent != NULL)
	    error("root->parent is %p should be null", tree->root->parent);
	chknode(&ctx, 0, tree->root, NULL, NULL);
    }
    printf("tree depth: %d\n", ctx.treedepth);
    /*
     * Enumerate the tree and ensure it matches up to the array.
     */
    for (i = 0; NULL != (p = index234(tree, i)); i++) {
	if (i >= arraylen)
	    error("tree contains more than %d elements", arraylen);
	if (array[i] != p)
	    error("enum at position %d: array says %s, tree says %s",
		  i, array[i], p);
    }
    if (ctx.elemcount != i) {
	error("tree really contains %d elements, enum gave %d",
	      ctx.elemcount, i);
    }
    if (i < arraylen) {
	error("enum gave only %d elements, array has %d", i, arraylen);
    }
    i = count234(tree);
    if (ctx.elemcount != i) {
	error("tree really contains %d elements, count234 gave %d",
	      ctx.elemcount, i);
    }
}
Exemplo n.º 3
0
int chknode(chkctx *ctx, int level, node234 *node,
             void *lowbound, void *highbound) {
    int nkids, nelems;
    int i;
    int count;

    /* Count the non-NULL kids. */
    for (nkids = 0; nkids < 4 && node->kids[nkids]; nkids++);
    /* Ensure no kids beyond the first NULL are non-NULL. */
    for (i = nkids; i < 4; i++)
        if (node->kids[i]) {
            error("node %p: nkids=%d but kids[%d] non-NULL",
                   node, nkids, i);
        } else if (node->counts[i]) {
            error("node %p: kids[%d] NULL but count[%d]=%d nonzero",
                   node, i, i, node->counts[i]);
	}

    /* Count the non-NULL elements. */
    for (nelems = 0; nelems < 3 && node->elems[nelems]; nelems++);
    /* Ensure no elements beyond the first NULL are non-NULL. */
    for (i = nelems; i < 3; i++)
        if (node->elems[i]) {
            error("node %p: nelems=%d but elems[%d] non-NULL",
                   node, nelems, i);
        }

    if (nkids == 0) {
        /*
         * If nkids==0, this is a leaf node; verify that the tree
         * depth is the same everywhere.
         */
        if (ctx->treedepth < 0)
            ctx->treedepth = level;    /* we didn't know the depth yet */
        else if (ctx->treedepth != level)
            error("node %p: leaf at depth %d, previously seen depth %d",
                   node, level, ctx->treedepth);
    } else {
        /*
         * If nkids != 0, then it should be nelems+1, unless nelems
         * is 0 in which case nkids should also be 0 (and so we
         * shouldn't be in this condition at all).
         */
        int shouldkids = (nelems ? nelems+1 : 0);
        if (nkids != shouldkids) {
            error("node %p: %d elems should mean %d kids but has %d",
                   node, nelems, shouldkids, nkids);
        }
    }

    /*
     * nelems should be at least 1.
     */
    if (nelems == 0) {
        error("node %p: no elems", node, nkids);
    }

    /*
     * Add nelems to the running element count of the whole tree.
     */
    ctx->elemcount += nelems;

    /*
     * Check ordering property: all elements should be strictly >
     * lowbound, strictly < highbound, and strictly < each other in
     * sequence. (lowbound and highbound are NULL at edges of tree
     * - both NULL at root node - and NULL is considered to be <
     * everything and > everything. IYSWIM.)
     */
    if (cmp) {
	for (i = -1; i < nelems; i++) {
	    void *lower = (i == -1 ? lowbound : node->elems[i]);
	    void *higher = (i+1 == nelems ? highbound : node->elems[i+1]);
	    if (lower && higher && cmp(lower, higher) >= 0) {
		error("node %p: kid comparison [%d=%s,%d=%s] failed",
		      node, i, lower, i+1, higher);
	    }
	}
    }

    /*
     * Check parent pointers: all non-NULL kids should have a
     * parent pointer coming back to this node.
     */
    for (i = 0; i < nkids; i++)
        if (node->kids[i]->parent != node) {
            error("node %p kid %d: parent ptr is %p not %p",
                   node, i, node->kids[i]->parent, node);
        }


    /*
     * Now (finally!) recurse into subtrees.
     */
    count = nelems;

    for (i = 0; i < nkids; i++) {
        void *lower = (i == 0 ? lowbound : node->elems[i-1]);
        void *higher = (i >= nelems ? highbound : node->elems[i]);
	int subcount = chknode(ctx, level+1, node->kids[i], lower, higher);
	if (node->counts[i] != subcount) {
	    error("node %p kid %d: count says %d, subtree really has %d",
		  node, i, node->counts[i], subcount);
	}
        count += subcount;
    }

    return count;
}