Exemplo n.º 1
0
/*
 * Make duplicate object index.
 *
 * If referred tag is only one, direct link which points the tag is generated.
 * Else if two or more tag exists, indirect link which points the tag list
 * is generated.
 */
int
makedupindex(void)
{
	STRBUF *sb = strbuf_open(0);
	STRBUF *tmp = strbuf_open(0);
	STRBUF *command = strbuf_open(0);
	int definition_count = 0;
	char srcdir[MAXPATHLEN];
	int db;
	FILEOP *fileop = NULL;
	FILE *op = NULL;
	FILE *ip = NULL;

	snprintf(srcdir, sizeof(srcdir), "../%s", SRCS);
	for (db = GTAGS; db < GTAGLIM; db++) {
		const char *kind = kinds[db];
		const char *option = options[db];
		int writing = 0;
		int count = 0;
		int entry_count = 0;
		const char *ctags_xid, *ctags_x;
		char tag[IDENTLEN], prev[IDENTLEN], first_line[MAXBUFLEN];

		if (gtags_exist[db] == 0)
			continue;
		prev[0] = 0;
		first_line[0] = 0;
		/*
		 * construct command line.
		 */
		strbuf_reset(command);
		strbuf_sprintf(command, "%s -x%s --result=ctags-xid --encode-path=\" \t\" --nofilter=path", quote_shell(global_path), option);
		/*
		 * Optimization when the --dynamic option is specified.
		 */
		if (dynamic) {
			strbuf_puts(command, " --nosource");
			if (db != GSYMS)
				strbuf_puts(command, " --nofilter=sort");
		}
		strbuf_puts(command, " \".*\"");
		if ((ip = popen(strbuf_value(command), "r")) == NULL)
			die("cannot execute command '%s'.", strbuf_value(command));
		while ((ctags_xid = strbuf_fgets(sb, ip, STRBUF_NOCRLF)) != NULL) {
			char fid[MAXFIDLEN];

			ctags_x = parse_xid(ctags_xid, fid, NULL);
			/* tag name */
			(void)strcpy_withterm(tag, ctags_x, sizeof(tag), ' ');
			if (strcmp(prev, tag)) {
				count++;
				if (vflag)
					fprintf(stderr, " [%d] adding %s %s\n", count, kind, tag);
				if (writing) {
					if (!dynamic) {
						fputs_nl(gen_list_end(), op);
						fputs_nl(body_end, op);
						fputs_nl(gen_page_end(), op);
						close_file(fileop);
						html_count++;
					}
					writing = 0;
					/*
					 * cache record: " <fid>\0<entry number>\0"
					 */
					strbuf_reset(tmp);
					strbuf_putc(tmp, ' ');
					strbuf_putn(tmp, count - 1);
					strbuf_putc(tmp, '\0');
					strbuf_putn(tmp, entry_count);
					cache_put(db, prev, strbuf_value(tmp), strbuf_getlen(tmp) + 1);
				}				
				/* single entry */
				if (first_line[0]) {
					char fid[MAXFIDLEN];
					const char *ctags_x = parse_xid(first_line, fid, NULL);
					const char *lno = nextelement(ctags_x);

					strbuf_reset(tmp);
					strbuf_puts_withterm(tmp, lno, ' ');
					strbuf_putc(tmp, '\0');
					strbuf_puts(tmp, fid);
					cache_put(db, prev, strbuf_value(tmp), strbuf_getlen(tmp) + 1);
				}
				/*
				 * Chop the tail of the line. It is not important.
				 * strlimcpy(first_line, ctags_x, sizeof(first_line));
				 */
				strncpy(first_line, ctags_xid, sizeof(first_line));
				first_line[sizeof(first_line) - 1] = '\0';
				strlimcpy(prev, tag, sizeof(prev));
				entry_count = 0;
			} else {
				/* duplicate entry */
				if (first_line[0]) {
					char fid[MAXFIDLEN];
					const char *ctags_x = parse_xid(first_line, fid, NULL);

					if (!dynamic) {
						char path[MAXPATHLEN];

						snprintf(path, sizeof(path), "%s/%s/%d.%s", distpath, dirs[db], count, HTML);
						fileop = open_output_file(path, cflag);
						op = get_descripter(fileop);
						fputs_nl(gen_page_begin(tag, SUBDIR), op);
						fputs_nl(body_begin, op);
						fputs_nl(gen_list_begin(), op);
						fputs_nl(gen_list_body(srcdir, ctags_x, fid), op);
					}
					writing = 1;
					entry_count++;
					first_line[0] = 0;
				}
				if (!dynamic) {
					fputs_nl(gen_list_body(srcdir, ctags_x, fid), op);
				}
				entry_count++;
			}
		}
		if (db == GTAGS)
			definition_count = count;
		if (pclose(ip) != 0)
			die("'%s' failed.", strbuf_value(command));
		if (writing) {
			if (!dynamic) {
				fputs_nl(gen_list_end(), op);
				fputs_nl(body_end, op);
				fputs_nl(gen_page_end(), op);
				close_file(fileop);
				html_count++;
			}
			/*
			 * cache record: " <fid>\0<entry number>\0"
			 */
			strbuf_reset(tmp);
			strbuf_putc(tmp, ' ');
			strbuf_putn(tmp, count);
			strbuf_putc(tmp, '\0');
			strbuf_putn(tmp, entry_count);
			cache_put(db, prev, strbuf_value(tmp), strbuf_getlen(tmp) + 1);
		}
		if (first_line[0]) {
			char fid[MAXFIDLEN];
			const char *ctags_x = parse_xid(first_line, fid, NULL);
			const char *lno = nextelement(ctags_x);

			strbuf_reset(tmp);
			strbuf_puts_withterm(tmp, lno, ' ');
			strbuf_putc(tmp, '\0');
			strbuf_puts(tmp, fid);
			cache_put(db, prev, strbuf_value(tmp), strbuf_getlen(tmp) + 1);
		}
	}
	strbuf_close(sb);
	strbuf_close(tmp);
	strbuf_close(command);
	return definition_count;
}
Exemplo n.º 2
0
/**
 * anchor_load: load anchor table
 *
 *	@param[in]	path	path name
 */
