Commit | Line | Data |
---|---|---|
b91c756d | 1 | /* dn.c 4.8 82/10/10 */ |
7119e7c0 BJ |
2 | |
3 | #include "dn.h" | |
4 | #if NDN > 0 | |
5 | /* | |
6 | * DN-11 ACU interface | |
7 | */ | |
8 | ||
9 | #include "../h/param.h" | |
10 | #include "../h/systm.h" | |
11 | #include "../h/dir.h" | |
12 | #include "../h/user.h" | |
13 | #include "../h/buf.h" | |
14 | #include "../h/map.h" | |
15 | #include "../h/pte.h" | |
7119e7c0 BJ |
16 | #include "../h/conf.h" |
17 | #include "../h/ioctl.h" | |
18 | ||
896962b1 BJ |
19 | #include "../vaxuba/ubavar.h" |
20 | ||
7119e7c0 | 21 | struct dndevice { |
401127f3 | 22 | u_short dn_reg[4]; |
7119e7c0 BJ |
23 | }; |
24 | ||
25 | struct uba_device *dninfo[NDN]; | |
26 | int dnprobe(), dnattach(); | |
27 | u_short dnstd[] = { 0175200 }; | |
28 | struct uba_driver dndriver = | |
29 | { dnprobe, 0, dnattach, 0, dnstd, "dn", dninfo }; | |
30 | ||
401127f3 SL |
31 | #define CRQ 0x001 /* call request */ |
32 | #define DPR 0x002 /* digit present */ | |
33 | #define MENABLE 0x004 /* master enable */ | |
34 | #define MAINT 0x008 /* maintenance mode */ | |
35 | #define PND 0x010 /* present next digit */ | |
36 | #define DSS 0x020 /* data set status */ | |
37 | #define IENABLE 0x040 /* interrupt enable */ | |
38 | #define DONE 0x080 /* operation complete */ | |
39 | #define DLO 0x1000 /* data line occupied */ | |
40 | #define ACR 0x4000 /* abandon call and retry */ | |
41 | #define PWI 0x8000 /* power indicate */ | |
7119e7c0 BJ |
42 | |
43 | #define DNPRI (PZERO+5) | |
44 | #define DNUNIT(dev) (minor(dev)>>2) | |
45 | #define DNREG(dev) ((dev)&03) | |
46 | ||
47 | #define OBUFSIZ 40 /* largest phone # dialer can handle */ | |
48 | ||
49 | /* | |
50 | * There's no good way to determine the correct number of dialers attached | |
89b8a44c | 51 | * to a single device (especially when dialers such as Vadic-821 MACS |
401127f3 | 52 | * exist which can address four chassis, each with its own dialer). |
7119e7c0 BJ |
53 | */ |
54 | dnprobe(reg) | |
55 | caddr_t reg; | |
56 | { | |
401127f3 | 57 | register int br, cvec; /* value-result, must be r11, r10 */ |
7119e7c0 BJ |
58 | register struct dndevice *dnaddr = (struct dndevice *)reg; |
59 | ||
60 | /* | |
61 | * If there's at least one dialer out there it better be | |
401127f3 | 62 | * at chassis 0. |
7119e7c0 BJ |
63 | */ |
64 | dnaddr->dn_reg[0] = MENABLE|IENABLE|DONE; | |
65 | DELAY(5); | |
66 | dnaddr->dn_reg[0] = 0; | |
9c0adba0 | 67 | return (sizeof (struct dndevice)); |
7119e7c0 BJ |
68 | } |
69 | ||
70 | dnattach(ui) | |
71 | struct uba_device *ui; | |
401127f3 | 72 | {} |
7119e7c0 BJ |
73 | |
74 | /*ARGSUSED*/ | |
75 | dnopen(dev, flag) | |
76 | dev_t dev; | |
77 | { | |
78 | register struct dndevice *dp; | |
401127f3 | 79 | register u_short unit, *dnreg; |
7119e7c0 BJ |
80 | register struct uba_device *ui; |
81 | register short dialer; | |
82 | ||
83 | if ((unit = DNUNIT(dev)) >= NDN || (ui = dninfo[unit]) == 0 || | |
401127f3 SL |
84 | ui->ui_alive == 0) { |
85 | u.u_error = ENXIO; | |
86 | return; | |
87 | } | |
88 | dialer = DNREG(dev); | |
89 | dp = (struct dndevice *)ui->ui_addr; | |
90 | if (dp->dn_reg[dialer] & PWI) { | |
7119e7c0 BJ |
91 | u.u_error = ENXIO; |
92 | return; | |
93 | } | |
94 | dnreg = &(dp->dn_reg[dialer]); | |
95 | if (*dnreg&(DLO|CRQ)) { | |
96 | u.u_error = EBUSY; | |
97 | return; | |
98 | } | |
99 | dp->dn_reg[0] |= MENABLE; | |
100 | *dnreg = IENABLE|MENABLE|CRQ; | |
101 | } | |
102 | ||
103 | /*ARGSUSED*/ | |
104 | dnclose(dev, flag) | |
105 | dev_t dev; | |
106 | { | |
107 | register struct dndevice *dp; | |
108 | ||
109 | dp = (struct dndevice *)dninfo[DNUNIT(dev)]->ui_addr; | |
110 | dp->dn_reg[DNREG(dev)] = MENABLE; | |
111 | } | |
112 | ||
406ddcbe | 113 | dnwrite(dev, uio) |
7119e7c0 | 114 | dev_t dev; |
406ddcbe | 115 | struct uio *uio; |
7119e7c0 | 116 | { |
401127f3 SL |
117 | register u_short *dnreg; |
118 | register int cc; | |
7119e7c0 | 119 | register struct dndevice *dp; |
401127f3 | 120 | char buf[OBUFSIZ]; |
7119e7c0 BJ |
121 | register char *cp; |
122 | extern lbolt; | |
b91c756d | 123 | int error; |
7119e7c0 BJ |
124 | |
125 | dp = (struct dndevice *)dninfo[DNUNIT(dev)]->ui_addr; | |
126 | dnreg = &(dp->dn_reg[DNREG(dev)]); | |
406ddcbe | 127 | cc = MIN(uio->uio_resid, OBUFSIZ); |
401127f3 | 128 | cp = buf; |
b91c756d BJ |
129 | error = uiomove(cp, (unsigned)cc, UIO_WRITE, uio); |
130 | if (error) | |
131 | return (error); | |
7119e7c0 | 132 | while ((*dnreg & (PWI|ACR|DSS)) == 0 && cc >= 0) { |
401127f3 SL |
133 | spl4(); |
134 | if ((*dnreg & PND) == 0 || cc == 0) | |
7119e7c0 BJ |
135 | sleep((caddr_t)dnreg, DNPRI); |
136 | else switch(*cp) { | |
137 | ||
138 | case '-': | |
139 | sleep((caddr_t)&lbolt, DNPRI); | |
140 | sleep((caddr_t)&lbolt, DNPRI); | |
141 | break; | |
142 | ||
143 | case 'f': | |
144 | *dnreg &= ~CRQ; | |
145 | sleep((caddr_t)&lbolt, DNPRI); | |
146 | *dnreg |= CRQ; | |
147 | break; | |
148 | ||
149 | case '*': case ':': | |
150 | *cp = 012; | |
151 | goto dial; | |
152 | ||
153 | case '#': case ';': | |
154 | *cp = 013; | |
155 | goto dial; | |
156 | ||
157 | case 'e': case '<': | |
158 | *cp = 014; | |
159 | goto dial; | |
160 | ||
161 | case 'w': case '=': | |
162 | *cp = 015; | |
163 | goto dial; | |
164 | ||
165 | default: | |
166 | if (*cp < '0' || *cp > '9') | |
167 | break; | |
168 | dial: | |
401127f3 | 169 | *dnreg = (*cp << 8) | (IENABLE|MENABLE|DPR|CRQ); |
7119e7c0 BJ |
170 | sleep((caddr_t)dnreg, DNPRI); |
171 | } | |
172 | cp++, cc--; | |
173 | spl0(); | |
174 | } | |
401127f3 | 175 | if (*dnreg & (PWI|ACR)) |
b91c756d BJ |
176 | return (EIO); |
177 | return (0); | |
7119e7c0 BJ |
178 | } |
179 | ||
7119e7c0 BJ |
180 | dnintr(dev) |
181 | dev_t dev; | |
182 | { | |
401127f3 | 183 | register u_short *basereg, *dnreg; |
7119e7c0 | 184 | |
401127f3 | 185 | basereg = (u_short *)dninfo[dev]->ui_addr; |
7119e7c0 | 186 | *basereg &= ~MENABLE; |
401127f3 SL |
187 | for (dnreg = basereg; dnreg < basereg + 4; dnreg++) |
188 | if (*dnreg & DONE) { | |
7119e7c0 BJ |
189 | *dnreg &= ~(DONE|DPR); |
190 | wakeup((caddr_t)dnreg); | |
191 | } | |
192 | *basereg |= MENABLE; | |
193 | } | |
194 | #endif |