view src/insert_verification/akashaCS.c @ 28:04283ef8f3ca

Free memory when backed previous depth
author Yasutaka Higa <e115763@ie.u-ryukyu.ac.jp>
date Tue, 26 Apr 2016 18:30:46 +0900
parents a416dd4093cf
children
line wrap: on
line source

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

#include "akashaLLRBContext.h"

extern __code initLLRBContext(struct Context*, enum Code);

/* utils */

bool eqNode(struct Node* n1, struct Node* n2) {
    if ((n1 == NULL) && (n2 == NULL))  return true;
    if (n1->key   != n2->key)          return false;
    if (n1->value != n2->value)        return false;
    if (n1->color != n2->color)        return false;
    if (!eqNode(n1->left,  n2->left))  return false;
    if (!eqNode(n1->right, n2->right)) return false;
    return true;
}

bool eqTree(struct Tree* t1, struct Tree* t2) {
    if ((t1 == NULL) && (t2 == NULL))      return true;
    if (t1->next   != t2->next)            return false;
    if (t2->result != t2->result)          return false;
    if (!eqNode(t1->root,    t2->root))    return false;
    if (!eqNode(t1->current, t2->current)) return false;
    if (!eqNode(t1->deleted, t2->deleted)) return false;
    return true;
}


bool eqIter(struct Iterator* iter1, struct Iterator* iter2) {
    if (iter1->head->val != iter2->head->val)         return false;
    if (iter1->last->val != iter2->last->val)         return false;
    if (iter1->iteratedValue != iter2->iteratedValue) return false;
    if (!eqTree(iter1->tree, iter2->tree))            return false;

    struct IterElem *ie1 = iter1->head->next;
    struct IterElem *ie2 = iter2->head->next;

    while (ie1->val != iter1->head->val) {
        if (ie1->val != ie2->val) return false;
        ie1 = ie1->next;
        ie2 = ie2->next;
    }

    if ((iter1->previousDepth == NULL) && (iter2->previousDepth == NULL)) return true;
    return eqIter(iter1->previousDepth, iter2->previousDepth);
}


/* C function */

void validateNodePointer(struct Node* node) {
    if (node == NULL) return;
    validateNodePointer(node->left);
    validateNodePointer(node->right);
}

void validateTreePointer(struct Tree* tree) {
    if (tree == NULL) return;
    validateNodePointer(tree->root);
    validateNodePointer(tree->current);
    validateNodePointer(tree->deleted);
}


void findInvalidPointer(struct Context* context) {
    validateNodePointer(&context->data[Node]->node);
    validateTreePointer(&context->data[Tree]->tree);
}

/* Code Segments */

__code meta(struct Context* context, enum Code next) {
    struct Iterator* iter = &context->data[Iter]->iterator;

    switch (context->prev) {
        case GoToPreviousDepth:
            if (iter->iteratedPointDataNum == 0) break;
            if (iter->iteratedPointHeap == NULL) break;

            unsigned int diff =(unsigned long)context->heap - (unsigned long)iter->iteratedPointHeap;
            memset(iter->iteratedPointHeap, 0, diff);
            context->dataNum = iter->iteratedPointDataNum;
            context->heap    = iter->iteratedPointHeap;
            break;
        default:
            break;
    }
    switch (next) {
        case PutAndGoToNextDepth:
            if (context->prev == GoToPreviousDepth) break;
            if (iter->previousDepth == NULL)        break;
            iter->previousDepth->iteratedPointDataNum = context->dataNum;
            iter->previousDepth->iteratedPointHeap    = context->heap;
            break;
        default:
            break;
    }

    findInvalidPointer(context);
    context->prev = next;
    goto (context->code[next])(context);
}

__code startCode(enum Code next) {
    struct Context* context = (struct Context*)malloc(sizeof(struct Context));

    goto initLLRBContext(context, next);
}

__code exitCode(struct Context* context) {
    free(context->code);
    free(context->data);
    free(context->heapStart);
    goto exit(0);
}