home *** CD-ROM | disk | FTP | other *** search
- /******************************************************************************
- *
- * table.c - manipulation routines for the name table
- *
- * init - initialize table
- * addname - put name in table at depth
- * getname - get next name at depth
- *
- *****************************************************************************/
-
- #include <stdio.h>
- #include "xtree.h"
-
- typedef struct table_entry {
- char *name;
- struct table_entry *next;
- } NTent;
-
- NTent *name_tbl[ABSMAX_DEPTH][256];
- int index[ABSMAX_DEPTH];
- extern int max_depth;
-
- /* initialize name table */
- #ifdef PROTOTYPE
- void init(void)
- #else
- void init()
- #endif /* PROTOTYPE */
- {
- int i, j;
-
- for(i = 0; i < max_depth; i++)
- {
- for(j = 0; j < 256; j++)
- name_tbl[i][j] = NULL;
- index[i] = 0;
- }
-
- return;
- }
-
- /* add 'name' to the name table at depth 'depth' */
- #ifdef PROTOTYPE
- void addname(char *name, int depth)
- #else
- void addname(name, depth)
- char *name;
- int depth;
- #endif /* PROTOTYPE */
- {
- int slot, done;
- NTent *new, *cur, *last;
-
- /* can only go so far */
- if(depth >= max_depth)
- return;
-
- /* build the new node */
- new = (NTent *) malloc(sizeof(NTent));
- new->name = (char *) malloc(strlen(name) + 1);
- strcpy(new->name, name);
-
- /* go to the table slot to start looking */
- slot = (int) *name;
- last = name_tbl[depth][slot];
-
- if(last == NULL)
- {
- new->next = NULL;
- name_tbl[depth][slot] = new;
- }
- else
- { /*
- * pass over all nodes with names that are alphabetically less then
- * the new name
- */
- if(strcmp(last->name, name) > 0)
- { /* goes before first node in bucket */
- new->next = last;
- name_tbl[depth][slot] = new;
- }
- else
- {
- for(cur = last->next, done = FALSE; cur != NULL && !done;
- cur = cur->next, last = last->next)
- if(strcmp(cur->name, new->name) > 0) /* lexically g.t. */
- done = TRUE;
- /* we now want to put new between last and cur */
- new->next = last->next;
- last->next = new;
- }
- }
- }
-
- #ifdef PROTOTYPE
- char *getname(int depth)
- #else
- char *getname(depth)
- int depth;
- #endif /* PROTOTYPE */
- {
- char *ret;
- NTent *n;
-
- /* can only go so far */
- if(depth >= max_depth)
- return NULL;
-
- /* find slot with nodes */
- for(n = name_tbl[depth][index[depth]]; n == NULL && index[depth] < 256; )
- {
- index[depth]++;
- n = name_tbl[depth][index[depth]];
- }
-
- if(n == NULL) /* nothing at this depth */
- {
- index[depth] = 0; /* performance loss if getname() is called many */
- return NULL; /* after exhausting at a given depth */
- }
-
- /* get string */
- ret = (char *) malloc(strlen(n->name) + 1);
- strcpy(ret, n->name);
-
- /* delete node */
- name_tbl[depth][index[depth]] = n->next;
- free(n->name);
- free(n);
-
- return(ret);
- }
-