/*
 * n1.c
 *
 *	consume options, initialization, main loop,
 *	input routines, escape function calling
 */

#include "tdef.h"
#include "fns.h"
#include "ext.h"
#include "dwbinit.h"

#undef MB_CUR_MAX
#define MB_CUR_MAX 3

#include <setjmp.h>
#include <time.h>

char	*Version	= "March 11, 1994";

#ifndef DWBVERSION
#define DWBVERSION      "???"
#endif

char	*DWBfontdir = FONTDIR;
char	*DWBntermdir = NTERMDIR;
char	*DWBalthyphens = ALTHYPHENS;
char	*DWBhomedir = "";

dwbinit dwbpaths[] = {
	&DWBfontdir, NULL, 0,
	&DWBntermdir, NULL, 0,
	&DWBalthyphens, NULL, 0,
	&DWBhomedir, NULL, 0,
	NULL, nextf, NS,
	NULL, NULL, 0
};

int	TROFF	= 1;	/* assume we started in troff... */

jmp_buf sjbuf;
Offset	ipl[NSO];

static	FILE	*ifile;
static	FILE	*ifl[NSO];	/* open input file pointers */
char	cfname[NSO+1][NS] = {  "stdin" };	/* file name stack */
int	cfline[NSO];		/* input line count stack */
char	*progname;		/* program name (troff or nroff) */

int	trace = 0;	/* tracing mode: default off */
int	trace1 = 0;

main(int argc, char *argv[])
{
	char *p;
	int j;
	Tchar i;
	char buf[100];

	ifile = stdin;
	ptid = stdout;

	buf[0] = '\0';		/* make sure it's empty (silly 3b2) */
	progname = argv[0];
	if ((p = strrchr(progname, '/')) == NULL)
		p = progname;
	else
		p++;
	DWBinit(progname, dwbpaths);
	if (strcmp(p, "nroff") == 0)
		TROFF = 0;
#ifdef UNICODE
	alphabet = 128;	/* unicode for plan 9 */
#endif	/*UNICODE*/
	mnspace();
	nnspace();
	mrehash();
	nrehash();
	numtabp[NL].val = -1;

	while (--argc > 0 && (++argv)[0][0] == '-')
		switch (argv[0][1]) {

		case 'N':	/* ought to be used first... */
			TROFF = 0;
			break;
		case 'd':
			fprintf(stderr, "troff/nroff version %s\n", Version);
			break;
		case 'F':	/* switch font tables from default */
			if (argv[0][2] != '\0') {
				strcpy(termtab, &argv[0][2]);
				strcpy(fontdir, &argv[0][2]);
			} else {
				argv++; argc--;
				strcpy(termtab, argv[0]);
				strcpy(fontdir, argv[0]);
			}
			break;
		case 0:
			goto start;
		case 'i':
			stdi++;
			break;
		case 'n':
			npn = atoi(&argv[0][2]);
			break;
		case 'u':	/* set emboldening amount */
			bdtab[3] = atoi(&argv[0][2]);
			if (bdtab[3] < 0 || bdtab[3] > 50)
				bdtab[3] = 0;
			break;
		case 's':
			if (!(stop = atoi(&argv[0][2])))
				stop++;
			break;
		case 'r':
			sprintf(buf + strlen(buf), ".nr %c %s\n",
				argv[0][2], &argv[0][3]);
			/* not yet cpushback(buf);*/
			/* dotnr(&argv[0][2], &argv[0][3]); */
			break;
		case 'm':
			if (mflg++ >= NMF) {
				ERROR "Too many macro packages: %s", argv[0] WARN;
				break;
			}
			strcpy(mfiles[nmfi], nextf);
			strcat(mfiles[nmfi++], &argv[0][2]);
			break;
		case 'o':
			getpn(&argv[0][2]);
			break;
		case 'T':
			strcpy(devname, &argv[0][2]);
			dotT++;
			break;
		case 'a':
			ascii = 1;
			break;
		case 'h':
			hflg++;
			break;
		case 'e':
			eqflg++;
			break;
		case 'q':
			quiet++;
			save_tty();
			break;
		case 'V':
			fprintf(stdout, "%croff: DWB %s\n", 
					TROFF ? 't' : 'n', DWBVERSION);
			exit(0);
		case 't':
			if (argv[0][2] != '\0')
				trace = trace1 = argv[0][2];
			break;		/* for the sake of compatibility */
		default:
			ERROR "unknown option %s", argv[0] WARN;
			done(02);
		}

start:
	/*
	 * cpushback maintains a LIFO, so push pack the -r arguments
	 * in reverse order to maintain a FIFO in case someone did -rC1 -rC3
	 */
	if (buf[0]) {
		char *p = buf;
		while(*p++)
			;
		while(p > buf) {
			while(strncmp(p, ".nr", 3) != 0)
				p--;
			cpushback(p);
			*p-- = '\0';
		}
	}
	argp = argv;
	rargc = argc;
	nmfi = 0;
	init2();
	setjmp(sjbuf);
loop:
	copyf = lgf = nb = nflush = nlflg = 0;
	if (ip && rbf0(ip) == 0 && ejf && frame->pframe <= ejl && dip == d) {
		nflush++;
		trap = 0;
		eject((Stack *)0);
		goto loop;
	}
	i = getch();
	if (pendt)
		goto Lt;
	if ((j = cbits(i)) == XPAR) {
		copyf++;
		tflg++;
		while (cbits(i) != '\n')
			pchar(i = getch());
		tflg = 0;
		copyf--;
		goto loop;
	}
	if (j == cc || j == c2) {
		if (j == c2)
			nb++;
		copyf++;
		while ((j = cbits(i = getch())) == ' ' || j == '\t')
			;
		ch = i;
		copyf--;
		control(getrq(), 1);
		flushi();
		goto loop;
	}
Lt:
	ch = i;
	text();
	if (nlflg)
		numtabp[HP].val = 0;
	goto loop;
}



