[BACK]Return to look.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / m4

Annotation of src/usr.bin/m4/look.c, Revision 1.12

1.12    ! espie       1: /*     $OpenBSD: look.c,v 1.11 2003/06/03 02:56:10 millert Exp $       */
1.2       deraadt     2:
1.1       deraadt     3: /*
                      4:  * Copyright (c) 1989, 1993
                      5:  *     The Regents of the University of California.  All rights reserved.
                      6:  *
                      7:  * This code is derived from software contributed to Berkeley by
                      8:  * Ozan Yigit at York University.
                      9:  *
                     10:  * Redistribution and use in source and binary forms, with or without
                     11:  * modification, are permitted provided that the following conditions
                     12:  * are met:
                     13:  * 1. Redistributions of source code must retain the above copyright
                     14:  *    notice, this list of conditions and the following disclaimer.
                     15:  * 2. Redistributions in binary form must reproduce the above copyright
                     16:  *    notice, this list of conditions and the following disclaimer in the
                     17:  *    documentation and/or other materials provided with the distribution.
1.11      millert    18:  * 3. Neither the name of the University nor the names of its contributors
1.1       deraadt    19:  *    may be used to endorse or promote products derived from this software
                     20:  *    without specific prior written permission.
                     21:  *
                     22:  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
                     23:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     24:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     25:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
                     26:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     27:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     28:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     29:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     30:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     31:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     32:  * SUCH DAMAGE.
                     33:  */
                     34:
                     35: #ifndef lint
                     36: static char sccsid[] = "@(#)look.c     8.1 (Berkeley) 6/6/93";
                     37: #endif /* not lint */
                     38:
                     39: /*
                     40:  * look.c
                     41:  * Facility: m4 macro processor
                     42:  * by: oz
                     43:  */
                     44:
                     45: #include <sys/types.h>
                     46: #include <stdio.h>
                     47: #include <stdlib.h>
1.3       espie      48: #include <stddef.h>
1.1       deraadt    49: #include <string.h>
                     50: #include "mdef.h"
                     51: #include "stdd.h"
                     52: #include "extern.h"
                     53:
1.12    ! espie      54: struct ndblock {               /* hastable structure         */
        !            55:        char            *name;  /* entry name..               */
        !            56:        struct macro_definition d;
        !            57:        unsigned int    hv;     /* hash function value..      */
        !            58:        ndptr           nxtptr; /* link to next entry..       */
        !            59: };
        !            60:
1.9       millert    61: static void freent(ndptr);
1.12    ! espie      62: static void    remhash(const char *, int);
        !            63: static unsigned        hash(const char *);
        !            64: static ndptr   addent(const char *);
1.5       espie      65:
1.12    ! espie      66: static unsigned int
1.10      espie      67: hash(const char *name)
1.1       deraadt    68: {
1.7       millert    69:        unsigned int h = 0;
1.1       deraadt    70:        while (*name)
                     71:                h = (h << 5) + h + *name++;
1.6       espie      72:        return (h);
1.1       deraadt    73: }
                     74:
                     75: /*
                     76:  * find name in the hash table
                     77:  */
                     78: ndptr
1.10      espie      79: lookup(const char *name)
1.1       deraadt    80: {
1.4       espie      81:        ndptr p;
1.7       millert    82:        unsigned int h;
1.1       deraadt    83:
1.6       espie      84:        h = hash(name);
1.12    ! espie      85:        for (p = hashtab[h % HASHSIZE]; p != NULL; p = p->nxtptr)
1.6       espie      86:                if (h == p->hv && STREQ(name, p->name))
1.1       deraadt    87:                        break;
                     88:        return (p);
                     89: }
                     90:
                     91: /*
                     92:  * hash and create an entry in the hash table.
                     93:  * The new entry is added in front of a hash bucket.
                     94:  */
1.12    ! espie      95: static ndptr
1.10      espie      96: addent(const char *name)
1.1       deraadt    97: {
1.7       millert    98:        unsigned int h;
1.1       deraadt    99:        ndptr p;
                    100:
                    101:        h = hash(name);
                    102:        p = (ndptr) xalloc(sizeof(struct ndblock));
1.6       espie     103:        p->nxtptr = hashtab[h % HASHSIZE];
                    104:        hashtab[h % HASHSIZE] = p;
1.1       deraadt   105:        p->name = xstrdup(name);
1.6       espie     106:        p->hv = h;
1.1       deraadt   107:        return p;
                    108: }
                    109:
                    110: static void
1.10      espie     111: freent(ndptr p)
1.1       deraadt   112: {
1.8       espie     113:        free((char *) p->name);
1.12    ! espie     114:        if (p->d.defn != null)
        !           115:                free((char *) p->d.defn);
1.1       deraadt   116:        free((char *) p);
                    117: }
                    118:
                    119: /*
                    120:  * remove an entry from the hashtable
                    121:  */
