123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834 |
- #include "tdef.h"
- #include "fns.h"
- #include "ext.h"
- #ifdef STRICT
- /* not in ANSI or POSIX */
- #define isascii(a) ((a) >= 0 && (a) <= 127)
- #endif
- #define GETCH gettch
- Tchar gettch(void);
- /*
- * troff7.c
- *
- * text
- */
- int brflg;
- void tbreak(void)
- {
- int pad, k;
- Tchar *i, j;
- int resol;
- int un0 = un;
- trap = 0;
- if (nb)
- return;
- if (dip == d && numtabp[NL].val == -1) {
- newline(1);
- return;
- }
- if (!nc) {
- setnel();
- if (!wch)
- return;
- if (pendw)
- getword(1);
- movword();
- } else if (pendw && !brflg) {
- getword(1);
- movword();
- }
- *linep = dip->nls = 0;
- if (NROFF && dip == d)
- horiz(po);
- if (lnmod)
- donum();
- lastl = ne;
- if (brflg != 1) {
- totout = 0;
- } else if (ad) {
- if ((lastl = ll - un) < ne)
- lastl = ne;
- }
- if (admod && ad && (brflg != 2)) {
- lastl = ne;
- adsp = adrem = 0;
- if (admod == 1)
- un += quant(nel / 2, HOR);
- else if (admod == 2)
- un += nel;
- }
- totout++;
- brflg = 0;
- if (lastl + un > dip->maxl)
- dip->maxl = lastl + un;
- horiz(un);
- if (NROFF) {
- if (adrem % t.Adj)
- resol = t.Hor;
- else
- resol = t.Adj;
- } else
- resol = HOR;
- lastl = ne + (nwd-1) * adsp + adrem;
- for (i = line; nc > 0; ) {
- if ((cbits(j = *i++)) == ' ') {
- pad = 0;
- do {
- pad += width(j);
- nc--;
- } while ((cbits(j = *i++)) == ' ');
- i--;
- pad += adsp;
- --nwd;
- if (adrem) {
- if (adrem < 0) {
- pad -= resol;
- adrem += resol;
- } else if ((totout & 01) || adrem / resol >= nwd) {
- pad += resol;
- adrem -= resol;
- }
- }
- pchar((Tchar) WORDSP);
- horiz(pad);
- } else {
- pchar(j);
- nc--;
- }
- }
- if (ic) {
- if ((k = ll - un0 - lastl + ics) > 0)
- horiz(k);
- pchar(ic);
- }
- if (icf)
- icf++;
- else
- ic = 0;
- ne = nwd = 0;
- un = in;
- setnel();
- newline(0);
- if (dip != d) {
- if (dip->dnl > dip->hnl)
- dip->hnl = dip->dnl;
- } else {
- if (numtabp[NL].val > dip->hnl)
- dip->hnl = numtabp[NL].val;
- }
- for (k = ls - 1; k > 0 && !trap; k--)
- newline(0);
- spread = 0;
- }
- void donum(void)
- {
- int i, nw;
- int lnv = numtabp[LN].val;
- nrbits = nmbits;
- nw = width('1' | nrbits);
- if (nn) {
- nn--;
- goto d1;
- }
- if (lnv % ndf) {
- numtabp[LN].val++;
- d1:
- un += nw * (nmwid + nms + ni);
- return;
- }
- i = 0;
- do { /* count digits in numtabp[LN].val */
- i++;
- } while ((lnv /= 10) > 0);
- horiz(nw * (ni + max(nmwid-i, 0)));
- nform = 0;
- fnumb(numtabp[LN].val, pchar);
- un += nw * nms;
- numtabp[LN].val++;
- }
- void text(void)
- {
- Tchar i;
- static int spcnt;
- nflush++;
- numtabp[HP].val = 0;
- if ((dip == d) && (numtabp[NL].val == -1)) {
- newline(1);
- return;
- }
- setnel();
- if (ce || !fi) {
- nofill();
- return;
- }
- if (pendw)
- goto t4;
- if (pendt)
- if (spcnt)
- goto t2;
- else
- goto t3;
- pendt++;
- if (spcnt)
- goto t2;
- while ((cbits(i = GETCH())) == ' ') {
- spcnt++;
- numtabp[HP].val += sps;
- widthp = sps;
- }
- if (nlflg) {
- t1:
- nflush = pendt = ch = spcnt = 0;
- callsp();
- return;
- }
- ch = i;
- if (spcnt) {
- t2:
- tbreak();
- if (nc || wch)
- goto rtn;
- un += spcnt * sps;
- spcnt = 0;
- setnel();
- if (trap)
- goto rtn;
- if (nlflg)
- goto t1;
- }
- t3:
- if (spread)
- goto t5;
- if (pendw || !wch)
- t4:
- if (getword(0))
- goto t6;
- if (!movword())
- goto t3;
- t5:
- if (nlflg)
- pendt = 0;
- adsp = adrem = 0;
- if (ad) {
- if (nwd == 1)
- adsp = nel;
- else
- adsp = nel / (nwd - 1);
- adsp = (adsp / HOR) * HOR;
- adrem = nel - adsp*(nwd-1);
- }
- brflg = 1;
- tbreak();
- spread = 0;
- if (!trap)
- goto t3;
- if (!nlflg)
- goto rtn;
- t6:
- pendt = 0;
- ckul();
- rtn:
- nflush = 0;
- }
- void nofill(void)
- {
- int j;
- Tchar i;
- if (!pendnf) {
- over = 0;
- tbreak();
- if (trap)
- goto rtn;
- if (nlflg) {
- ch = nflush = 0;
- callsp();
- return;
- }
- adsp = adrem = 0;
- nwd = 10000;
- }
- while ((j = (cbits(i = GETCH()))) != '\n') {
- if (j == ohc)
- continue;
- if (j == CONT) {
- pendnf++;
- nflush = 0;
- flushi();
- ckul();
- return;
- }
- j = width(i);
- widthp = j;
- numtabp[HP].val += j;
- storeline(i, j);
- }
- if (ce) {
- ce--;
- if ((i = quant(nel / 2, HOR)) > 0)
- un += i;
- }
- if (!nc)
- storeline((Tchar)FILLER, 0);
- brflg = 2;
- tbreak();
- ckul();
- rtn:
- pendnf = nflush = 0;
- }
- void callsp(void)
- {
- int i;
- if (flss)
- i = flss;
- else
- i = lss;
- flss = 0;
- casesp1(i);
- }
- void ckul(void)
- {
- if (ul && (--ul == 0)) {
- cu = 0;
- font = sfont;
- mchbits();
- }
- if (it && --it == 0 && itmac)
- control(itmac, 0);
- }
- void storeline(Tchar c, int w)
- {
- int diff;
- if (linep >= line + lnsize - 2) {
- lnsize += LNSIZE;
- diff = linep - line;
- if (( line = (Tchar *)realloc((char *)line, lnsize * sizeof(Tchar))) != NULL) {
- if (linep && diff)
- linep = line + diff;
- } else {
- if (over) {
- return;
- } else {
- flusho();
- ERROR "Line overflow." WARN;
- over++;
- *linep++ = LEFTHAND;
- w = width(LEFTHAND);
- nc++;
- c = '\n';
- }
- }
- }
- *linep++ = c;
- ne += w;
- nel -= w;
- nc++;
- }
- void newline(int a)
- {
- int i, j, nlss;
- int opn;
- if (a)
- goto nl1;
- if (dip != d) {
- j = lss;
- pchar1((Tchar)FLSS);
- if (flss)
- lss = flss;
- i = lss + dip->blss;
- dip->dnl += i;
- pchar1((Tchar)i);
- pchar1((Tchar)'\n');
- lss = j;
- dip->blss = flss = 0;
- if (dip->alss) {
- pchar1((Tchar)FLSS);
- pchar1((Tchar)dip->alss);
- pchar1((Tchar)'\n');
- dip->dnl += dip->alss;
- dip->alss = 0;
- }
- if (dip->ditrap && !dip->ditf && dip->dnl >= dip->ditrap && dip->dimac)
- if (control(dip->dimac, 0)) {
- trap++;
- dip->ditf++;
- }
- return;
- }
- j = lss;
- if (flss)
- lss = flss;
- nlss = dip->alss + dip->blss + lss;
- numtabp[NL].val += nlss;
- if (TROFF && ascii) {
- dip->alss = dip->blss = 0;
- }
- pchar1((Tchar)'\n');
- flss = 0;
- lss = j;
- if (numtabp[NL].val < pl)
- goto nl2;
- nl1:
- ejf = dip->hnl = numtabp[NL].val = 0;
- ejl = frame;
- if (donef) {
- if ((!nc && !wch) || ndone)
- done1(0);
- ndone++;
- donef = 0;
- if (frame == stk)
- nflush++;
- }
- opn = numtabp[PN].val;
- numtabp[PN].val++;
- if (npnflg) {
- numtabp[PN].val = npn;
- npn = npnflg = 0;
- }
- nlpn:
- if (numtabp[PN].val == pfrom) {
- print++;
- pfrom = -1;
- } else if (opn == pto) {
- print = 0;
- opn = -1;
- chkpn();
- goto nlpn;
- }
- if (print)
- ptpage(numtabp[PN].val); /* supposedly in a clean state so can pause */
- if (stop && print) {
- dpn++;
- if (dpn >= stop) {
- dpn = 0;
- ptpause();
- }
- }
- nl2:
- trap = 0;
- if (numtabp[NL].val == 0) {
- if ((j = findn(0)) != NTRAP)
- trap = control(mlist[j], 0);
- } else if ((i = findt(numtabp[NL].val - nlss)) <= nlss) {
- if ((j = findn1(numtabp[NL].val - nlss + i)) == NTRAP) {
- flusho();
- ERROR "Trap botch." WARN;
- done2(-5);
- }
- trap = control(mlist[j], 0);
- }
- }
- findn1(int a)
- {
- int i, j;
- for (i = 0; i < NTRAP; i++) {
- if (mlist[i]) {
- if ((j = nlist[i]) < 0)
- j += pl;
- if (j == a)
- break;
- }
- }
- return(i);
- }
- void chkpn(void)
- {
- pto = *(pnp++);
- pfrom = pto>=0 ? pto : -pto;
- if (pto == -INT_MAX) {
- flusho();
- done1(0);
- }
- if (pto < 0) {
- pto = -pto;
- print++;
- pfrom = 0;
- }
- }
- findt(int a)
- {
- int i, j, k;
- k = INT_MAX;
- if (dip != d) {
- if (dip->dimac && (i = dip->ditrap - a) > 0)
- k = i;
- return(k);
- }
- for (i = 0; i < NTRAP; i++) {
- if (mlist[i]) {
- if ((j = nlist[i]) < 0)
- j += pl;
- if ((j -= a) <= 0)
- continue;
- if (j < k)
- k = j;
- }
- }
- i = pl - a;
- if (k > i)
- k = i;
- return(k);
- }
- findt1(void)
- {
- int i;
- if (dip != d)
- i = dip->dnl;
- else
- i = numtabp[NL].val;
- return(findt(i));
- }
- void eject(Stack *a)
- {
- int savlss;
- if (dip != d)
- return;
- ejf++;
- if (a)
- ejl = a;
- else
- ejl = frame;
- if (trap)
- return;
- e1:
- savlss = lss;
- lss = findt(numtabp[NL].val);
- newline(0);
- lss = savlss;
- if (numtabp[NL].val && !trap)
- goto e1;
- }
- movword(void)
- {
- int w;
- Tchar i, *wp;
- int savwch, hys;
- over = 0;
- wp = wordp;
- if (!nwd) {
- while (cbits(*wp++) == ' ') {
- wch--;
- wne -= sps;
- }
- wp--;
- }
- if (wne > nel && !hyoff && hyf && (!nwd || nel > 3 * sps) &&
- (!(hyf & 02) || (findt1() > lss)))
- hyphen(wp);
- savwch = wch;
- hyp = hyptr;
- nhyp = 0;
- while (*hyp && *hyp <= wp)
- hyp++;
- while (wch) {
- if (hyoff != 1 && *hyp == wp) {
- hyp++;
- if (!wdstart || (wp > wdstart + 1 && wp < wdend &&
- (!(hyf & 04) || wp < wdend - 1) && /* 04 => last 2 */
- (!(hyf & 010) || wp > wdstart + 2))) { /* 010 => 1st 2 */
- nhyp++;
- storeline((Tchar)IMP, 0);
- }
- }
- i = *wp++;
- w = width(i);
- wne -= w;
- wch--;
- storeline(i, w);
- }
- if (nel >= 0) {
- nwd++;
- return(0); /* line didn't fill up */
- }
- if (TROFF)
- xbits((Tchar)HYPHEN, 1);
- hys = width((Tchar)HYPHEN);
- m1:
- if (!nhyp) {
- if (!nwd)
- goto m3;
- if (wch == savwch)
- goto m4;
- }
- if (*--linep != IMP)
- goto m5;
- if (!(--nhyp))
- if (!nwd)
- goto m2;
- if (nel < hys) {
- nc--;
- goto m1;
- }
- m2:
- if ((i = cbits(*(linep - 1))) != '-' && i != EMDASH) {
- *linep = (*(linep - 1) & SFMASK) | HYPHEN;
- w = width(*linep);
- nel -= w;
- ne += w;
- linep++;
- }
- m3:
- nwd++;
- m4:
- wordp = wp;
- return(1); /* line filled up */
- m5:
- nc--;
- w = width(*linep);
- ne -= w;
- nel += w;
- wne += w;
- wch++;
- wp--;
- goto m1;
- }
- void horiz(int i)
- {
- vflag = 0;
- if (i)
- pchar(makem(i));
- }
- void setnel(void)
- {
- if (!nc) {
- linep = line;
- if (un1 >= 0) {
- un = un1;
- un1 = -1;
- }
- nel = ll - un;
- ne = adsp = adrem = 0;
- }
- }
- getword(int x)
- {
- int j, k;
- Tchar i, *wp;
- int noword;
- int obits;
- noword = 0;
- if (x)
- if (pendw) {
- *pendw = 0;
- goto rtn;
- }
- if (wordp = pendw)
- goto g1;
- hyp = hyptr;
- wordp = word;
- over = wne = wch = 0;
- hyoff = 0;
- obits = chbits;
- while (1) { /* picks up 1st char of word */
- j = cbits(i = GETCH());
- if (j == '\n') {
- wne = wch = 0;
- noword = 1;
- goto rtn;
- }
- if (j == ohc) {
- hyoff = 1; /* 1 => don't hyphenate */
- continue;
- }
- if (j == ' ') {
- numtabp[HP].val += sps;
- widthp = sps;
- storeword(i, sps);
- continue;
- }
- break;
- }
- storeword(' ' | obits, sps);
- if (spflg) {
- storeword(' ' | obits, sps);
- spflg = 0;
- }
- g0:
- if (j == CONT) {
- pendw = wordp;
- nflush = 0;
- flushi();
- return(1);
- }
- if (hyoff != 1) {
- if (j == ohc) {
- hyoff = 2;
- *hyp++ = wordp;
- if (hyp > hyptr + NHYP - 1)
- hyp = hyptr + NHYP - 1;
- goto g1;
- }
- if (((j == '-' || j == EMDASH)) && !(i & ZBIT)) /* zbit avoids \X */
- if (wordp > word + 1) {
- hyoff = 2;
- *hyp++ = wordp + 1;
- if (hyp > hyptr + NHYP - 1)
- hyp = hyptr + NHYP - 1;
- }
- }
- j = width(i);
- numtabp[HP].val += j;
- storeword(i, j);
- g1:
- j = cbits(i = GETCH());
- if (j != ' ') {
- static char *sentchar = ".?!"; /* sentence terminators */
- if (j != '\n')
- goto g0;
- wp = wordp-1; /* handle extra space at end of sentence */
- while (wp >= word) {
- j = cbits(*wp--);
- if (j=='"' || j=='\'' || j==')' || j==']' || j=='*' || j==DAGGER)
- continue;
- for (k = 0; sentchar[k]; k++)
- if (j == sentchar[k]) {
- spflg++;
- break;
- }
- break;
- }
- }
- *wordp = 0;
- numtabp[HP].val += sps;
- rtn:
- for (wp = word; *wp; wp++) {
- if (ismot(j))
- break; /* drechsler */
- j = cbits(*wp);
- if (j == ' ')
- continue;
- if (!(isascii(j) && isdigit(j)) && j != '-')
- break;
- }
- if (*wp == 0) /* all numbers, so don't hyphenate */
- hyoff = 1;
- wdstart = 0;
- wordp = word;
- pendw = 0;
- *hyp++ = 0;
- setnel();
- return(noword);
- }
- void storeword(Tchar c, int w)
- {
- Tchar *savp;
- int i;
- if (wordp >= word + wdsize - 2) {
- wdsize += WDSIZE;
- savp = word;
- if (( word = (Tchar *)realloc((char *)word, wdsize * sizeof(Tchar))) != NULL) {
- if (wordp)
- wordp = word + (wordp - savp);
- if (pendw)
- pendw = word + (pendw - savp);
- if (wdstart)
- wdstart = word + (wdstart - savp);
- if (wdend)
- wdend = word + (wdend - savp);
- for (i = 0; i < NHYP; i++)
- if (hyptr[i])
- hyptr[i] = word + (hyptr[i] - savp);
- } else {
- if (over) {
- return;
- } else {
- flusho();
- ERROR "Word overflow." WARN;
- over++;
- c = LEFTHAND;
- w = width(LEFTHAND);
- }
- }
- }
- widthp = w;
- wne += w;
- *wordp++ = c;
- wch++;
- }
- Tchar gettch(void)
- {
- extern int c_isalnum;
- Tchar i;
- int j;
- if (TROFF)
- return getch();
- i = getch();
- j = cbits(i);
- if (ismot(i) || fbits(i) != ulfont)
- return(i);
- if (cu) {
- if (trtab[j] == ' ') {
- setcbits(i, '_');
- setfbits(i, FT); /* default */
- }
- return(i);
- }
- /* should test here for characters that ought to be underlined */
- /* in the old nroff, that was the 200 bit on the width! */
- /* for now, just do letters, digits and certain special chars */
- if (j <= 127) {
- if (!isalnum(j))
- setfbits(i, FT);
- } else {
- if (j < c_isalnum)
- setfbits(i, FT);
- }
- return(i);
- }
|