V4/nsys/dmr/dc.c

Compare this file to the similar file:
Show the results in this format:

#
/*
 *   DC-11 driver
 */
#include "/sys/nsys/param.h"
#include "/sys/nsys/conf.h"
#include "/sys/nsys/user.h"
#include "/sys/nsys/tty.h"
#include "/sys/nsys/proc.h"

/* base address */
#define	DCADDR	0174000

/* Control bits */
#define	CDLEAD	01
#define	CARRIER	04
#define	SPEED1	010
#define	STOP1	0400
#define	RQSEND	01
#define	PARITY	040
#define	ERROR	0100000
#define	CTRANS	040000
#define	RINGIND	020000


struct	tty dc11[NDC11];

struct dcregs {
	int dcrcsr;
	int dcrbuf;
	int dctcsr;
	int dctbuf;
};

struct {
	char	lbyte;
	char	hbyte;
};

int dcrstab[] {
	0,		/* 0 baud */
	0,		/* 75 baud */
	0,		/* 110 baud */
	01101,		/* 134.5 baud: 7b/ch, speed 0 */
	0111,		/* 150 baud: 8b/ch, speed 1 */
	0121,		/* 300 baud: 8b/ch, speed 2 */
	0,		/* 600 baud */
	0131,		/* 1200 baud */
	0,		/* 1800 baud */
	0,		/* 2400 baud */
	0,		/* 4800 baud */
	0,		/* 9600 baud */
	0,		/* X0 */
	0,		/* X1 */
	0,		/* X2 */
	0		/* X3 */
};

int dctstab[] {
	0,		/* 0 baud */
	0,		/* 75 baud */
	0,		/* 110 baud */
	0501,		/* 134.5 baud: stop 1 */
	0511,		/* 150 baud */
	0521,		/* 300 baud */
	0,		/* 600 baud */
	0531,		/* 1200 baud */
	0,		/* 1800 baud */
	0,		/* 2400 baud */
	0,		/* 4800 baud */
	0,		/* 9600 baud */
	0,		/* X0 */
	0,		/* X1 */
	0,		/* X2 */
	0		/* X3 */
};

dcopen(dev, flag)
{
	struct tty *tp;
	register struct tty *rtp;
	int *addr;

	if (dev.d_minor >= NDC11) {
		u.u_error = ENXIO;
		return;
	}
	rtp = tp = &dc11[dev.d_minor];
	rtp->t_addr = addr = DCADDR + dev.d_minor*8;
	rtp->t_state =| WOPEN;
	addr->dcrcsr =| IENABLE|CDLEAD;
	if ((rtp->t_state&ISOPEN) == 0) {
		rtp->t_quit = 034;		/* FS */
		rtp->t_intrup = 0177;		/* DEL */
		addr->dcrcsr = IENABLE|CDLEAD|SPEED1;
		addr->dctcsr = IENABLE|SPEED1|STOP1|RQSEND;
		rtp->t_state = ISOPEN | WOPEN;
		rtp->t_flags = ODDP|EVENP|ECHO;
	}
	while (((addr->dcrcsr) & CARRIER) == 0)
		sleep(&tp->t_rawq, TTIPRI);
	tp->t_state =& ~WOPEN;
	if (u.u_procp->p_ttyp == 0)
		u.u_procp->p_ttyp = tp;
}

dcclose(dev)
{
	register struct tty *tp;

	(tp = &dc11[dev.d_minor])->t_state = 0;
	wflushtty(tp);
}

dcread(dev)
{
	register struct tty *tp;

	tp = &dc11[dev.d_minor];
	if ((tp->t_addr->dcrcsr&CARRIER) != 0)
		ttread(tp);
}

dcwrite(dev)
{
	register struct tty *tp;

	tp = &dc11[dev.d_minor];
	if ((tp->t_addr->dcrcsr & CARRIER) != 0)
		ttwrite(tp);
}

dcxint(dev)
{
	struct tty *tp;

	ttstart(tp = &dc11[dev.d_minor]);
	if (tp->t_outq.c_cc <= TTLOWAT)
		wakeup(&tp->t_outq);
}

dcrint(dev)
{
	struct tty *tp;
	register struct tty *rtp;
	register int c, csr;

	tp = rtp = &dc11[dev.d_minor];
	c = rtp->t_addr->dcrbuf;
	if (((csr = rtp->t_addr->dcrcsr) & CARRIER) == 0) {
		if ((rtp->t_state&WOPEN) == 0) {
			rtp->t_addr->dcrcsr =& ~CDLEAD;
			signal(rtp, SIGHUP);
			flushtty(tp);
		}
		return;
	}
	if (csr&ERROR || (rtp->t_state&ISOPEN)==0) {
		wakeup(rtp);
		return;
	}
	csr =& PARITY;
	if (csr&&(rtp->t_flags&ODDP) || !csr&&(rtp->t_flags&EVENP))
		ttyinput(c, rtp);
}

dcsgtty(dev, v)
int *v;
{
	register struct tty *tp;
	struct tty *atp;
	register r;

	tp = &dc11[dev.d_minor];
	if (v) {
		v[0] = tp->t_speeds;
		v[1] = 0;
		v[2] = tp->t_flags;
		return;
	}
	atp = tp;
	wflushtty(tp);
	tp = atp;
	tp->t_speeds = u.u_arg[0];
	tp->t_flags = u.u_arg[2];
	if (r = dcrstab[tp->t_speeds.lbyte&017])
		tp->t_addr->dcrcsr = r;
	if (r = dctstab[tp->t_speeds.hbyte&017])
		tp->t_addr->dctcsr = r;
}