void
anchor_load(const char *path)
{
	int db, current_fid;

	/* Get fid of the path */
	{
		const char *p = path2fid(path);
		if (p == NULL)
			die("anchor_load: internal error. file '%s' not found in GPATH.", path);
		current_fid = atoi(p);
	}
	FIRST = LAST = 0;
	end = CURRENT = NULL;

	if (vb == NULL)
		vb = varray_open(sizeof(struct anchor), 1000);
	else
		varray_reset(vb);

	for (db = GTAGS; db < GTAGLIM; db++) {
		XARGS *xp;
		char *ctags_xid;

		if ((xp = anchor_input[db]) == NULL)
			continue;
		/*
		 * Read from input stream until it reaches end of file
		 * or the line of another file appears.
		 */
		while ((ctags_xid = xargs_read(xp)) != NULL) {
			SPLIT ptable;
			struct anchor *a;
			int type, fid;
			const char *ctags_x = parse_xid(ctags_xid, NULL, &fid);

			/*
			 * It is the following file.
			 */
			if (current_fid != fid) {
				xargs_unread(xp);
				break;
			}
			if (split(ctags_x, 4, &ptable) < 4) {
				recover(&ptable);
				die("too small number of parts in anchor_load().\n'%s'", ctags_x);
			}
			if (db == GTAGS) {
				char *p = ptable.part[PART_LINE].start;

				for (; *p && isspace((unsigned char)*p); p++)
					;
				if (!*p) {
					recover(&ptable);
					die("The output of parser is illegal.\n%s", ctags_x);
				}
				/*
				 * Function header is applied only to the anchor whoes type is 'D'.
				 * (D: function, M: macro, T: type)
				 */
				type = 'T';
				if (*p == '#')
					type = 'M';
				else if (locatestring(p, "typedef", MATCH_AT_FIRST))
					type = 'T';
				else if ((p = locatestring(p, ptable.part[PART_TAG].start, MATCH_FIRST)) != NULL) {
					/* skip a tag and the following blanks */
					p += strlen(ptable.part[PART_TAG].start);
					for (; *p && isspace((unsigned char)*p); p++)
						;
					if (*p == '(')
						type = 'D';
				}
			}  else if (db == GRTAGS)
				type = 'R';
			else
				type = 'Y';
			/* allocate an entry */
			a = varray_append(vb);
			a->lineno = atoi(ptable.part[PART_LNO].start);
			a->type = type;
			a->done = 0;
			settag(a, ptable.part[PART_TAG].start);
			recover(&ptable);
		}
		if (ctags_xid == NULL) {
			xargs_close(anchor_input[db]);
			anchor_input[db] = NULL;
		}
	}
	if (vb->length == 0) {
		table = NULL;
	} else {
		int i, used = vb->length;
		/*
		 * Sort by lineno.
		 */
		table = varray_assign(vb, 0, 0);
		qsort(table, used, sizeof(struct anchor), cmp); 
		/*
		 * Setup some lineno.
		 */
		for (i = 0; i < used; i++)
			if (table[i].type == 'D')
				break;
		if (i < used)
			FIRST = table[i].lineno;
		for (i = used - 1; i >= 0; i--)
			if (table[i].type == 'D')
				break;
		if (i >= 0)
			LAST = table[i].lineno;
	}
	/*
	 * Setup loop range.
	 */
	start = table;
	curp = NULL;
	end = &table[vb->length];
	/* anchor_dump(stderr, 0);*/
}
Exemplo n.º 3
0
/**
 * makecommonpart: make a common part for "mains.html" and "index.html"
 *
 *	@param[in]	title
 *	@param[in]	defines
 *	@param[in]	files
 *	@return	index	common part
 */
