1: /*
2: * Copyright (c) 1982, 1986 Regents of the University of California.
3: * All rights reserved. The Berkeley software License Agreement
4: * specifies the terms and conditions for redistribution.
5: *
6: * @(#)ct.c 7.1 (Berkeley) 6/5/86
7: */
8:
9: #include "ct.h"
10: #if NCT > 0
11: /*
12: * GP DR11C driver used for C/A/T or Autologic APS micro-5
13: */
14: #include "../machine/pte.h"
15:
16: #include "param.h"
17: #include "systm.h"
18: #include "ioctl.h"
19: #include "tty.h"
20: #include "map.h"
21: #include "buf.h"
22: #include "conf.h"
23: #include "dir.h"
24: #include "user.h"
25: #include "kernel.h"
26:
27: #include "ubareg.h"
28: #include "ubavar.h"
29:
30: #define PCAT (PZERO+9)
31: #define CATHIWAT 100
32: #define CATLOWAT 30
33:
34: #define REQUEST_B 0x8000
35: #define REQUEST_A 0x80
36: #define INT_ENB_A 0x40
37: #define INT_ENB_B 0x20
38: #define CSR1 0x2
39: #define CSR0 0x1
40:
41: struct ct_softc {
42: int sc_state;
43: struct clist sc_oq;
44: } ct_softc[NCT];
45:
46: #define CT_OPEN 0x1
47: #define CT_RUNNING 0x2
48:
49: struct ctdevice {
50: u_short ctcsr;
51: u_short ctobuf;
52: u_short ctibuf;
53: };
54:
55: int ctprobe(), ctattach(), ctintr();
56: struct uba_device *ctdinfo[NCT];
57: u_short ctstd[] = { 0167770, 0 };
58: struct uba_driver ctdriver =
59: { ctprobe, 0, ctattach, 0, ctstd, "ct", ctdinfo };
60:
61: #define CTUNIT(dev) (minor(dev))
62:
63: int ct_init = 0; /* set to CSR1 for testing loopback on controller */
64:
65: ctprobe(reg)
66: caddr_t reg;
67: {
68: register int br, cvec; /* value-result */
69: register struct ctdevice *ctaddr = (struct ctdevice *)reg;
70:
71: #ifdef lint
72: br = 0; cvec = br; br = cvec;
73: ctintr(0);
74: #endif
75: /*
76: * There is no way to make a DR11c interrupt without some
77: * external support. We can't always trust that the typesetter
78: * will be online and ready so we've made other provisions.
79: * This probe assumes setting the B Int Enb will generate
80: * an interrupt. To do this, we set CSR0 and loop this back
81: * to REQUEST_B in the second plug on the controller.
82: * Then, we reset the vector to be that for the "real" device.
83: */
84: ctaddr->ctcsr = INT_ENB_B | CSR0; /* Assume hardware loopback! */
85: DELAY(1000);
86: ctaddr->ctcsr = ct_init; /* should be CSR1 for loopback testing */
87: if (cvec & 04) {
88: printf("ct: resetting vector %o to %o\n", cvec, cvec&0773);
89: cvec &= 0773;
90: }
91: return (sizeof (struct ctdevice));
92: }
93:
94: /*ARGSUSED*/
95: ctattach(ui)
96: struct uba_device *ui;
97: {
98: }
99:
100: ctopen(dev)
101: dev_t dev;
102: {
103: register struct ct_softc *sc;
104: register struct uba_device *ui;
105: register struct ctdevice *ctaddr;
106:
107: if (CTUNIT(dev) >= NCT || (ui = ctdinfo[CTUNIT(dev)]) == 0 ||
108: ui->ui_alive == 0)
109: return (ENODEV);
110: if ((sc = &ct_softc[CTUNIT(dev)])->sc_state&CT_OPEN)
111: return (EBUSY);
112: sc->sc_state = CT_OPEN;
113: ctaddr = (struct ctdevice *)ui->ui_addr;
114: ctaddr->ctcsr |= INT_ENB_A;
115: return (0);
116: }
117:
118: ctclose(dev)
119: dev_t dev;
120: {
121: ct_softc[CTUNIT(dev)].sc_state = 0;
122: ctintr(dev);
123: return (0);
124: }
125:
126: ctwrite(dev, uio)
127: dev_t dev;
128: struct uio *uio;
129: {
130: register struct ct_softc *sc = &ct_softc[CTUNIT(dev)];
131: register int c;
132: int s;
133:
134: while ((c = uwritec(uio)) >= 0) {
135: s = spl5();
136: while (sc->sc_oq.c_cc > CATHIWAT)
137: sleep((caddr_t)&sc->sc_oq, PCAT);
138: while (putc(c, &sc->sc_oq) < 0)
139: sleep((caddr_t)&lbolt, PCAT);
140: if ( ! (sc->sc_state & CT_RUNNING) )
141: ctintr(dev);
142: splx(s);
143: }
144: return (0);
145: }
146:
147: /*
148: * The C/A/T is usually wired to accept data on the .5us DATA_AVAIL strobe.
149: * If you use this with a C/A/T you can remove the lines with "APSu5" below.
150: * This is way out of spec for the Autologic APS micro-5 which requires
151: * at least a 40 microsec strobe. We therefore use CSR1 output as the
152: * "strobe". It is set after data is loaded and reset only in the
153: * interrupt routine. Therefore, the "strobe" is high for adequate time.
154: * The constant "ctdelay" determines the "low" time for the strobe
155: * and may have to be larger on a 780. "2" gives about 10us on a 750.
156: */
157: int ctdelay = 2; /* here so it's visible & changeable */
158:
159: ctintr(dev)
160: dev_t dev;
161: {
162: register int c;
163: register struct ct_softc *sc = &ct_softc[CTUNIT(dev)];
164: register struct ctdevice *ctaddr =
165: (struct ctdevice *)ctdinfo[CTUNIT(dev)]->ui_addr;
166:
167: if ((ctaddr->ctcsr&(INT_ENB_B|REQUEST_B)) == (INT_ENB_B|REQUEST_B)) {
168: ctaddr->ctcsr &= ~(CSR0 | INT_ENB_B); /* set in ctprobe */
169: }
170: if ((ctaddr->ctcsr&(INT_ENB_A|REQUEST_A)) == (INT_ENB_A|REQUEST_A)) {
171: if ((c = getc(&sc->sc_oq)) >= 0) {
172: ctaddr->ctcsr &= ~CSR1; /* APSu5 - drop strobe */
173: ctaddr->ctobuf = c;
174: DELAY(ctdelay); /* APSu5 - pause a bit */
175: ctaddr->ctcsr |= CSR1; /* APSu5 - raise strobe */
176: sc->sc_state |= CT_RUNNING;
177: if (sc->sc_oq.c_cc==0 || sc->sc_oq.c_cc==CATLOWAT)
178: wakeup((caddr_t)&sc->sc_oq);
179: } else if (sc->sc_state == 0) {
180: ctaddr->ctcsr = 0;
181: } else
182: sc->sc_state &= ~CT_RUNNING;
183: }
184: }
185: #endif
Defined functions
Defined variables
ctstd
defined in line
57; used 1 times
Defined struct's
Defined macros
CSR0
defined in line
39; used 2 times
CSR1
defined in line
38; used 2 times
PCAT
defined in line
30; used 2 times