use more simple hashing algorithm, made namelist generation dependant on a #define

This commit is contained in:
ceriel 1989-10-26 16:16:35 +00:00
parent cd1bb106ec
commit 0f8516f861
6 changed files with 20 additions and 35 deletions

View file

@ -316,7 +316,7 @@ garbage:
do { /* read the identifier */
if (++pos < idfsize) {
*tg++ = ch;
hash = ENHASH(hash, ch, pos);
hash = ENHASH(hash, ch);
}
ch = GetChar();
} while (in_idf(ch));

View file

@ -137,7 +137,7 @@ str2idf(tg)
hash = STARTHASH();
while (++pos < idfsize && (ch = *cp++)) {
*ncp++ = ch;
hash = ENHASH(hash, ch, pos);
hash = ENHASH(hash, ch);
}
hash = STOPHASH(hash);
*ncp++ = '\0';
@ -757,18 +757,3 @@ free_formals(fm)
fm = tmp;
}
}
char hmask[IDFSIZE];
init_hmask()
{
/* A simple congruence random number generator, as
described in Knuth, vol 2.
*/
register int h, rnd = HASH_X;
for (h = 0; h < IDFSIZE; h++) {
hmask[h] = rnd;
rnd = (HASH_A * rnd + HASH_C) & HASHMASK;
}
}

View file

@ -7,24 +7,11 @@
#include "nopp.h"
/* Since the % operation in the calculation of the hash function
turns out to be expensive, it is replaced by the cheaper XOR (^).
Each character of the identifier is xored with an 8-bit mask which
depends on the position of the character; the sum of these results
is the hash value. The random masks are obtained from a
congruence generator in idf.c.
*/
#define HASHSIZE 307 /* must be odd */
#define HASHSIZE 256 /* must be a power of 2 */
#define HASH_X 0253 /* Knuth's X */
#define HASH_A 77 /* Knuth's a */
#define HASH_C 153 /* Knuth's c */
extern char hmask[]; /* the random masks */
#define HASHMASK (HASHSIZE-1) /* since it is a power of 2 */
#define STARTHASH() (0)
#define ENHASH(hs,ch,ps) (hs + (ch ^ hmask[ps]))
#define STOPHASH(hs) (hs & HASHMASK)
#define ENHASH(hs,ch) ((hs << 2) + ch)
#define STOPHASH(hs) ((unsigned)hs % HASHSIZE)
struct idf {
struct idf *next;

View file

@ -83,7 +83,6 @@ main(argc, argv)
/* parse and interpret the command line options */
prog_name = argv[0];
init_hmask();
#ifndef NOPP
inctable = (char **) Malloc(10 * sizeof(char *));
inctable[0] = "";
@ -125,7 +124,9 @@ main(argc, argv)
char *source = 0;
#ifdef GEN_NM_LIST
char *nmlist = 0;
#endif GEN_NM_LIST
compile(argc, argv)
char *argv[];
@ -157,15 +158,21 @@ compile(argc, argv)
case 2:
destination = argv[1];
break;
#ifdef GEN_NM_LIST
case 3:
nmlist = argv[2];
destination = argv[1];
break;
#endif GEN_NM_LIST
#endif LINT
default:
#ifndef LINT
#ifdef GEN_NM_LIST
fatal("use: %s source destination [namelist]", prog_name);
#else GEN_NM_LIST
fatal("use: %s source destination", prog_name);
#endif GEN_NM_LIST
#else LINT
fatal("use: %s source", prog_name);
#endif LINT

View file

@ -313,7 +313,7 @@ actual(repl)
do {
if (++pos < idfsize) {
*p++ = ch;
hash = ENHASH(hash, ch, pos);
hash = ENHASH(hash, ch);
}
ch = GetChar();
} while (in_idf(ch));

View file

@ -179,7 +179,9 @@ unstack_world()
lint_global_level(local_level);
#endif LINT
#ifdef GEN_NM_LIST
open_name_list();
#endif GEN_NM_LIST
while (se) {
register struct idf *idf = se->se_idf;
@ -227,8 +229,10 @@ unstack_world()
&& !def->df_initialized) {
/* space must be allocated */
bss(idf);
#ifdef GEN_NM_LIST
if (def->df_sc != STATIC)
namelist(idf->id_text); /* may be common */
#endif GEN_NM_LIST
def->df_alloc = ALLOC_DONE; /* see Note below */
}
se = se->next;
@ -247,6 +251,7 @@ unstack_world()
*/
}
#ifdef GEN_NM_LIST
/* A list of potential common names is kept, to be fed to
an understanding loader. The list is written to a file
the name of which is nmlist. If nmlist == NULL, no name
@ -269,3 +274,4 @@ namelist(nm)
sys_write(nfp, "\n", 1);
}
}
#endif GEN_NM_LIST