summaryrefslogtreecommitdiffstats
path: root/contrib/global/gtags
diff options
context:
space:
mode:
authorsimokawa <simokawa@FreeBSD.org>1999-01-18 06:59:18 +0000
committersimokawa <simokawa@FreeBSD.org>1999-01-18 06:59:18 +0000
commitcf4b2ca9b8568c15972f1570d34cedbb6483b021 (patch)
tree2d073c94248fff7dcaa8a3b1356933e1dcd784db /contrib/global/gtags
parent490818046d130f0f1520df3695f71a48ebf07726 (diff)
downloadFreeBSD-src-cf4b2ca9b8568c15972f1570d34cedbb6483b021.zip
FreeBSD-src-cf4b2ca9b8568c15972f1570d34cedbb6483b021.tar.gz
Import Global v3_4_2 sources.
Ok'd by: peter Discussed with: msmith
Diffstat (limited to 'contrib/global/gtags')
-rw-r--r--contrib/global/gtags/Makefile3
-rw-r--r--contrib/global/gtags/gtags.123
-rw-r--r--contrib/global/gtags/gtags.c406
3 files changed, 310 insertions, 122 deletions
diff --git a/contrib/global/gtags/Makefile b/contrib/global/gtags/Makefile
index 9afed80..ecfb0ea 100644
--- a/contrib/global/gtags/Makefile
+++ b/contrib/global/gtags/Makefile
@@ -1,6 +1,3 @@
PROG= gtags
-CFLAGS+=-I${.CURDIR}/../lib
-LDADD= $(LIBUTIL)
-DPADD= $(LIBUTIL)
.include <bsd.prog.mk>
diff --git a/contrib/global/gtags/gtags.1 b/contrib/global/gtags/gtags.1
index ed18616..e6b09e6 100644
--- a/contrib/global/gtags/gtags.1
+++ b/contrib/global/gtags/gtags.1
@@ -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,26 +28,28 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
-.Dd Sep 12, 1997
+.Dd Oct 10, 1998
.Dt GTAGS 1
.Os BSD 4
.Sh NAME
.Nm gtags
-.Nd create GTAGS, GRTAGS and GSYMS file
+.Nd create tag files for global.
.Sh SYNOPSIS
.Nm gtags
+.Op Fl c
.Op Fl i
.Op Fl o
+.Op Fl w
.Op Fl v
.Op Ar dbpath
.Sh DESCRIPTION
.Nm Gtags
-makes GTAGS, GRTAGS and GSYMS file for
+makes GTAGS, GRTAGS, GSYMS and GPATH file for
.Xr global 1 .
.Nm Gtags
trace subdirectories, read source files,
locate symbols and save the information into tag files.
-C, yacc and assembler source files are supported.
+C, yacc, java and assembler source files are supported.
You should execute this command at the root of the source tree.
.Pp
If your source directory is on a read only device like CDROM, specify
@@ -55,13 +57,16 @@ If your source directory is on a read only device like CDROM, specify
of the directory on which make tag files.
.Pp
.Bl -tag -width Ds
+.It Fl c
+make tag files with compact format.
.It Fl i
-update tag files incrementally by files which modified after the tag files were
-last updated.
+update tag files incrementally.
.It Fl o
suppress making GSYMS file.
Use this option if you don't use -s option of
.Xr global 1 .
+.It Fl w
+print warning messages.
.It Fl v
verbose mode.
.Sh FILES
@@ -72,6 +77,8 @@ tag file for function definitions.
tag file for function references.
.It Pa GSYMS
tag file for other symbols.
+.It Pa GPATH
+path index file which is used for incremental updating and compact format.
.El
.Sh DIAGNOSTICS
.Nm Gtags
@@ -85,7 +92,7 @@ exits with a non 0 value if an error occurred, 0 otherwise.
GTAGS, GRTAGS and GSYMS are very large.
In advance of using this command, check the space of your disk.
.br
-Assembler support is far from completeness. It extracts only ENTRY()
+Assembler support is far from complete. It extracts only ENTRY()
and ALTENTRY() from source file. Probably valid only for FreeBSD and Linux
kernel source.
.br
diff --git a/contrib/global/gtags/gtags.c b/contrib/global/gtags/gtags.c
index 288c16c..7a88747 100644
--- a/contrib/global/gtags/gtags.c
+++ b/contrib/global/gtags/gtags.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,60 +28,105 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * gtags.c 12-Dec-97
+ * gtags.c 8-Oct-98
*
*/
-
+#include <sys/types.h>
#include <sys/stat.h>
#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
+#include <string.h>
#include <time.h>
#include <unistd.h>
#include "global.h"
-char *progname = "gtags"; /* command name */
+const char *progname = "gtags"; /* command name */
static void usage __P((void));
-void main __P((int, char **));
-int incremental __P((char *));
-void tagadd __P((int, char *));
-void createtags __P((char *, int));
-char *current __P((void));
+int main __P((int, char **));
+int incremental __P((char *, char *));
+void updatetags __P((char *, char *, char *, int));
+void createtags __P((char *, char *, int));
+int printconf __P((char *));
+char *now __P((void));
-static int iflag;
-static int oflag;
-static int vflag;
+int cflag; /* compact format */
+int iflag; /* incremental update */
+int oflag; /* suppress making GSYMS */
+int wflag; /* warning message */
+int vflag; /* verbose mode */
+int extractmethod = 0;
static void
usage()
{
- fprintf(stderr, "usage:\t%s [-i][-o][-v][dbpath]\n", progname);
+ fprintf(stderr, "usage:\t%s [-c][-i][-l][-o][-w][-v][dbpath]\n", progname);
exit(1);
}
-void
+int
main(argc, argv)
int argc;
char *argv[];
{
char dbpath[MAXPATHLEN+1];
+ char cwd[MAXPATHLEN+1];
char env[MAXENVLEN+1];
- char *p;
+ STRBUF *sb = stropen();
int db;
while (--argc > 0 && (++argv)[0][0] == '-') {
+ char *p;
+ /*
+ * Secret option for htags(1).
+ */
+ if (!strcmp(argv[0], "--config")) {
+ if (argc == 1)
+ fprintf(stdout, "%s\n", configpath());
+ else if (argc == 2) {
+ if (!printconf(argv[1]))
+ exit(1);
+ }
+ exit(0);
+ } else if (!strcmp(argv[0], "--find")) {
+ for (findopen(); (p = findread(NULL)) != NULL; )
+ fprintf(stdout, "%s\n", p);
+ findclose();
+ exit(0);
+ } else if (!strcmp(argv[0], "--expand")) {
+ FILE *ip;
+
+ ++argv; --argc;
+ if (argc && argv[0][0] == '-') {
+ settabs(atoi(&argv[0][1]));
+ ++argv; --argc;
+ }
+ ip = (argc) ? fopen(argv[0], "r") : stdin;
+ if (ip == NULL)
+ exit(1);
+ while ((p = mgets(ip, NULL, 0)) != NULL)
+ detab(stdout, p);
+ exit(0);
+ }
+
for (p = argv[0] + 1; *p; p++) {
switch (*p) {
+ case 'c':
+ cflag++;
+ break;
case 'i':
iflag++;
break;
case 'o':
oflag++;
break;
+ case 'w':
+ wflag++;
+ break;
case 'v':
vflag++;
break;
@@ -94,30 +139,48 @@ char *argv[];
}
}
}
- if (argc > 0) {
- strcpy(dbpath, *argv);
- } else {
- if (!getcwd(dbpath, MAXPATHLEN))
- die("cannot get current directory.");
- }
+ if (!getcwd(cwd, MAXPATHLEN))
+ die("cannot get current directory.");
+ if (argc > 0)
+ realpath(*argv,dbpath) ;
+ else
+ strcpy(dbpath, cwd);
if (!strcmp(dbpath, "/"))
die("It's root directory! What are you doing?");
if (!test("d", dbpath))
die1("directory '%s' not found.", dbpath);
if (vflag)
- fprintf(stderr, "[%s] Gtags started\n", current());
+ fprintf(stderr, "[%s] Gtags started\n", now());
+ /*
+ * load .gtagsrc or /etc/gtags.conf
+ */
+ openconf();
+ if (getconfb("extractmethod"))
+ extractmethod = 1;
+ strstart(sb);
+ if (getconfs("format", sb) && !strcmp(strvalue(sb), "compact"))
+ cflag++;
/*
* teach gctags(1) where is dbpath.
*/
sprintf(env, "GTAGSDBPATH=%s", dbpath);
putenv(env);
+ if (wflag) {
+ sprintf(env, "GTAGSWARNING=1");
+ putenv(env);
+ }
/*
* incremental update.
*/
if (iflag && test("f", makepath(dbpath, dbname(GTAGS))) &&
test("f", makepath(dbpath, dbname(GRTAGS))))
{
- (void)incremental(dbpath);
+ /* open for version check */
+ GTOP *gtop = gtagsopen(dbpath, cwd, GTAGS, GTAGS_MODIFY, 0);
+ gtagsclose(gtop);
+ if (!test("f", makepath(dbpath, "GPATH")))
+ die("Old version tag file found. Please remake it.");
+ (void)incremental(dbpath, cwd);
exit(0);
}
if (iflag && vflag)
@@ -126,32 +189,43 @@ char *argv[];
* create GTAGS, GRTAGS and GSYMS
*/
for (db = GTAGS; db < GTAGLIM; db++) {
+
if (oflag && db == GSYMS)
continue;
+ strstart(sb);
+ if (!getconfs(dbname(db), sb))
+ continue;
+ if (!usable(strmake(strvalue(sb), " \t")))
+ die1("Parser '%s' not found or not executable.", strmake(strvalue(sb), " \t"));
if (vflag)
- fprintf(stderr, "[%s] Creating '%s'.\n", current(), dbname(db));
- createtags(dbpath, db);
+ fprintf(stderr, "[%s] Creating '%s'.\n", now(), dbname(db));
+ createtags(dbpath, cwd, db);
}
if (vflag)
- fprintf(stderr, "[%s] Done.\n", current());
+ fprintf(stderr, "[%s] Done.\n", now());
+ closeconf();
exit(0);
}
/*
* incremental: incremental update
*
* i) dbpath dbpath directory
+ * i) root root directory of source tree
* r) 0: not updated, 1: updated
*/
int
-incremental(dbpath)
+incremental(dbpath, root)
char *dbpath;
+char *root;
{
- struct stat sb;
+ struct stat statp;
time_t gtags_mtime;
+ STRBUF *addlist = stropen();
+ STRBUF *updatelist = stropen();
+ STRBUF *deletelist = stropen();
int updated = 0;
char *path;
- int db;
if (vflag) {
fprintf(stderr, " Tag found in '%s'.\n", dbpath);
@@ -161,145 +235,255 @@ char *dbpath;
* get modified time of GTAGS.
*/
path = makepath(dbpath, dbname(GTAGS));
- if (stat(path, &sb) < 0)
+ if (stat(path, &statp) < 0)
die1("stat failed '%s'.", path);
- gtags_mtime = sb.st_mtime;
+ gtags_mtime = statp.st_mtime;
+ if (pathopen(dbpath, 0) < 0)
+ die("GPATH not found.");
+ /*
+ * make add list and update list.
+ */
for (findopen(); (path = findread(NULL)) != NULL; ) {
- if (stat(path, &sb) < 0)
+ if (stat(path, &statp) < 0)
die1("stat failed '%s'.", path);
- /*
- * only the path modified after GTAGS was modified.
- */
- if (gtags_mtime < sb.st_mtime) {
- updated = 1;
- if (vflag)
- fprintf(stderr, " Updating tags of '%s' ...", path + 2);
- for (db = GTAGS; db < GTAGLIM; db++) {
- if (db == GSYMS && !test("f", makepath(dbpath, dbname(db))))
- continue;
- if (vflag)
- fprintf(stderr, "%s", dbname(db));
- tagopen(dbpath, db, 2);
- /*
- * GTAGS needed to make GRTAGS.
- */
- if (db == GRTAGS)
- lookupopen(dbpath);
- tagdelete(path);
- if (vflag)
- fprintf(stderr, "..");
- tagadd(db, path);
- if (db == GRTAGS)
- lookupclose();
- tagclose();
- }
- if (vflag)
- fprintf(stderr, " Done.\n");
- }
+ if (!pathget(path))
+ strnputs(addlist, path, strlen(path) + 1);
+ else if (gtags_mtime < statp.st_mtime)
+ strnputs(updatelist, path, strlen(path) + 1);
}
findclose();
+ /*
+ * make delete list.
+ */
+ {
+ int i, limit = nextkey();
+
+ for (i = 0; i < limit; i++) {
+ if ((path = pathiget(i)) == NULL)
+ continue;
+ if (!test("f", path))
+ strnputs(deletelist, path, strlen(path) + 1);
+ }
+ }
+ pathclose();
+ if (strbuflen(addlist) + strbuflen(deletelist) + strbuflen(updatelist))
+ updated = 1;
+ /*
+ * execute updating.
+ */
+ if (strbuflen(updatelist) > 0) {
+ char *start = strvalue(updatelist);
+ char *end = start + strbuflen(updatelist);
+ char *p;
+
+ for (p = start; p < end; p += strlen(p) + 1)
+ updatetags(dbpath, root, p, 0);
+ updated = 1;
+ }
+ if (strbuflen(addlist) > 0) {
+ char *start = strvalue(addlist);
+ char *end = start + strbuflen(addlist);
+ char *p;
+
+ for (p = start; p < end; p += strlen(p) + 1)
+ updatetags(dbpath, root, p, 1);
+ updated = 1;
+ }
+ if (strbuflen(deletelist) > 0) {
+ char *start = strvalue(deletelist);
+ char *end = start + strbuflen(deletelist);
+ char *p;
+
+ for (p = start; p < end; p += strlen(p) + 1)
+ updatetags(dbpath, root, p, 2);
+
+ pathopen(dbpath, 2);
+ for (p = start; p < end; p += strlen(p) + 1)
+ pathdel(p);
+ pathclose();
+ updated = 1;
+ }
if (vflag) {
if (updated)
fprintf(stderr, " Global databases have been modified.\n");
else
fprintf(stderr, " Global databases are up to date.\n");
- fprintf(stderr, "[%s] Done.\n", current());
-
- fprintf(stderr, " Done.\n");
+ fprintf(stderr, "[%s] Done.\n", now());
}
+ strclose(addlist);
+ strclose(deletelist);
+ strclose(updatelist);
return updated;
}
/*
- * tagadd: add records which has specified path.
+ * updatetags: update tag file.
*
- * i) db 0: GTAGS, 1: GRTAGS, 2: GSYMS
- * i) path source file
+ * i) dbpath directory in which tag file exist
+ * i) root root directory of source tree
+ * i) path path which should be updated
+ * i) type 0:update, 1:add, 2:delete
*/
void
-tagadd(db, path)
-int db;
+updatetags(dbpath, root, path, type)
+char *dbpath;
+char *root;
char *path;
+int type;
{
- char *tagline, *p, *q;
- char key[IDENTLEN+1];
- FILE *ip;
+ GTOP *gtop;
+ STRBUF *sb = stropen();
+ int db;
+ const char *msg = NULL;
- stropen();
- /*
- * make command line.
- */
- strputs("gctags -Dex");
- if (db == GRTAGS)
- strputs("r");
- if (db == GSYMS)
- strputs("sc");
- strputc(' ');
- strputs(path);
- p = strclose();
- if (!(ip = popen(p, "r")))
- die1("cannot execute '%s'.", p);
- while ((tagline = mgets(ip, 0, NULL)) != NULL) {
- p = tagline;
- q = key;
- while (*p && !isspace(*p))
- *q++ = *p++;
- *q = 0;
- tagput(key, tagline);
+ switch (type) {
+ case 0: msg = "Updating"; break;
+ case 1: msg = "Adding"; break;
+ case 2: msg = "Deleting"; break;
+ }
+ if (vflag)
+ fprintf(stderr, " %s tags of '%s' ...", msg, path + 2);
+ for (db = GTAGS; db < GTAGLIM; db++) {
+ int flags = 0;
+
+ if (db == GSYMS && !test("f", makepath(dbpath, dbname(db))))
+ continue;
+ if (vflag)
+ fprintf(stderr, "%s", dbname(db));
+ /*
+ * get tag command.
+ */
+ strstart(sb);
+ if (!getconfs(dbname(db), sb))
+ die1("cannot get tag command. (%s)", dbname(db));
+ gtop = gtagsopen(dbpath, root, db, GTAGS_MODIFY, 0);
+ /*
+ * GTAGS needed to make GRTAGS.
+ */
+ if (db == GRTAGS && !test("f", makepath(dbpath, "GTAGS")))
+ die("GTAGS needed to create GRTAGS.");
+ if (type != 1)
+ gtagsdelete(gtop, path);
+ if (vflag)
+ fprintf(stderr, "..");
+ if (type != 2) {
+ if (db == GSYMS)
+ flags |= GTAGS_UNIQUE;
+ if (extractmethod)
+ flags |= GTAGS_EXTRACTMETHOD;
+ gtagsadd(gtop, strvalue(sb), path, flags);
+ }
+ gtagsclose(gtop);
}
- pclose(ip);
+ if (vflag)
+ fprintf(stderr, " Done.\n");
+ strclose(sb);
}
/*
* createtags: create tags file
*
* i) dbpath dbpath directory
+ * i) root root directory of source tree
* i) db GTAGS, GRTAGS, GSYMS
*/
void
-createtags(dbpath, db)
+createtags(dbpath, root, db)
char *dbpath;
+char *root;
int db;
{
char *path;
+ GTOP *gtop;
+ int flags;
+ char *comline;
+ STRBUF *sb = stropen();
/*
+ * get tag command.
+ */
+ if (!getconfs(dbname(db), sb))
+ die1("cannot get tag command. (%s)", dbname(db));
+ comline = strdup(strvalue(sb));
+ if (!comline)
+ die("short of memory.");
+ /*
* GTAGS needed to make GRTAGS.
*/
- if (db == GRTAGS)
- lookupopen(dbpath);
- tagopen(dbpath, db, 1);
+ if (db == GRTAGS && !test("f", makepath(dbpath, "GTAGS")))
+ die("GTAGS needed to create GRTAGS.");
+ flags = 0;
+ strstart(sb);
+ if (cflag) {
+ flags |= GTAGS_COMPACT;
+ flags |= GTAGS_PATHINDEX;
+ }
+ strstart(sb);
+ if (vflag > 1 && getconfs(dbname(db), sb))
+ fprintf(stderr, " using tag command '%s <path>'.\n", strvalue(sb));
+ gtop = gtagsopen(dbpath, root, db, GTAGS_CREATE, flags);
for (findopen(); (path = findread(NULL)) != NULL; ) {
+ int gflags = 0;
/*
* GSYMS doesn't treat asembler.
*/
- if (db == GSYMS) {
- char *p = path + strlen(path) - 1;
- if ((*p == 's' || *p == 'S') && *(p - 1) == '.')
+ if (db == GSYMS)
+ if (locatestring(path, ".s", MATCH_AT_LAST) != NULL ||
+ locatestring(path, ".S", MATCH_AT_LAST) != NULL)
continue;
- }
if (vflag)
fprintf(stderr, " extracting tags of %s.\n", path);
- tagadd(db, path);
+ if (db == GSYMS)
+ gflags |= GTAGS_UNIQUE;
+ if (extractmethod)
+ gflags |= GTAGS_EXTRACTMETHOD;
+ gtagsadd(gtop, comline, path, gflags);
}
findclose();
- tagclose();
- if (db == GRTAGS)
- lookupclose();
+ gtagsclose(gtop);
+ free(comline);
+ strclose(sb);
}
/*
- * current: current date and time
+ * now: current date and time
*
* r) date and time
*/
-char *
-current(void)
+char *
+now(void)
{
static char buf[80];
time_t tval;
if (time(&tval) == -1)
die("cannot get current time.");
- (void)strftime(buf, sizeof(buf), "%+", localtime(&tval));
-
+ (void)strftime(buf, sizeof(buf), "%a %b %e %H:%M:%S %Z %Y", localtime(&tval));
return buf;
}
+/*
+ * printconf: print configuration data.
+ *
+ * i) name label of config data
+ * r) exit code
+ */
+int
+printconf(name)
+char *name;
+{
+ STRBUF *sb;
+ int num;
+ int exist = 1;
+
+ if (getconfn(name, &num))
+ fprintf(stdout, "%d\n", num);
+ else if (getconfb(name))
+ fprintf(stdout, "1\n");
+ else {
+ sb = stropen();
+ if (getconfs(name, sb))
+ fprintf(stdout, "%s\n", strvalue(sb));
+ else
+ exist = 0;
+ strclose(sb);
+ }
+ return exist;
+}
OpenPOWER on IntegriCloud