/* * makesearchpart: make search part * * @param[in] target $target * @return html */ static char * makesearchpart(const char *target) { STATIC_STRBUF(sb); strbuf_clear(sb); strbuf_puts(sb, header_begin); if (Fflag) strbuf_puts(sb, gen_href_begin(NULL, "search", normal_suffix, NULL)); strbuf_puts(sb, "SEARCH"); if (Fflag) strbuf_puts(sb, gen_href_end()); strbuf_puts_nl(sb, header_end); if (!target) { strbuf_puts(sb, "Please input object name and select [Search]. POSIX's regular expression is allowed."); strbuf_puts_nl(sb, br); } strbuf_puts_nl(sb, gen_form_begin(target)); strbuf_puts_nl(sb, gen_input("pattern", NULL, NULL)); strbuf_puts_nl(sb, gen_input(NULL, "Search", "submit")); strbuf_puts(sb, gen_input(NULL, "Reset", "reset")); strbuf_puts_nl(sb, br); strbuf_puts(sb, gen_input_radio("type", "definition", 1, "Retrieve the definition place of the specified symbol.")); strbuf_puts_nl(sb, target ? "Def" : "Definition"); strbuf_puts(sb, gen_input_radio("type", "reference", 0, "Retrieve the reference place of the specified symbol.")); strbuf_puts_nl(sb, target ? "Ref" : "Reference"); strbuf_puts(sb, gen_input_radio("type", "symbol", 0, "Retrieve the place of the specified symbol is used.")); strbuf_puts_nl(sb, target ? "Sym" : "Other symbol"); strbuf_puts(sb, gen_input_radio("type", "path", 0, "Look for path name which matches to the specified pattern.")); strbuf_puts_nl(sb, target ? "Path" : "Path name"); if (enable_grep) { strbuf_puts(sb, gen_input_radio("type", "grep", 0, "Retrieve lines which matches to the specified pattern.")); strbuf_puts_nl(sb, target ? "Grep" : "Grep pattern"); } if (enable_idutils && test("f", makepath(dbpath, "ID", NULL))) { strbuf_puts(sb, gen_input_radio("type", "idutils", 0, "Retrieve lines which matches to the specified pattern using idutils(1).")); strbuf_puts_nl(sb, target ? "Id" : "Id pattern"); } strbuf_puts_nl(sb, br); strbuf_puts(sb, gen_input_checkbox("icase", NULL, "Ignore case distinctions in the pattern.")); strbuf_puts_nl(sb, target ? "Icase" : "Ignore case"); if (other_files) { strbuf_puts(sb, gen_input_checkbox("other", NULL, "Files other than the source code are also retrieved.")); strbuf_puts_nl(sb, target ? "Other" : "Other files"); } if (other_files && !target) { strbuf_puts_nl(sb, br); strbuf_puts(sb, "('Other files' is effective only to 'Path name'"); if (enable_grep) strbuf_puts(sb, " and 'Grep pattern'"); strbuf_puts_nl(sb, ".)"); } strbuf_puts_nl(sb, gen_form_end()); return strbuf_value(sb); }
/* * makedefineindex: make definition index (including alphabetic index) * * @param[in] file definition index file * @param[in] total definitions total * @param[out] defines @defines * Globals used (input): * tag cache XXX: should this be global output, not input? */ int makedefineindex(const char *file, int total, STRBUF *defines) { int count = 0; int alpha_count = 0; FILEOP *fileop_MAP = NULL, *fileop_DEFINES, *fileop_ALPHA = NULL; FILE *MAP = NULL; FILE *DEFINES, *STDOUT, *TAGS, *ALPHA = NULL; STRBUF *sb = strbuf_open(0); STRBUF *url = strbuf_open(0); /* Index link */ const char *target = (Fflag) ? "mains" : "_top"; const char *indexlink; const char *index_string = "Index Page"; char command[1024], buf[1024], alpha[32], alpha_f[32], *_; if (!aflag && !Fflag) indexlink = "mains"; else if (Fflag) indexlink = "../defines"; else indexlink = "../mains"; if (map_file) { fileop_MAP = open_output_file(makepath(distpath, "MAP", NULL), 0); MAP = get_descripter(fileop_MAP); } fileop_DEFINES = open_output_file(makepath(distpath, file, NULL), 0); DEFINES = get_descripter(fileop_DEFINES); fputs_nl(gen_page_begin(title_define_index, TOPDIR), DEFINES); fputs_nl(body_begin, DEFINES); fputs(header_begin, DEFINES); if (Fflag) fputs(gen_href_begin(NULL, "defines", normal_suffix, NULL), DEFINES); fputs(title_define_index, DEFINES); if (Fflag) fputs(gen_href_end(), DEFINES); fputs_nl(header_end, DEFINES); if (!aflag && !Fflag) { fputs(gen_href_begin_with_title(NULL, indexlink, normal_suffix, NULL, index_string), DEFINES); if (Iflag) fputs(gen_image(CURRENT, back_icon, ".."), DEFINES); else fputs("[..]", DEFINES); fputs_nl(gen_href_end(), DEFINES); } if (!aflag) { if (!no_order_list) fputs_nl(list_begin, DEFINES); } /* * map DEFINES to STDOUT. */ STDOUT = DEFINES; snprintf(command, sizeof(command), PQUOTE "%s -c" PQUOTE, quote_shell(global_path)); if ((TAGS = popen(command, "r")) == NULL) die("cannot execute '%s'.", command); alpha[0] = '\0'; while ((_ = strbuf_fgets(sb, TAGS, STRBUF_NOCRLF)) != NULL) { const char *tag, *line; char guide[1024], url_for_map[1024]; count++; tag = _; message(" [%d/%d] adding %s", count, total, tag); if (aflag && (alpha[0] == '\0' || !locatestring(tag, alpha, MATCH_AT_FIRST))) { const char *msg = (alpha_count == 1) ? "definition" : "definitions"; int c; if (alpha[0]) { char tmp[128]; snprintf(tmp, sizeof(tmp), "%d %s", alpha_count, msg); strbuf_puts(defines, gen_href_begin_with_title("defines", alpha_f, HTML, NULL, tmp)); strbuf_sprintf(defines, "[%s]", alpha); strbuf_puts_nl(defines, gen_href_end()); alpha_count = 0; if (!no_order_list) fputs_nl(list_end, ALPHA); else fputs_nl(br, ALPHA); fputs(gen_href_begin_with_title(NULL, indexlink, normal_suffix, NULL, index_string), ALPHA); if (Iflag) fputs(gen_image(PARENT, back_icon, ".."), ALPHA); else fputs("[..]", ALPHA); fputs_nl(gen_href_end(), ALPHA); fputs_nl(body_end, ALPHA); fputs_nl(gen_page_end(), ALPHA); close_file(fileop_ALPHA); html_count++; } /* * setup index char (for example, 'a' of '[a]'). * alpha is used for display. * alpha_f is used for part of path. */ c = (unsigned char)*tag; if (c > 127) { int i2 = *(tag + 1) & 0xff; /* * for multi-byte(EUC) code. */ alpha[0] = *tag; alpha[1] = *(tag + 1); alpha[2] = '\0'; snprintf(alpha_f, sizeof(alpha_f), "%03d%03d", c, i2); } else if (isalpha(c) || c == '_') { alpha[0] = *tag; alpha[1] = '\0'; /* * for CD9660 or FAT file system */ if (islower(c)) { alpha_f[0] = 'l'; alpha_f[1] = *tag; alpha_f[2] = '\0'; } else { alpha_f[0] = *tag; alpha_f[1] = '\0'; } } else { alpha[0] = *tag; alpha[1] = '\0'; snprintf(alpha_f, sizeof(alpha_f), "%03d", c); } snprintf(buf, sizeof(buf), "%s/defines/%s.%s", distpath, alpha_f, HTML); fileop_ALPHA = open_output_file(buf, 0); ALPHA = get_descripter(fileop_ALPHA); snprintf(buf, sizeof(buf), "[%s]", alpha); fputs_nl(gen_page_begin(buf, SUBDIR), ALPHA); fputs_nl(body_begin, ALPHA); fprintf(ALPHA, "%s[%s]%s\n", header_begin, alpha, header_end); fputs(gen_href_begin_with_title(NULL, indexlink, normal_suffix, NULL, index_string), ALPHA); if (Iflag) fputs(gen_image(PARENT, back_icon, ".."), ALPHA); else fputs("[..]", ALPHA); fputs_nl(gen_href_end(), ALPHA); if (!no_order_list) fputs_nl(list_begin, ALPHA); else fprintf(ALPHA, "%s%s\n", br, br); STDOUT = ALPHA; } alpha_count++; /* * generating url for function definition. */ line = cache_get(GTAGS, tag); strbuf_reset(url); if (line == NULL) die("internal error in makedefineindex()."); /* * About the format of 'line', please see the head comment of cache.c. */ if (*line == ' ') { const char *fid = line + 1; const char *enumber = nextstring(fid); snprintf(url_for_map, sizeof(url_for_map), "%s/%s.%s", DEFS, fid, HTML); if (dynamic) { if (*action != '/' && aflag) strbuf_puts(url, "../"); strbuf_puts(url, action); strbuf_sprintf(url, "?pattern=%s%stype=definitions", tag, quote_amp); } else { if (aflag) strbuf_puts(url, "../"); strbuf_sprintf(url, "%s/%s.%s", DEFS, fid, HTML); } snprintf(guide, sizeof(guide), "Multiple defined in %s places.", enumber); } else { const char *lno = line; const char *fid = nextstring(line); const char *path = gpath_fid2path(fid, NULL); path += 2; /* remove './' */ snprintf(url_for_map, sizeof(url_for_map), "%s/%s.%s#L%s", SRCS, fid, HTML, lno); if (aflag) strbuf_puts(url, "../"); strbuf_sprintf(url, "%s/%s.%s#L%s", SRCS, fid, HTML, lno); snprintf(guide, sizeof(guide), "Defined at %s in %s.", lno, path); } if (!no_order_list) fputs(item_begin, STDOUT); fputs(gen_href_begin_with_title_target(NULL, strbuf_value(url), NULL, NULL, guide, target), STDOUT); fputs(tag, STDOUT); fputs(gen_href_end(), STDOUT); if (!no_order_list) fputs(item_end, STDOUT); else fputs(br, STDOUT); fputc('\n', STDOUT); if (map_file) fprintf(MAP, "%s\t%s\n", tag, url_for_map); } if (pclose(TAGS) != 0) die("terminated abnormally '%s' (errno = %d).", command, errno); if (aflag && alpha[0]) { char tmp[128]; const char *msg = (alpha_count == 1) ? "definition" : "definitions"; snprintf(tmp, sizeof(tmp), "%d %s", alpha_count, msg); strbuf_puts(defines, gen_href_begin_with_title("defines", alpha_f, HTML, NULL, tmp)); strbuf_sprintf(defines, "[%s]", alpha); strbuf_puts_nl(defines, gen_href_end()); if (!no_order_list) fputs_nl(list_end, ALPHA); else fputs_nl(br, ALPHA); fputs(gen_href_begin_with_title(NULL, indexlink, normal_suffix, NULL, index_string), ALPHA); if (Iflag) fputs(gen_image(PARENT, back_icon, ".."), ALPHA); else fputs("[..]", ALPHA); fputs_nl(gen_href_end(), ALPHA); fputs_nl(body_end, ALPHA); fputs_nl(gen_page_end(), ALPHA); close_file(fileop_ALPHA); html_count++; fputs(strbuf_value(defines), DEFINES); } if (!no_order_list && !aflag) fputs_nl(list_end, DEFINES); if (!aflag && !Fflag) { fputs(gen_href_begin_with_title(NULL, "mains", normal_suffix, NULL, index_string), DEFINES); if (Iflag) fputs(gen_image(CURRENT, back_icon, ".."), DEFINES); else fputs("[..]", DEFINES); fputs_nl(gen_href_end(), DEFINES); } fputs_nl(body_end, DEFINES); fputs_nl(gen_page_end(), DEFINES); close_file(fileop_DEFINES); html_count++; if (map_file) close_file(fileop_MAP); strbuf_close(sb); strbuf_close(url); return count; }
/* * makecflowindex: make call-tree based on cflow's output * * i) output output file name * i) cflow_file input file which is the output of Cflow with --format=posix */ int makecflowindex(const char *output, const char *cflow_file) { STRBUF *input = strbuf_open(0); FILE *ip, *op; char *cflow_posix, *p; const char *m0 = "Gave up making call-tree because of illegal POSIX cflow format."; const char *m1 = ""; const char *title = locatestring(output, "callee", MATCH_AT_FIRST) ? title_callee_tree : title_call_tree; int line = 0; int status = 0; #define ERROR do { warning("%s\n%s:%d %s.", m0, cflow_file, line, m1); status = -1; goto finish; } while(0) /* * If syntax error occured then stop the jobs and return error status. * Don't die() because htags has already done a lot of work. */ if ((ip = fopen(cflow_file, "r")) == NULL) { warning("cannot open cflow file '%s'.", cflow_file); return -1; } if ((op = fopen(makepath(distpath, output, NULL), "w")) == NULL) { warning("cannot create file '%s'.", output); fclose(ip); return -1; } fputs_nl(gen_page_begin(title, TOPDIR), op); fputs_nl(body_begin, op); fputs(header_begin, op); fputs(gen_href_begin_simple(output), op); /* fputs(gen_href_begin(NULL, "cflow", normal_suffix, NULL), op);*/ fputs(title, op); fputs(gen_href_end(), op); fputs_nl(header_end, op); fputs_nl(verbatim_begin, op); /* * Cflow's output format (with the --format=posix) * +---------------------------------------------------------------- * | 25 isregex: int (const char *s), <libutil/char.c 54>... * | 32 func: 10 * +---------------------------------------------------------------- * cflow_posix * v * 25 isregex: int ... , <libutil/char.c 54>... * ^ ^ ^ ^ * anchor name path lineno * * cflow_posix * v * 32 func: 10 * ^ ^ ^ * anchor name lineno */ while ((cflow_posix = strbuf_fgets(input, ip, STRBUF_NOCRLF)) != NULL) { char *anchor, *name, *path, *lineno; char *anchor_end, *name_end, *path_end, *lineno_end; anchor = name = path = lineno = anchor_end = name_end = path_end = lineno_end = NULL; line++; for (p = cflow_posix; *p && isspace(*p); p++) ; m1 = "line number at the head not found"; if (!*p || !isdigit(*p)) ERROR; anchor = p; /* anchor */ for (; *p && isdigit(*p); p++) ; if (!*p || !isspace(*p)) ERROR; anchor_end = p; /* seek to the function name */ for (; *p; p++) { /* skip special characters of HTML like '├'*/ if (*p == '&') { for (p++; *p && *p != ';'; p++) ; if (*p != ';') ERROR; } else if (isalpha(*p) || *p == '_') break; } m1 = "function name not found"; if (!*p || !isalpha(*p)) ERROR; name = p; /* name */ for (; *p && *p != ':'; p++) ; if (*p != ':') ERROR; name_end = p++; if (*p++ != ' ') ERROR; if (isdigit(*p)) { /* (1) name: 999 */ lineno = p; /* lineno */ for (; *p && isdigit(*p); p++) ; lineno_end = p; } else if (*p == '<' && *(p + 1) == '>') { /* (2) name: <> */ ; } else { /* (3) name: ... <path lineno> */ m1 = "<path lineno> not found"; for (; *p && *p != '<'; p++) ; if (!*p++) ERROR; path = p; m1 = "path not found"; for (; *p && !isspace(*p); p++) if (*p == '>') ERROR; if (!*p || *p != ' ') ERROR; path_end = p++; m1 = "lineno not found"; if (!isdigit(*p)) ERROR; lineno = p; for (; *p && isdigit(*p); p++) ; if (*p != '>') ERROR; lineno_end = p; } /* * print anchor */ fprintf(op, gen_name_number(atoi(anchor))); /* * print until name */ fwrite(cflow_posix, name - cflow_posix, 1, op); /* * print name */ if (path) { const char *fid = NULL; int path_save = *path_end; int lineno_save = *lineno_end; *path_end = *lineno_end = 0; if (test("f", path) && (fid = path2fid_readonly(path)) != NULL) fprintf(op, gen_href_begin(SRCS, fid, HTML, lineno)); else path = lineno = NULL; /* not to print </a> */ *path_end = path_save; *lineno_end = lineno_save; } else if (lineno) { int lineno_save = *lineno_end; *lineno_end = 0; fprintf(op, gen_href_begin(NULL, NULL, NULL, lineno)); *lineno_end = lineno_save; } fwrite(name, name_end - name, 1, op); if (path || lineno) fputs(gen_href_end(), op); /* * print the rest */ for (p = name_end; *p; p++) { if (*p == '<') fputs(quote_little, op); else if (*p == '>') fputs(quote_great, op); else fputc(*p, op); } fputc('\n', op); } finish: fputs_nl(verbatim_end, op); fputs_nl(body_end, op); fputs_nl(gen_page_end(), op); strbuf_close(input); fclose(ip); fclose(op); return status; }
/** * Generate list body. * * @NAME{ctags_x} with the @CODE{--encode-path=\" \\t\"} */ const char * gen_list_body(const char *srcdir, const char *ctags_x, const char *fid) /* virtually const */ { STATIC_STRBUF(sb); char path[MAXPATHLEN]; const char *p; SPLIT ptable; strbuf_clear(sb); if (split((char *)ctags_x, 4, &ptable) < 4) { recover(&ptable); die("too small number of parts in list_body().\n'%s'", ctags_x); } strlimcpy(path, decode_path(ptable.part[PART_PATH].start + 2), sizeof(path)); if (fid == NULL) fid = path2fid(path); if (table_list) { strbuf_puts(sb, current_row_begin); if (enable_xhtml) { strbuf_puts(sb, "<td class='tag'>"); strbuf_puts(sb, gen_href_begin(srcdir, fid, HTML, ptable.part[PART_LNO].start)); strbuf_puts(sb, ptable.part[PART_TAG].start); strbuf_puts(sb, gen_href_end()); strbuf_sprintf(sb, "</td><td class='line'>%s</td><td class='file'>%s</td><td class='code'>", ptable.part[PART_LNO].start, path); } else { strbuf_puts(sb, "<td nowrap='nowrap'>"); strbuf_puts(sb, gen_href_begin(srcdir, fid, HTML, ptable.part[PART_LNO].start)); strbuf_puts(sb, ptable.part[PART_TAG].start); strbuf_puts(sb, gen_href_end()); strbuf_sprintf(sb, "</td><td nowrap='nowrap' align='right'>%s</td>" "<td nowrap='nowrap' align='left'>%s</td><td nowrap='nowrap'>", ptable.part[PART_LNO].start, path); } for (p = ptable.part[PART_LINE].start; *p; p++) { unsigned char c = *p; if (c == '&') strbuf_puts(sb, quote_amp); else if (c == '<') strbuf_puts(sb, quote_little); else if (c == '>') strbuf_puts(sb, quote_great); else if (c == ' ') strbuf_puts(sb, quote_space); else if (c == '\t') { strbuf_puts(sb, quote_space); strbuf_puts(sb, quote_space); } else strbuf_putc(sb, c); } strbuf_puts(sb, "</td>"); strbuf_puts(sb, current_row_end); recover(&ptable); } else { /* print tag name with anchor */ strbuf_puts(sb, current_line_begin); strbuf_puts(sb, gen_href_begin(srcdir, fid, HTML, ptable.part[PART_LNO].start)); strbuf_puts(sb, ptable.part[PART_TAG].start); strbuf_puts(sb, gen_href_end()); recover(&ptable); /* print line number */ for (p = ptable.part[PART_TAG].end; p < ptable.part[PART_PATH].start; p++) strbuf_putc(sb, *p); /* print file name */ strbuf_puts(sb, path); /* print the rest */ for (p = ptable.part[PART_PATH].end; *p; p++) { unsigned char c = *p; if (c == '&') strbuf_puts(sb, quote_amp); else if (c == '<') strbuf_puts(sb, quote_little); else if (c == '>') strbuf_puts(sb, quote_great); else strbuf_putc(sb, c); } strbuf_puts(sb, current_line_end); } return strbuf_value(sb); }
/** * 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 */ }
/** * makefileindex: make file index. * * @param[in] file output file name * @param[out] a_files top level file index */ int makefileindex(const char *file, STRBUF *a_files) { STATIC_STRBUF(sb); FILE *filesop; int flags = REG_EXTENDED; /* * Basedir is a directory to which we are paying attention on each * occasion. It starts with ".", grows and shrink according to the * progress of processing. It isn't copied each every recursive call * not to waste the stack. */ char basedir[MAXPATHLEN]; /* * Initialize data. */ indexlink = (Fflag) ? "../files" : "../mains"; src_count = 0; gp = gfind_open(dbpath, NULL, other_files ? GPATH_BOTH : GPATH_SOURCE); /* * for collecting include files. */ if (w32) flags |= REG_ICASE; strbuf_clear(sb); strbuf_puts(sb, "\\.("); { const char *p = include_file_suffixes; int c; while ((c = (unsigned char)*p++) != '\0') { if (isregexchar(c)) strbuf_putc(sb, '\\'); else if (c == ',') c = '|'; strbuf_putc(sb, c); } } strbuf_puts(sb, ")$"); if (regcomp(&is_include_file, strbuf_value(sb), flags) != 0) die("cannot compile regular expression '%s'.", strbuf_value(sb)); /* * Write to files.html. */ if ((filesop = fopen(makepath(distpath, file, NULL), "w")) == NULL) die("cannot open file '%s'.", file); fputs_nl(gen_page_index_begin(title_file_index, jscode), filesop); fputs_nl(body_begin, filesop); fputs(header_begin, filesop); fputs(gen_href_begin(NULL, "files", normal_suffix, NULL), filesop); fputs(title_file_index, filesop); fputs(gen_href_end(), filesop); fputs_nl(header_end, filesop); if (tree_view) { fputs_nl(tree_control, filesop); fputs_nl(tree_loading, filesop); if (tree_view_type) { fprintf(filesop, tree_begin_using, tree_view_type); fputc('\n', filesop); } else { fputs_nl(tree_begin, filesop); } } else if (table_flist) fputs_nl(flist_begin, filesop); else if (!no_order_list) fputs_nl(list_begin, filesop); FILEMAP = NULL; if (filemap_file) { if (!(FILEMAP = fopen(makepath(distpath, "FILEMAP", NULL), "w"))) die("cannot open '%s'.", makepath(distpath, "FILEMAP", NULL)); } /* * print whole directory tree. */ files = a_files; strcpy(basedir, "."); (void)print_directory(0, basedir); if (tree_view) strbuf_puts(files, tree_end); if (filemap_file) fclose(FILEMAP); gfind_close(gp); regfree(&is_include_file); fputs(strbuf_value(files), filesop); if (tree_view) fputs_nl(tree_end, filesop); else if (table_flist) fputs_nl(flist_end, filesop); else if (!no_order_list) fputs_nl(list_end, filesop); fputs_nl(body_end, filesop); fputs_nl(gen_page_end(), filesop); fclose(filesop); html_count++; return src_count; }
/** * print directory header. * * @param[in] op file index * @param[in] level 1,2... * @param[in] dir directory name */ static void print_directory_header(FILE *op, int level, const char *dir) { STATIC_STRBUF(sb); const char *top = (Fflag && !tree_view) ? "../files" : "../mains"; if (level == 0) die("print_directory_header: internal error."); strbuf_clear(sb); strbuf_puts(sb, removedotslash(dir)); strbuf_putc(sb, '/'); fputs_nl(gen_page_begin(strbuf_value(sb), SUBDIR), op); fputs_nl(body_begin, op); strbuf_clear(sb); strbuf_sprintf(sb, "%s%sroot%s/", header_begin, gen_href_begin(NULL, top, normal_suffix, NULL), gen_href_end()); fputs(strbuf_value(sb), op); { char path[MAXPATHLEN]; char *p, *q; strlimcpy(path, dir, sizeof(path)); for (p = path + 1; p != NULL; p = strchr(p, '/')) { int save = 0; q = ++p; while (*q && *q != '/') q++; save = *q; if (*q == '/') *q = '\0'; if (save == '/') fputs(gen_href_begin(NULL, path2fid(path), HTML, NULL), op); fputs(p, op); if (save == '/') fputs(gen_href_end(), op); *q = save; fputc('/', op); } } fputs_nl(header_end, op); { char parentdir[MAXPATHLEN]; const char *suffix, *parent; (void)dirpart(dir, parentdir); if (level == 1) { parent = top; suffix = normal_suffix; } else { parent = path2fid(parentdir); suffix = HTML; } fputs(gen_href_begin_with_title(NULL, parent, suffix, NULL, "Parent Directory"), op); } if (Iflag) fputs(gen_image(PARENT, back_icon, ".."), op); else fputs("[..]", op); fputs_nl(gen_href_end(), op); if (table_flist) fputs_nl(flist_begin, op); else if (!no_order_list) fputs_nl(list_begin, op); else { fputs(br, op); fputs_nl(br, op); } }