|
|
1.1 ! root 1: /* ! 2: * n1.c ! 3: * ! 4: * consume options, initialization, main loop, ! 5: * input routines, escape function calling ! 6: */ ! 7: ! 8: #include "tdef.h" ! 9: #include "fns.h" ! 10: #include "ext.h" ! 11: ! 12: #include <setjmp.h> ! 13: #include <time.h> ! 14: ! 15: char *Version = "Dec 1, 1992"; ! 16: ! 17: int TROFF = 1; /* assume we started in troff... */ ! 18: ! 19: jmp_buf sjbuf; ! 20: Offset ipl[NSO]; ! 21: ! 22: static FILE *ifile = stdin; ! 23: static FILE *ifl[NSO]; /* open input file pointers */ ! 24: char cfname[NSO+1][NS] = { "stdin" }; /* file name stack */ ! 25: int cfline[NSO]; /* input line count stack */ ! 26: char *progname; /* program name (troff or nroff) */ ! 27: ! 28: int trace = 0; /* tracing flag */ ! 29: #define TRMAC 01 /* trace macros */ ! 30: #define TRREQ 02 /* trace requests */ ! 31: ! 32: main(int argc, char *argv[]) ! 33: { ! 34: char *p; ! 35: int j; ! 36: Tchar i; ! 37: int eileenct; /* count to test for "Eileen's loop" */ ! 38: char buf[100]; ! 39: ! 40: progname = argv[0]; ! 41: if ((p = strrchr(progname, '/')) == NULL) ! 42: p = progname; ! 43: else ! 44: p++; ! 45: if (strcmp(p, "nroff") == 0) ! 46: TROFF = 0; ! 47: if ((p = getenv("TYPESETTER")) != 0) ! 48: strcpy(devname, p); ! 49: mrehash(); ! 50: nrehash(); ! 51: numtab[NL].val = -1; ! 52: ! 53: while (--argc > 0 && (++argv)[0][0] == '-') ! 54: switch (argv[0][1]) { ! 55: ! 56: case 'N': /* ought to be used first... */ ! 57: TROFF = 0; ! 58: break; ! 59: case 'd': ! 60: fprintf(stderr, "troff/nroff version %s\n", Version); ! 61: break; ! 62: case 'F': /* switch font tables from default */ ! 63: if (argv[0][2] != '\0') { ! 64: strcpy(termtab, &argv[0][2]); ! 65: strcpy(fontdir, &argv[0][2]); ! 66: } else { ! 67: argv++; argc--; ! 68: strcpy(termtab, argv[0]); ! 69: strcpy(fontdir, argv[0]); ! 70: } ! 71: break; ! 72: case 0: ! 73: goto start; ! 74: case 'i': ! 75: stdi++; ! 76: break; ! 77: case 'n': ! 78: npn = atoi(&argv[0][2]); ! 79: break; ! 80: case 'u': /* set emboldening amount */ ! 81: bdtab[3] = atoi(&argv[0][2]); ! 82: if (bdtab[3] < 0 || bdtab[3] > 50) ! 83: bdtab[3] = 0; ! 84: break; ! 85: case 's': ! 86: if (!(stop = atoi(&argv[0][2]))) ! 87: stop++; ! 88: break; ! 89: case 'r': ! 90: sprintf(buf + strlen(buf), ".nr %c %s\n", ! 91: argv[0][2], &argv[0][3]); ! 92: cpushback(buf); ! 93: /* dotnr(&argv[0][2], &argv[0][3]); */ ! 94: break; ! 95: case 'm': ! 96: if (mflg++ >= NMF) { ! 97: ERROR "Too many macro packages: %s", argv[0] WARN; ! 98: break; ! 99: } ! 100: strcpy(mfiles[nmfi], nextf); ! 101: strcat(mfiles[nmfi++], &argv[0][2]); ! 102: break; ! 103: case 'o': ! 104: getpn(&argv[0][2]); ! 105: break; ! 106: case 'T': ! 107: strcpy(devname, &argv[0][2]); ! 108: dotT++; ! 109: break; ! 110: case 'a': ! 111: ascii = 1; ! 112: break; ! 113: case 'h': ! 114: hflg++; ! 115: break; ! 116: case 'e': ! 117: eqflg++; ! 118: break; ! 119: case 'q': ! 120: quiet++; ! 121: save_tty(); ! 122: break; ! 123: default: ! 124: ERROR "unknown option %s", argv[0] WARN; ! 125: done(02); ! 126: } ! 127: ! 128: start: ! 129: argp = argv; ! 130: rargc = argc; ! 131: nmfi = 0; ! 132: init2(); ! 133: setjmp(sjbuf); ! 134: eileenct = 0; /*reset count for "Eileen's loop"*/ ! 135: /* this is a really sick bit of code */ ! 136: /* but i've never been able to figure out */ ! 137: /* how to fix it. */ ! 138: loop: ! 139: copyf = lgf = nb = nflush = nlflg = 0; ! 140: if (ip && rbf0(ip) == 0 && ejf && frame->pframe <= ejl) { ! 141: nflush++; ! 142: trap = 0; ! 143: eject((Stack *)0); ! 144: if (eileenct > 20) { ! 145: ERROR "job looping; check abuse of macros" WARN; ! 146: ejf = 0; /* try to break Eileen's loop */ ! 147: eileenct = 0; ! 148: } else ! 149: eileenct++; ! 150: goto loop; ! 151: } ! 152: eileenct = 0; /*reset count for "Eileen's loop"*/ ! 153: i = getch(); ! 154: if (pendt) ! 155: goto Lt; ! 156: if ((j = cbits(i)) == XPAR) { ! 157: copyf++; ! 158: tflg++; ! 159: while (cbits(i) != '\n') ! 160: pchar(i = getch()); ! 161: tflg = 0; ! 162: copyf--; ! 163: goto loop; ! 164: } ! 165: if (j == cc || j == c2) { ! 166: if (j == c2) ! 167: nb++; ! 168: copyf++; ! 169: while ((j = cbits(i = getch())) == ' ' || j == '\t') ! 170: ; ! 171: ch = i; ! 172: copyf--; ! 173: control(getrq(), 1); ! 174: flushi(); ! 175: goto loop; ! 176: } ! 177: Lt: ! 178: ch = i; ! 179: text(); ! 180: if (nlflg) ! 181: numtab[HP].val = 0; ! 182: goto loop; ! 183: } ! 184: ! 185: ! 186: ! 187: void init2(void) ! 188: { ! 189: int i; ! 190: char buf[100]; ! 191: ! 192: for (i = NTRTAB; --i; ) ! 193: trtab[i] = i; ! 194: trtab[UNPAD] = ' '; ! 195: iflg = 0; ! 196: obufp = obuf; ! 197: if (TROFF) ! 198: t_ptinit(); ! 199: else ! 200: n_ptinit(); ! 201: mchbits(); ! 202: cvtime(); ! 203: numtab[PID].val = getpid(); ! 204: olinep = oline; ! 205: numtab[HP].val = init = 0; ! 206: numtab[NL].val = -1; ! 207: nfo = 0; ! 208: copyf = raw = 0; ! 209: sprintf(buf, ".ds .T %s\n", devname); ! 210: cpushback(buf); ! 211: numtab[CD].val = -1; /* compensation */ ! 212: nx = mflg; ! 213: frame = stk = (Stack *)setbrk(STACKSIZE); ! 214: dip = &d[0]; ! 215: nxf = frame + 1; ! 216: for (i = 1; i < NEV; i++) /* propagate the environment */ ! 217: envcopy(&env[i], &env[0]); ! 218: blockinit(); ! 219: } ! 220: ! 221: void cvtime(void) ! 222: { ! 223: long tt; ! 224: struct tm *ltime; ! 225: ! 226: time(&tt); ! 227: ltime = localtime(&tt); ! 228: numtab[YR].val = ltime->tm_year; ! 229: numtab[MO].val = ltime->tm_mon + 1; /* troff uses 1..12 */ ! 230: numtab[DY].val = ltime->tm_mday; ! 231: numtab[DW].val = ltime->tm_wday + 1; /* troff uses 1..7 */ ! 232: } ! 233: ! 234: ! 235: ! 236: char errbuf[200]; ! 237: ! 238: void errprint(void) /* error message printer */ ! 239: { ! 240: fprintf(stderr, "%s: ", progname); ! 241: fputs(errbuf, stderr); ! 242: if (numtab[CD].val > 0) ! 243: fprintf(stderr, "; line %d, file %s", numtab[CD].val, cfname[ifi]); ! 244: fputs("\n", stderr); ! 245: stackdump(); ! 246: } ! 247: ! 248: ! 249: int control(int a, int b) ! 250: { ! 251: int j; ! 252: ! 253: if (a == 0 || (j = findmn(a)) == -1) ! 254: return(0); ! 255: if (contab[j].f == 0) { ! 256: if (trace & TRMAC) ! 257: fprintf(stderr, "invoke macro %s\n", unpair(a)); ! 258: nxf->nargs = 0; ! 259: if (b) ! 260: collect(); ! 261: flushi(); ! 262: return pushi(contab[j].mx, a); /* BUG??? all that matters is 0/!0 */ ! 263: } ! 264: if (b) { ! 265: if (trace & TRREQ) ! 266: fprintf(stderr, "invoke request %s\n", unpair(a)); ! 267: (*contab[j].f)(); ! 268: } ! 269: return(0); ! 270: } ! 271: ! 272: void casept(void) ! 273: { ! 274: skip(); ! 275: noscale++; ! 276: trace = atoi0(); ! 277: noscale = 0; ! 278: } ! 279: ! 280: ! 281: int getrq(void) ! 282: { ! 283: int i, j; ! 284: ! 285: if ((i = getach()) == 0 || (j = getach()) == 0) ! 286: goto rtn; ! 287: i = PAIR(i, j); ! 288: rtn: ! 289: return(i); ! 290: } ! 291: ! 292: /* ! 293: * table encodes some special characters, to speed up tests ! 294: * in getch, viz FLSS, RPT, f, \b, \n, fc, tabch, ldrch ! 295: */ ! 296: ! 297: char gchtab[NCHARS] = { ! 298: 000,004,000,000,010,000,000,000, /* fc, ldr */ ! 299: 001,002,001,000,001,000,000,000, /* \b, tab, nl, RPT */ ! 300: 000,000,000,000,000,000,000,000, ! 301: 000,001,000,001,000,000,000,000, /* FLSS, ESC */ ! 302: 000,000,000,000,000,000,000,000, ! 303: 000,000,000,000,000,000,000,000, ! 304: 000,000,000,000,000,000,000,000, ! 305: 000,000,000,000,000,000,000,000, ! 306: 000,000,000,000,000,000,000,000, ! 307: 000,000,000,000,000,000,000,000, ! 308: 000,000,000,000,000,000,000,000, ! 309: 000,000,000,000,000,000,000,000, ! 310: 000,000,000,000,000,000,001,000, /* f */ ! 311: 000,000,000,000,000,000,000,000, ! 312: 000,000,000,000,000,000,000,000, ! 313: 000,000,000,000,000,000,000,000, ! 314: }; ! 315: ! 316: int realcbits(Tchar c) /* return character bits, or MOTCH if motion */ ! 317: { ! 318: if (ismot(c)) ! 319: return MOTCH; ! 320: else ! 321: return c & 0xFFFF; ! 322: } ! 323: ! 324: Tchar getch(void) ! 325: { ! 326: int k; ! 327: Tchar i, j; ! 328: ! 329: g0: ! 330: if (ch) { ! 331: i = ch; ! 332: if (cbits(i) == '\n') ! 333: nlflg++; ! 334: ch = 0; ! 335: return(i); ! 336: } ! 337: ! 338: if (nlflg) ! 339: return('\n'); ! 340: i = getch0(); ! 341: if (ismot(i)) ! 342: return(i); ! 343: k = cbits(i); ! 344: if (k >= sizeof(gchtab)/sizeof(gchtab[0]) || gchtab[k] == 0) /* nothing special */ ! 345: return(i); ! 346: if (k != ESC) { ! 347: if (k == '\n') { ! 348: nlflg++; ! 349: if (ip == 0) ! 350: numtab[CD].val++; /* line number */ ! 351: return(k); ! 352: } ! 353: if (k == FLSS) { ! 354: copyf++; ! 355: raw++; ! 356: i = getch0(); ! 357: if (!fi) ! 358: flss = i; ! 359: copyf--; ! 360: raw--; ! 361: goto g0; ! 362: } ! 363: if (k == RPT) { ! 364: setrpt(); ! 365: goto g0; ! 366: } ! 367: if (!copyf) { ! 368: if (k == 'f' && lg && !lgf) { ! 369: i = getlg(i); ! 370: return(i); ! 371: } ! 372: if (k == fc || k == tabch || k == ldrch) { ! 373: if ((i = setfield(k)) == 0) ! 374: goto g0; ! 375: else ! 376: return(i); ! 377: } ! 378: if (k == '\b') { ! 379: i = makem(-width(' ' | chbits)); ! 380: return(i); ! 381: } ! 382: } ! 383: return(i); ! 384: } ! 385: ! 386: k = cbits(j = getch0()); ! 387: if (ismot(j)) ! 388: return(j); ! 389: ! 390: switch (k) { ! 391: case 'n': /* number register */ ! 392: setn(); ! 393: goto g0; ! 394: case '$': /* argument indicator */ ! 395: seta(); ! 396: goto g0; ! 397: case '*': /* string indicator */ ! 398: setstr(); ! 399: goto g0; ! 400: case '{': /* LEFT */ ! 401: i = LEFT; ! 402: goto gx; ! 403: case '}': /* RIGHT */ ! 404: i = RIGHT; ! 405: goto gx; ! 406: case '"': /* comment */ ! 407: while (cbits(i = getch0()) != '\n') ! 408: ; ! 409: nlflg++; ! 410: if (ip == 0) ! 411: numtab[CD].val++; ! 412: return(i); ! 413: ! 414: /* experiment: put it here instead of copy mode */ ! 415: case '(': /* special char name \(xx */ ! 416: case 'C': /* \C'...' */ ! 417: if ((i = setch(k)) == 0) ! 418: goto g0; ! 419: goto gx; ! 420: ! 421: case ESC: /* double backslash */ ! 422: i = eschar; ! 423: goto gx; ! 424: case 'e': /* printable version of current eschar */ ! 425: i = PRESC; ! 426: goto gx; ! 427: case '\n': /* concealed newline */ ! 428: goto g0; ! 429: case ' ': /* unpaddable space */ ! 430: i = UNPAD; ! 431: goto gx; ! 432: case '\'': /* \(aa */ ! 433: i = ACUTE; ! 434: goto gx; ! 435: case '`': /* \(ga */ ! 436: i = GRAVE; ! 437: goto gx; ! 438: case '_': /* \(ul */ ! 439: i = UNDERLINE; ! 440: goto gx; ! 441: case '-': /* current font minus */ ! 442: i = MINUS; ! 443: goto gx; ! 444: case '&': /* filler */ ! 445: i = FILLER; ! 446: goto gx; ! 447: case 'c': /* to be continued */ ! 448: i = CONT; ! 449: goto gx; ! 450: case '!': /* transparent indicator */ ! 451: i = XPAR; ! 452: goto gx; ! 453: case 't': /* tab */ ! 454: i = '\t'; ! 455: return(i); ! 456: case 'a': /* leader (SOH) */ ! 457: /* old: *pbp++ = LEADER; goto g0; */ ! 458: i = LEADER; ! 459: return i; ! 460: case '%': /* ohc */ ! 461: i = OHC; ! 462: return(i); ! 463: case 'g': /* return format of a number register */ ! 464: setaf(); /* should this really be in copy mode??? */ ! 465: goto g0; ! 466: case '.': /* . */ ! 467: i = '.'; ! 468: gx: ! 469: setsfbits(i, sfbits(j)); ! 470: return(i); ! 471: } ! 472: if (copyf) { ! 473: *pbp++ = j; ! 474: return(eschar); ! 475: } ! 476: switch (k) { ! 477: ! 478: case 'f': /* font indicator */ ! 479: setfont(0); ! 480: goto g0; ! 481: case 's': /* size indicator */ ! 482: setps(); ! 483: goto g0; ! 484: case 'v': /* vert mot */ ! 485: if (i = vmot()) { ! 486: return(i); ! 487: } ! 488: goto g0; ! 489: case 'h': /* horiz mot */ ! 490: if (i = hmot()) ! 491: return(i); ! 492: goto g0; ! 493: case '|': /* narrow space */ ! 494: if (NROFF) ! 495: goto g0; ! 496: return(makem((int)(EM)/6)); ! 497: case '^': /* half narrow space */ ! 498: if (NROFF) ! 499: goto g0; ! 500: return(makem((int)(EM)/12)); ! 501: case 'w': /* width function */ ! 502: setwd(); ! 503: goto g0; ! 504: case 'p': /* spread */ ! 505: spread++; ! 506: goto g0; ! 507: case 'N': /* absolute character number */ ! 508: if ((i = setabs()) == 0) ! 509: goto g0; ! 510: return i; ! 511: case 'H': /* character height */ ! 512: return(setht()); ! 513: case 'S': /* slant */ ! 514: return(setslant()); ! 515: case 'z': /* zero with char */ ! 516: return(setz()); ! 517: case 'l': /* hor line */ ! 518: setline(); ! 519: goto g0; ! 520: case 'L': /* vert line */ ! 521: setvline(); ! 522: goto g0; ! 523: case 'D': /* drawing function */ ! 524: setdraw(); ! 525: goto g0; ! 526: case 'X': /* \X'...' for copy through */ ! 527: setxon(); ! 528: goto g0; ! 529: case 'b': /* bracket */ ! 530: setbra(); ! 531: goto g0; ! 532: case 'o': /* overstrike */ ! 533: setov(); ! 534: goto g0; ! 535: case 'k': /* mark hor place */ ! 536: if ((k = findr(getsn())) != -1) { ! 537: numtab[k].val = numtab[HP].val; ! 538: } ! 539: goto g0; ! 540: case '0': /* number space */ ! 541: return(makem(width('0' | chbits))); ! 542: case 'x': /* extra line space */ ! 543: if (i = xlss()) ! 544: return(i); ! 545: goto g0; ! 546: case 'u': /* half em up */ ! 547: case 'r': /* full em up */ ! 548: case 'd': /* half em down */ ! 549: return(sethl(k)); ! 550: default: ! 551: return(j); ! 552: } ! 553: /* NOTREACHED */ ! 554: } ! 555: ! 556: void setxon(void) /* \X'...' for copy through */ ! 557: { ! 558: Tchar xbuf[NC]; ! 559: Tchar *i; ! 560: Tchar c; ! 561: int delim, k; ! 562: ! 563: if (ismot(c = getch())) ! 564: return; ! 565: delim = cbits(c); ! 566: i = xbuf; ! 567: *i++ = XON | chbits; ! 568: while ((k = cbits(c = getch())) != delim && k != '\n' && i < xbuf+NC-1) { ! 569: if (k == ' ') ! 570: setcbits(c, WORDSP); ! 571: *i++ = c | ZBIT; ! 572: } ! 573: *i++ = XOFF | chbits; ! 574: *i = 0; ! 575: pushback(xbuf); ! 576: } ! 577: ! 578: ! 579: char ifilt[32] = { 0, 001, 002, 003, 0, 005, 006, 007, 010, 011, 012 }; ! 580: ! 581: Tchar getch0(void) ! 582: { ! 583: int j; ! 584: Tchar i; ! 585: ! 586: again: ! 587: if (pbp > lastpbp) ! 588: i = *--pbp; ! 589: else if (ip) { ! 590: /* i = rbf(); */ ! 591: i = rbf0(ip); ! 592: if (i == 0) ! 593: i = rbf(); ! 594: else { ! 595: ++ip; ! 596: if (pastend(ip)) { ! 597: --ip; ! 598: rbf(); ! 599: } ! 600: } ! 601: } else { ! 602: if (donef || ndone) ! 603: done(0); ! 604: if (nx || 1) { /* BUG: was ibufp >= eibuf, so EOF test is wrong */ ! 605: if (nfo < 0) ! 606: ERROR "in getch0, nfo = %d", nfo WARN; ! 607: if (nfo == 0) { ! 608: g0: ! 609: if (nextfile()) { ! 610: if (ip) ! 611: goto again; ! 612: } ! 613: } ! 614: nx = 0; ! 615: if ((i = getc(ifile)) == EOF) ! 616: goto g0; ! 617: if (ip) ! 618: goto again; ! 619: } ! 620: g2: ! 621: if (i >= 040) /* zapped: && i < 0177 */ ! 622: goto g4; ! 623: i = ifilt[i]; ! 624: } ! 625: if (cbits(i) == IMP && !raw) ! 626: goto again; ! 627: if (i == 0 && !init && !raw) { /* zapped: || i == 0177 */ ! 628: goto again; ! 629: } ! 630: g4: ! 631: if (ismot(i)) ! 632: return i; ! 633: if (copyf == 0 && sfbits(i) == 0) ! 634: i |= chbits; ! 635: if (cbits(i) == eschar && !raw) ! 636: setcbits(i, ESC); ! 637: return(i); ! 638: } ! 639: ! 640: void pushback(Tchar *b) ! 641: { ! 642: Tchar *ob = b; ! 643: ! 644: while (*b++) ! 645: ; ! 646: b--; ! 647: while (b > ob && pbp < &pbbuf[NC-3]) ! 648: *pbp++ = *--b; ! 649: if (pbp >= &pbbuf[NC-3]) { ! 650: ERROR "pushback overflow" WARN; ! 651: done(2); ! 652: } ! 653: } ! 654: ! 655: void cpushback(char *b) ! 656: { ! 657: char *ob = b; ! 658: ! 659: while (*b++) ! 660: ; ! 661: b--; ! 662: while (b > ob && pbp < &pbbuf[NC-3]) ! 663: *pbp++ = *--b; ! 664: if (pbp >= &pbbuf[NC-3]) { ! 665: ERROR "cpushback overflow" WARN; ! 666: done(2); ! 667: } ! 668: } ! 669: ! 670: int nextfile(void) ! 671: { ! 672: char *p; ! 673: ! 674: n0: ! 675: if (ifile != stdin) ! 676: fclose(ifile); ! 677: if (ifi > 0 && !nx) { ! 678: if (popf()) ! 679: goto n0; /* popf error */ ! 680: return(1); /* popf ok */ ! 681: } ! 682: if (nx || nmfi < mflg) { ! 683: p = mfiles[nmfi++]; ! 684: if (*p != 0) ! 685: goto n1; ! 686: } ! 687: if (rargc-- <= 0) { ! 688: if ((nfo -= mflg) && !stdi) { ! 689: done(0); ! 690: } ! 691: nfo++; ! 692: numtab[CD].val = stdi = mflg = 0; ! 693: ifile = stdin; ! 694: strcpy(cfname[ifi], "stdin"); ! 695: return(0); ! 696: } ! 697: p = (argp++)[0]; ! 698: n1: ! 699: numtab[CD].val = 0; ! 700: if (p[0] == '-' && p[1] == 0) { ! 701: ifile = stdin; ! 702: strcpy(cfname[ifi], "stdin"); ! 703: } else if ((ifile = fopen(p, "r")) == NULL) { ! 704: ERROR "cannot open file %s", p WARN; ! 705: nfo -= mflg; ! 706: done(02); ! 707: } else ! 708: strcpy(cfname[ifi],p); ! 709: nfo++; ! 710: return(0); ! 711: } ! 712: ! 713: ! 714: popf(void) ! 715: { ! 716: --ifi; ! 717: if (ifi < 0) { ! 718: ERROR "popf went negative" WARN; ! 719: return 1; ! 720: } ! 721: numtab[CD].val = cfline[ifi]; /* restore line counter */ ! 722: ip = ipl[ifi]; /* input pointer */ ! 723: ifile = ifl[ifi]; /* input FILE * */ ! 724: return(0); ! 725: } ! 726: ! 727: ! 728: void flushi(void) ! 729: { ! 730: if (nflush) ! 731: return; ! 732: ch = 0; ! 733: copyf++; ! 734: while (!nlflg) { ! 735: if (donef && frame == stk) ! 736: break; ! 737: getch(); ! 738: } ! 739: copyf--; ! 740: } ! 741: ! 742: ! 743: getach(void) /* return ascii/alphabetic character */ ! 744: { ! 745: Tchar i; ! 746: int j; ! 747: ! 748: lgf++; ! 749: j = cbits(i = getch()); ! 750: if (ismot(i) || !isgraph(j)) { ! 751: ch = i; ! 752: j = 0; ! 753: } ! 754: lgf--; ! 755: return j; ! 756: } ! 757: ! 758: ! 759: void casenx(void) ! 760: { ! 761: lgf++; ! 762: skip(); ! 763: getname(); ! 764: nx++; ! 765: if (nmfi > 0) ! 766: nmfi--; ! 767: strcpy(mfiles[nmfi], nextf); ! 768: nextfile(); ! 769: nlflg++; ! 770: ip = 0; ! 771: pendt = 0; ! 772: frame = stk; ! 773: nxf = frame + 1; ! 774: } ! 775: ! 776: ! 777: getname(void) ! 778: { ! 779: int j, k; ! 780: Tchar i; ! 781: ! 782: lgf++; ! 783: for (k = 0; k < NS - 1; k++) { ! 784: j = getach(); ! 785: if (!j) ! 786: break; ! 787: nextf[k] = j; ! 788: } ! 789: nextf[k] = 0; ! 790: lgf--; ! 791: return(nextf[0]); ! 792: } ! 793: ! 794: ! 795: void caseso(void) ! 796: { ! 797: FILE *fp; ! 798: char *p, *q; ! 799: ! 800: lgf++; ! 801: nextf[0] = 0; ! 802: if (skip() || !getname() || (fp = fopen(nextf, "r")) == NULL || ifi >= NSO) { ! 803: ERROR "can't open file %s", nextf WARN; ! 804: done(02); ! 805: } ! 806: strcpy(cfname[ifi+1], nextf); ! 807: cfline[ifi] = numtab[CD].val; /*hold line counter*/ ! 808: numtab[CD].val = 0; ! 809: flushi(); ! 810: ifl[ifi] = ifile; ! 811: ifile = fp; ! 812: ipl[ifi] = ip; ! 813: ip = 0; ! 814: nx++; ! 815: nflush++; ! 816: ifi++; ! 817: } ! 818: ! 819: void caself(void) /* set line number and file */ ! 820: { ! 821: int n; ! 822: ! 823: if (skip()) ! 824: return; ! 825: n = atoi0(); ! 826: cfline[ifi] = numtab[CD].val = n - 2; ! 827: if (skip()) ! 828: return; ! 829: if (getname()) ! 830: strcpy(cfname[ifi], nextf); ! 831: } ! 832: ! 833: ! 834: void casecf(void) ! 835: { /* copy file without change */ ! 836: int fd, n; ! 837: char buf[1024]; ! 838: extern int hpos, esc, po; ! 839: ! 840: /* this may not make much sense in nroff... */ ! 841: ! 842: lgf++; ! 843: nextf[0] = 0; ! 844: if (skip() || !getname() || (fd = open(nextf, 0)) < 0) { ! 845: ERROR "can't open file %s", nextf WARN; ! 846: done(02); ! 847: } ! 848: lgf--; ! 849: ! 850: /* make it into a clean state, be sure that everything is out */ ! 851: tbreak(); ! 852: hpos = po; ! 853: esc = 0; ! 854: ptesc(); /* to left margin */ ! 855: esc = un; ! 856: ptesc(); ! 857: ptlead(); ! 858: ptps(); ! 859: ptfont(); ! 860: flusho(); ! 861: while ((n = read(fd, buf, sizeof buf)) > 0) ! 862: fwrite(buf, n, 1, ptid); ! 863: close(fd); ! 864: ptps(); ! 865: ptfont(); ! 866: } ! 867: ! 868: void getline(char *s, int n) /* get rest of input line into s */ ! 869: { ! 870: int i; ! 871: ! 872: lgf++; ! 873: copyf++; ! 874: skip(); ! 875: for (i = 0; i < n-1; i++) ! 876: if ((s[i] = cbits(getch())) == '\n' || s[i] == RIGHT) ! 877: break; ! 878: s[i] = 0; ! 879: copyf--; ! 880: lgf--; ! 881: } ! 882: ! 883: void casesy(void) /* call system */ ! 884: { ! 885: char sybuf[NTM]; ! 886: ! 887: getline(sybuf, NTM); ! 888: system(sybuf); ! 889: } ! 890: ! 891: ! 892: void getpn(char *a) ! 893: { ! 894: int n, neg; ! 895: ! 896: if (*a == 0) ! 897: return; ! 898: neg = 0; ! 899: for ( ; *a; a++) ! 900: switch (*a) { ! 901: case '+': ! 902: case ',': ! 903: continue; ! 904: case '-': ! 905: neg = 1; ! 906: continue; ! 907: default: ! 908: n = 0; ! 909: if (isdigit(*a)) { ! 910: do ! 911: n = 10 * n + *a++ - '0'; ! 912: while (isdigit(*a)); ! 913: a--; ! 914: } else ! 915: n = 9999; ! 916: *pnp++ = neg ? -n : n; ! 917: neg = 0; ! 918: if (pnp >= &pnlist[NPN-2]) { ! 919: ERROR "too many page numbers" WARN; ! 920: done3(-3); ! 921: } ! 922: } ! 923: if (neg) ! 924: *pnp++ = -9999; ! 925: *pnp = -INT_MAX; ! 926: print = 0; ! 927: pnp = pnlist; ! 928: if (*pnp != -INT_MAX) ! 929: chkpn(); ! 930: } ! 931: ! 932: ! 933: void setrpt(void) ! 934: { ! 935: Tchar i, j; ! 936: ! 937: copyf++; ! 938: raw++; ! 939: i = getch0(); ! 940: copyf--; ! 941: raw--; ! 942: if ((long) i < 0 || cbits(j = getch0()) == RPT) ! 943: return; ! 944: while (i > 0 && pbp < &pbbuf[NC-3]) { ! 945: i--; ! 946: *pbp++ = j; ! 947: } ! 948: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.