void init2(void)
{
	int i;
	char buf[100];

	for (i = NTRTAB; --i; )
		trtab[i] = i;
	trtab[UNPAD] = ' ';
	iflg = 0;
	obufp = obuf;
	if (TROFF)
		t_ptinit();
	else
		n_ptinit();
	mchbits();
	cvtime();
	numtabp[PID].val = getpid();
	numtabp[HP].val = init = 0;
	numtabp[NL].val = -1;
	nfo = 0;
	copyf = raw = 0;
	sprintf(buf, ".ds .T %s\n", devname);
	cpushback(buf);
	sprintf(buf, ".ds .P %s\n", DWBhomedir);
	cpushback(buf);
	numtabp[CD].val = -1;	/* compensation */
	nx = mflg;
	frame = stk = (Stack *)setbrk(STACKSIZE);
	dip = &d[0];
	nxf = frame + 1;
	for (i = 1; i < NEV; i++)	/* propagate the environment */
		envcopy(&env[i], &env[0]);
	for (i = 0; i < NEV; i++) {
		if ((env[i]._word._bufp = (Tchar *)calloc(WDSIZE, sizeof(Tchar))) == NULL) {
			ERROR "not enough room for word buffers" WARN;
			done2(1);
		}
		env[i]._word._size = WDSIZE;
		if ((env[i]._line._bufp = (Tchar *)calloc(LNSIZE, sizeof(Tchar))) == NULL) {
			ERROR "not enough room for line buffers" WARN;
			done2(1);
		}
		env[i]._line._size = LNSIZE;
	}
	if ((oline = (Tchar *)calloc(OLNSIZE, sizeof(Tchar))) == NULL) {
		ERROR "not enough room for line buffers" WARN;
		done2(1);
	}
	olinep = oline;
	olnsize = OLNSIZE;
	blockinit();
}

void cvtime(void)
{
	long tt;
	struct tm *ltime;

	time(&tt);
	ltime = localtime(&tt);
	numtabp[YR].val = ltime->tm_year % 100;
	numtabp[YR].fmt = 2;
	numtabp[MO].val = ltime->tm_mon + 1;	/* troff uses 1..12 */
	numtabp[DY].val = ltime->tm_mday;
	numtabp[DW].val = ltime->tm_wday + 1;	/* troff uses 1..7 */
}



char	errbuf[200];

void errprint(void)	/* error message printer */
{
	int savecd = numtabp[CD].val;

	if (!nlflg)
		numtabp[CD].val++;

	fprintf(stderr, "%s: ", progname);
	fputs(errbuf, stderr);
	if (cfname[ifi][0])
		fprintf(stderr, "; %s:%d", cfname[ifi], numtabp[CD].val);
	fputs("\n", stderr);
	if (cfname[ifi][0])
		stackdump();
	numtabp[CD].val = savecd;
}


int control(int a, int b)
{
	int j, k;
	extern Contab *contabp;

	numerr.type = RQERR;
	numerr.req = a;
	if (a == 0 || (j = findmn(a)) == -1)
		return(0);
	if (contabp[j].f == 0) {
		if (trace & TRMAC)
			fprintf(stderr, "invoke macro %s\n", unpair(a));
		if (dip != d)
			for (k = dilev; k; k--)
				if (d[k].curd == a) {
					ERROR "diversion %s invokes itself during diversion",
								unpair(a) WARN;
					edone(0100);
				}
		nxf->nargs = 0;
		if (b)
			collect();
		flushi();
		return pushi(contabp[j].mx, a);	/* BUG??? all that matters is 0/!0 */
	}
	if (b) {
		if (trace & TRREQ)
			fprintf(stderr, "invoke request %s\n", unpair(a));
		 (*contabp[j].f)();
	}
	return(0);
}

void casept(void)
{
	int i;

	noscale++;
	if (skip())
		i = trace1;
	else {
		i = max(inumb(&trace), 0);
		if (nonumb)
			i = trace1;
	}
	trace1 = trace;
	trace = i;
	noscale = 0;
}


int getrq(void)
{
	int i, j;

	if ((i = getach()) == 0 || (j = getach()) == 0)
		goto rtn;
	i = PAIR(i, j);
rtn:
	return(i);
}

/*
 * table encodes some special characters, to speed up tests
 * in getch, viz FLSS, RPT, f, \b, \n, fc, tabch, ldrch
 */

char gchtab[NCHARS] = {
	000,004,000,000,010,000,000,000, /* fc, ldr */
	001,002,001,000,001,000,000,000, /* \b, tab, nl, RPT */
	000,000,000,000,000,000,000,000,
	000,001,000,001,000,000,000,000, /* FLSS, ESC */
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,001,000, /* f */
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
	000,000,000,000,000,000,000,000,
};

int realcbits(Tchar c)	/* return character bits, or MOTCH if motion */
{
	if (ismot(c))
		return MOTCH;
	else
		return c & 0xFFFF;
}

Tchar getch(void)
{
	int k;
	Tchar i, j;

g0:
	if (ch) {
		i = ch;
		if (cbits(i) == '\n')
			nlflg++;
		ch = 0;
		return(i);
	}

	if (nlflg)
		return('\n');
	i = getch0();
	if (ismot(i))
		return(i);
	k = cbits(i);
	if (k >= sizeof(gchtab)/sizeof(gchtab[0]) || gchtab[k] == 0)	/* nothing special */
		return(i);
	if (k != ESC) {
		if (k == '\n') {
			nlflg++;
			if (ip == 0)
				numtabp[CD].val++; /* line number */
			return(k);
		}
		if (k == FLSS) {
			copyf++; 
			raw++;
			i = getch0();
			if (!fi)
				flss = i;
			copyf--; 
			raw--;
			goto g0;
		}
		if (k == RPT) {
			setrpt();
			goto g0;
		}
		if (!copyf) {
			if (k == 'f' && lg && !lgf) {
				i = getlg(i);
				return(i);
			}
			if (k == fc || k == tabch || k == ldrch) {
				if ((i = setfield(k)) == 0)
					goto g0; 
				else 
					return(i);
			}
			if (k == '\b') {
				i = makem(-width(' ' | chbits));
				return(i);
			}
		}
		return(i);
	}

	k = cbits(j = getch0());
	if (ismot(j))
		return(j);

	switch (k) {
	case 'n':	/* number register */
		setn();
		goto g0;
	case '$':	/* argument indicator */
		seta();
		goto g0;
	case '*':	/* string indicator */
		setstr();
		goto g0;
	case '{':	/* LEFT */
		i = LEFT;
		goto gx;
	case '}':	/* RIGHT */
		i = RIGHT;
		goto gx;
	case '"':	/* comment */
		while (cbits(i = getch0()) != '\n')
			;
		if (ip == 0)
			numtabp[CD].val++; /* line number */
		nlflg++;
		return(i);

/* experiment: put it here instead of copy mode */
	case '(':	/* special char name \(xx */
	case 'C':	/* 		\C'...' */
		if ((i = setch(k)) == 0)
			goto g0;
		goto gx;

	case ESC:	/* double backslash */
		i = eschar;
		goto gx;
	case 'e':	/* printable version of current eschar */
		i = PRESC;
		goto gx;
	case '\n':	/* concealed newline */
		numtabp[CD].val++;
		goto g0;
	case ' ':	/* unpaddable space */
		i = UNPAD;
		goto gx;
	case '\'':	/* \(aa */
		i = ACUTE;
		goto gx;
	case '`':	/* \(ga */
		i = GRAVE;
		goto gx;
	case '_':	/* \(ul */
		i = UNDERLINE;
		goto gx;
	case '-':	/* current font minus */
		i = MINUS;
		goto gx;
	case '&':	/* filler */
		i = FILLER;
		goto gx;
	case 'c':	/* to be continued */
		i = CONT;
		goto gx;
	case '!':	/* transparent indicator */
		i = XPAR;
		goto gx;
	case 't':	/* tab */
		i = '\t';
		return(i);
	case 'a':	/* leader (SOH) */
/* old:		*pbp++ = LEADER; goto g0; */
		i = LEADER;
		return i;
	case '%':	/* ohc */
		i = OHC;
		return(i);
	case 'g':	/* return format of a number register */
		setaf();	/* should this really be in copy mode??? */
		goto g0;
	case '.':	/* . */
		i = '.';
gx:
		setsfbits(i, sfbits(j));
		return(i);
	}
	if (copyf) {
		*pbp++ = j;
		return(eschar);
	}
	switch (k) {

	case 'f':	/* font indicator */
		setfont(0);
		goto g0;
	case 's':	/* size indicator */
		setps();
		goto g0;
	case 'v':	/* vert mot */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		if (i = vmot()) {
			return(i);
		}
		goto g0;
	case 'h': 	/* horiz mot */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		if (i = hmot())
			return(i);
		goto g0;
	case '|':	/* narrow space */
		if (NROFF)
			goto g0;
		return(makem((int)(EM)/6));
	case '^':	/* half narrow space */
		if (NROFF)
			goto g0;
		return(makem((int)(EM)/12));
	case 'w':	/* width function */
		setwd();
		goto g0;
	case 'p':	/* spread */
		spread++;
		goto g0;
	case 'N':	/* absolute character number */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		if ((i = setabs()) == 0)
			goto g0;
		return i;
	case 'H':	/* character height */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		return(setht());
	case 'S':	/* slant */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		return(setslant());
	case 'z':	/* zero with char */
		return(setz());
	case 'l':	/* hor line */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		setline();
		goto g0;
	case 'L':	/* vert line */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		setvline();
		goto g0;
	case 'D':	/* drawing function */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		setdraw();
		goto g0;
	case 'X':	/* \X'...' for copy through */
		setxon();
		goto g0;
	case 'b':	/* bracket */
		setbra();
		goto g0;
	case 'o':	/* overstrike */
		setov();
		goto g0;
	case 'k':	/* mark hor place */
		if ((k = findr(getsn())) != -1) {
			numtabp[k].val = numtabp[HP].val;
		}
		goto g0;
	case '0':	/* number space */
		return(makem(width('0' | chbits)));
	case 'x':	/* extra line space */
		numerr.type = numerr.escarg = 0; numerr.esc = k;
		if (i = xlss())
			return(i);
		goto g0;
	case 'u':	/* half em up */
	case 'r':	/* full em up */
	case 'd':	/* half em down */
		return(sethl(k));
	default:
		return(j);
	}
	/* NOTREACHED */
}

