1 # 2 /* Re-coding of advent in C: data structure routines */ 3 4 static char sccsid[] = " vocab.c 4.1 82/05/11 "; 5 6 # include "hdr.h" 7 8 dstroy(object) 9 int object; 10 { move(object,0); 11 } 12 13 juggle(object) 14 int object; 15 { register int i,j; 16 i=place[object]; 17 j=fixed[object]; 18 move(object,i); 19 move(object+100,j); 20 } 21 22 23 move(object,where) 24 int object,where; 25 { register int from; 26 if (object<=100) 27 from=place[object]; 28 else 29 from=fixed[object-100]; 30 if (from>0 && from<=300) carry(object,from); 31 drop(object,where); 32 } 33 34 35 put(object,where,pval) 36 int object,where,pval; 37 { move(object,where); 38 return(-1-pval); 39 } 40 41 42 43 carry(object,where) 44 int object,where; 45 { register int temp; 46 if (object<=100) 47 { if (place[object]== -1) return; 48 place[object] = -1; 49 holdng++; 50 } 51 if (atloc[where]==object) 52 { atloc[where]=link[object]; 53 return; 54 } 55 for (temp=atloc[where]; link[temp]!=object; temp=link[temp]); 56 link[temp]=link[object]; 57 } 58 59 60 61 62 drop(object,where) 63 int object,where; 64 { if (object>100) fixed[object-100]=where; 65 else 66 { if (place[object]== -1) holdng--; 67 place[object]=where; 68 } 69 if (where<=0) return; 70 link[object]=atloc[where]; 71 atloc[where]=object; 72 } 73 74 75 vocab(word,type,value) /* look up or store a word */ 76 char *word; 77 int type; /* -2 for store, -1 for user word, >=0 for canned lookup*/ 78 int value; /* used for storing only */ 79 { register int adr; 80 register char *s,*t; 81 int hash, i; 82 struct hashtab *h; 83 for (hash=0,s=word,i=0; i<5 &&*s; i++) /* some kind of hash */ 84 hash += *s++; /* add all chars in the word */ 85 hash = (hash*3719)&077777; /* pulled that one out of a hat */ 86 hash %= HTSIZE; /* put it into range of table */ 87 88 for(adr=hash;; adr++) /* look for entry in table */ 89 { if (adr==HTSIZE) adr=0; /* wrap around */ 90 h = &voc[adr]; /* point at the entry */ 91 switch(type) 92 { case -2: /* fill in entry */ 93 if (h->val) /* already got an entry? */ 94 goto exitloop2; 95 h->val=value; 96 h->atab=malloc(length(word)); 97 for (s=word,t=h->atab; *s;) 98 *t++ = *s++ ^ '='; 99 *t=0^'='; 100 /* encrypt slightly to thwart core reader */ 101 /* printf("Stored \"%s\" (%d ch) as entry %d\n", */ 102 /* word, length(word), adr); */ 103 return(0); /* entry unused */ 104 case -1: /* looking up user word */ 105 if (h->val==0) return(-1); /* not found */ 106 for (s=word, t=h->atab;*t ^ '=';) 107 if ((*s++ ^ '=') != *t++) 108 goto exitloop2; 109 if ((*s ^ '=') != *t && s-word<5) goto exitloop2; 110 /* the word matched o.k. */ 111 return(h->val); 112 default: /* looking up known word */ 113 if (h->val==0) 114 { printf("Unable to find %s in vocab\n",word); 115 exit(0); 116 } 117 for (s=word, t=h->atab;*t ^ '=';) 118 if ((*s++ ^ '=') != *t++) goto exitloop2; 119 /* the word matched o.k. */ 120 if (h->val/1000 != type) continue; 121 return(h->val%1000); 122 } 123 124 exitloop2: /* hashed entry does not match */ 125 if (adr+1==hash || (adr==HTSIZE && hash==0)) 126 { printf("Hash table overflow\n"); 127 exit(0); 128 } 129 } 130 } 131 132 133 copystr(w1,w2) /* copy one string to another */ 134 char *w1,*w2; 135 { register char *s,*t; 136 for (s=w1,t=w2; *s;) 137 *t++ = *s++; 138 *t=0; 139 } 140 141 weq(w1,w2) /* compare words */ 142 char *w1,*w2; /* w1 is user, w2 is system */ 143 { register char *s,*t; 144 register int i; 145 s=w1; 146 t=w2; 147 for (i=0; i<5; i++) /* compare at most 5 chars */ 148 { if (*t==0 && *s==0) 149 return(TRUE); 150 if (*s++ != *t++) return(FALSE); 151 } 152 return(TRUE); 153 } 154 155 156 length(str) /* includes 0 at end */ 157 char *str; 158 { register char *s; 159 register int n; 160 for (n=0,s=str; *s++;) n++; 161 return(n+1); 162 } 163 164 prht() /* print hash table */ 165 { register int i,j,l; 166 char *c; 167 struct hashtab *h; 168 for (i=0; i<HTSIZE/10+1; i++) 169 { printf("%4d",i*10); 170 for (j=0; j<10; j++) 171 { if (i*10+j>=HTSIZE) break; 172 h= &voc[i*10+j]; 173 putchar(' '); 174 if (h->val==0) 175 { printf("-----"); 176 continue; 177 } 178 for (l=0, c=h->atab; l<5; l++) 179 if ((*c ^ '=')) putchar(*c++ ^ '='); 180 else putchar(' '); 181 } 182 putchar('\n'); 183 } 184 } 185 186