Blob
1 /*2 * n2.c3 *4 * output, cleanup5 */7 #define _BSD_SOURCE 1 /* popen */8 #include "tdef.h"9 #include "fns.h"10 #include "ext.h"11 #include <setjmp.h>13 #ifdef STRICT14 /* not in ANSI or POSIX */15 FILE* popen(char*, char*);16 #endif19 extern jmp_buf sjbuf;20 int toolate;21 int error;23 char obuf[2*BUFSIZ];24 char *obufp = obuf;26 /* pipe command structure; allows redicously long commends for .pi */27 struct Pipe {28 char *buf;29 int tick;30 int cnt;31 } Pipe;34 int xon = 0; /* records if in middle of \X */36 int pchar(Tchar i)37 {38 int j;39 static int hx = 0; /* records if have seen HX */41 if (hx) {42 hx = 0;43 j = absmot(i);44 if (isnmot(i)) {45 if (j > dip->blss)46 dip->blss = j;47 } else {48 if (j > dip->alss)49 dip->alss = j;50 ralss = dip->alss;51 }52 return 0;53 }54 if (ismot(i)) {55 pchar1(i);56 return 0;57 }58 switch (j = cbits(i)) {59 case 0:60 case IMP:61 case RIGHT:62 case LEFT:63 return 0;64 case HX:65 hx = 1;66 return 0;67 case XON:68 xon++;69 break;70 case XOFF:71 xon--;72 break;73 case PRESC:74 if (!xon && !tflg && dip == &d[0])75 j = eschar; /* fall through */76 default:77 setcbits(i, trtab[j]);78 }79 if (NROFF & xon) /* rob fix for man2html */80 return 0;81 pchar1(i);82 return 0;83 }86 void pchar1(Tchar i)87 {88 int j;90 j = cbits(i);91 if (dip != &d[0]) {92 wbf(i);93 dip->op = offset;94 return;95 }96 if (!tflg && !print) {97 if (j == '\n')98 dip->alss = dip->blss = 0;99 return;100 }101 if (j == FILLER && !xon)102 return;103 if (tflg) { /* transparent mode, undiverted */104 if (print) /* assumes that it's ok to print */105 /* OUT "%c", j PUT; /* i.e., is ascii */106 outascii(i);107 return;108 }109 if (TROFF && ascii)110 outascii(i);111 else112 ptout(i);113 }116 void outweird(int k) /* like ptchname() but ascii */117 {118 char *chn = chname(k);120 switch (chn[0]) {121 case MBchar:122 OUT "%s", chn+1 PUT; /* \n not needed? */123 break;124 case Number:125 OUT "\\N'%s'", chn+1 PUT;126 break;127 case Troffchar:128 if (strlen(chn+1) == 2)129 OUT "\\(%s", chn+1 PUT;130 else131 OUT "\\C'%s'", chn+1 PUT;132 break;133 default:134 OUT " %s? ", chn PUT;135 break;136 }137 }139 void outascii(Tchar i) /* print i in best-guess ascii */140 {141 int j = cbits(i);143 /* is this ever called with NROFF set? probably doesn't work at all. */145 if (ismot(i))146 oput(' ');147 else if (j < ALPHABET && j >= ' ' || j == '\n' || j == '\t')148 oput(j);149 else if (j == DRAWFCN)150 oputs("\\D");151 else if (j == HYPHEN)152 oput('-');153 else if (j == MINUS) /* special pleading for strange encodings */154 oputs("\\-");155 else if (j == PRESC)156 oputs("\\e");157 else if (j == FILLER)158 oputs("\\&");159 else if (j == UNPAD)160 oputs("\\ ");161 else if (j == OHC) /* this will never occur; stripped out earlier */162 oputs("\\%");163 else if (j == XON)164 oputs("\\X");165 else if (j == XOFF)166 oputs(" ");167 else if (j == LIG_FI)168 oputs("fi");169 else if (j == LIG_FL)170 oputs("fl");171 else if (j == LIG_FF)172 oputs("ff");173 else if (j == LIG_FFI)174 oputs("ffi");175 else if (j == LIG_FFL)176 oputs("ffl");177 else if (j == WORDSP) { /* nothing at all */178 if (xon) /* except in \X */179 oput(' ');181 } else182 outweird(j);183 }185 int flusho(void)186 {187 if (NROFF && !toolate && t.twinit)188 fwrite(t.twinit, strlen(t.twinit), 1, ptid);190 if (obufp > obuf) {191 if (pipeflg && !toolate) {192 /* fprintf(stderr, "Pipe to <%s>\n", Pipe.buf); */193 if (!Pipe.buf[0] || (ptid = popen(Pipe.buf, "w")) == NULL)194 ERROR "pipe %s not created.", Pipe.buf WARN;195 if (Pipe.buf)196 free(Pipe.buf);197 }198 if (!toolate)199 toolate++;200 *obufp = 0;201 fputs(obuf, ptid);202 fflush(ptid);203 obufp = obuf;204 }205 return 1;206 }209 void caseex(void)210 {211 done(0);212 }215 void done(int x)216 {217 int i;219 error |= x;220 app = ds = lgf = 0;221 if (i = em) {222 donef = -1;223 eschar = '\\';224 em = 0;225 if (control(i, 0))226 longjmp(sjbuf, 1);227 }228 if (!nfo)229 done3(0);230 mflg = 0;231 dip = &d[0];232 if (woff) /* BUG!!! This isn't set anywhere */233 wbf((Tchar)0);234 if (pendw)235 getword(1);236 pendnf = 0;237 if (donef == 1)238 done1(0);239 donef = 1;240 ip = 0;241 frame = stk;242 nxf = frame + 1;243 if (!ejf)244 tbreak();245 nflush++;246 eject((Stack *)0);247 longjmp(sjbuf, 1);248 }251 void done1(int x)252 {253 error |= x;254 if (numtabp[NL].val) {255 trap = 0;256 eject((Stack *)0);257 longjmp(sjbuf, 1);258 }259 if (!ascii)260 pttrailer();261 done2(0);262 }265 void done2(int x)266 {267 ptlead();268 if (TROFF && !ascii)269 ptstop();270 flusho();271 done3(x);272 }274 void done3(int x)275 {276 error |= x;277 flusho();278 if (NROFF)279 twdone();280 if (pipeflg)281 pclose(ptid);282 exit(error);283 }286 void edone(int x)287 {288 frame = stk;289 nxf = frame + 1;290 ip = 0;291 done(x);292 }295 void casepi(void)296 {297 int j;298 char buf[NTM];300 if (Pipe.buf == NULL) {301 if ((Pipe.buf = (char *)calloc(NTM, sizeof(char))) == NULL) {302 ERROR "No buf space for pipe cmd" WARN;303 return;304 }305 Pipe.tick = 1;306 } else307 Pipe.buf[Pipe.cnt++] = '|';309 getline(buf, NTM);310 j = strlen(buf);311 if (toolate) {312 ERROR "Cannot create pipe to %s", buf WARN;313 return;314 }315 Pipe.cnt += j;316 if (j >= NTM +1) {317 Pipe.tick++;318 if ((Pipe.buf = (char *)realloc(Pipe.buf, Pipe.tick * NTM * sizeof(char))) == NULL) {319 ERROR "No more buf space for pipe cmd" WARN;320 return;321 }322 }323 strcat(Pipe.buf, buf);324 pipeflg++;325 }