📄 gctags.c
字号:
/* * Copyright (c) 1998, 1999, 2000, 2001, 2002, 2003, 2005 * Tama Communications Corporation * * This file is part of GNU GLOBAL. * * GNU GLOBAL is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2, or (at your option) * any later version. * * GNU GLOBAL is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. */#ifdef HAVE_CONFIG_H#include <config.h>#endif#ifdef HAVE_LIMITS_H#include <limits.h>#endif#include <stdio.h>#ifdef STDC_HEADERS#include <stdlib.h>#endif#ifdef HAVE_STRING_H#include <string.h>#else#include <strings.h>#endif#ifdef HAVE_UNISTD_H#include <unistd.h>#endif#include "getopt.h"#include "global.h"#include "gctags.h"#include "const.h"int main(int, char **);static void usage(void);static void help(void);struct words { const char *name; int val;};struct words *words;static int tablesize;static char *langmap;int bflag; /* -b: force level 1 block start */int dflag; /* -d: treat #define with no argument */int eflag; /* -e: force level 1 block end */int nflag; /* -n: doen't print tag */int rflag; /* -r: function reference */int sflag; /* -s: collect symbols */int tflag; /* -t: treat typedefs, structs, unions, and enums. */int wflag; /* -w: warning message */int vflag; /* -v: verbose mode */int do_check;int show_version;int show_help;int debug;/*----------------------------------------------------------------------*//* Parser switch *//*----------------------------------------------------------------------*//* * This is the linkage section of each parsers. * If you want to support new language, you must define parser procedure * which requires file name as an argument. */struct lang_entry { const char *lang_name; void (*parser)(const char *); /* parser procedure */};/* * The first entry is default language. */static struct lang_entry lang_switch[] = { /* lang_name parser_proc */ {"c", C}, /* DEFAULT */ {"yacc", yacc}, {"cpp", Cpp}, {"java", java}, {"php", php}, {"asm", assembler}};#define DEFAULT_ENTRY &lang_switch[0]/* * get language entry. * * i) lang language name (NULL means 'not specified'.) * r) language entry */static struct lang_entry *get_lang_entry(lang) const char *lang;{ int i, size = sizeof(lang_switch) / sizeof(struct lang_entry); /* * if language not specified, it assumes default language. */ if (lang == NULL) return DEFAULT_ENTRY; for (i = 0; i < size; i++) if (!strcmp(lang, lang_switch[i].lang_name)) return &lang_switch[i]; /* * if specified language not found, it assumes default language. */ return DEFAULT_ENTRY;}static voidusage(void){ fputs(usage_const, stderr); exit(2);}static voidhelp(void){ fputs(usage_const, stdout); fputs(help_const, stdout); exit(0);}static struct option const long_options[] = { {"begin-block", no_argument, NULL, 'b'}, {"check", no_argument, &do_check, 1}, {"define", no_argument, NULL, 'd'}, {"end-block", no_argument, NULL, 'e'}, {"no-tags", no_argument, NULL, 'n'}, {"reference", no_argument, NULL, 'r'}, {"symbol", no_argument, NULL, 's'}, {"typedef", no_argument, NULL, 't'}, {"verbose", no_argument, NULL, 'v'}, {"warning", no_argument, NULL, 'w'}, /* long name only */ {"debug", no_argument, &debug, 1}, {"langmap", required_argument, NULL, 0}, {"version", no_argument, &show_version, 1}, {"help", no_argument, &show_help, 1}, { 0 }};intmain(argc, argv) int argc; char **argv;{ char *p; int optchar; int option_index = 0; while ((optchar = getopt_long(argc, argv, "bdenrstvw", long_options, &option_index)) != EOF) { switch(optchar) { case 0: p = (char *)long_options[option_index].name; if (!strcmp(p, "langmap")) langmap = optarg; break; case 'b': bflag++; break; case 'd': dflag++; break; case 'e': eflag++; break; case 'n': nflag++; break; case 'r': rflag++; sflag = 0; break; case 's': sflag++; rflag = 0; break; case 't': tflag++; break; case 'v': vflag++; break; case 'w': wflag++; break; default: usage(); /* NOTREACHED */ } } if (show_version) version(NULL, vflag); else if (show_help) help(); else if (do_check) { fprintf(stdout, "Part of GLOBAL\n"); exit(0); } /* * If langmap is not passed as argument, environment variable * GTAGSLANGMAP should be checked. Gtags(1) call gtags-parser * in this method. */ if (langmap == NULL) langmap = getenv("GTAGSLANGMAP"); if (langmap == NULL) langmap = DEFAULTLANGMAP; setup_langmap(langmap); argc -= optind; argv += optind; if (argc < 1) usage(); if (getenv("GTAGSWARNING")) wflag++; /* * This is a hack for FreeBSD. * In the near future, it will be removed. */#ifdef __DJGPP__ if (test("r", NOTFUNCTION) || test("r", DOS_NOTFUNCTION))#else if (test("r", NOTFUNCTION))#endif { FILE *ip; STRBUF *sb = strbuf_open(0); STRBUF *ib = strbuf_open(0); char *p; int i; if ((ip = fopen(NOTFUNCTION, "r")) == 0)#ifdef __DJGPP__ if ((ip = fopen(DOS_NOTFUNCTION, "r")) == 0)#endif die("'%s' cannot read.", NOTFUNCTION); for (tablesize = 0; (p = strbuf_fgets(ib, ip, STRBUF_NOCRLF)) != NULL; tablesize++) strbuf_puts0(sb, p); fclose(ip); if ((words = (struct words *)malloc(sizeof(struct words) * tablesize)) == NULL) die("short of memory."); /* * Don't free *p. */ p = (char *)malloc(strbuf_getlen(sb) + 1); if (p == NULL) die("short of memory."); memcpy(p, strbuf_value(sb), strbuf_getlen(sb) + 1); for (i = 0; i < tablesize; i++) { words[i].name = p; p += strlen(p) + 1; } qsort(words, tablesize, sizeof(struct words), cmp); strbuf_close(sb); strbuf_close(ib); } /* * pick up files and parse them. */ for (; argc > 0; argv++, argc--) { const char *lang, *suffix; struct lang_entry *ent; /* get suffix of the path. */ suffix = locatestring(argv[0], ".", MATCH_LAST); if (!suffix) continue; lang = decide_lang(suffix); if (lang == NULL) continue; if (vflag) fprintf(stderr, "suffix '%s' assumed language '%s'.\n", suffix, lang); /* * Select parser. * If lang == NULL then default parser is selected. */ ent = get_lang_entry(lang); /* * call language specific parser. */ ent->parser(argv[0]); } return 0;}intcmp(s1, s2) const void *s1, *s2;{ return strcmp(((struct words *)s1)->name, ((struct words *)s2)->name);}intisnotfunction(name) char *name;{ struct words tmp; struct words *result; if (words == NULL) return 0; tmp.name = name; result = (struct words *)bsearch(&tmp, words, tablesize, sizeof(struct words), cmp); return (result != NULL) ? 1 : 0;}voiddbg_print(level, s) int level; const char *s;{ if (!debug) return; fprintf(stderr, "[%04d]", lineno); for (; level > 0; level--) fprintf(stderr, " "); fprintf(stderr, "%s\n", s);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -