summaryrefslogtreecommitdiffstats
path: root/contrib/global/gtags/gtags.c
diff options
context:
space:
mode:
authorcwt <cwt@FreeBSD.org>1997-12-15 23:08:46 +0000
committercwt <cwt@FreeBSD.org>1997-12-15 23:08:46 +0000
commitb1200e5a86469f83f9487d32847b49df6f6e8d81 (patch)
tree84ffbd5bfaa52e29af60dccffd70e807e7110a91 /contrib/global/gtags/gtags.c
parentd9973ba95ba5804ff9b4d3b5295bc5126726e474 (diff)
parent2d4696c8a0217d673b65b4f308e71d6ae8f5ebc6 (diff)
downloadFreeBSD-src-b1200e5a86469f83f9487d32847b49df6f6e8d81.zip
FreeBSD-src-b1200e5a86469f83f9487d32847b49df6f6e8d81.tar.gz
This commit was generated by cvs2svn to compensate for changes in r31750,
which included commits to RCS files with non-trunk default branches.
Diffstat (limited to 'contrib/global/gtags/gtags.c')
-rw-r--r--contrib/global/gtags/gtags.c302
1 files changed, 302 insertions, 0 deletions
diff --git a/contrib/global/gtags/gtags.c b/contrib/global/gtags/gtags.c
new file mode 100644
index 0000000..ef4a8e9
--- /dev/null
+++ b/contrib/global/gtags/gtags.c
@@ -0,0 +1,302 @@
+/*
+ * Copyright (c) 1996, 1997 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.
+ *
+ * gtags.c 12-Dec-97
+ *
+ */
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/stat.h>
+#include "global.h"
+
+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(());
+
+static int iflag;
+static int oflag;
+static int vflag;
+static int Dflag;
+static int Rflag;
+
+static void
+usage()
+{
+ fprintf(stderr, "usage:\t%s [-i][-o][-v][dbpath]\n", progname);
+ exit(1);
+}
+
+void
+main(argc, argv)
+int argc;
+char *argv[];
+{
+ char dbpath[MAXPATHLEN+1];
+ char env[MAXENVLEN+1];
+ char *path, *p;
+ FILE *ip;
+ int db;
+
+ while (--argc > 0 && (++argv)[0][0] == '-') {
+ for (p = argv[0] + 1; *p; p++) {
+ switch (*p) {
+ case 'i':
+ iflag++;
+ break;
+ case 'o':
+ oflag++;
+ break;
+ case 'v':
+ vflag++;
+ break;
+ /* for compatibility */
+ case 's':
+ case 'e':
+ break;
+ default:
+ usage();
+ }
+ }
+ }
+ if (argc > 0) {
+ strcpy(dbpath, *argv);
+ } else {
+ if (!getcwd(dbpath, MAXPATHLEN))
+ die("cannot get current directory.");
+ }
+ 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());
+ /*
+ * teach gctags(1) where is dbpath.
+ */
+ sprintf(env, "GTAGSDBPATH=%s", dbpath);
+ putenv(env);
+ /*
+ * incremental update.
+ */
+ if (iflag && test("f", makepath(dbpath, dbname(GTAGS))) &&
+ test("f", makepath(dbpath, dbname(GRTAGS))))
+ {
+ (void)incremental(dbpath);
+ exit(0);
+ }
+ if (iflag && vflag)
+ fprintf(stderr, " GTAGS and GRTAGS not found. -i option ignored.\n");
+ /*
+ * create GTAGS, GRTAGS and GSYMS
+ */
+ for (db = GTAGS; db < GTAGLIM; db++) {
+ if (oflag && db == GSYMS)
+ continue;
+ if (vflag)
+ fprintf(stderr, "[%s] Creating '%s'.\n", current(), dbname(db));
+ createtags(dbpath, db);
+ }
+
+ if (vflag)
+ fprintf(stderr, "[%s] Done.\n", current());
+ exit(0);
+}
+/*
+ * incremental: incremental update
+ *
+ * i) dbpath dbpath directory
+ * r) 0: not updated, 1: updated
+ */
+int
+incremental(dbpath)
+char *dbpath;
+{
+ struct stat sb;
+ time_t gtags_mtime;
+ int updated = 0;
+ char *path;
+ int db;
+
+ if (vflag) {
+ fprintf(stderr, " Tag found in '%s'.\n", dbpath);
+ fprintf(stderr, " Incremental update.\n");
+ }
+ /*
+ * get modified time of GTAGS.
+ */
+ path = makepath(dbpath, dbname(GTAGS));
+ if (stat(path, &sb) < 0)
+ die1("stat failed '%s'.", path);
+ gtags_mtime = sb.st_mtime;
+
+ for (findopen(); path = findread(NULL); ) {
+ if (stat(path, &sb) < 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");
+ }
+ }
+ findclose();
+ 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");
+ }
+ return updated;
+}
+/*
+ * tagadd: add records which has specified path.
+ *
+ * i) db 0: GTAGS, 1: GRTAGS, 2: GSYMS
+ * i) path source file
+ */
+void
+tagadd(db, path)
+int db;
+char *path;
+{
+ char *tagline, *p, *q;
+ char key[IDENTLEN+1];
+ FILE *ip;
+
+ 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)) {
+ p = tagline;
+ q = key;
+ while (*p && !isspace(*p))
+ *q++ = *p++;
+ *q = 0;
+ tagput(key, tagline);
+ }
+ pclose(ip);
+}
+/*
+ * createtags: create tags file
+ *
+ * i) dbpath dbpath directory
+ * i) db GTAGS, GRTAGS, GSYMS
+ */
+void
+createtags(dbpath, db)
+char *dbpath;
+int db;
+{
+ char *path;
+
+ /*
+ * GTAGS needed to make GRTAGS.
+ */
+ if (db == GRTAGS)
+ lookupopen(dbpath);
+ tagopen(dbpath, db, 1);
+ for (findopen(); path = findread(NULL); ) {
+ /*
+ * GRTAGS and GSYMS doesn't treat asembler.
+ */
+ if (db != GTAGS) {
+ char *p = path + strlen(path) - 1;
+ if ((*p == 's' || *p == 'S') && *(p - 1) == '.')
+ continue;
+ }
+ if (vflag)
+ fprintf(stderr, " extracting tags of %s.\n", path);
+ tagadd(db, path);
+ }
+ findclose();
+ tagclose();
+ if (db == GRTAGS)
+ lookupclose();
+}
+/*
+ * current: current date and time
+ *
+ * r) date and time
+ */
+#include <time.h>
+char *
+current()
+{
+ static char buf[80];
+ time_t tval;
+
+ if (time(&tval) == -1)
+ die("cannot get current time.");
+ (void)strftime(buf, sizeof(buf), "%+", localtime(&tval));
+
+ return buf;
+}
OpenPOWER on IntegriCloud