assoctab.c 1.67 KB
/*
 * Copyright (C) 1996-1998 by the Board of Trustees
 *    of Leland Stanford Junior University.
 * 
 * This file is part of the SimOS distribution. 
 * See LICENSE file for terms of the license. 
 *
 */

#include <string.h>
#include <assert.h>
#include <stdlib.h>
#include <stdio.h>
#include "assoctab.h"

#define TAB_SIZE    1024
#define HASH_MASK   (TAB_SIZE - 1)

int hash(char* label)
{
   char *c;
   int key = 0;
   
   for (c=label; *c; c++) {
      key = (key<< 1) ^ *c;
   }
   
   return key & HASH_MASK;
}

AssocTab *AssocTabCreate(void)
{
   AssocTab *at;
   int i;
   
   at = (AssocTab *)malloc(sizeof(ATHeader*)*TAB_SIZE);
   
   for (i=0; i<TAB_SIZE; i++) {
      at[i] = NULL;
   }

   return at;
}

int AssocTabEnter(AssocTab *at, ATHeader *item)
{
   int key = hash(item->label);

#ifdef DEBUG
   ATHeader *mark = at[key];

   while (mark) {
      if (strcmp(item->label, mark->label) == 0) {
         return AT_ERROR;
      }
      mark = mark->next;
   }
#endif
   
   item->next = at[key];
   at[key] = item;

   return AT_OK;
}

int AssocTabLookup(AssocTab *at, char *index, ATHeader **item)
{
   ATHeader* mark = at[hash(index)];
   
   while (mark) {
      if (strcmp(index, mark->label) == 0) {
         if (item) {
            *item = mark;
         }
         return AT_OK;
      }
      mark = mark->next;
   }
   
   return AT_ERROR;
}

void AssocTabForeach(AssocTab *at, void (*p)(ATHeader *item))
{
   ATHeader *mark;
   int i;
   
   for (i=0; i<TAB_SIZE; i++) {
      mark = at[i];
      while (mark) {
         if (p) {
            p(mark);
         } else {
            printf("at[%d]: %s\n", i, mark->label);
         }
         mark = mark->next;
      }
   }
}