static char *
makecommonpart(const char *title, const char *defines, const char *files)
{
	FILE *ip;
	STRBUF *sb = strbuf_open(0);
	STRBUF *ib = strbuf_open(0);
	char buf[MAXFILLEN];
	const char *tips = "Go to the GLOBAL project page.";
	const char *_, *item;

	strbuf_puts(sb, title_begin);
	strbuf_puts(sb, title);
	strbuf_puts_nl(sb, title_end);
	strbuf_puts_nl(sb, poweredby_begin);
	strbuf_sprintf(sb, "Last updated %s%s\n", now(), br);
	if (Iflag) {
		snprintf(buf, sizeof(buf), "Powered by GLOBAL-%s.", get_version());
		strbuf_puts(sb, gen_href_begin_with_title_target(NULL, www, NULL, NULL, tips,"_top"));
		strbuf_puts(sb, gen_image(CURRENT, "pglobe", buf));
		strbuf_puts(sb, gen_href_end());
		strbuf_puts(sb, br);
	} else {
		strbuf_sprintf(sb, "Powered by %sGLOBAL-%s%s.%s\n",
			gen_href_begin_with_title_target(NULL, www, NULL, NULL, tips, "_top"),
			get_version(),
			gen_href_end(),
			br);
	}
	strbuf_puts_nl(sb, poweredby_end);
	strbuf_puts_nl(sb, hr);
	/*
	 * Print items according to the value of variable 'item_order'.
	 */
	for (item = item_order; *item; item++) {
		switch (*item) {
		case 'c':
			if (caution) {
				strbuf_puts_nl(sb, caution_begin);
				strbuf_sprintf(sb, "<font size='+2' color='red'>CAUTION</font>%s\n", br);
				strbuf_sprintf(sb, "This hypertext consists of %d files.\n", html_count);
				strbuf_puts_nl(sb, "Please don't download the whole hypertext using a hypertext copy tool.");
				strbuf_puts_nl(sb, "Our network cannot afford such traffic.");
				strbuf_puts_nl(sb, "Instead, you can generate the same thing in your computer using");
				strbuf_puts(sb, gen_href_begin_with_title_target(NULL, www, NULL, NULL, NULL, "_top"));
				strbuf_puts(sb, "GLOBAL source code tag system");
				strbuf_puts_nl(sb, gen_href_end());
				strbuf_puts_nl(sb, "Thank you.");
				strbuf_puts_nl(sb, caution_end);
				strbuf_sprintf(sb, "\n%s\n", hr);
			}
			break;
		case 's':
			if (fflag) {
				strbuf_puts(sb, makesearchpart(NULL));
				strbuf_puts_nl(sb, hr);
			}
			break;
		case 't':
			if (call_file || callee_file) {
				strbuf_puts(sb, header_begin);
				if (call_file) {
					strbuf_puts(sb, gen_href_begin(NULL, "call", normal_suffix, NULL));
					strbuf_puts(sb, title_call_tree);
					strbuf_puts(sb, gen_href_end());
				}
				if (call_file && callee_file)
					strbuf_puts(sb, " / ");
				if (callee_file) {
					strbuf_puts(sb, gen_href_begin(NULL, "callee", normal_suffix, NULL));
					strbuf_puts(sb, title_callee_tree);
					strbuf_puts(sb, gen_href_end());
				}
				strbuf_puts_nl(sb, header_end);
				strbuf_puts_nl(sb, hr);
			}
			break;
		case 'm':
			strbuf_sprintf(sb, "%sMAINS%s\n", header_begin, header_end);

			snprintf(buf, sizeof(buf), PQUOTE "%s --result=ctags-xid --encode-path=\" \t\" --nofilter=path %s" PQUOTE, quote_shell(global_path), main_func);
			ip = popen(buf, "r");
			if (!ip)
				die("cannot execute '%s'.", buf);
			strbuf_puts_nl(sb, gen_list_begin());
			while ((_ = strbuf_fgets(ib, ip, STRBUF_NOCRLF)) != NULL) {
				char fid[MAXFIDLEN];
				const char *ctags_x = parse_xid(_, fid, NULL);

				strbuf_puts_nl(sb, gen_list_body(SRCS, ctags_x, fid));
			}
			strbuf_puts_nl(sb, gen_list_end());
			if (pclose(ip) != 0)
				die("terminated abnormally '%s' (errno = %d).", buf, errno);
			strbuf_puts_nl(sb, hr);
			break;
		case 'd':
			if (aflag && !Fflag) {
				strbuf_puts(sb, header_begin);
				strbuf_puts(sb, title_define_index);
				strbuf_puts_nl(sb, header_end);
				strbuf_puts(sb, defines);
			} else {
				strbuf_puts(sb, header_begin);
				strbuf_puts(sb, gen_href_begin(NULL, "defines", normal_suffix, NULL));
				strbuf_puts(sb, title_define_index);
				strbuf_puts(sb, gen_href_end());
				strbuf_puts_nl(sb, header_end);
			}
			strbuf_puts_nl(sb, hr);
			break;
		case 'f':
			if (Fflag) {
				strbuf_puts(sb, header_begin);
				strbuf_puts(sb, gen_href_begin(NULL, "files", normal_suffix, NULL));
				strbuf_puts(sb, title_file_index);
				strbuf_puts(sb, gen_href_end());
				strbuf_puts_nl(sb, header_end);
			} else {
				strbuf_puts(sb, header_begin);
				strbuf_puts(sb, title_file_index);
				strbuf_puts_nl(sb, header_end);
				if (tree_view) {
					strbuf_puts_nl(sb, tree_control);
					strbuf_puts_nl(sb, tree_loading);
					if (tree_view_type) {
						strbuf_sprintf(sb, tree_begin_using, tree_view_type);
						strbuf_putc(sb, '\n');
					} else {
						strbuf_puts_nl(sb, tree_begin);
					}
				} else if (table_flist)
					strbuf_puts_nl(sb, flist_begin);
				else if (!no_order_list)
					strbuf_puts_nl(sb, list_begin);
				strbuf_puts(sb, files);
				if (tree_view)
					strbuf_puts_nl(sb, tree_end);
				else if (table_flist)
					strbuf_puts_nl(sb, flist_end);
				else if (!no_order_list)
					strbuf_puts_nl(sb, list_end);
				else
					strbuf_puts_nl(sb, br);
			}
			strbuf_puts_nl(sb, hr);
			break;
		default:
			warning("unknown item '%c'. (Ignored)", *item);
			break;
		}
	}
	strbuf_close(ib);

	return strbuf_value(sb);
	/* doesn't close string buffer */
}