diff options
Diffstat (limited to 'contrib/global/lib')
36 files changed, 3204 insertions, 187 deletions
diff --git a/contrib/global/lib/Makefile b/contrib/global/lib/Makefile index 99d49efabddc..83d8be057d41 100644 --- a/contrib/global/lib/Makefile +++ b/contrib/global/lib/Makefile @@ -1,8 +1,9 @@ -LIB= util -SRCS= tag.o tab.o strop.o mgets.o lookup.o gtagsopen.o getdbpath.o \ - find.o dbname.o dbio.o test.o makepath.o locatestring.o -NOPROFILE= yes -install: - @echo -n +LIB= gloutil +SRCS= gtagsop.c tab.c strbuf.c mgets.c defined.c getdbpath.c \ + find.c dbop.c test.c makepath.c locatestring.c pathop.c \ + conf.c strmake.c usable.c token.c +NOPROFILE= noprofile +INTERNALLIB= true +INTERNALSTATICLIB= true .include <bsd.lib.mk> diff --git a/contrib/global/lib/conf.c b/contrib/global/lib/conf.c new file mode 100644 index 000000000000..887663d71e25 --- /dev/null +++ b/contrib/global/lib/conf.c @@ -0,0 +1,308 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * conf.c 30-Jun-98 + * + */ +#include <sys/param.h> +#include <assert.h> +#include <ctype.h> +#include <stdlib.h> +#include <string.h> + +#include "conf.h" +#include "die.h" +#include "gparam.h" +#include "locatestring.h" +#include "makepath.h" +#include "mgets.h" +#include "strbuf.h" +#include "strmake.h" +#include "test.h" +/* + * Access library for gtags.conf (.gtagsrc). + * File format is a subset of XXXcap (termcap, printcap) file. + */ +#define GTAGSCONF "/etc/global.conf" +#define GTAGSRC ".globalrc" +#define DEFAULTLABEL "default" +static FILE *fp; +static char *line; +static int allowed_nest_level = 8; +static int opened; + +static void trim __P((char *)); +static char *readrecord __P((const char *)); +static void includelabel __P((STRBUF *, const char *, int)); + +static void +trim(l) +char *l; +{ + char *f, *b; + int colon = 0; + + for (f = b = l; *f; f++) { + if (colon && isspace(*f)) + continue; + colon = 0; + if ((*b++ = *f) == ':') + colon = 1; + } + *b = 0; +} +static char * +readrecord(label) +const char *label; +{ + char *p, *q; + + rewind(fp); + while ((p = mgets(fp, NULL, MGETS_CONT|MGETS_SKIPCOM)) != NULL) { + trim(p); + for (;;) { + if ((q = strmake(p, "|:")) == NULL) + die1("illegal configuration file format (%s).", p); + if (!strcmp(label, q)) { + if (!(p = locatestring(p, ":", MATCH_FIRST))) + die("illegal configuration file format."); + p = strdup(p); + if (!p) + die("short of memory."); + return p; + } + p += strlen(q); + if (*p == ':') + break; + else if (*p == '|') + p++; + else + assert(0); + } + } + return NULL; +} +static void +includelabel(sb, label, level) +STRBUF *sb; +const char *label; +int level; +{ + char *savep, *p, *q; + + if (++level > allowed_nest_level) + die("nested include= (or tc=) over flow."); + if (!(savep = p = readrecord(label))) + die1("label '%s' not found.", label); + while ((q = locatestring(p, ":include=", MATCH_FIRST)) || (q = locatestring(p, ":tc=", MATCH_FIRST))) { + char inclabel[MAXPROPLEN+1], *c = inclabel; + + strnputs(sb, p, q - p); + q = locatestring(q, "=", MATCH_FIRST) + 1; + while (*q && *q != ':') + *c++ = *q++; + *c = 0; + includelabel(sb, inclabel, level); + p = q; + } + strputs(sb, p); + free(savep); +} +/* + * configpath: get path of configuration file. + */ +char * +configpath() { + static char config[MAXPATHLEN+1]; + char *p; + + if ((p = getenv("GTAGSCONF")) != NULL) { + if (!test("r", p)) + config[0] = 0; + else + strcpy(config, p); + } else if ((p = getenv("HOME")) && test("r", makepath(p, GTAGSRC))) + strcpy(config, makepath(p, GTAGSRC)); + else if (test("r", GTAGSCONF)) + strcpy(config, GTAGSCONF); + else + config[0] = 0; + return config; +} +/* + * openconf: load configuration file. + * + * go) line specified entry + */ +void +openconf() +{ + const char *label, *config; + STRBUF *sb; + + assert(opened == 0); + + config = configpath(); + /* + * if configuration file is not found, default values are set + * for upper compatibility. + */ + if (*config == 0) { + sb = stropen(); + strputs(sb, "suffixes=c,h,y,s,S,java:"); + strputs(sb, "skip=y.tab.c,y.tab.h,SCCS/,RCS/,CVS/:"); + strputs(sb, "format=standard:"); + strputs(sb, "extractmethod:"); + strputs(sb, "GTAGS=gctags %s:"); + strputs(sb, "GRTAGS=gctags -r %s:"); + strputs(sb, "GSYMS=gctags -s %s:"); + line = strdup(strvalue(sb)); + if (!line) + die("short of memory."); + strclose(sb); + opened = 1; + return; + } + if ((label = getenv("GTAGSLABEL")) == NULL) + label = "default"; + if (!(fp = fopen(config, "r"))) + die1("cannot open '%s'.", config); + sb = stropen(); + includelabel(sb, label, 0); + line = strdup(strvalue(sb)); + strclose(sb); + fclose(fp); + opened = 1; + return; +} +/* + * getconfn: get property number + * + * i) name property name + * o) num value (if not NULL) + * r) 1: found, 0: not found + */ +int +getconfn(name, num) +const char *name; +int *num; +{ + char *p; + char buf[MAXPROPLEN+1]; + + if (!opened) + openconf(); + sprintf(buf, ":%s#", name); + if ((p = locatestring(line, buf, MATCH_FIRST)) != NULL) { + p += strlen(buf); + if (num != NULL) + *num = atoi(p); + return 1; + } + return 0; +} +/* + * getconfs: get property string + * + * i) name property name + * o) sb string buffer (if not NULL) + * r) 1: found, 0: not found + */ +int +getconfs(name, sb) +const char *name; +STRBUF *sb; +{ + char *p; + char buf[MAXPROPLEN+1]; + int all = 0; + int exist = 0; + + if (!opened) + openconf(); + if (!strcmp(name, "suffixes") || !strcmp(name, "skip") || !strcmp(name, "reserved_words")) + all = 1; + sprintf(buf, ":%s=", name); + p = line; + while ((p = locatestring(p, buf, MATCH_FIRST)) != NULL) { + if (exist && sb) + strputc(sb, ','); + exist = 1; + for (p += strlen(buf); *p && *p != ':'; p++) + if (sb) + strputc(sb, *p); + if (!all) + break; + } + /* + * It may be that these code should be moved to applications. + * But nothing cannot start without them. + */ + if (!exist) { + exist = 1; + if (!strcmp(name, "suffixes")) { + if (sb) + strputs(sb, "c,h,y,s,S,java"); + } else if (!strcmp(name, "skip")) { + if (sb) + strputs(sb, "y.tab.c,y.tab.h,SCCS/,RCS/,CVS/"); + } else + exist = 0; + } + return exist; +} +/* + * getconfb: get property bool value + * + * i) name property name + * r) 1: TRUE, 0: FALSE + */ +int +getconfb(name) +const char *name; +{ + char *p; + char buf[MAXPROPLEN+1]; + + if (!opened) + openconf(); + sprintf(buf, ":%s:", name); + if ((p = locatestring(line, buf, MATCH_FIRST)) != NULL) + return 1; + return 0; +} +void +closeconf() +{ + if (!opened) + return; + free(line); + opened = 0; +} diff --git a/contrib/global/lib/conf.h b/contrib/global/lib/conf.h new file mode 100644 index 000000000000..9317d9ff8726 --- /dev/null +++ b/contrib/global/lib/conf.h @@ -0,0 +1,54 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * conf.h 16-Oct-97 + * + */ + +#ifndef _CONF_H_ +#define _CONF_H_ + +#include "strbuf.h" +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +char *configpath __P((void)); +void openconf __P((void)); +int getconfn __P((const char *, int *)); +int getconfs __P((const char *, STRBUF *)); +int getconfb __P((const char *)); +void closeconf __P((void)); + +#endif /* ! _CONF_H_ */ diff --git a/contrib/global/lib/dbop.c b/contrib/global/lib/dbop.c new file mode 100644 index 000000000000..9bd98f328624 --- /dev/null +++ b/contrib/global/lib/dbop.c @@ -0,0 +1,332 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redilogibution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redilogibutions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redilogibutions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the dilogibution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * dbop.c 12-Nov-98 + * + */ +#include <sys/types.h> +#include <sys/stat.h> + +#include <assert.h> +#include <fcntl.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#include "dbop.h" +#include "die.h" +#include "test.h" + +static DBT key; /* key of record */ +static DBT dat; /* data of record */ +/* + * dbop_open: open db database. + * + * i) dbname database name + * i) mode 0: read only, 1: create, 2: modify + * i) perm file permission + * i) flags + * DBOP_DUP: allow duplicate records. + * DBOP_REMOVE: remove on closed. + * r) descripter for dbop_xxx() + */ +DBOP * +dbop_open(dbname, mode, perm, flags) +const char *dbname; +int mode; +int perm; +int flags; +{ + DB *db; + int rw = 0; + DBOP *dbop; + BTREEINFO info; + + /* + * setup argments. + */ + switch (mode) { + case 0: + rw = O_RDONLY; + break; + case 1: + rw = O_RDWR|O_CREAT|O_TRUNC; + break; + case 2: + rw = O_RDWR; + break; + default: + assert(0); + } + memset(&info, 0, sizeof(info)); + if (flags & DBOP_DUP) + info.flags |= R_DUP; + info.cachesize = 500000; + + /* + * if unlink do job normally, those who already open tag file can use + * it until closing. + */ + if (mode == 1 && test("f", dbname)) + (void)unlink(dbname); + db = dbopen(dbname, rw, 0600, DB_BTREE, &info); + if (!db) + return NULL; + if (!(dbop = (DBOP *)malloc(sizeof(DBOP)))) + die("short of memory."); + strcpy(dbop->dbname, dbname); + dbop->db = db; + dbop->openflags = flags; + dbop->perm = (mode == 1) ? perm : 0; + dbop->lastkey = NULL; + dbop->lastdat = NULL; + + return dbop; +} +/* + * dbop_get: get data by a key. + * + * i) dbop descripter + * i) name name + * r) pointer to data + */ +char * +dbop_get(dbop, name) +DBOP *dbop; +const char *name; +{ + DB *db = dbop->db; + int status; + + key.data = (char *)name; + key.size = strlen(name)+1; + + status = (*db->get)(db, &key, &dat, 0); + dbop->lastkey = (char *)key.data; + dbop->lastdat = (char *)dat.data; + switch (status) { + case RET_SUCCESS: + break; + case RET_ERROR: + die("cannot read from database."); + case RET_SPECIAL: + return (NULL); + } + return((char *)dat.data); +} +/* + * dbop_put: put data by a key. + * + * i) dbop descripter + * i) name key + * i) data data + */ +void +dbop_put(dbop, name, data) +DBOP *dbop; +const char *name; +const char *data; +{ + DB *db = dbop->db; + int status; + + if (strlen(name) > MAXKEYLEN) + die("primary key too long."); + key.data = (char *)name; + key.size = strlen(name)+1; + dat.data = (char *)data; + dat.size = strlen(data)+1; + + status = (*db->put)(db, &key, &dat, 0); + switch (status) { + case RET_SUCCESS: + break; + case RET_ERROR: + case RET_SPECIAL: + die("cannot write to database."); + } +} +/* + * dbop_del: delete record by a key. + * + * i) dbop descripter + * i) name key + */ +void +dbop_del(dbop, name) +DBOP *dbop; +const char *name; +{ + DB *db = dbop->db; + int status; + + if (name) { + key.data = (char *)name; + key.size = strlen(name)+1; + status = (*db->del)(db, &key, 0); + } else + status = (*db->del)(db, &key, R_CURSOR); + if (status == RET_ERROR) + die("cannot delete record."); +} +/* + * dbop_first: get first record. + * + * i) dbop dbop descripter + * i) name key + * !=NULL: indexed read by key + * ==NULL: sequential read + * i) flags following dbop_next call take over this. + * DBOP_KEY read key part + * DBOP_PREFIX prefix read + * only valied when sequential read + * r) data + */ +char * +dbop_first(dbop, name, flags) +DBOP *dbop; +const char *name; +int flags; +{ + DB *db = dbop->db; + int status; + + if (flags & DBOP_PREFIX && !name) + flags &= ~DBOP_PREFIX; + if (name) { + if (strlen(name) > MAXKEYLEN) + die("primary key too long."); + strcpy(dbop->key, name); + key.data = (char *)name; + key.size = strlen(name); + /* + * includes NULL character unless prefix read. + */ + if (!(flags & DBOP_PREFIX)) + key.size++; + dbop->keylen = key.size; + status = (*db->seq)(db, &key, &dat, R_CURSOR); + } else { + dbop->keylen = dbop->key[0] = 0; + /* skip META records */ + for (status = (*db->seq)(db, &key, &dat, R_FIRST); + status == RET_SUCCESS; + status = (*db->seq)(db, &key, &dat, R_NEXT)) { + int c = (flags & DBOP_KEY) ? *((char *)key.data) : *((char *)dat.data); + if (c != ' ') + break; + } + } + dbop->lastkey = (char *)key.data; + dbop->lastdat = (char *)dat.data; + switch (status) { + case RET_SUCCESS: + break; + case RET_ERROR: + die("dbop_first failed."); + case RET_SPECIAL: + return (NULL); + } + dbop->ioflags = flags; + if (flags & DBOP_PREFIX) { + if (strncmp((char *)key.data, dbop->key, dbop->keylen)) + return NULL; + } else if (dbop->keylen) { + if (strcmp((char *)key.data, dbop->key)) + return NULL; + } + if (flags & DBOP_KEY) { + strcpy(dbop->prev, (char *)key.data); + return (char *)key.data; + } + return ((char *)dat.data); +} +/* + * dbop_next: get next record. + * + * i) dbop dbop descripter + * r) data + * + * Db_next always skip meta records. + */ +char * +dbop_next(dbop) +DBOP *dbop; +{ + DB *db = dbop->db; + int flags = dbop->ioflags; + int status; + + while ((status = (*db->seq)(db, &key, &dat, R_NEXT)) == RET_SUCCESS) { + assert(dat.data != NULL); + if (flags & DBOP_KEY && *((char *)key.data) == ' ') + continue; + else if (*((char *)dat.data) == ' ') + continue; + if (flags & DBOP_KEY) { + if (!strcmp(dbop->prev, (char *)key.data)) + continue; + if (strlen((char *)key.data) > MAXKEYLEN) + die("primary key too long."); + strcpy(dbop->prev, (char *)key.data); + } + dbop->lastkey = (char *)key.data; + dbop->lastdat = (char *)dat.data; + if (flags & DBOP_PREFIX) { + if (strncmp((char *)key.data, dbop->key, dbop->keylen)) + return NULL; + } else if (dbop->keylen) { + if (strcmp((char *)key.data, dbop->key)) + return NULL; + } + return (flags & DBOP_KEY) ? (char *)key.data : (char *)dat.data; + } + if (status == RET_ERROR) + die("dbop_next failed."); + return NULL; +} +/* + * dbop_close: close db + * + * i) dbop dbop descripter + */ +void +dbop_close(dbop) +DBOP *dbop; +{ + DB *db = dbop->db; + + (void)db->close(db); + if (dbop->openflags & DBOP_REMOVE) + (void)unlink(dbop->dbname); + else if (dbop->perm && chmod(dbop->dbname, dbop->perm) < 0) + die("cannot change file mode."); + (void)free(dbop); +} diff --git a/contrib/global/lib/dbop.h b/contrib/global/lib/dbop.h new file mode 100644 index 000000000000..38342ca52d04 --- /dev/null +++ b/contrib/global/lib/dbop.h @@ -0,0 +1,88 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redilogibution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redilogibutions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redilogibutions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the dilogibution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * dbop.h 12-Nov-98 + * + */ +#ifndef _DBOP_H_ +#define _DBOP_H_ + +#include <sys/param.h> +#include <db.h> + +#ifndef LITTLE_ENDIAN +#define LITTLE_ENDIAN 1234 +#endif +#ifndef BIG_ENDIAN +#define BIG_ENDIAN 4321 +#endif + +#define MAXKEYLEN 300 + +typedef struct { + DB *db; /* descripter of DB */ + char dbname[MAXPATHLEN+1]; /* dbname */ + char key[MAXKEYLEN+1]; /* key */ + int keylen; /* key length */ + char prev[MAXKEYLEN+1]; /* previous key value */ + char *lastkey; /* the key of last located record */ + char *lastdat; /* the data of last located record */ + int openflags; /* flags of dbop_open() */ + int ioflags; /* flags of dbop_first() */ + int perm; /* file permission */ +} DBOP; + +/* + * openflags + */ +#define DBOP_DUP 1 /* allow duplicate records */ +#define DBOP_REMOVE 2 /* remove file when closed */ +/* + * ioflags + */ +#define DBOP_KEY 1 /* read key part */ +#define DBOP_PREFIX 2 /* prefixed read */ + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +DBOP *dbop_open __P((const char *, int, int, int)); +char *dbop_get __P((DBOP *, const char *)); +void dbop_put __P((DBOP *, const char *, const char *)); +void dbop_del __P((DBOP *, const char *)); +char *dbop_first __P((DBOP *, const char *, int)); +char *dbop_next __P((DBOP *)); +void dbop_close __P((DBOP *)); +#endif /* _DBOP_H_ */ diff --git a/contrib/global/lib/defined.c b/contrib/global/lib/defined.c new file mode 100644 index 000000000000..1e72b46c05dd --- /dev/null +++ b/contrib/global/lib/defined.c @@ -0,0 +1,66 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * defined.c 12-Nov-98 + * + */ +#include <stdlib.h> + +#include "die.h" +#include "dbop.h" +#include "defined.h" +#include "makepath.h" + +static DBOP *dbop = NULL; + +/* + * Tag command that supports referenced tag must call this function + * to decide whether or not the tag is defined. + */ +int +defined(name) +const char *name; +{ + if (dbop == NULL) { + const char *dbpath; + + /* + * gtags(1) set GTAGSDBPATH to the path GTAGS exist. + */ + if (!(dbpath = getenv("GTAGSDBPATH"))) + dbpath = "."; + dbop = dbop_open(makepath(dbpath, "GTAGS"), 0, 0, 0); + if (dbop == NULL) + die1("GTAGS not found. (%s)", makepath(dbpath, "GTAGS")); + } + if (dbop_get(dbop, name)) + return 1; + return 0; +} diff --git a/contrib/global/lib/defined.h b/contrib/global/lib/defined.h new file mode 100644 index 000000000000..6d342ac5ec06 --- /dev/null +++ b/contrib/global/lib/defined.h @@ -0,0 +1,48 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * defined.h 2-May-98 + * + */ + +#ifndef _DEFINED_H_ +#define _DEFINED_H_ + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +int defined __P((const char *)); + +#endif /* ! _DEFINED_H_ */ diff --git a/contrib/global/lib/die.h b/contrib/global/lib/die.h index 46813d415953..fc0e9e014493 100644 --- a/contrib/global/lib/die.h +++ b/contrib/global/lib/die.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -35,7 +35,7 @@ #define _DIE_H_ #include <stdio.h> -extern char *progname; +extern const char *progname; #define die(a) fprintf(stderr, "%s: ", progname),\ fprintf(stderr, a),\ @@ -46,4 +46,8 @@ extern char *progname; fprintf(stderr, a, b),\ fputs("\n", stderr),\ exit(1) +#define die2(a,b,c) fprintf(stderr, "%s: ", progname),\ + fprintf(stderr, a, b, c),\ + fputs("\n", stderr),\ + exit(1) #endif /* ! _DIE_H_ */ diff --git a/contrib/global/lib/find.c b/contrib/global/lib/find.c index 6203e008a6f5..4682beec1d6d 100644 --- a/contrib/global/lib/find.c +++ b/contrib/global/lib/find.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,114 +28,159 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * find.c 20-Oct-97 + * find.c 1-May-98 * */ +/* + * USEFIND use find(1) to traverse directory tree. + * Otherwise, use dirent(3) library. + */ +#define USEFIND + +#include <sys/param.h> + +#include <assert.h> +#include <ctype.h> +#ifndef USEFIND +#include <dirent.h> +#ifndef BSD4_4 +#include <sys/stat.h> +#endif +#endif #include <stdio.h> -#include <sys/types.h> +#include <stdlib.h> +#include <strings.h> #include <regex.h> -#include <sys/param.h> -#include "gparam.h" -#include "find.h" + +#include "conf.h" #include "die.h" +#include "find.h" +#include "gparam.h" #include "locatestring.h" +#include "makepath.h" +#include "strbuf.h" /* * usage of findxxx() * - * findopen(); + * findopen(db); * while (path = findread(&length)) { * ... * } * findclose(); * */ -static char *skippath[] = { - "y.tab.c", - "y.tab.h", - "SCCS/", - "RCS/", -}; -static char *ext[] = { - "c", - "h", - "y", - "s", - "S", -}; -static char findcom[MAXCOMLINE+1]; static regex_t skip_area; -static regex_t *skip; -static FILE *ip; +static regex_t *skip = &skip_area; static int opened; -int -issource(path) -char *path; +static void trim __P((char *)); + +/* + * trim: remove blanks and '\'. + */ +static void +trim(s) +char *s; { char *p; - if (!(p = locatestring(path, ".", 2))) - return 0; - ++p; - if (sizeof(ext) != 0) { - int i, lim = sizeof(ext)/sizeof(char *); - for (i = 0; i < lim; i++) - if (*ext[i] == *p && !strcmp(ext[i], p)) - return 1; + for (p = s; *s; s++) { + if (isspace(*s)) + continue; + if (*s == '\\' && *(s + 1)) + s++; + *p++ = *s; } - return 0; + *p = 0; } +#ifdef USEFIND +/*----------------------------------------------------------------------*/ +/* find command version */ +/*----------------------------------------------------------------------*/ +static FILE *ip; void -findopen(void) +findopen() { - char edit[512], *p, *q; - int i, lim; + char *findcom, *p, *q; + STRBUF *sb; + char *sufflist = NULL; + char *skiplist = NULL; - if (opened) - die("nested call to findopen."); + assert(opened == 0); opened = 1; - p = findcom; - strcpy(p, "find . \\( -type f -o -type l \\) \\("); - p += strlen(p); - lim = sizeof(ext)/sizeof(char *); - for (i = 0; i < lim; i++) { - sprintf(p, " -name '*.%s'%s", ext[i], (i + 1 < lim) ? " -o" : ""); - p += strlen(p); + + sb = stropen(); + if (!getconfs("suffixes", sb)) + die("cannot get suffixes data."); + sufflist = strdup(strvalue(sb)); + if (!sufflist) + die("short of memory."); + trim(sufflist); + strstart(sb); + if (getconfs("skip", sb)) { + skiplist = strdup(strvalue(sb)); + if (!skiplist) + die("short of memory."); + trim(skiplist); + } + + strstart(sb); + strputs(sb, "find . \\( -type f -o -type l \\) \\("); + for (p = sufflist; p; ) { + char *suff = p; + if ((p = locatestring(p, ",", MATCH_FIRST)) != NULL) + *p++ = 0; + strputs(sb, " -name '*."); + strputs(sb, suff); + strputs(sb, "'"); + if (p) + strputs(sb, " -o"); } - sprintf(p, " \\) -print"); - if (sizeof(skippath) != 0) { - int i, lim = sizeof(skippath)/sizeof(char *); + strputs(sb, " \\) -print"); + findcom = strvalue(sb); + + if (skiplist) { + char *reg; + STRBUF *sbb = stropen(); /* * construct regular expression. */ - p = edit; - *p++ = '('; - for (i = 0; i < lim; i++) { - *p++ = '/'; - for (q = skippath[i]; *q; q++) { + strputc(sbb, '('); /* ) */ + for (p = skiplist; p; ) { + char *skipf = p; + if ((p = locatestring(p, ",", MATCH_FIRST)) != NULL) + *p++ = 0; + strputc(sbb, '/'); + for (q = skipf; *q; q++) { if (*q == '.') - *p++ = '\\'; - *p++ = *q; + strputc(sbb, '\\'); + strputc(sbb, *q); } if (*(q - 1) != '/') - *p++ = '$'; - *p++ = '|'; + strputc(sbb, '$'); + if (p) + strputc(sbb, '|'); } - *(p - 1) = ')'; - *p = 0; + strputc(sbb, ')'); + reg = strvalue(sbb); /* * compile regular expression. */ - skip = &skip_area; - if (regcomp(skip, edit, REG_EXTENDED|REG_NEWLINE) != 0) + if (regcomp(skip, reg, REG_EXTENDED|REG_NEWLINE) != 0) die("cannot compile regular expression."); + strclose(sbb); } else { skip = (regex_t *)0; } if (!(ip = popen(findcom, "r"))) die("cannot execute find."); + strclose(sb); + if (sufflist) + free(sufflist); + if (skiplist) + free(skiplist); } char * findread(length) @@ -144,8 +189,12 @@ int *length; static char path[MAXPATHLEN+1]; char *p; + assert(opened == 1); while (fgets(path, MAXPATHLEN, ip)) { if (!skip || regexec(skip, path, 0, 0, 0) != 0) { + /* + * chop(path) + */ p = path + strlen(path) - 1; if (*p != '\n') die("output of find(1) is wrong (findread)."); @@ -155,11 +204,242 @@ int *length; return path; } } - return (char *)0; + return NULL; } void findclose(void) { + assert(opened == 1); pclose(ip); opened = 0; } +#else /* USEFIND */ +/*----------------------------------------------------------------------*/ +/* dirent version findxxx() */ +/*----------------------------------------------------------------------*/ +#define STACKSIZE 50 +static char dir[MAXPATHLEN+1]; /* directory path */ +static struct { + STRBUF *sb; + char *dirp, *start, *end, *p; +} stack[STACKSIZE], *topp, *curp; /* stack */ + +static regex_t suff_area; +static regex_t *suff = &suff_area; + +static int +getdirs(dir, sb) +char *dir; +STRBUF *sb; +{ + DIR *dirp; + struct dirent *dp; +#ifndef BSD4_4 + struct stat st; +#endif + + if ((dirp = opendir(dir)) == NULL) + return -1; + while ((dp = readdir(dirp)) != NULL) { +#ifdef BSD4_4 + if (dp->d_namlen == 1 && dp->d_name[0] == '.') + continue; + if (dp->d_namlen == 2 && dp->d_name[0] == '.' && dp->d_name[1] == '.') + continue; + if (dp->d_type == DT_DIR) + strputc(sb, 'd'); + else if (dp->d_type == DT_REG) + strputc(sb, 'f'); + else if (dp->d_type == DT_LNK) + strputc(sb, 'l'); + else + strputc(sb, ' '); + strnputs(sb, dp->d_name, (int)dp->d_namlen); +#else + if (stat(path, &st) < 0) { + fprintf(stderr, "cannot stat '%s'. (Ignored)\n", path); + continue; + } + if (S_ISDIR(st.st_mode)) + strputc(sb, 'd'); + else if (S_ISREG(st.st_mode)) + strputc(sb, 'f'); + else if (S_ISLNK(st.st_mode)) + strputc(sb, 'l'); + else + strputc(sb, ' '); + strputs(sb, dp->d_name); +#endif /* BSD4_4 */ + strputc(sb, '\0'); + } + (void)closedir(dirp); + return 0; +} +void +findopen() +{ + STRBUF *sb = stropen(); + char *sufflist = NULL; + char *skiplist = NULL; + + assert(opened == 0); + opened = 1; + + /* + * setup stack. + */ + curp = &stack[0]; + topp = curp + STACKSIZE; + strcpy(dir, "."); + + curp->dirp = dir + strlen(dir); + curp->sb = stropen(); + if (getdirs(dir, curp->sb) < 0) + die("cannot open '.' directory."); + curp->start = curp->p = strvalue(curp->sb); + curp->end = curp->start + strbuflen(curp->sb); + + /* + * preparing regular expression. + */ + strstart(sb); + if (!getconfs("suffixes", sb)) + die("cannot get suffixes data."); + sufflist = strdup(strvalue(sb)); + if (!sufflist) + die("short of memory."); + trim(sufflist); + strstart(sb); + if (getconfs("skip", sb)) { + skiplist = strdup(strvalue(sb)); + if (!skiplist) + die("short of memory."); + trim(skiplist); + } + { + char *p; + + strstart(sb); + strputc(sb, '('); /* ) */ + for (p = sufflist; p; ) { + char *suffp = p; + if ((p = locatestring(p, ",", MATCH_FIRST)) != NULL) + *p++ = 0; + strputs(sb, "\\."); + strputs(sb, suffp); + strputc(sb, '$'); + if (p) + strputc(sb, '|'); + } + strputc(sb, ')'); + /* + * compile regular expression. + */ + if (regcomp(suff, strvalue(sb), REG_EXTENDED) != 0) + die("cannot compile regular expression."); + } + if (skiplist) { + char *p, *q; + /* + * construct regular expression. + */ + strstart(sb); + strputc(sb, '('); /* ) */ + for (p = skiplist; p; ) { + char *skipf = p; + if ((p = locatestring(p, ",", MATCH_FIRST)) != NULL) + *p++ = 0; + strputc(sb, '/'); + for (q = skipf; *q; q++) { + if (*q == '.') + strputc(sb, '\\'); + strputc(sb, *q); + } + if (*(q - 1) != '/') + strputc(sb, '$'); + if (p) + strputc(sb, '|'); + } + strputc(sb, ')'); + /* + * compile regular expression. + */ + if (regcomp(skip, strvalue(sb), REG_EXTENDED) != 0) + die("cannot compile regular expression."); + } else { + skip = (regex_t *)0; + } + strclose(sb); + if (sufflist) + free(sufflist); + if (skiplist) + free(skiplist); +} +char * +findread(length) +int *length; +{ + static char val[MAXPATHLEN+1]; + + for (;;) { + while (curp->p < curp->end) { + char type = *(curp->p); + char *unit = curp->p + 1; + + curp->p += strlen(curp->p) + 1; + if (type == 'f' || type == 'l') { + char *path = makepath(dir, unit); + if (regexec(suff, path, 0, 0, 0) != 0) + continue; + if (skip && regexec(skip, path, 0, 0, 0) == 0) + continue; + strcpy(val, path); + return val; + } + if (type == 'd') { + STRBUF *sb = stropen(); + char *dirp = curp->dirp; + + strcat(dirp, "/"); + strcat(dirp, unit); + if (getdirs(dir, sb) < 0) { + fprintf(stderr, "cannot open directory '%s'. (Ignored)\n", dir); + strclose(sb); + *(curp->dirp) = 0; + continue; + } + /* + * Push stack. + */ + if (++curp >= topp) + die("directory stack over flow."); + curp->dirp = dirp + strlen(dirp); + curp->sb = sb; + curp->start = curp->p = strvalue(sb); + curp->end = curp->start + strbuflen(sb); + } + } + strclose(curp->sb); + curp->sb = NULL; + if (curp == &stack[0]) + break; + /* + * Pop stack. + */ + curp--; + *(curp->dirp) = 0; + } + return NULL; +} +void +findclose(void) +{ + assert(opened == 1); + for (curp = &stack[0]; curp < topp; curp++) + if (curp->sb != NULL) + strclose(curp->sb); + else + break; + opened = 0; +} +#endif /* !USEFIND */ diff --git a/contrib/global/lib/find.h b/contrib/global/lib/find.h index bb140e05ddcb..ae16f7230872 100644 --- a/contrib/global/lib/find.h +++ b/contrib/global/lib/find.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions diff --git a/contrib/global/lib/getdbpath.c b/contrib/global/lib/getdbpath.c index 1e4e7cfaefff..372d9ec3b2e8 100644 --- a/contrib/global/lib/getdbpath.c +++ b/contrib/global/lib/getdbpath.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -40,12 +40,10 @@ #include "die.h" #include "getdbpath.h" -#include "locatestring.h" #include "test.h" -static char *makeobjdirprefix; /* obj partition */ -static char *makeobjdir; /* obj directory */ -static int bsd; /* if BSD */ +static const char *makeobjdirprefix; /* obj partition */ +static const char *makeobjdir; /* obj directory */ /* * gtagsexist: test whether GTAGS's existence. @@ -66,17 +64,15 @@ char *dbpath; strcpy(dbpath, candidate); return 1; } - if (bsd) { - sprintf(path, "%s/%s/GTAGS", candidate, makeobjdir); - if (test("fr", path)) { - sprintf(dbpath, "%s/%s", candidate, makeobjdir); - return 1; - } - sprintf(path, "%s%s/GTAGS", makeobjdirprefix, candidate); - if (test("fr", path)) { - sprintf(dbpath, "%s%s", makeobjdirprefix, candidate); - return 1; - } + sprintf(path, "%s/%s/GTAGS", candidate, makeobjdir); + if (test("fr", path)) { + sprintf(dbpath, "%s/%s", candidate, makeobjdir); + return 1; + } + sprintf(path, "%s%s/GTAGS", makeobjdirprefix, candidate); + if (test("fr", path)) { + sprintf(dbpath, "%s%s", makeobjdirprefix, candidate); + return 1; } return 0; } @@ -109,17 +105,14 @@ char *dbpath; if (!strcmp(cwd, "/")) die("It's root directory! What are you doing?"); - if (getenv("OSTYPE") && locatestring(getenv("OSTYPE"), "BSD", 0)) { - if ((p = getenv("MAKEOBJDIRPREFIX")) != NULL) - makeobjdirprefix = p; - else - makeobjdirprefix = "/usr/obj"; - if ((p = getenv("MAKEOBJDIR")) != NULL) - makeobjdir = p; - else - makeobjdir = "obj"; - bsd = 1; - } + if ((p = getenv("MAKEOBJDIRPREFIX")) != NULL) + makeobjdirprefix = p; + else + makeobjdirprefix = "/usr/obj"; + if ((p = getenv("MAKEOBJDIR")) != NULL) + makeobjdir = p; + else + makeobjdir = "obj"; if ((p = getenv("GTAGSROOT")) != NULL) { if (*p != '/') diff --git a/contrib/global/lib/getdbpath.h b/contrib/global/lib/getdbpath.h index 193dfffc596a..063d2367055a 100644 --- a/contrib/global/lib/getdbpath.h +++ b/contrib/global/lib/getdbpath.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions diff --git a/contrib/global/lib/global.h b/contrib/global/lib/global.h index 7fbc2b8ef230..5ab2ca563dc4 100644 --- a/contrib/global/lib/global.h +++ b/contrib/global/lib/global.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,27 +28,30 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * global.h 16-Oct-97 + * global.h 2-May-98 * */ #ifndef _GLOBAL_H_ #define _GLOBAL_H_ -#include "gparam.h" -#include "dbname.h" -#include "makepath.h" -#include "dbio.h" -#include "locatestring.h" -#include "mgets.h" +#include "conf.h" +#include "dbop.h" +#include "defined.h" #include "die.h" #include "find.h" #include "getdbpath.h" -#include "strop.h" -#include "gtagsopen.h" -#include "lookup.h" +#include "gparam.h" +#include "gtagsop.h" +#include "locatestring.h" +#include "makepath.h" +#include "mgets.h" +#include "pathop.h" +#include "strbuf.h" +#include "strmake.h" #include "tab.h" -#include "tag.h" #include "test.h" +#include "token.h" +#include "usable.h" #endif /* ! _GLOBAL_H_ */ diff --git a/contrib/global/lib/gparam.h b/contrib/global/lib/gparam.h index 8a506c465cae..8a13c7e64349 100644 --- a/contrib/global/lib/gparam.h +++ b/contrib/global/lib/gparam.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,15 +28,17 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * gparam.h 16-Oct-97 + * gparam.h 16-Jul-98 * */ #ifndef _GPARAM_H_ #define _GPARAM_H_ -#define MAXCOMLINE 1024 /* max length of filter */ -#define IDENTLEN 512 /* max length of ident */ -#define MAXENVLEN 1024 /* max length of env */ -#define MAXBUFLEN 1024 /* max length of buffer */ +#define MAXFILLEN 1024 /* max length of filter */ +#define IDENTLEN 512 /* max length of ident */ +#define MAXENVLEN 1024 /* max length of env */ +#define MAXBUFLEN 1024 /* max length of buffer */ +#define MAXPROPLEN 1024 /* max length of property */ +#define MAXARGLEN 512 /* max length of argment */ #endif /* ! _GPARAM_H_ */ diff --git a/contrib/global/lib/gtagsop.c b/contrib/global/lib/gtagsop.c new file mode 100644 index 000000000000..41635695fef3 --- /dev/null +++ b/contrib/global/lib/gtagsop.c @@ -0,0 +1,644 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * gtagsop.c 12-Nov-98 + * + */ +#include <assert.h> +#include <ctype.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "dbop.h" +#include "die.h" +#include "gtagsop.h" +#include "locatestring.h" +#include "makepath.h" +#include "mgets.h" +#include "pathop.h" +#include "strbuf.h" +#include "strmake.h" +#include "tab.h" + +static char *genrecord __P((GTOP *)); +static int belongto __P((GTOP *, char *, char *)); + +static int support_version = 2; /* acceptable format version */ +static const char *tagslist[] = {"GTAGS", "GRTAGS", "GSYMS"}; +/* + * dbname: return db name + * + * i) db 0: GTAGS, 1: GRTAGS, 2: GSYMS + * r) dbname + */ +const char * +dbname(db) +int db; +{ + assert(db >= 0 && db < GTAGLIM); + return tagslist[db]; +} +/* + * makecommand: make command line to make global tag file + * + * i) comline skelton command line + * i) path path name + * o) sb command line + */ +void +makecommand(comline, path, sb) +char *comline; +char *path; +STRBUF *sb; +{ + char *p; + + if (!(p = strmake(comline, "%"))) + die1("'%%s' is needed in tag command line. (%s)\n", comline); + strputs(sb, p); + strputs(sb, path); + if (!(p = locatestring(comline, "%s", MATCH_FIRST))) + die1("'%%s' is needed in tag command line. (%s)\n", comline); + strputs(sb, p+2); +} +/* + * formatcheck: check format of tag command's output + * + * i) line input + * i) flags flag + * r) 0: normal + * -1: tag name + * -2: line number + * -3: path + * + * [example of right format] + * + * $1 $2 $3 $4 + * ---------------------------------------------------- + * main 83 ./ctags.c main(argc, argv) + */ +int +formatcheck(line, flags) +char *line; +int flags; +{ + char *p, *q; + /* + * $1 = tagname: allowed any char except sepalator. + */ + p = q = line; + while (*p && !isspace(*p)) + p++; + while (*p && isspace(*p)) + p++; + if (p == q) + return -1; + /* + * $2 = line number: must be digit. + */ + q = p; + while (*p && !isspace(*p)) + if (!isdigit(*p)) + return -2; + else + p++; + if (p == q) + return -2; + while (*p && isspace(*p)) + p++; + /* + * $3 = path: + * standard format: must start with './'. + * compact format: must be digit. + */ + if (flags & GTAGS_PATHINDEX) { + while (*p && !isspace(*p)) + if (!isdigit(*p)) + return -3; + else + p++; + } else { + if (!(*p == '.' && *(p + 1) == '/' && *(p + 2))) + return -3; + } + return 0; +} +/* + * gtagsopen: open global tag. + * + * i) dbpath dbpath directory + * i) root root directory (needed when compact format) + * i) db GTAGS, GRTAGS, GSYMS + * i) mode GTAGS_READ: read only + * GTAGS_CREATE: create tag + * GTAGS_MODIFY: modify tag + * i) flags GTAGS_COMPACT + * GTAGS_PATHINDEX + * r) GTOP structure + * + * when error occurred, gtagopen doesn't return. + * GTAGS_PATHINDEX needs GTAGS_COMPACT. + */ +GTOP * +gtagsopen(dbpath, root, db, mode, flags) +char *dbpath; +char *root; +int db; +int mode; +int flags; +{ + GTOP *gtop; + int dbmode = 0; + + if ((gtop = (GTOP *)calloc(sizeof(GTOP), 1)) == NULL) + die("short of memory."); + gtop->db = db; + gtop->mode = mode; + switch (gtop->mode) { + case GTAGS_READ: + dbmode = 0; + break; + case GTAGS_CREATE: + dbmode = 1; + break; + case GTAGS_MODIFY: + dbmode = 2; + break; + default: + assert(0); + } + + /* + * allow duplicate records. + */ + gtop->dbop = dbop_open(makepath(dbpath, dbname(db)), dbmode, 0644, DBOP_DUP); + if (gtop->dbop == NULL) { + if (dbmode == 1) + die1("cannot make %s.", dbname(db)); + die1("%s not found.", dbname(db)); + } + /* + * decide format version. + */ + gtop->format_version = 1; + gtop->format = GTAGS_STANDARD; + /* + * This is a special case. GSYMS had compact format even if + * format version 1. + */ + if (db == GSYMS) + gtop->format |= GTAGS_COMPACT; + if (gtop->mode == GTAGS_CREATE) { + if (flags & GTAGS_COMPACT) { + char buf[80]; + + gtop->format_version = 2; + sprintf(buf, "%s %d", VERSIONKEY, gtop->format_version); + dbop_put(gtop->dbop, VERSIONKEY, buf); + gtop->format |= GTAGS_COMPACT; + dbop_put(gtop->dbop, COMPACTKEY, COMPACTKEY); + if (flags & GTAGS_PATHINDEX) { + gtop->format |= GTAGS_PATHINDEX; + dbop_put(gtop->dbop, PATHINDEXKEY, PATHINDEXKEY); + } + } + } else { + /* + * recognize format version of GTAGS. 'format version record' + * is saved as a META record in GTAGS and GRTAGS. + * if 'format version record' is not found, it's assumed + * version 1. + */ + char *p; + + if ((p = dbop_get(gtop->dbop, VERSIONKEY)) != NULL) { + for (p += strlen(VERSIONKEY); *p && isspace(*p); p++) + ; + gtop->format_version = atoi(p); + } + if (gtop->format_version > support_version) + die("GTAGS seems new format. Please install the latest GLOBAL."); + if (gtop->format_version > 1) { + if (dbop_get(gtop->dbop, COMPACTKEY) != NULL) + gtop->format |= GTAGS_COMPACT; + if (dbop_get(gtop->dbop, PATHINDEXKEY) != NULL) + gtop->format |= GTAGS_PATHINDEX; + } + } + if (gtop->format & GTAGS_PATHINDEX || gtop->mode != GTAGS_READ) { + if (pathopen(dbpath, dbmode) < 0) { + if (dbmode == 1) + die("cannot create GPATH."); + else + die("GPATH not found."); + } + } + /* + * Stuff for compact format. + */ + if (gtop->format & GTAGS_COMPACT) { + assert(root != NULL); + strcpy(gtop->root, root); + if (gtop->mode != GTAGS_READ) + gtop->sb = stropen(); + } + return gtop; +} +/* + * gtagsput: put tag record with packing. + * + * i) gtop descripter of GTOP + * i) tag tag name + * i) record ctags -x image + */ +void +gtagsput(gtop, tag, record) +GTOP *gtop; +char *tag; +char *record; +{ + char *p, *q; + char lno[10]; + char path[MAXPATHLEN+1]; + + if (gtop->format == GTAGS_STANDARD) { + entab(record); + dbop_put(gtop->dbop, tag, record); + return; + } + /* + * gtop->format & GTAGS_COMPACT + */ + p = record; /* ignore $1 */ + while (*p && !isspace(*p)) + p++; + while (*p && isspace(*p)) + p++; + q = lno; /* lno = $2 */ + while (*p && !isspace(*p)) + *q++ = *p++; + *q = 0; + while (*p && isspace(*p)) + p++; + q = path; /* path = $3 */ + while (*p && !isspace(*p)) + *q++ = *p++; + *q = 0; + /* + * First time, it occurs, because 'prev_tag' and 'prev_path' are NULL. + */ + if (strcmp(gtop->prev_tag, tag) || strcmp(gtop->prev_path, path)) { + if (gtop->prev_tag[0]) + dbop_put(gtop->dbop, gtop->prev_tag, strvalue(gtop->sb)); + strcpy(gtop->prev_tag, tag); + strcpy(gtop->prev_path, path); + /* + * Start creating new record. + */ + strstart(gtop->sb); + strputs(gtop->sb, strmake(record, " \t")); + strputc(gtop->sb, ' '); + strputs(gtop->sb, path); + strputc(gtop->sb, ' '); + strputs(gtop->sb, lno); + } else { + strputc(gtop->sb, ','); + strputs(gtop->sb, lno); + } +} +/* + * gtagsadd: add tags belonging to the path into tag file. + * + * i) gtop descripter of GTOP + * i) comline tag command line + * i) path source file + * i) flags GTAGS_UNIQUE, GTAGS_EXTRACTMETHOD + */ +void +gtagsadd(gtop, comline, path, flags) +GTOP *gtop; +char *comline; +char *path; +int flags; +{ + char *tagline; + FILE *ip; + STRBUF *sb = stropen(); + + /* + * add path index if not yet. + */ + pathput(path); + /* + * make command line. + */ + makecommand(comline, path, sb); + /* + * Compact format. + */ + if (gtop->format & GTAGS_PATHINDEX) { + char *pno; + + if ((pno = pathget(path)) == NULL) + die1("GPATH is corrupted.('%s' not found)", path); + strputs(sb, "| sed 's!"); + strputs(sb, path); + strputs(sb, "!"); + strputs(sb, pno); + strputs(sb, "!'"); + } + if (gtop->format & GTAGS_COMPACT) + strputs(sb, "| sort +0 -1 +1n -2"); + if (flags & GTAGS_UNIQUE) + strputs(sb, "| uniq"); + if (!(ip = popen(strvalue(sb), "r"))) + die1("cannot execute '%s'.", strvalue(sb)); + while ((tagline = mgets(ip, NULL, MGETS_TAILCUT)) != NULL) { + char *tag, *p; + + if (formatcheck(tagline, gtop->format) < 0) + die1("illegal parser output.\n'%s'", tagline); + tag = strmake(tagline, " \t"); /* tag = $1 */ + /* + * extract method when class method definition. + * + * Ex: Class::method(...) + * + * key = 'method' + * data = 'Class::method 103 ./class.cpp ...' + */ + if (flags & GTAGS_EXTRACTMETHOD) { + if ((p = locatestring(tag, ".", MATCH_LAST)) != NULL) + tag = p + 1; + else if ((p = locatestring(tag, "::", MATCH_LAST)) != NULL) + tag = p + 2; + } + gtagsput(gtop, tag, tagline); + } + pclose(ip); + strclose(sb); +} +/* + * belongto: wheather or not record belongs to the path. + * + * i) gtop GTOP structure + * i) path path name (in standard format) + * path number (in compact format) + * i) p record + * r) 1: belong, 0: not belong + */ +static int +belongto(gtop, path, p) +GTOP *gtop; +char *path; +char *p; +{ + char *q; + int length = strlen(path); + + /* + * seek to path part. + */ + if (gtop->format & GTAGS_PATHINDEX) { + for (q = p; *q && !isspace(*q); q++) + ; + if (*q == 0) + die1("illegal tag format. '%s'", p); + for (; *q && isspace(*q); q++) + ; + } else + q = locatestring(p, "./", MATCH_FIRST); + if (*q == 0) + die1("illegal tag format. '%s'", p); + if (!strncmp(q, path, length) && isspace(*(q + length))) + return 1; + return 0; +} +/* + * gtagsdelete: delete records belong to path. + * + * i) gtop GTOP structure + * i) path path name + */ +void +gtagsdelete(gtop, path) +GTOP *gtop; +char *path; +{ + char *p, *key; + int length; + + /* + * In compact format, a path is saved as a file number. + */ + key = path; + if (gtop->format & GTAGS_PATHINDEX) + if ((key = pathget(path)) == NULL) + die1("GPATH is corrupted.('%s' not found)", path); + length = strlen(key); + /* + * read sequentially, because db(1) has just one index. + */ + for (p = dbop_first(gtop->dbop, NULL, 0); p; p = dbop_next(gtop->dbop)) + if (belongto(gtop, key, p)) + dbop_del(gtop->dbop, NULL); + /* + * don't delete from path index. + */ +} +/* + * gtagsfirst: return first record + * + * i) gtop GTOP structure + * i) tag tag name + * i) flags GTOP_PREFIX prefix read + * GTOP_KEY read key only + * r) record + */ +char * +gtagsfirst(gtop, tag, flags) +GTOP *gtop; +char *tag; +int flags; +{ + int dbflags = 0; + char *line; + + gtop->flags = flags; + if (flags & GTOP_PREFIX && tag != NULL) + dbflags |= DBOP_PREFIX; + if (flags & GTOP_KEY) + dbflags |= DBOP_KEY; + if ((line = dbop_first(gtop->dbop, tag, dbflags)) == NULL) + return NULL; + if (gtop->format == GTAGS_STANDARD || gtop->flags & GTOP_KEY) + return line; + /* + * Compact format. + */ + gtop->line = line; /* gtop->line = $0 */ + gtop->opened = 0; + return genrecord(gtop); +} +/* + * gtagsnext: return followed record + * + * i) gtop GTOP structure + * r) record + * NULL end of tag + */ +char * +gtagsnext(gtop) +GTOP *gtop; +{ + char *line; + + /* + * If it is standard format or only key. + * Just return it. + */ + if (gtop->format == GTAGS_STANDARD || gtop->flags & GTOP_KEY) + return dbop_next(gtop->dbop); + /* + * gtop->format & GTAGS_COMPACT + */ + if ((line = genrecord(gtop)) != NULL) + return line; + /* + * read next record. + */ + if ((line = dbop_next(gtop->dbop)) == NULL) + return line; + gtop->line = line; /* gtop->line = $0 */ + gtop->opened = 0; + return genrecord(gtop); +} +/* + * gtagsclose: close tag file + * + * i) gtop GTOP structure + */ +void +gtagsclose(gtop) +GTOP *gtop; +{ + if (gtop->format & GTAGS_PATHINDEX || gtop->mode != GTAGS_READ) + pathclose(); + if (gtop->sb && gtop->prev_tag[0]) + dbop_put(gtop->dbop, gtop->prev_tag, strvalue(gtop->sb)); + if (gtop->sb) + strclose(gtop->sb); + dbop_close(gtop->dbop); + free(gtop); +} +static char * +genrecord(gtop) +GTOP *gtop; +{ + static char output[MAXBUFLEN+1]; + char path[MAXPATHLEN+1]; + static char buf[1]; + char *buffer = buf; + char *lnop; + int tagline; + + if (!gtop->opened) { + char *p, *q; + + gtop->opened = 1; + p = gtop->line; + q = gtop->tag; /* gtop->tag = $1 */ + while (!isspace(*p)) + *q++ = *p++; + *q = 0; + for (; isspace(*p) ; p++) + ; + if (gtop->format & GTAGS_PATHINDEX) { /* gtop->path = $2 */ + char *name; + + q = path; + while (!isspace(*p)) + *q++ = *p++; + *q = 0; + if ((name = pathget(path)) == NULL) + die1("GPATH is corrupted.('%s' not found)", path); + strcpy(gtop->path, name); + } else { + q = gtop->path; + while (!isspace(*p)) + *q++ = *p++; + *q = 0; + } + for (; isspace(*p) ; p++) + ; + gtop->lnop = p; /* gtop->lnop = $3 */ + + if (gtop->root) + sprintf(path, "%s/%s", gtop->root, >op->path[2]); + else + sprintf(path, "%s", >op->path[2]); + if ((gtop->fp = fopen(path, "r")) != NULL) { + buffer = mgets(gtop->fp, NULL, MGETS_TAILCUT); + gtop->lno = 1; + } + } + + lnop = gtop->lnop; + if (*lnop >= '0' && *lnop <= '9') { + /* get line number */ + for (tagline = 0; *lnop >= '0' && *lnop <= '9'; lnop++) + tagline = tagline * 10 + *lnop - '0'; + if (*lnop == ',') + lnop++; + gtop->lnop = lnop; + if (gtop->fp) { + if (gtop->lno == tagline) + return output; + while (gtop->lno < tagline) { + if (!(buffer = mgets(gtop->fp, NULL, MGETS_TAILCUT))) + die1("unexpected end of file. '%s'", path); + gtop->lno++; + } + } + if (strlen(gtop->tag) >= 16 && tagline >= 1000) + sprintf(output, "%-16s %4d %-16s %s", + gtop->tag, tagline, gtop->path, buffer); + else + sprintf(output, "%-16s%4d %-16s %s", + gtop->tag, tagline, gtop->path, buffer); + return output; + } + if (gtop->opened && gtop->fp != NULL) { + gtop->opened = 0; + fclose(gtop->fp); + } + return NULL; +} diff --git a/contrib/global/lib/gtagsop.h b/contrib/global/lib/gtagsop.h new file mode 100644 index 000000000000..c6e75d72a63e --- /dev/null +++ b/contrib/global/lib/gtagsop.h @@ -0,0 +1,109 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * gtagsop.h 23-Dec-97 + * + */ + +#ifndef _GTOP_H_ +#define _GTOP_H_ +#include <stdio.h> +#include "dbop.h" +#include "gparam.h" +#include "strbuf.h" + +#define VERSIONKEY " __.VERSION" +#define COMPACTKEY " __.COMPACT" +#define PATHINDEXKEY " __.PATHINDEX" + +#define GTAGS 0 +#define GRTAGS 1 +#define GSYMS 2 +#define GTAGLIM 3 + +#define GTAGS_READ 0 +#define GTAGS_CREATE 1 +#define GTAGS_MODIFY 2 + +/* gtagsopen() */ +#define GTAGS_STANDARD 0 /* standard format */ +#define GTAGS_COMPACT 1 /* compact format */ +#define GTAGS_PATHINDEX 2 /* use path index */ +/* gtagsadd() */ +#define GTAGS_UNIQUE 1 /* compress duplicate lines */ +#define GTAGS_EXTRACTMETHOD 2 /* extract method from class definition */ +/* gtagsfirst() */ +#define GTOP_KEY 1 /* read key part */ +#define GTOP_PREFIX 2 /* prefixed read */ + +typedef struct { + DBOP *dbop; /* descripter of DBOP */ + int format_version; /* format version */ + int format; /* GTAGS_STANDARD, GTAGS_COMPACT */ + int mode; /* mode */ + int db; /* 0:GTAGS, 1:GRTAGS, 2:GSYMS */ + int flags; /* flags */ + char root[MAXPATHLEN+1]; /* root directory of source tree */ + /* + * Stuff for compact format + */ + int opened; /* wether or not file opened */ + char *line; /* current record */ + char tag[IDENTLEN+1]; /* current tag */ + char prev_tag[IDENTLEN+1]; /* previous tag */ + char path[MAXPATHLEN+1]; /* current path */ + char prev_path[MAXPATHLEN+1];/* previous path */ + STRBUF *sb; /* string buffer */ + FILE *fp; /* descriptor of 'path' */ + char *lnop; /* current line number */ + int lno; /* integer value of 'lnop' */ +} GTOP; + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +const char *dbname __P((int)); +void makecommand __P((char *, char *, STRBUF *)); +int formatcheck __P((char *, int)); +GTOP *gtagsopen __P((char *, char *, int, int, int)); +void gtagsput __P((GTOP *, char *, char *)); +char *gtagsget __P((GTOP *, char *)); +void gtagsadd __P((GTOP *, char *, char *, int)); +void gtagsdelete __P((GTOP *, char *)); +char *gtagsfirst __P((GTOP *, char *, int)); +char *gtagsnext __P((GTOP *)); +void gtagsclose __P((GTOP *)); + +#endif /* ! _GTOP_H_ */ diff --git a/contrib/global/lib/locatestring.c b/contrib/global/lib/locatestring.c index 230ccce5149a..76285994befb 100644 --- a/contrib/global/lib/locatestring.c +++ b/contrib/global/lib/locatestring.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,7 +28,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * locatestring.c 20-Oct-97 + * locatestring.c 25-Jul-98 * */ #include <string.h> @@ -40,35 +40,36 @@ * * i) string string * i) pattern pattern - * i) flag 0: match first - * 1: match only at first column - * 2: match last - * 3: match only at last column + * i) flag MATCH_FIRST: match first + * MATCH_AT_FIRST: match only at first column + * MATCH_LAST: match last + * MATCH_AT_LAST: match only at last column * r) pointer or NULL * * This function is made to avoid compatibility problems. */ char * locatestring(string, pattern, flag) -char *string; -char *pattern; +const char *string; +const char *pattern; int flag; { int c = *pattern; - char *p = (char *)0; + int slen, plen; + const char *p = NULL; - if (flag == 3 && strlen(string) > strlen(pattern)) { - string += strlen(string) - strlen(pattern); - } + plen = strlen(pattern); + if (flag == MATCH_AT_LAST && (slen = strlen(string)) > plen) + string += (slen - plen); for (; *string; string++) { if (*string == c) - if (!strncmp(string, pattern, strlen(pattern))) { + if (!strncmp(string, pattern, plen)) { p = string; - if (flag == 0) + if (flag == MATCH_FIRST) break; } - if (flag == 1 || flag == 3) + if (flag == MATCH_AT_FIRST || flag == MATCH_AT_LAST) break; } - return p; + return (char *)p; } diff --git a/contrib/global/lib/locatestring.h b/contrib/global/lib/locatestring.h index cdaeedb1e5b0..2b881c6f447e 100644 --- a/contrib/global/lib/locatestring.h +++ b/contrib/global/lib/locatestring.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,13 +28,18 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * locatestring.h 16-Oct-97 + * locatestring.h 25-Jul-98 * */ #ifndef _LOCATESTRING_H_ #define _LOCATESTRING_H_ +#define MATCH_FIRST 0 +#define MATCH_AT_FIRST 1 +#define MATCH_LAST 2 +#define MATCH_AT_LAST 3 + #ifndef __P #if defined(__STDC__) #define __P(protos) protos @@ -43,6 +48,6 @@ #endif #endif -char *locatestring __P((char *, char *, int)); +char *locatestring __P((const char *, const char *, int)); #endif /* ! _LOCATESTRING_H_ */ diff --git a/contrib/global/lib/makepath.c b/contrib/global/lib/makepath.c index ba00ecfc6c2f..cf9858e95aab 100644 --- a/contrib/global/lib/makepath.c +++ b/contrib/global/lib/makepath.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,11 +28,15 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * makepath.c 20-Oct-97 + * makepath.c 15-May-98 * */ #include <sys/param.h> +#include "die.h" #include "makepath.h" +#include "strbuf.h" + +static STRBUF *sb; /* * makepath: make path from directory and file. * @@ -42,16 +46,21 @@ */ char * makepath(dir, file) -char *dir; -char *file; +const char *dir; +const char *file; { - static char path[MAXPATHLEN+1]; - char *p; + int length; - strcpy(path, dir); - p = path + strlen(path); - if (*(p - 1) != '/') - *p++ = '/'; - strcpy(p, file); - return path; + if (sb == NULL) + sb = stropen(); + strstart(sb); + if ((length = strlen(dir)) > MAXPATHLEN) + die1("path name too long. '%s'\n", dir); + strputs(sb, dir); + strunputc(sb, '/'); + strputc(sb, '/'); + strputs(sb, file); + if ((length = strlen(strvalue(sb))) > MAXPATHLEN) + die1("path name too long. '%s'\n", dir); + return strvalue(sb); } diff --git a/contrib/global/lib/makepath.h b/contrib/global/lib/makepath.h index 47d292d482dc..74b1c16f7620 100644 --- a/contrib/global/lib/makepath.h +++ b/contrib/global/lib/makepath.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -43,6 +43,6 @@ #endif #endif -char *makepath __P((char *, char *)); +char *makepath __P((const char *, const char *)); #endif /* ! _MAKEPATH_H_ */ diff --git a/contrib/global/lib/mgets.c b/contrib/global/lib/mgets.c index 2bc6099517c2..7f0cc7221c0e 100644 --- a/contrib/global/lib/mgets.c +++ b/contrib/global/lib/mgets.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,16 +28,19 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * mgets.c 8-Nov-97 + * mgets.c 29-Aug-98 * */ +#include <ctype.h> #include <stdio.h> #include <stdlib.h> -#include "mgets.h" #include "die.h" +#include "mgets.h" + +#define EXPANDSIZE 127 +#define MINSIZE 16 -#define EXPANDSIZE 512 static int mbufsize = EXPANDSIZE; static char *mbuf; @@ -45,20 +48,21 @@ static char *mbuf; * mgets: read whole record into allocated buffer * * i) ip input stream + * o) length record length * i) flags flags - * MGETS_CONT \\ + \n -> \n + * MGETS_CONT \\ + \n -> '' * MGETS_SKIPCOM skip line which start with '#'. - * o) length length of record + * MGETS_TAILCUT remove following blanks * r) record buffer (NULL at end of file) * * Returned buffer has whole record. * The buffer end with '\0' and doesn't include '\r' and '\n'. */ char * -mgets(ip, flags, length) +mgets(ip, length, flags) FILE *ip; -int flags; int *length; +int flags; { char *p; @@ -72,27 +76,33 @@ int *length; * read whole record. */ if (!fgets(mbuf, mbufsize, ip)) - return (char *)0; + return NULL; if (flags & MGETS_SKIPCOM) while (*mbuf == '#') if (!fgets(mbuf, mbufsize, ip)) - return (char *)0; + return NULL; p = mbuf + strlen(mbuf); + for (;;) { /* * get a line. */ while (*(p - 1) != '\n') { /* - * expand and read additionally. + * expand buffer and read additionally. */ int count = p - mbuf; - mbufsize += EXPANDSIZE; - if (!(mbuf = (char *)realloc(mbuf, mbufsize + 1))) - die("short of memory."); - p = mbuf + count; - if (!fgets(p, mbufsize - count, ip)) - die("illegal end of file."); + + if (mbufsize - count < MINSIZE) { + mbufsize += EXPANDSIZE; + if (!(mbuf = (char *)realloc(mbuf, mbufsize + 1))) + die("short of memory."); + p = mbuf + count; + } + if (!fgets(p, mbufsize - count, ip)) { + *p++ = '\n'; + break; + } p += strlen(p); } /* @@ -109,6 +119,17 @@ int *length; else break; } +/* + if (flags & MGETS_SKIPCOM) + for (p = mbuf; *p; p++) + if (*p == '#') { + *p = 0; + break; + } +*/ + if (flags & MGETS_TAILCUT) + while (isspace(*(--p))) + *p = 0; if (length) *length = p - mbuf; return mbuf; diff --git a/contrib/global/lib/mgets.h b/contrib/global/lib/mgets.h index ea3aef2fa8d8..75b5e831268f 100644 --- a/contrib/global/lib/mgets.h +++ b/contrib/global/lib/mgets.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redilogibution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -37,6 +37,7 @@ #include <stdio.h> #define MGETS_CONT 1 #define MGETS_SKIPCOM 2 +#define MGETS_TAILCUT 4 #ifndef __P #if defined(__STDC__) @@ -46,6 +47,6 @@ #endif #endif -char *mgets __P((FILE *, int, int *)); +char *mgets __P((FILE *, int *, int)); #endif /* ! _MGETS_H_ */ diff --git a/contrib/global/lib/pathop.c b/contrib/global/lib/pathop.c new file mode 100644 index 000000000000..2eb9e6982675 --- /dev/null +++ b/contrib/global/lib/pathop.c @@ -0,0 +1,155 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * pathop.c 12-Nov-98 + * + */ +#include <assert.h> +#include <stdlib.h> +#include <string.h> + +#include "die.h" +#include "dbop.h" +#include "makepath.h" +#include "pathop.h" + +static DBOP *dbop; +static const char *gpath = "GPATH"; +static int _nextkey; +static int _mode; +static int opened; +static int created; + +/* + * pathopen: open path dictionary tag. + * + * i) mode 0: read only + * 1: create + * 2: modify + * r) 0: normal + * -1: error + */ +int +pathopen(dbpath, mode) +char *dbpath; +int mode; +{ + char *p; + + assert(opened == 0); + /* + * We create GPATH just first time. + */ + _mode = mode; + if (mode == 1 && created) + mode = 0; + dbop = dbop_open(makepath(dbpath, gpath), mode, 0644, 0); + if (dbop == NULL) + return -1; + if (mode == 1) + _nextkey = 0; + else { + if (!(p = dbop_get(dbop, NEXTKEY))) + die("nextkey not found in GPATH."); + _nextkey = atoi(p); + } + opened = 1; + return 0; +} +void +pathput(path) +char *path; +{ + char buf[10]; + + assert(opened == 1); + if (_mode == 1 && created) + return; + if (dbop_get(dbop, path) != NULL) + return; + sprintf(buf, "%d", _nextkey++); + dbop_put(dbop, path, buf); + dbop_put(dbop, buf, path); +} +char * +pathget(key) +char *key; +{ + assert(opened == 1); + return dbop_get(dbop, key); +} +char * +pathiget(n) +int n; +{ + char key[80]; + assert(opened == 1); + sprintf(key, "%d", n); + return dbop_get(dbop, key); +} +void +pathdel(key) +char *key; +{ + char *d; + + assert(opened == 1); + assert(_mode == 2); + assert(key[0] == '.' && key[1] == '/'); + d = dbop_get(dbop, key); + if (d == NULL) + return; + dbop_del(dbop, d); + dbop_del(dbop, key); +} +int +nextkey(void) +{ + assert(_mode != 1); + return _nextkey; +} +void +pathclose(void) +{ + char buf[10]; + + assert(opened == 1); + opened = 0; + if (_mode == 1 && created) { + dbop_close(dbop); + return; + } + sprintf(buf, "%d", _nextkey); + if (_mode == 1 || _mode == 2) + dbop_put(dbop, NEXTKEY, buf); + dbop_close(dbop); + if (_mode == 1) + created = 1; +} diff --git a/contrib/global/lib/pathop.h b/contrib/global/lib/pathop.h new file mode 100644 index 000000000000..5bfef5dbaf55 --- /dev/null +++ b/contrib/global/lib/pathop.h @@ -0,0 +1,59 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * pathop.h 14-May-98 + * + */ + +#ifndef _PATHOP_H_ +#define _PATHOP_H_ +#include <stdio.h> +#include "dbop.h" +#include "gparam.h" + +#define NEXTKEY " __.NEXTKEY" + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +int pathopen __P((char *, int)); +char *pathget __P((char *)); +char *pathiget __P((int)); +void pathput __P((char *)); +void pathdel __P((char *)); +void pathclose __P((void)); +int nextkey __P((void)); + +#endif /* ! _PATHOP_H_ */ diff --git a/contrib/global/lib/strbuf.c b/contrib/global/lib/strbuf.c new file mode 100644 index 000000000000..3df14c9ee370 --- /dev/null +++ b/contrib/global/lib/strbuf.c @@ -0,0 +1,137 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * strbuf.c 5-Jul-98 + * + */ +#include <stdlib.h> +#include <string.h> + +#include "die.h" +#include "strbuf.h" + +/* + * usage: string buffer + * + * sb = stropen(); + * for (s = string; *s; s++) + * strputc(sb, *s); + * s = strvalue(sb); + * strstart(sb); + * strputs(sb, "hello"); + * s = strvalue(sb); + * strclose(sb); + */ +/* + * expandbuf: expand buffer so that afford to the length data at least. + * + * i) sb STRBUF structure + * i) length required room + */ +void +expandbuf(sb, length) +STRBUF *sb; +int length; +{ + int count = sb->curp - sb->sbuf; + + sb->sbufsize += (length > EXPANDSIZE) ? length : EXPANDSIZE; + if (!(sb->sbuf = (char *)realloc(sb->sbuf, sb->sbufsize + 1))) + die("short of memory."); + sb->curp = sb->sbuf + count; + sb->endp = sb->sbuf + sb->sbufsize; +} +/* + * stropen: open string buffer. + * + * r) sb STRBUF structure + */ +STRBUF * +stropen(void) +{ + STRBUF *sb = (STRBUF *)calloc(sizeof(STRBUF), 1); + + if (sb == NULL) + die("short of memory."); + sb->sbufsize = INITIALSIZE; + if (!(sb->sbuf = (char *)malloc(sb->sbufsize + 1))) + die("short of memory."); + sb->curp = sb->sbuf; + sb->endp = sb->sbuf + sb->sbufsize; + + return sb; +} +/* + * strstart: reset string buffer for new string. + * + * i) sb STRBUF structure + */ +void +strstart(sb) +STRBUF *sb; +{ + sb->curp = sb->sbuf; +} +/* + * strbuflen: return the length of string buffer. + * + * i) sb STRBUF structure + */ +int +strbuflen(sb) +STRBUF *sb; +{ + return sb->curp - sb->sbuf; +} +/* + * strvalue: return the content of string buffer. + * + * i) sb STRBUF structure + * r) string + */ +char * +strvalue(sb) +STRBUF *sb; +{ + *sb->curp = 0; + return sb->sbuf; +} +/* + * strclose: close string buffer. + * + * i) sb STRBUF structure + */ +void +strclose(sb) +STRBUF *sb; +{ + (void)free(sb->sbuf); + (void)free(sb); +} diff --git a/contrib/global/lib/strbuf.h b/contrib/global/lib/strbuf.h new file mode 100644 index 000000000000..e62c7ab3e034 --- /dev/null +++ b/contrib/global/lib/strbuf.h @@ -0,0 +1,82 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * strbuf.h 5-Jul-98 + * + */ + +#ifndef _STRBUF_H +#define _STRBUF_H + +#include <string.h> +#define INITIALSIZE 80 +#define EXPANDSIZE 80 + +typedef struct { + char *sbuf; + char *endp; + char *curp; + int sbufsize; +} STRBUF; + +#define strputc(sb,c) do {\ + if (sb->curp + 1 > sb->endp)\ + expandbuf(sb, 0);\ + *sb->curp++ = c;\ +} while (0) +#define strunputc(sb,c) do {\ + if (sb->curp > sb->sbuf && *(sb->curp - 1) == c)\ + sb->curp--;\ +} while (0) +#define strnputs(sb, s, len) do {\ + unsigned int _length = len;\ + if (sb->curp + _length > sb->endp)\ + expandbuf(sb, _length);\ + strncpy(sb->curp, s, _length);\ + sb->curp += _length;\ +} while (0) +#define strputs(sb, s) strnputs(sb, s, strlen(s)) + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +void expandbuf __P((STRBUF *, int)); +STRBUF *stropen __P((void)); +void strstart __P((STRBUF *)); +int strbuflen __P((STRBUF *)); +char *strvalue __P((STRBUF *)); +void strclose __P((STRBUF *)); + +#endif /* ! _STRBUF_H */ diff --git a/contrib/global/lib/strmake.c b/contrib/global/lib/strmake.c new file mode 100644 index 000000000000..da5dea4f25be --- /dev/null +++ b/contrib/global/lib/strmake.c @@ -0,0 +1,59 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * strmake.c 15-May-98 + * + */ +#include <stdlib.h> + +#include "strbuf.h" +#include "strmake.h" + +static STRBUF *sb; + +char * +strmake(p, lim) +const char *p; +const char *lim; +{ + const char *c; + + if (sb == NULL) + sb = stropen(); + strstart(sb); + for (; *p; p++) { + for (c = lim; *c; c++) + if (*p == *c) + goto end; + strputc(sb,*p); + } +end: + return strvalue(sb); +} diff --git a/contrib/global/lib/strmake.h b/contrib/global/lib/strmake.h new file mode 100644 index 000000000000..3558c5514972 --- /dev/null +++ b/contrib/global/lib/strmake.h @@ -0,0 +1,48 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * strmake.h 17-Apr-98 + * + */ + +#ifndef _STRMAKE_H_ +#define _STRMAKE_H_ + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +char *strmake __P((const char *, const char *)); + +#endif /* ! _STRMAKE_H_ */ diff --git a/contrib/global/lib/tab.c b/contrib/global/lib/tab.c index d309386a2d41..1a9896ff8b26 100644 --- a/contrib/global/lib/tab.c +++ b/contrib/global/lib/tab.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,14 +28,29 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * tab.c 20-Oct-97 + * tab.c 8-Oct-98 * */ #include <stdio.h> #include "tab.h" -#define TABPOS(i) ((i)%8 == 0) +static int tabs = 8; + +#define TABPOS(i) ((i)%tabs == 0) +/* + * settabs: set default tab stop + * + * i) n tab stop + */ +void +settabs(n) +int n; +{ + if (n < 1 || n > 32) + return; + tabs = n; +} /* * detab: convert tabs into spaces and print * @@ -84,7 +99,8 @@ char *buf; blanks++; /* count blanks */ continue; } - buf[dst++] = '\t'; + /* don't convert single blank into tab */ + buf[dst++] = (blanks == 0) ? ' ' : '\t'; } else if (c == '\t') { while (!TABPOS(++pos)) ; @@ -97,5 +113,8 @@ char *buf; } blanks = 0; } + if (blanks > 0) + while (blanks--) + buf[dst++] = ' '; buf[dst] = 0; } diff --git a/contrib/global/lib/tab.h b/contrib/global/lib/tab.h index c2b507969506..6153ff186c31 100644 --- a/contrib/global/lib/tab.h +++ b/contrib/global/lib/tab.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -28,7 +28,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * tab.h 16-Oct-97 + * tab.h 8-Oct-98 * */ @@ -43,6 +43,7 @@ #endif #endif +void settabs __P((int)); void detab __P((FILE *, char *)); void entab __P((char *)); diff --git a/contrib/global/lib/test.c b/contrib/global/lib/test.c index a3b5966e26a4..d5c940ea294c 100644 --- a/contrib/global/lib/test.c +++ b/contrib/global/lib/test.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -31,8 +31,8 @@ * test.c 12-Dec-97 * */ -#include <sys/stat.h> #include <sys/types.h> +#include <sys/stat.h> #include <unistd.h> @@ -50,21 +50,23 @@ * "x" [ -x path ] * * i) path path + * if NULL then previous path. * r) 0: no, 1: ok * * You can specify more than one character. It assumed 'and' test. */ int test(flags, path) -char *flags; -char *path; +const char *flags; +const char *path; { - struct stat sb; + static struct stat sb; int c; - if (stat(path, &sb) < 0) - return 0; - while ((c = *flags++) != NULL) { + if (path != NULL) + if (stat(path, &sb) < 0) + return 0; + while ((c = *flags++) != 0) { switch (c) { case 'f': if (!S_ISREG(sb.st_mode)) diff --git a/contrib/global/lib/test.h b/contrib/global/lib/test.h index edadbdaafd7a..c44ee48bb340 100644 --- a/contrib/global/lib/test.h +++ b/contrib/global/lib/test.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 1997 Shigio Yamaguchi. All rights reserved. + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -43,6 +43,6 @@ #endif #endif -int test __P((char *, char *)); +int test __P((const char *, const char *)); #endif /* ! _TEST_H_ */ diff --git a/contrib/global/lib/token.c b/contrib/global/lib/token.c new file mode 100644 index 000000000000..27dbe4226eef --- /dev/null +++ b/contrib/global/lib/token.c @@ -0,0 +1,293 @@ +/* + * Copyright (c) 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * token.c 14-Aug-98 + */ + +#include <ctype.h> +#include <stdio.h> +#include <string.h> +#include <sys/param.h> + +#include "mgets.h" +#include "token.h" + +/* + * File input method. + */ +int lineno; +char *sp, *cp, *lp; +int crflag; /* 1: return '\n', 0: doesn't return */ +int cmode; /* allow token which start with '#' */ +int ymode; /* allow token which start with '%' */ +char token[MAXTOKEN]; +char curfile[MAXPATHLEN]; + +static char ptok[MAXTOKEN]; +static int lasttok; +static FILE *ip; + +static void pushbackchar __P((void)); + +/* + * opentoken: + */ +int +opentoken(file) + char *file; +{ + if ((ip = fopen(file, "r")) == NULL) + return 0; + strcpy(curfile, file); + sp = cp = lp = NULL; lineno = 0; + return 1; +} +/* + * closetoken: + */ +void +closetoken() +{ + fclose(ip); +} + +/* + * nexttoken: get next token + * + * i) interested interested special charactor + * if NULL then all charactor. + * i) reserved converter from token to token number + * if this is specified, nexttoken() return + * word number, else return symbol. + * r) EOF(-1) end of file + * ==0 symbol ('tok' has the value.) + * > 255 reserved word + * <=255 interested special charactor + * + * nexttoken() doesn't return followings. + * + * o comment + * o space (' ', '\t', '\f') + * o quoted string ("...", '.') + */ + +int +nexttoken(interested, reserved) + const char *interested; + int (*reserved)(char *); +{ + int c; + char *p; + int sharp = 0; + int percent = 0; + + /* check push back buffer */ + if (ptok[0]) { + strcpy(token, ptok); + ptok[0] = 0; + return lasttok; + } + + for (;;) { + /* skip spaces */ + if (!crflag) + while ((c = nextchar()) != EOF && isspace(c)) + ; + else + while ((c = nextchar()) != EOF && (c == ' ' || c == '\t' || c == '\f')) + ; + if (c == EOF || c == '\n') + break; + + if (c == '"' || c == '\'') { /* quoted string */ + int quote = c; + + while ((c = nextchar()) != EOF) { + if (c == quote) + break; + if (quote == '\'' && c == '\n') + break; + if (c == '\\' && (c = nextchar()) == EOF) + break; + } + } else if (c == '/') { /* comment */ + if ((c = nextchar()) == '/') { + while ((c = nextchar()) != EOF) + if (c == '\n') + break; + } else if (c == '*') { + while ((c = nextchar()) != EOF) { + if (c == '*') { + if ((c = nextchar()) == '/') + break; + pushbackchar(); + } + } + } else + pushbackchar(); + } else if (c == '\\') { + (void)nextchar(); + } else if (isdigit(c)) { /* digit */ + while ((c = nextchar()) != EOF && (c == '.' || isdigit(c) || isalpha(c))) + ; + pushbackchar(); + } else if (c == '#' && cmode) { + /* recognize '##' as a token if it is reserved word. */ + if (peekc(1) == '#') { + p = token; + *p++ = c; + *p++ = nextchar(); + *p = 0; + if (reserved && (c = (*reserved)(token)) == 0) + break; + } else if (atfirst_exceptspace()) { + sharp = 1; + continue; + } + } else if (c == '%' && ymode) { + /* recognize '%%' as a token if it is reserved word. */ + if (atfirst) { + p = token; + *p++ = c; + if ((c = peekc(1)) == '%' || c == '{' || c == '}') { + *p++ = nextchar(); + *p = 0; + if (reserved && (c = (*reserved)(token)) != 0) + break; + } else if (!isspace(c)) { + percent = 1; + continue; + } + } + } else if (c & 0x80 || isalpha(c) || c == '_') {/* symbol */ + p = token; + if (sharp) { + sharp = 0; + *p++ = '#'; + } else if (percent) { + percent = 0; + *p++ = '%'; + } + for (*p++ = c; (c = nextchar()) != EOF && (c & 0x80 || isalnum(c) || c == '_'); *p++ = c) + ; + *p = 0; + if (c != EOF) + pushbackchar(); + /* convert token string into token number */ + if (reserved) + c = (*reserved)(token); + break; + } else { /* special char */ + if (interested == NULL || strchr(interested, c)) + break; + /* otherwise ignore it */ + } + sharp = percent = 0; + } + return lasttok = c; +} +/* + * pushbacktoken: push back token + * + * following nexttoken() return same token again. + */ +void +pushbacktoken() +{ + strcpy(ptok, token); +} +/* + * peekc: peek next char + * + * i) immediate 0: ignore blank, 1: include blank + * + * Peekc() read ahead following blanks but doesn't chage line. + */ +int +peekc(immediate) + int immediate; +{ + int c; + long pos; + + if (cp != NULL) { + if (immediate) + c = nextchar(); + else + while ((c = nextchar()) != EOF && c != '\n' && isspace(c)) + ; + if (c != EOF) + pushbackchar(); + if (c != '\n' || immediate) + return c; + } + pos = ftell(ip); + if (immediate) + c = getc(ip); + else + while ((c = getc(ip)) != EOF && isspace(c)) + ; + (void)fseek(ip, pos, SEEK_SET); + + return c; +} +/* + * atfirst_exceptspace: return if current position is the first column + * except for space. + * | 1 0 + * | v v + * | # define + */ +int +atfirst_exceptspace() +{ + char *start = sp; + char *end = cp ? cp - 1 : lp; + + while (start < end && *start && isspace(*start)) + start++; + return (start == end) ? 1 : 0; +} +/* + * pushbackchar: push back charactor. + * + * following nextchar() return same charactor again. + * + */ +static void +pushbackchar() +{ + if (sp == NULL) + return; /* nothing to do */ + if (cp == NULL) + cp = lp; + else + --cp; +} diff --git a/contrib/global/lib/token.h b/contrib/global/lib/token.h new file mode 100644 index 000000000000..571b8505c88d --- /dev/null +++ b/contrib/global/lib/token.h @@ -0,0 +1,75 @@ +/* + * Copyright (c) 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * token.h 14-Aug-98 + */ + +#ifndef _TOKEN_H_ +#define _TOKEN_H_ + +#include <sys/param.h> +#include "mgets.h" +#define MAXTOKEN 512 +#define SYMBOL 0 + +extern char *sp, *cp, *lp; +extern int lineno; +extern int crflag; +extern int cmode; +extern int ymode; +extern char token[MAXTOKEN]; +extern char curfile[MAXPATHLEN]; + +#define nextchar() \ + (cp == NULL ? \ + ((sp = cp = mgets(ip, NULL, 0)) == NULL ? \ + EOF : \ + (lineno++, *cp == 0 ? \ + lp = cp, cp = NULL, '\n' : \ + *cp++)) : \ + (*cp == 0 ? (lp = cp, cp = NULL, '\n') : *cp++)) +#define atfirst (sp && sp == (cp ? cp - 1 : lp)) + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +int opentoken __P((char *)); +void closetoken __P((void)); +int nexttoken __P((const char *, int (*)(char *))); +void pushbacktoken __P((void)); +int peekc __P((int)); +int atfirst_exceptspace __P((void)); + +#endif /* ! _TOKEN_H_ */ diff --git a/contrib/global/lib/usable.c b/contrib/global/lib/usable.c new file mode 100644 index 000000000000..af8dd0ab0fbb --- /dev/null +++ b/contrib/global/lib/usable.c @@ -0,0 +1,70 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * usable.c 22-Jun-98 + * + */ +#include <assert.h> +#include <stdlib.h> +#include <string.h> + +#include "locatestring.h" +#include "gparam.h" +#include "makepath.h" +#include "test.h" +#include "usable.h" + +/* + * usable: check executable or not about the command. + * + * i) command + * r) 1: executable + * 0: non executable + */ +int +usable(command) +char *command; +{ + char buf[MAXENVLEN+1], *p, *dir; + + if (*command == '/' || locatestring(command, "./", MATCH_AT_FIRST) || locatestring(command, "../", MATCH_AT_FIRST)) + return test("fx", command); + + strcpy(buf, getenv("PATH")); + p = buf; + while (p) { + dir = p; + if ((p = locatestring(p, ":", MATCH_FIRST)) != NULL) + *p++ = 0; + if (test("fx", makepath(dir, command))) + return 1; + } + return 0; +} diff --git a/contrib/global/lib/usable.h b/contrib/global/lib/usable.h new file mode 100644 index 000000000000..647769d7ac4a --- /dev/null +++ b/contrib/global/lib/usable.h @@ -0,0 +1,48 @@ +/* + * Copyright (c) 1996, 1997, 1998 Shigio Yamaguchi. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Shigio Yamaguchi. + * 4. Neither the name of the author nor the names of any co-contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * usable.h 22-Jul-98 + * + */ + +#ifndef _USABLE_H_ +#define _USABLE_H_ + +#ifndef __P +#if defined(__STDC__) +#define __P(protos) protos +#else +#define __P(protos) () +#endif +#endif + +int usable __P((char *)); + +#endif /* ! _USABLE_H_ */ |