📄 ms2html.c
字号:
case 'c': r = getrune(); if (r == '\n') { sol = ignore_nl = 1; if (indirective) break; } else ungetrune(); return getnext(); /* escape backslash */ case 'e': return "\\"; /* font change */ case 'f': r = getrune(); switch(r){ case '(': str[0] = getrune(); str[1] = getrune(); str[2] = 0; token[0] = 0; if(strcmp("BI", str) == 0) return changefont(&bifont); else if(strcmp("CW", str) == 0) return changefont(&cwfont); else return changefont(nil); case '3': case 'B': return changefont(&bfont); case '2': case 'I': return changefont(&ifont); case '4': return changefont(&bifont); case '5': return changefont(&cwfont); case 'P': return changebackfont(); case 'R': default: return changefont(nil); } /* number register */ case 'n': r = getrune(); if (r == '(') /*)*/ { r = getrune(); if (r < 0) return nil; str[0] = r; r = getrune(); if (r < 0) return nil; str[1] = r; str[2] = 0; } else { str[0] = r; str[1] = 0; } pushstr(getnr(str)); return getnext(); /* font size */ case 's': r = getrune(); switch(r){ case '0': return changesize(0); case '-': r = getrune(); if (!isdigit(r)) return getnext(); return changesize(-(r - '0')); case '+': r = getrune(); if (!isdigit(r)) return getnext(); return changesize(r - '0'); } return getnext(); /* vertical movement */ case 'v': r = getrune(); if(r != '\''){ ungetrune(); return getnext(); } r = getrune(); if(r != '-') vert--; else vert++; while(r != '\'' && r != '\n') r = getrune(); if(r != '\'') ungetrune(); if(vert > 0) return "^"; return getnext(); /* horizontal line */ case 'l': r = getrune(); if(r != '\''){ ungetrune(); return "<HR>"; } while(getrune() != '\'') ; return "<HR>"; /* character height and slant */ case 'S': case 'H': r = getrune(); if(r != '\''){ ungetrune(); return "<HR>"; } while(getrune() != '\'') ; return getnext(); /* digit-width space */ case '0': return " "; /*for .if, .ie, .el */ case '{': return "\\{"; /*}*/ case '}': return ""; /* up and down */ case 'u': if (isdown) { isdown = 0; return "</sub>"; } isup = 1; return "<sup>"; case 'd': if (isup) { isup = 0; return "</sup>"; } isdown = 1; return "<sub>"; } break; case '&': if(msp >= 0 || strsp >= 0) return "&"; return "&"; case '<': if(msp >= 0 || strsp >= 0) return "<"; return "<"; case '>': if(msp >= 0 || strsp >= 0) return ">"; return ">"; } if (r < Runeself) { token[0] = r; token[1] = 0; } else { R = r; token[runetochar(token,&R)] = 0; } return token;}/* if arg0 is set, read up to (and expand) to the next whitespace, else to the end of line */char*copyline(char *p, char *e, int arg0){ int c; Rune r; char *p1; while((c = getrune()) == ' ' || c == '\t') ; for(indirective = 1; p < e; c = getrune()) { if (c < 0) goto done; switch(c) { case '\\': break; case '\n': if (arg0) ungetrune(); goto done; case ' ': case '\t': if (arg0) goto done; default: r = c; p += runetochar(p,&r); continue; } ungetrune(); p1 = getnext(); if (p1 == nil) goto done; if (*p1 == '\n') { if (arg0) ungetrune(); break; } while((*p = *p1++) && p < e) p++; }done: indirective = 0; *p++ = 0; return p;}char*copyarg(char *p, char *e, int *nullarg){ int c, quoted, last; Rune r; *nullarg = 0; quoted = 0; do{ c = getrune(); } while(c == ' ' || c == '\t'); if(c == '"'){ quoted = 1; *nullarg = 1; c = getrune(); } if(c == '\n') goto done; last = 0; for(; p < e; c = getrune()) { if (c < 0) break; switch(c) { case '\n': ungetrune(); goto done; case '\\': r = c; p += runetochar(p,&r); if(last == '\\') r = 0; break; case ' ': case '\t': if(!quoted && last != '\\') goto done; r = c; p += runetochar(p,&r); break; case '"': if(quoted && last != '\\') goto done; r = c; p += runetochar(p,&r); break; default: r = c; p += runetochar(p,&r); break; } last = r; }done: *p++ = 0; return p;}intparseargs(char *p, char *e, char **argv){ int argc; char *np; int nullarg; indirective = 1; *p++ = 0; for(argc = 1; argc < Narg; argc++){ np = copyarg(p, e, &nullarg); if(nullarg==0 && np == p+1) break; argv[argc] = p; p = np; } argv[argc] = nil; indirective = 0; return argc;}voiddodirective(void){ char *p, *e; Goobie *g; Goobieif *gif; char line[Nline], *line1; int i, argc; char *argv[Narg]; Mstack *m; /* read line, translate special bytes */ e = line + sizeof(line) - UTFmax - 1; line1 = copyline(line, e, 1); if (!line[0]) return; argv[0] = line; /* first look through user defined macros */ p = getmacro(argv[0]); if(p != nil){ if(msp == Maxmstack-1){ fprint(2, "ms2html: macro stack overflow\n"); return; } argc = parseargs(line1, e, argv); m = &mstack[++msp]; m->ptr = p; memset(m->argv, 0, sizeof(m->argv)); for(i = 0; i < argc; i++) m->argv[i] = strdup(argv[i]); return; } /* check for .if or .ie */ for(gif = gtabif; gif->name; gif++) if(strcmp(gif->name, argv[0]) == 0){ (*gif->f)(line1, e); return; } argc = parseargs(line1, e, argv); /* try standard ms macros */ for(g = gtab; g->name; g++) if(strcmp(g->name, argv[0]) == 0){ (*g->f)(argc, argv); return; } if(debug) fprint(2, "stdin %d(%s:%d): unknown directive %s\n", ssp->lno, ssp->filename, ssp->rlno, line);}voidprintarg(char *a){ char *e, *p; e = a + strlen(a); pushstr(a); while(strsp >= 0 && strstack[strsp] >= a && strstack[strsp] < e){ p = getnext(); if(p == nil) return; Bprint(&bout, "%s", p); }}voidprintargs(int argc, char **argv){ argc--; argv++; while(--argc > 0){ printarg(*argv++); Bprint(&bout, " "); } if(argc == 0) printarg(*argv);}voiddohangingdt(void){ switch(hangingdt){ case 3: hangingdt--; break; case 2: Bprint(&bout, "<dd>"); hangingdt = 0; break; }}voiddohangingau(void){ if(hangingau == 0) return; Bprint(&bout, "</I></DL>\n"); hangingau = 0;}voiddohanginghead(void){ if(hanginghead == 0) return; Bprint(&bout, "</H%d>\n", hanginghead); hanginghead = 0;}/* * convert a man page to html and output */voiddoconvert(void){ char c, *p; Tm *t; pushsrc(nil); sol = 1; Bprint(&bout, "<html>\n"); Bflush(&bout); for(;;){ p = getnext(); if(p == nil) break; c = *p; if(c == '.' && sol){ dodirective(); dohangingdt(); ssp->lno++; ssp->rlno++; sol = 1; } else if(c == '\n'){ if (ignore_nl) ignore_nl = 0; else { if(hangingau) Bprint(&bout, "<br>\n"); else Bprint(&bout, "%s", p); dohangingdt(); } ssp->lno++; ssp->rlno++; sol = 1; } else{ Bprint(&bout, "%s", p); ignore_nl = sol = 0; } } dohanginghead(); dohangingdt(); closel(); if(fsp >= 0 && fstack[fsp]) Bprint(&bout, "%s", fstack[fsp]->end); Bprint(&bout, "<br> <br>\n"); Bprint(&bout, "<A href=http://www.lucent.com/copyright.html>\n"); t = localtime(time(nil)); Bprint(&bout, "Copyright</A> © %d Lucent Technologies Inc. All rights reserved.\n", t->year+1900); Bprint(&bout, "</body></html>\n");}static voidusage(void){ sysfatal("usage: ms2html [-q] [-b basename] [-d '$$'] [-t title]\n");}voidmain(int argc, char **argv){ quiet = 1; ARGBEGIN { case 't': title = EARGF(usage()); break; case 'b': basename = EARGF(usage()); break; case 'q': quiet = 0; break; case 'd': delim = EARGF(usage()); break; case '?': default: usage(); } ARGEND; Binit(&bout, 1, OWRITE); ds("R", "®"); doconvert(); exits(nil);}voidg_notyet(int, char **argv){ fprint(2, "ms2html: .%s not yet supported\n", argv[0]);}voidg_ignore(int, char **argv){ if(quiet) return; fprint(2, "ms2html: line %d: ignoring .%s\n", ssp->lno, argv[0]);}voidg_PP(int, char**){ dohanginghead(); closel(); closefont(); Bprint(&bout, "<P>\n"); paragraph = 1;}voidg_LP(int, char**){ dohanginghead(); closel(); closefont(); Bprint(&bout, "<br> <br>\n");}/* close a list */voidclosel(void){ g_P2(1, nil); dohangingau(); if(paragraph){ Bprint(&bout, "</P>\n"); paragraph = 0; } switch(list){ case Lordered: Bprint(&bout, "</ol>\n"); break; case Lunordered: Bprint(&bout, "</ul>\n"); break; case Lother: case Ldef: Bprint(&bout, "</dl>\n"); break; } list = 0; }voidg_IP(int argc, char **argv){ switch(list){ default: closel(); if(argc > 1){ if(strcmp(argv[1], "1") == 0){ list = Lordered; listnum = 1; Bprint(&bout, "<OL>\n"); } else if(strcmp(argv[1], "\\(bu") == 0){ list = Lunordered; Bprint(&bout, "<UL>\n"); } else { list = Lother; Bprint(&bout, "<DL COMPACT>\n"); } } else { list = Lother; Bprint(&bout, "<DL>\n"); } break; case Lother: case Lordered: case Lunordered: break; } switch(list){ case Lother: Bprint(&bout, "<DT>"); if(argc > 1) printarg(argv[1]); else Bprint(&bout, "<DT> "); Bprint(&bout, "<DD>\n"); break; case Lordered: case Lunordered: Bprint(&bout, "<LI>\n"); break; }}/* * .5i is one <DL><DT><DD> */voidg_in(int argc, char **argv){ float f; int delta, x; char *p; f = indent/0.5; delta = f; if(argc <= 1){ indent = 0.0; } else { f = strtod(argv[1], &p); switch(*p){ case 'i': break; case 'c': f = f / 2.54; break; case 'P': f = f / 6; break; default: case 'u': case 'm': f = f * (12 / 72); break; case 'n': f = f * (6 / 72); break; case 'p': f = f / 72.0; break; } switch(argv[1][0]){ case '+': case '-': indent += f; break; default: indent = f; break; } } if(indent < 0.0) indent = 0.0; f = (indent/0.5); x = f; delta = x - delta; while(delta < 0){ Bprint(&bout, "</DL>\n"); delta++; } while(delta > 0){ Bprint(&bout, "<DL><DT><DD>\n"); delta--; }}voidg_HP(int, char**){ switch(list){ default: closel(); list = Ldef; hangingdt = 1; Bprint(&bout, "<DL><DT>\n"); break; case Ldef: if(hangingdt) Bprint(&bout, "<DD>"); Bprint(&bout, "<DT>"); hangingdt = 1; break; }}voidg_SH(int, char**){ dohanginghead(); dohangingcenter(); closel(); closefont(); Bprint(&bout, "<H%d>", HH); hanginghead = HH;}voidg_NH(int argc, char **argv){ int i, level; closel(); closefont(); dohangingcenter(); if(argc == 1) level = 0; else { level = atoi(argv[1])-1; if(level < 0 || level >= Maxnh) level = Maxnh - 1; } nh[level]++; Bprint(&bout, "<H%d>", HH); hanginghead = HH; Bprint(&bout, "%d", nh[0]); for(i = 1; i <= level; i++) Bprint(&bout, ".%d", nh[i]); Bprint(&bout, " "); for(i = level+1; i < Maxnh; i++) nh[i] = 0;}voidg_TL(int, char**){ char *p, *np; char name[128]; closefont(); if(!titleseen){ if(!title){ /* get base part of filename */ p = strrchr(ssp->filename, '/'); if(p == nil) p = ssp->filename; else p++; strncpy(name, p, sizeof(name)); name[sizeof(name)-1] = 0; /* dump any extensions */ np = strchr(name, '.'); if(np) *np = 0; title = p; } Bprint(&bout, "<title>\n"); Bprint(&bout, "%s\n", title); Bprint(&bout, "</title>\n"); Bprint(&bout, "<body BGCOLOR=\"#FFFFFF\" TEXT=\"#000000\" LINK=\"#0000FF\" VLINK=\"#330088\" ALINK=\"#FF0044\">\n"); titleseen = 1; } Bprint(&bout, "<center>"); hangingcenter = 1; Bprint(&bout, "<H%d>", 1); hanginghead = 1;}voiddohangingcenter(void){ if(hangingcenter){ Bprint(&bout, "</center>"); hangingcenter = 1; }}voidg_AU(int, char**){ closel(); dohanginghead(); Bprint(&bout, "<DL><DD><I>"); hangingau = 1;}voidpushfont(Font *f){ if(fsp == Maxfsp) return; if(fsp >= 0 && fstack[fsp]) Bprint(&bout, "%s", fstack[fsp]->end); if(f != nil) Bprint(&bout, "%s", f->start); fstack[++fsp] = f;}voidpopfont(void){ if(fsp >= 0){ if(fstack[fsp]) Bprint(&bout, "%s", fstack[fsp]->end); fsp--; }}/* * for 3 args print arg3 \fxarg1\fP arg2 * for 2 args print arg1 \fxarg2\fP * for 1 args print \fxarg1\fP */voidfont(Font *f, int argc, char **argv){ if(argc == 1){ pushfont(nil); return; } if(argc > 3) printarg(argv[3]); pushfont(f); printarg(argv[1]); popfont(); if(argc > 2) printarg(argv[2]); Bprint(&bout, "\n");}voidclosefont(void){ if(fsp >= 0 && fstack[fsp]) Bprint(&bout, "%s", fstack[fsp]->end); fsp = -1;}voidg_B(int argc, char **argv){ font(&bfont, argc, argv);}voidg_R(int argc, char **argv){ font(nil, argc, argv);}voidg_BI(int argc, char **argv){ font(&bifont, argc, argv);}voidg_CW(int argc, char **argv){ font(&cwfont, argc, argv);}char*
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -