/* wasp - copyright Steven Reiz 1990, 1991
 * see wasp.c for further info
 * io.c, 30/5/91 - 2/6/91, 8/7/91
 */

#include "wasp.h"
#ifndef NOSH
#include "io.sh"
#endif

extern int errno;

#ifdef __STDC__
cread(void *buf, int len)
#else
cread(buf, len)
void *buf;
int len;
#endif
{
	int rr;

	if ((rr=read(infd, buf, len))!=len) {
		if (rr<0)
			error1(E0_FATAL, E1_IO, E2_READ, E3_ERRNO, infilename);
		else
			error1(E0_FATAL, E1_IO, E2_READ, E3_UNEXPEND, infilename);
	}
}


#ifdef __STDC__
cwrite(void *buf, int len)
#else
cwrite(buf, len)
void *buf;
int len;
#endif
{
	if (write(outfd, buf, len)!=len)
		error1(E0_FATAL, E1_IO, E2_WRITE, E3_ERRNO, outfilename);
}


#ifdef __STDC__
wrl(u_long l)
#else
wrl(l)
u_long l;
#endif
{
	cwrite(&l, 4);
}


printe(char *s, ...)
{
	va_list argp;

	va_start(argp, s);
	vfprintf(stderr, s, argp);
	va_end(argp);
}


#ifdef __STDC__
pute(char c)
#else
pute(c)
char c;
#endif
{
	putc(c, stderr);
}


static int co, cur, step, dir, len, last1;

init_counter(int start, int end, int instep, char *s, ...)
{
	va_list argp;

	va_start(argp, s);
	if (start<=end)
		dir=1;
	else
		dir= -1;
	step=instep;
	if (step<0)
		step= -step;
	cur=start;
	co=1;
	last1=end;
	len=printe("\r       [%d..%d] ", start, end)-1;
	if (s)
		len+=vfprintf(stderr, s, argp);
	pute('\r');
	fflush(stderr);
	va_end(argp);
}


#ifdef __STDC__
counter(void)
#else
counter()
#endif
{
	if (--co && (co!=1 || ((dir<0 && cur-step>last1) || (dir>=0 && cur+step<last1))))
		return;
	printe("\r%6d", cur);
	co=step;
	if (dir<0)
		cur-=step;
	else
		cur+=step;
	fflush(stderr);
}


erase_counter(char *s, ...)
{
	va_list argp;
	int l1;

	va_start(argp, s);
	pute('\r');
	if (s)
		l1=vfprintf(stderr, s, argp);
	else
		l1=0;
	while (l1++ <len)
		pute(' ');
	pute(s ? '\n' : '\r');
	fflush(stderr);
	va_end(argp);
}


#ifdef __STDC__
prin1(char *p)
#else
prin1(p)
char *p;
#endif
{
	if (p)
		printe("%s ", p);
}


errorx(long code, ...)
{
	va_list argp;
	char c0, c1, c2, c3;
	char *p;

	va_start(argp, code);
	c0=code>>24;
	c1=code>>16;
	c2=code>>8;
	c3=code;
	if (c0==E0_INTERNAL) {
		printe("internal error in wasp %s, file %s, line %ld; please report to sreiz@cs.vu.nl\n",
		 version, va_arg(argp, char *), code&0x00ffffff);
		exit(1);
	}
	assert(c0>E0_INTERNAL && c0<E0_NUM && c1>0 && c1<E1_NUM && c2>0
	 && c2<E2_NUM && c3>0 && c3<E3_NUM);
	prin1(e0_s[c0].s1);
	prin1(e1_s[c1]);
	prin1(e2_s[c2]);
	p=e0_s[c0].s2;
	if (p)
		printe("%s", p);
	if (c3==E3_ERRNO) {
		printe(" in ");
		perror(va_arg(argp, char *));
	} else {
		p=e3_s[c3];
		if (p) {
			printe(": ");
			vfprintf(stderr, p, argp);
		}
		pute('\n');
	}
	if (c0==E0_FATAL)
		exit(1);
	va_end(argp);
}