void setxon(void)	/* \X'...' for copy through */
{
	Tchar xbuf[NC];
	Tchar *i;
	Tchar c;
	int delim, k;

	if (ismot(c = getch()))
		return;
	delim = cbits(c);
	i = xbuf;
	*i++ = XON | chbits;
	while ((k = cbits(c = getch())) != delim && k != '\n' && i < xbuf+NC-1) {
		if (k == ' ')
			setcbits(c, WORDSP);
		*i++ = c | ZBIT;
	}
	*i++ = XOFF | chbits;
	*i = 0;
	pushback(xbuf);
}


char	ifilt[32] = { 0, 001, 002, 003, 0, 005, 006, 007, 010, 011, 012 };

Tchar getch0(void)
{
	int j;
	Tchar i;

again:
	if (pbp > lastpbp)
		i = *--pbp;
	else if (ip) {
		/* i = rbf(); */
		i = rbf0(ip);
		if (i == 0)
			i = rbf();
		else {
			++ip;
			if (pastend(ip)) {
				--ip;
				rbf();
			}
		}
	} else {
		if (donef || ndone)
			done(0);
		if (nx || 1) {	/* BUG: was ibufp >= eibuf, so EOF test is wrong */
			if (nfo < 0)
				ERROR "in getch0, nfo = %d", nfo WARN;
			if (nfo == 0) {
g0:
				if (nextfile()) {
					if (ip)
						goto again;
				}
			}
			nx = 0;
#ifdef UNICODE
			if (MB_CUR_MAX > 1)
				i = get1ch(ifile);
			else
#endif	/*UNICODE*/
				i = getc(ifile);
			if (i == EOF)
				goto g0;
			if (ip)
				goto again;
		}
g2:
		if (i >= 040)			/* zapped: && i < 0177 */
			goto g4;
		i = ifilt[i];
	}
	if (cbits(i) == IMP && !raw)
		goto again;
	if (i == 0 && !init && !raw) {		/* zapped:  || i == 0177 */
		goto again;
	}
g4:
	if (ismot(i))
		return i;
	if (copyf == 0 && sfbits(i) == 0)
		i |= chbits;
	if (cbits(i) == eschar && !raw)
		setcbits(i, ESC);
	return(i);
}


#ifdef UNICODE
Tchar get1ch(FILE *fp)	/* get one "character" from input, figure out what alphabet */
{
	wchar_t wc;
	char buf[100], *p;
	int i, n, c;

	for (i = 0, p = buf; i < MB_CUR_MAX; i++) {
		if ((c = getc(fp)) == EOF)
			return c;
		*p++ = c;
		if ((n = mbtowc(&wc, buf, p-buf)) >= 0)
			break;
	}
	if (n == 1)	/* real ascii, presumably */
		return wc;
	if (n == 0)
		return p[-1];	/* illegal, but what else to do? */
	if (c == EOF)
		return EOF;
	*p = 0;
	return chadd(buf, MBchar, Install);	/* add name even if haven't seen it */
}
#endif	/*UNICODE*/

void pushback(Tchar *b)
{
	Tchar *ob = b;

	while (*b++)
		;
	b--;
	while (b > ob && pbp < &pbbuf[NC-3])
		*pbp++ = *--b;
	if (pbp >= &pbbuf[NC-3]) {
		ERROR "pushback overflow" WARN;
		done(2);
	}
}

void cpushback(char *b)
{
	char *ob = b;

	while (*b++)
		;
	b--;
	while (b > ob && pbp < &pbbuf[NC-3])
		*pbp++ = *--b;
	if (pbp >= &pbbuf[NC-3]) {
		ERROR "cpushback overflow" WARN;
		done(2);
	}
}

int nextfile(void)
{
	char *p;

n0:
	if (ifile != stdin)
		fclose(ifile);
	if (ifi > 0 && !nx) {
		if (popf())
			goto n0; /* popf error */
		return(1);	 /* popf ok */
	}
	if (nx || nmfi < mflg) {
		p = mfiles[nmfi++];
		if (*p != 0)
			goto n1;
	}
	if (rargc-- <= 0) {
		if ((nfo -= mflg) && !stdi) {
			done(0);
}
		nfo++;
		numtabp[CD].val = stdi = mflg = 0;
		ifile = stdin;
		strcpy(cfname[ifi], "stdin");
		return(0);
	}
	p = (argp++)[0];
	if (rargc >= 0)
		cfname[ifi][0] = 0;
n1:
	numtabp[CD].val = 0;
	if (p[0] == '-' && p[1] == 0) {
		ifile = stdin;
		strcpy(cfname[ifi], "stdin");
	} else if ((ifile = fopen(unsharp(p), "r")) == NULL) {
		ERROR "cannot open file %s", p WARN;
		nfo -= mflg;
		done(02);
	} else
		strcpy(cfname[ifi],p);
	nfo++;
	return(0);
}


popf(void)
{
	--ifi;
	if (ifi < 0) {
		ERROR "popf went negative" WARN;
		return 1;
	}
	numtabp[CD].val = cfline[ifi];	/* restore line counter */
	ip = ipl[ifi];			/* input pointer */
	ifile = ifl[ifi];		/* input FILE * */
	return(0);
}


void flushi(void)
{
	if (nflush)
		return;
	ch = 0;
	copyf++;
	while (!nlflg) {
		if (donef && frame == stk)
			break;
		getch();
	}
	copyf--;
}

/*
 * return 16-bit, ascii/alphabetic character, ignore chars with more bits,
 * (internal names), spaces and special cookies (below 040).
 * Leave STX ETX ENQ ACK and BELL in to maintain compatibility with v7 troff.
 */
getach(void)
{
	Tchar i;
	int j;

	lgf++;
	j = cbits(i = getch());
        if (ismot(i)
	    || j > SHORTMASK
	    || (j <= 040 && j != 002	/*STX*/
			&& j != 003	/*ETX*/
			&& j != 005	/*ENQ*/
			&& j != 006	/*ACK*/
			&& j != 007)) {	/*BELL*/
		ch = i;
		j = 0;
	}
	lgf--;
	return j;
}


void casenx(void)
{
	lgf++;
	skip();
	getname();
	nx++;
	if (nmfi > 0)
		nmfi--;
	strcpy(mfiles[nmfi], nextf);
	nextfile();
	nlflg++;
	ip = 0;
	pendt = 0;
	frame = stk;
	nxf = frame + 1;
}


getname(void)
{
	int j, k;
	Tchar i;

	lgf++;
	for (k = 0; k < NS - 1; k++) {
		j = getach();
		if (!j)
			break;
		nextf[k] = j;
	}
	nextf[k] = 0;
	lgf--;
	return(nextf[0]);
}


void caseso(void)
{
	FILE *fp;
	char *p, *q;

	lgf++;
	nextf[0] = 0;
	if (skip() || !getname() || (fp = fopen(unsharp(nextf), "r")) == NULL || ifi >= NSO) {
		ERROR "can't open file %s", nextf WARN;
		done(02);
	}
	strcpy(cfname[ifi+1], nextf);
	cfline[ifi] = numtabp[CD].val;		/*hold line counter*/
	numtabp[CD].val = 0;
	flushi();
	ifl[ifi] = ifile;
	ifile = fp;
	ipl[ifi] = ip;
	ip = 0;
	nx++;
	nflush++;
	ifi++;
}

