home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Power-Programmierung
/
CD1.mdf
/
icon
/
dos
/
src
/
common
/
strtbl.c
< prev
next >
Wrap
C/C++ Source or Header
|
1992-02-10
|
3KB
|
156 lines
/*
* The functions in this file maintain a hash table of strings and manage
* string buffers.
*/
#include "../h/gsupport.h"
/*
* Prototype for static function.
*/
hidden int streq Params((int len,char *s1,char *s2));
struct str_entry {
char *s;
int length;
struct str_entry *next;
};
#define SBufSize 1024
#define StrTblSz 149
static struct str_entry *str_tbl[StrTblSz];
/*
* init_str - initialize string hash table.
*/
novalue init_str()
{
static int first_time = 1;
int h;
if (first_time)
first_time = 0;
else
return;
for (h = 0; h < StrTblSz; ++h)
str_tbl[h] = NULL;
}
/*
* init_sbuf - initialize a new sbuf struct, allocating an initial buffer.
*/
novalue init_sbuf(sbuf)
struct str_buf *sbuf;
{
sbuf->size = SBufSize;
sbuf->strtimage = (char *)alloc((unsigned)SBufSize);
sbuf->endimage = sbuf->strtimage;
sbuf->end = sbuf->strtimage + SBufSize;
}
/*
* new_sbuf - allocate a new buffer for a sbuf struct, copying the partially
* created string from the full buffer to the new one.
*/
novalue new_sbuf(sbuf)
struct str_buf *sbuf;
{
char *s1, *s2;
#if IntBits == 16
unsigned int oldsize = sbuf->size;
sbuf->size += (sbuf->size/2);
if (sbuf->size < oldsize) { /* check for overflow */
sbuf->size = MaxBlock;
}
#else /* IntBits == 16 */
sbuf->size *= 2;
#endif /* IntBits == 16 */
s1 = sbuf->strtimage;
sbuf->strtimage = (char *)alloc((unsigned)sbuf->size);
s2 = sbuf->strtimage;
while (s1 < sbuf->endimage)
*s2++ = *s1++;
sbuf->endimage = s2;
sbuf->end = sbuf->strtimage + sbuf->size;
}
/*
* spec_str - install a special string in the string table.
*/
char *spec_str(s)
char *s;
{
struct str_entry *se;
register char *s1;
register int l;
register int h;
h = 0;
l = 1;
for (s1 = s; *s1 != '\0'; ++s1) {
h += *s1 & 0377;
++l;
}
h %= StrTblSz;
for (se = str_tbl[h]; se != NULL; se = se->next)
if (l == se->length && streq(l, s, se->s))
return se->s;
se = NewStruct(str_entry);
se->s = s;
se->length = l;
se->next = str_tbl[h];
str_tbl[h] = se;
return s;
}
/*
* str_install - find out if the string in the buffer is in the string table.
* If not, put it there. Return a pointer to the string in the table.
*/
char *str_install(sbuf)
struct str_buf *sbuf;
{
int h;
struct str_entry *se;
register char *s;
register char *e;
int l;
AppChar(*sbuf, '\0')
s = sbuf->strtimage;
e = sbuf->endimage;
h = 0;
while (s < e)
h += *s++ & 0377;
h %= StrTblSz;
s = sbuf->strtimage;
l = e - s;
for (se = str_tbl[h]; se != NULL; se = se->next)
if (l == se->length && streq(l, s, se->s)) {
sbuf->endimage = s;
return se->s;
}
se = NewStruct(str_entry);
se->s = s;
se->length = l;
sbuf->strtimage = e;
se->next = str_tbl[h];
str_tbl[h] = se;
return se->s;
}
/*
* streq - compare s1 with s2 for len bytes, and return 1 for equal,
* 0 for not equal.
*/
static int streq(len, s1, s2)
register int len;
register char *s1, *s2;
{
while (len--)
if (*s1++ != *s2++)
return 0;
return 1;
}