|
|
1.1 ! root 1: #ifndef lint ! 2: static char sccsid[] = "@(#)n4.c 4.1 6/7/82"; ! 3: #endif lint ! 4: ! 5: #include "tdef.h" ! 6: extern ! 7: #include "d.h" ! 8: extern ! 9: #include "v.h" ! 10: #ifdef NROFF ! 11: extern ! 12: #include "tw.h" ! 13: #endif ! 14: #include "sdef.h" ! 15: /* ! 16: troff4.c ! 17: ! 18: number registers, conversion, arithmetic ! 19: */ ! 20: ! 21: extern int inchar[LNSIZE], *pinchar; /* XXX */ ! 22: extern struct s *frame; ! 23: ! 24: extern int ascii; ! 25: extern int cbuf[NC]; ! 26: extern int *cp; ! 27: extern int r[NN]; ! 28: extern int *vlist; ! 29: extern int inc[NN]; ! 30: extern int fmt[NN]; ! 31: extern int ch; ! 32: extern int lgf; ! 33: extern int pl; ! 34: extern int lastl; ! 35: extern int ralss; ! 36: extern int totout; ! 37: extern int nrbits; ! 38: extern int nonumb; ! 39: extern int vflag; ! 40: extern int noscale; ! 41: extern int dfact; ! 42: extern int dfactd; ! 43: extern int po; ! 44: extern int nform; ! 45: extern int ll; ! 46: extern int in; ! 47: extern int font; ! 48: extern int bdtab[]; ! 49: extern int lss; ! 50: extern int pts; ! 51: extern int fi; ! 52: extern int res; ! 53: extern int cwidth; ! 54: extern int dotT; ! 55: extern int ev; ! 56: extern int ne; ! 57: extern int ad, admod; ! 58: extern int print; ! 59: extern int ls; ! 60: extern int nel, un; ! 61: extern int xxx; ! 62: int regcnt = NNAMES; ! 63: ! 64: setn() ! 65: { ! 66: register i,j; ! 67: int f; ! 68: ! 69: f = nform = 0; ! 70: if((i=getch() & CMASK) == '+')f = 1; ! 71: else if(i == '-')f = -1; ! 72: else ch = i; ! 73: if((i=getsn()) == 0)return; ! 74: if((i & 0177) == '.')switch(i>>BYTE){ ! 75: case 's': i = pts & 077; break; ! 76: case 'v': i = lss; break; ! 77: case 'f': i = font + 1; break; ! 78: case 'p': i = pl; break; ! 79: case 't': i = findt1(); break; ! 80: case 'o': i = po; break; ! 81: case 'l': i = ll; break; ! 82: case 'i': i = in; break; ! 83: case '$': i = frame->nargs; break; ! 84: case 'A': i = ascii; break; ! 85: case 'c': i = v.cd; break; ! 86: case 'n': i = lastl; break; ! 87: case 'a': i = ralss; break; ! 88: case 'h': i = dip->hnl; break; ! 89: case 'd': ! 90: if(dip != d)i = dip->dnl; else i = v.nl; ! 91: break; ! 92: case 'u': i = fi; break; ! 93: case 'j': i = ad + 2*admod; break; ! 94: case 'w': i = width(*(pinchar-1)); break; /* XXX */ ! 95: case 'x': i = nel; break; ! 96: case 'y': i = un; break; ! 97: case 'T': i = dotT; break; /*-Tterm used in nroff*/ ! 98: case 'V': i = VERT; break; ! 99: case 'H': i = HOR; break; ! 100: case 'k': i = ne; break; ! 101: case 'P': i = print; break; ! 102: case 'L': i = ls; break; ! 103: case 'R': i = NN - regcnt; break; ! 104: case 'z': i = dip->curd; ! 105: cbuf[0] = i & BMASK; ! 106: cbuf[1] = (i >> BYTE) & BMASK; ! 107: cbuf[2] = 0; ! 108: cp = cbuf; ! 109: return; ! 110: #ifndef NROFF ! 111: case 'b': i = bdtab[font]; break; ! 112: #endif ! 113: ! 114: default: ! 115: goto s0; ! 116: } ! 117: else{ ! 118: s0: ! 119: if((j=findr(i)) == -1)i = 0; ! 120: else{ ! 121: i = (vlist[j] = (vlist[j] + inc[j]*f)); ! 122: nform = fmt[j]; ! 123: } ! 124: } ! 125: setn1(i); ! 126: cp = cbuf; ! 127: } ! 128: setn1(i) ! 129: int i; ! 130: { ! 131: extern int wrc(); ! 132: ! 133: cp = cbuf; ! 134: nrbits = 0; ! 135: fnumb(i,wrc); ! 136: *cp = 0; ! 137: cp = cbuf; ! 138: } ! 139: findr(i) ! 140: int i; ! 141: { ! 142: register j; ! 143: static int numerr; ! 144: ! 145: if(i == 0)return(-1); ! 146: for(j=0;j<NN;j++){ ! 147: if(i == r[j])break; ! 148: } ! 149: if(j != NN)return(j); ! 150: for(j=0; j<NN; j++){ ! 151: if(r[j] == 0){ ! 152: r[j] = i; ! 153: regcnt++; ! 154: break; ! 155: } ! 156: } ! 157: if(j==NN){ ! 158: if(!numerr)prstrfl("Too many number registers.\n"); ! 159: if(++numerr > 1)done2(04); else edone(04); ! 160: } ! 161: return(j); ! 162: } ! 163: fnumb(i,f) ! 164: int i, (*f)(); ! 165: { ! 166: register j; ! 167: ! 168: j = 0; ! 169: if(i < 0){ ! 170: j = (*f)('-' | nrbits); ! 171: i = -i; ! 172: } ! 173: switch(nform){ ! 174: default: ! 175: case '1': ! 176: case 0: return(decml(i,f) + j); ! 177: case 'i': ! 178: case 'I': return(roman(i,f) + j); ! 179: case 'a': ! 180: case 'A': return(abc(i,f) + j); ! 181: } ! 182: } ! 183: decml(i,f) ! 184: int i, (*f)(); ! 185: { ! 186: register j,k; ! 187: ! 188: k = 0; ! 189: nform--; ! 190: if((j=i/10) || (nform > 0))k = decml(j,f); ! 191: return(k + (*f)((i%10 + '0') | nrbits)); ! 192: } ! 193: roman(i,f) ! 194: int i, (*f)(); ! 195: { ! 196: ! 197: if(!i)return((*f)('0' | nrbits)); ! 198: if(nform == 'i')return(roman0(i,f,"ixcmz","vldw")); ! 199: else return(roman0(i,f,"IXCMZ","VLDW")); ! 200: } ! 201: roman0(i,f,onesp,fivesp) ! 202: int i, (*f)(); ! 203: char *onesp, *fivesp; ! 204: { ! 205: register q, rem, k; ! 206: ! 207: k = 0; ! 208: if(!i)return(0); ! 209: k = roman0(i/10,f,onesp+1,fivesp+1); ! 210: q = (i=i%10)/5; ! 211: rem = i%5; ! 212: if(rem == 4){ ! 213: k += (*f)(*onesp | nrbits); ! 214: if(q)i = *(onesp+1); ! 215: else i = *fivesp; ! 216: return(k += (*f)(i | nrbits)); ! 217: } ! 218: if(q)k += (*f)(*fivesp | nrbits); ! 219: while(--rem >= 0) ! 220: k += (*f)(*onesp | nrbits); ! 221: return(k); ! 222: } ! 223: abc(i,f) ! 224: int i, (*f)(); ! 225: { ! 226: if(!i)return((*f)('0' | nrbits)); ! 227: else return(abc0(i-1,f)); ! 228: } ! 229: abc0(i,f) ! 230: int i, (*f)(); ! 231: { ! 232: register j, k; ! 233: ! 234: k = 0; ! 235: if(j=i/26)k = abc0(j-1,f); ! 236: return(k + (*f)((i%26 + nform) | nrbits)); ! 237: } ! 238: wrc(i) ! 239: int i; ! 240: { ! 241: if(cp >= &cbuf[NC])return(0); ! 242: *cp++ = i; ! 243: return(1); ! 244: } ! 245: atoi(){ ! 246: extern long atoi0(); ! 247: ! 248: return((int)atoi0()); ! 249: } ! 250: long atoi0() ! 251: { ! 252: register ii, k, cnt; ! 253: long i, acc; ! 254: extern long ckph(); ! 255: ! 256: i = 0; acc = 0; ! 257: nonumb = 0; ! 258: cnt = -1; ! 259: a0: ! 260: cnt++; ! 261: switch((ii=getch()) & CMASK){ ! 262: default: ! 263: ch = ii; ! 264: if(cnt)break; ! 265: case '+': ! 266: i = ckph(); ! 267: if(nonumb)break; ! 268: acc += i; ! 269: goto a0; ! 270: case '-': ! 271: i = ckph(); ! 272: if(nonumb)break; ! 273: acc -= i; ! 274: goto a0; ! 275: case '*': ! 276: i = ckph(); ! 277: if(nonumb)break; ! 278: acc *= i; ! 279: goto a0; ! 280: case '/': ! 281: i = ckph(); ! 282: if(nonumb)break; ! 283: if(i == 0){ ! 284: prstrfl("Divide by zero.\n"); ! 285: acc = 0; ! 286: }else acc /= i; ! 287: goto a0; ! 288: case '%': ! 289: i = ckph(); ! 290: if(nonumb)break; ! 291: acc %= i; ! 292: goto a0; ! 293: case '&': /*and*/ ! 294: i = ckph(); ! 295: if(nonumb)break; ! 296: if((acc > 0) && (i > 0))acc = 1; else acc = 0; ! 297: goto a0; ! 298: case ':': /*or*/ ! 299: i = ckph(); ! 300: if(nonumb)break; ! 301: if((acc > 0) || (i > 0))acc = 1; else acc = 0; ! 302: goto a0; ! 303: case '=': ! 304: if(((ii=getch()) & CMASK) != '=')ch = ii; ! 305: i = ckph(); ! 306: if(nonumb){acc = 0; break;} ! 307: if(i == acc)acc = 1; ! 308: else acc = 0; ! 309: goto a0; ! 310: case '>': ! 311: k = 0; ! 312: if(((ii=getch()) & CMASK) == '=')k++; else ch =ii; ! 313: i = ckph(); ! 314: if(nonumb){acc = 0; break;} ! 315: if(acc > (i - k))acc = 1; else acc = 0; ! 316: goto a0; ! 317: case '<': ! 318: k = 0; ! 319: if(((ii=getch()) & CMASK) == '=')k++; else ch =ii; ! 320: i = ckph(); ! 321: if(nonumb){acc = 0; break;} ! 322: if(acc < (i + k))acc = 1; else acc = 0; ! 323: goto a0; ! 324: case ')': break; ! 325: case '(': ! 326: acc = atoi0(); ! 327: goto a0; ! 328: } ! 329: return(acc); ! 330: } ! 331: long ckph(){ ! 332: register i; ! 333: long j; ! 334: extern long atoi0(); ! 335: extern long atoi1(); ! 336: ! 337: if(((i = getch()) & CMASK) == '(')j = atoi0(); ! 338: else{ ! 339: ch = i; ! 340: j = atoi1(); ! 341: } ! 342: return(j); ! 343: } ! 344: long atoi1() ! 345: { ! 346: register i, j, digits; ! 347: long acc; ! 348: int neg, abs, field; ! 349: ! 350: neg = abs = field = digits = 0; ! 351: acc = 0; ! 352: a0: ! 353: switch((i = getch()) & CMASK){ ! 354: default: ! 355: ch = i; ! 356: break; ! 357: case '+': ! 358: goto a0; ! 359: case '-': ! 360: neg = 1; ! 361: goto a0; ! 362: case '|': ! 363: abs = 1 + neg; ! 364: neg = 0; ! 365: goto a0; ! 366: } ! 367: a1: ! 368: while(((j = ((i = getch()) & CMASK) - '0') >= 0) && (j <= 9)){ ! 369: field++; ! 370: digits++; ! 371: acc = 10*acc + j; ! 372: } ! 373: if((i & CMASK) == '.'){ ! 374: field++; ! 375: digits = 0; ! 376: goto a1; ! 377: } ! 378: ch = i; ! 379: if(!field)goto a2; ! 380: switch((i = getch()) & CMASK){ ! 381: case 'u': ! 382: i = j = 1; ! 383: break; ! 384: case 'v': /*VSs - vert spacing*/ ! 385: j = lss; ! 386: i = 1; ! 387: break; ! 388: case 'm': /*Ems*/ ! 389: j = EM; ! 390: i = 1; ! 391: break; ! 392: case 'n': /*Ens*/ ! 393: j = EM; ! 394: #ifndef NROFF ! 395: i = 2; ! 396: #endif ! 397: #ifdef NROFF ! 398: i = 1; /*Same as Ems in NROFF*/ ! 399: #endif ! 400: break; ! 401: case 'p': /*Points*/ ! 402: j = INCH; ! 403: i = 72; ! 404: break; ! 405: case 'i': /*Inches*/ ! 406: j = INCH; ! 407: i = 1; ! 408: break; ! 409: case 'c': /*Centimeters*/ ! 410: j = INCH*50; ! 411: i = 127; ! 412: break; ! 413: case 'P': /*Picas*/ ! 414: j = INCH; ! 415: i = 6; ! 416: break; ! 417: default: ! 418: j = dfact; ! 419: ch = i; ! 420: i = dfactd; ! 421: } ! 422: if(neg) acc = -acc; ! 423: if(!noscale){ ! 424: acc = (acc*j)/i; ! 425: } ! 426: if((field != digits) && (digits > 0))while(digits--)acc /= 10; ! 427: if(abs){ ! 428: if(dip != d)j = dip->dnl; else j = v.nl; ! 429: if(!vflag)j = v.hp = sumhp(); /* XXX */ ! 430: if(abs == 2)j = -j; ! 431: acc -= j; ! 432: } ! 433: a2: ! 434: nonumb = !field; ! 435: return(acc); ! 436: } ! 437: caserr(){ ! 438: register i,j; ! 439: ! 440: lgf++; ! 441: while(!skip() && (i=getrq()) ){ ! 442: for(j=NNAMES; j<NN; j++){ /*NNAMES predefined names*/ ! 443: if(i == r[j])break; ! 444: } ! 445: if(j!=NN){ ! 446: r[j]=vlist[j]=inc[j]=fmt[j]=0; ! 447: regcnt--; ! 448: } ! 449: } ! 450: } ! 451: casenr(){ ! 452: register i, j; ! 453: ! 454: lgf++; ! 455: skip(); ! 456: if((i = findr(getrq())) == -1)goto rtn; ! 457: skip(); ! 458: j = inumb(&vlist[i]); ! 459: if(nonumb)goto rtn; ! 460: vlist[i] = j; ! 461: skip(); ! 462: j = atoi(); ! 463: if(nonumb)goto rtn; ! 464: inc[i] = j; ! 465: rtn: ! 466: return; ! 467: } ! 468: caseaf(){ ! 469: register i, j, k; ! 470: ! 471: lgf++; ! 472: if(skip() || !(i = getrq()) || skip())return; ! 473: k = 0; ! 474: if(!alph(j=getch())){ ! 475: ch = j; ! 476: while(((j = getch() & CMASK) >= '0') && ! 477: (j <= '9'))k++; ! 478: } ! 479: if(!k)k=j; ! 480: fmt[findr(i)] = k & BMASK; ! 481: } ! 482: vnumb(i) ! 483: int *i; ! 484: { ! 485: vflag++; ! 486: dfact = lss; ! 487: res = VERT; ! 488: return(inumb(i)); ! 489: } ! 490: hnumb(i) ! 491: int *i; ! 492: { ! 493: dfact = EM; ! 494: res = HOR; ! 495: return(inumb(i)); ! 496: } ! 497: inumb(n) ! 498: int *n; ! 499: { ! 500: register i, j, f; ! 501: ! 502: f = 0; ! 503: if(n){ ! 504: if((j = (i = getch()) & CMASK) == '+')f = 1; ! 505: else if(j == '-')f = -1; ! 506: else ch = i; ! 507: } ! 508: i = atoi(); ! 509: if(n && f)i = *n + f*i; ! 510: i = quant(i,res); ! 511: vflag = 0; ! 512: res = dfactd = dfact = 1; ! 513: if(nonumb)i = 0; ! 514: return(i); ! 515: } ! 516: quant(n,m) ! 517: int n, m; ! 518: { ! 519: register i, neg; ! 520: ! 521: neg = 0; ! 522: if(n<0){ ! 523: neg++; ! 524: n = -n; ! 525: } ! 526: i = n/m; ! 527: if((n - m*i) > (m/2))i += 1; ! 528: i *= m; ! 529: if(neg)i = -i; ! 530: return(i); ! 531: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.