1.12    ! espie     122: static void
1.10      espie     123: remhash(const char *name, int all)
1.1       deraadt   124: {
1.7       millert   125:        unsigned int h;
1.4       espie     126:        ndptr xp, tp, mp;
1.1       deraadt   127:
                    128:        h = hash(name);
1.6       espie     129:        mp = hashtab[h % HASHSIZE];
1.12    ! espie     130:        tp = NULL;
        !           131:        while (mp != NULL) {
1.6       espie     132:                if (mp->hv == h && STREQ(mp->name, name)) {
1.1       deraadt   133:                        mp = mp->nxtptr;
1.12    ! espie     134:                        if (tp == NULL) {
1.6       espie     135:                                freent(hashtab[h % HASHSIZE]);
                    136:                                hashtab[h % HASHSIZE] = mp;
1.1       deraadt   137:                        }
                    138:                        else {
                    139:                                xp = tp->nxtptr;
                    140:                                tp->nxtptr = mp;
                    141:                                freent(xp);
                    142:                        }
                    143:                        if (!all)
                    144:                                break;
                    145:                }
                    146:                else {
                    147:                        tp = mp;
                    148:                        mp = mp->nxtptr;
                    149:                }
                    150:        }
1.12    ! espie     151: }
        !           152:
        !           153: struct macro_definition *
        !           154: lookup_macro_definition(const char *name)
        !           155: {
        !           156:        ndptr p;
        !           157:
        !           158:        p = lookup(name);
        !           159:        if (p)
        !           160:                return &(p->d);
        !           161:        else
        !           162:                return NULL;
        !           163: }
        !           164:
        !           165: static void
        !           166: setup_definition(struct macro_definition *d, const char *defn)
        !           167: {
        !           168:        int n;
        !           169:
        !           170:        if (strncmp(defn, BUILTIN_MARKER, sizeof(BUILTIN_MARKER)-1) == 0) {
        !           171:                n = builtin_type(defn+sizeof(BUILTIN_MARKER)-1);
        !           172:                if (n != -1) {
        !           173:                        d->type = n & TYPEMASK;
        !           174:                        if ((n & NOARGS) == 0)
        !           175:                                d->type |= NEEDARGS;
        !           176:                        d->defn = xstrdup(defn+sizeof(BUILTIN_MARKER)-1);
        !           177:                        return;
        !           178:                }
        !           179:        }
        !           180:        if (!*defn)
        !           181:                d->defn = null;
        !           182:        else
        !           183:                d->defn = xstrdup(defn);
        !           184:        d->type = MACRTYPE;
        !           185: }
        !           186:
        !           187: void
        !           188: macro_define(const char *name, const char *defn)
        !           189: {
        !           190:        ndptr p;
        !           191:
        !           192:        if ((p = lookup(name)) == NULL)
        !           193:                p = addent(name);
        !           194:        else if (p->d.defn != null)
        !           195:                free((char *) p->d.defn);
        !           196:        setup_definition(&(p->d), defn);
        !           197:        if (STREQ(name, defn))
        !           198:                p->d.type |= RECDEF;
        !           199: }
        !           200:
        !           201: void
        !           202: macro_pushdef(const char *name, const char *defn)
        !           203: {
        !           204:        ndptr p;
        !           205:
        !           206:        p = addent(name);
        !           207:        setup_definition(&(p->d), defn);
        !           208:        if (STREQ(name, defn))
        !           209:                p->d.type |= RECDEF;
        !           210: }
        !           211:
        !           212: void
        !           213: macro_undefine(const char *name)
        !           214: {
        !           215:        remhash(name, ALL);
        !           216: }
        !           217:
        !           218: void
        !           219: macro_popdef(const char *name)
        !           220: {
        !           221:        remhash(name, TOP);
        !           222: }
        !           223:
        !           224: void
        !           225: macro_for_all(void (*f)(const char *, struct macro_definition *))
        !           226: {
        !           227:        int n;
        !           228:        ndptr p;
        !           229:
        !           230:        for (n = 0; n < HASHSIZE; n++)
        !           231:                for (p = hashtab[n]; p != NULL; p = p->nxtptr)
        !           232:                        f(p->name, &(p->d));
        !           233: }
        !           234:
        !           235: void
        !           236: setup_builtin(const char *name, unsigned int type)
        !           237: {
        !           238:        unsigned int h;
        !           239:        ndptr p;
        !           240:
        !           241:        h = hash(name);
        !           242:        p = (ndptr) xalloc(sizeof(struct ndblock));
        !           243:        p->nxtptr = hashtab[h % HASHSIZE];
        !           244:        hashtab[h % HASHSIZE] = p;
        !           245:        p->name = xstrdup(name);
        !           246:        p->d.defn = xstrdup(name);
        !           247:        p->hv = h;
        !           248:        p->d.type = type;
        !           249: }
        !           250:
        !           251: const char *
        !           252: macro_name(ndptr p)
        !           253: {
        !           254:        return p->name;
        !           255: }
        !           256:
        !           257: struct macro_definition *
        !           258: macro_getdef(ndptr p)
        !           259: {
        !           260:        return &(p->d);
1.1       deraadt   261: }