void caself(void)	/* set line number and file */
{
	int n;

	if (skip())
		return;
	n = atoi0();
	if (!nonumb)
		cfline[ifi] = numtabp[CD].val = n - 1;
	if (!skip())
		if (getname()) {	/* eats '\n' ? */
			strcpy(cfname[ifi], nextf);
			if (!nonumb)
				numtabp[CD].val--;
		}
}

void cpout(FILE *fin, char *token)
{
	int n;
	char buf[1024];

	if (token) {	/* BUG: There should be no NULL bytes in input */
		char *newl = buf;
		while ((fgets(buf, sizeof buf, fin)) != NULL) {
			if (newl) {
				numtabp[CD].val++; /* line number */
				if (strcmp(token, buf) == 0)
					return;
			}
			newl = strchr(buf, '\n');
			fputs(buf, ptid);
		}
	} else {
		while ((n = fread(buf, sizeof *buf, sizeof buf, fin)) > 0)
			fwrite(buf, n, 1, ptid);
		fclose(fin);
	}
}

void casecf(void)
{	/* copy file without change */
	FILE *fd;
	char *eof, *p;
	extern int hpos, esc, po;

	/* this may not make much sense in nroff... */

	lgf++;
	nextf[0] = 0;
	if (!skip() && getname()) {
		if (strncmp("<<", nextf, 2) != 0) {
			if ((fd = fopen(unsharp(nextf), "r")) == NULL) {
				ERROR "can't open file %s", nextf WARN;
				done(02);
			}
			eof = (char *) NULL;
		} else {	/* current file */
			if (pbp > lastpbp || ip) {
				ERROR "casecf: not reading from file" WARN;
				done(02);
			}
			eof = &nextf[2];
			if (!*eof)  {
				ERROR "casecf: missing end of input token" WARN;
				done(02);
			}
			p = eof;
			while(*++p)
				;
			*p++ = '\n';
			*p = 0;
			fd = ifile;
		}
	} else {
		ERROR "casecf: no argument" WARN;
		lgf--;
		return;
	}
	lgf--;

	/* make it into a clean state, be sure that everything is out */
	tbreak();
	hpos = po;
	esc = 0;
	ptesc();	/* to left margin */
	esc = un;
	ptesc();
	ptlead();
	ptps();
	ptfont();
	flusho();
	cpout(fd, eof);
	ptps();
	ptfont();
}

void getline(char *s, int n)	/* get rest of input line into s */
{
	int i;

	lgf++;
	copyf++;
	skip();
	for (i = 0; i < n-1; i++)
		if ((s[i] = cbits(getch())) == '\n' || s[i] == RIGHT)
			break;
	s[i] = 0;
	copyf--;
	lgf--;
}

void casesy(void)	/* call system */
{
	char sybuf[NTM];

	getline(sybuf, NTM);
	system(sybuf);
}


void getpn(char *a)
{
	int n, neg;

	if (*a == 0)
		return;
	neg = 0;
	for ( ; *a; a++)
		switch (*a) {
		case '+':
		case ',':
			continue;
		case '-':
			neg = 1;
			continue;
		default:
			n = 0;
			if (isdigit(*a)) {
				do
					n = 10 * n + *a++ - '0';
				while (isdigit(*a));
				a--;
			} else
				n = 9999;
			*pnp++ = neg ? -n : n;
			neg = 0;
			if (pnp >= &pnlist[NPN-2]) {
				ERROR "too many page numbers" WARN;
				done3(-3);
			}
		}
	if (neg)
		*pnp++ = -9999;
	*pnp = -INT_MAX;
	print = 0;
	pnp = pnlist;
	if (*pnp != -INT_MAX)
		chkpn();
}


void setrpt(void)
{
	Tchar i, j;

	copyf++;
	raw++;
	i = getch0();
	copyf--;
	raw--;
	if ((long) i < 0 || cbits(j = getch0()) == RPT)
		return;
	while (i > 0 && pbp < &pbbuf[NC-3]) {
		i--;
		*pbp++ = j;
	}
}
