1 /* va.c 4.5 12/30/80 */ 2 3 #include "va.h" 4 #if NVA > 0 5 /* 6 * Benson-Varian matrix printer/plotter 7 * dma interface driver 8 */ 9 #include "../h/param.h" 10 #include "../h/dir.h" 11 #include "../h/user.h" 12 #include "../h/buf.h" 13 #include "../h/systm.h" 14 #include "../h/map.h" 15 #include "../h/pte.h" 16 #include "../h/uba.h" 17 #include "../h/vcmd.h" 18 19 int vabdp = 1; 20 21 unsigned minvaph(); 22 23 #define VAPRI (PZERO-1) 24 25 #define ushort unsigned short 26 struct varegs { 27 ushort vaba; 28 short vawc; 29 union { 30 short Vacsw; 31 struct { 32 char Vacsl; 33 char Vacsh; 34 } vacsr; 35 } vacs; 36 short vadata; 37 }; 38 39 #define vacsw vacs.Vacsw 40 #define vacsh vacs.vacsr.Vacsh 41 #define vacsl vacs.vacsr.Vacsl 42 43 /* vacsw bits */ 44 #define ERROR 0100000 /* Some error has occurred */ 45 #define NPRTIMO 01000 /* DMA timeout error */ 46 #define NOTREADY 0400 /* Something besides NPRTIMO */ 47 #define DONE 0200 48 #define IENABLE 0100 /* Interrupt enable */ 49 #define SUPPLIESLOW 04 50 #define BOTOFFORM 02 51 #define BYTEREVERSE 01 /* Reverse byte order in words */ 52 53 /* vacsh command bytes */ 54 #define VAPLOT 0340 55 #define VAPRINT 0100 56 #define VAPRINTPLOT 0160 57 #define VAAUTOSTEP 0244 58 #define VANOAUTOSTEP 0045 /* unused */ 59 #define VAFORMFEED 0263 /* unused */ 60 #define VASLEW 0265 /* unused */ 61 #define VASTEP 0064 /* unused */ 62 63 struct { 64 char va_open; 65 char va_busy; 66 int va_state; /* State: bits are commands in vcmd.h. */ 67 int va_wc; 68 int va_bufp; 69 struct buf *va_bp; 70 } va11; 71 int va_ubinfo; 72 73 struct buf rvabuf; /* Used by physio for a buffer. */ 74 75 vaopen() 76 { 77 78 if (va11.va_open) { 79 u.u_error = ENXIO; 80 return; 81 } 82 va11.va_open = 1; 83 VAADDR->vawc = 0; 84 va11.va_wc = 0; 85 va11.va_state = 0; 86 VAADDR->vacsl = IENABLE; 87 vatimo(); 88 vacmd(VPRINT); 89 if (u.u_error) 90 vaclose(); 91 } 92 93 vastrategy(bp) 94 register struct buf *bp; 95 { 96 register int e; 97 98 (void) spl4(); 99 while (va11.va_busy) 100 sleep((caddr_t)&va11, VAPRI); 101 va11.va_busy = 1; 102 va11.va_bp = bp; 103 va_ubinfo = ubasetup(bp, vabdp); 104 va11.va_bufp = va_ubinfo & 0x3ffff; 105 if (e = vaerror(DONE)) 106 goto brkout; 107 va11.va_wc = -(bp->b_bcount/2); 108 vastart(); 109 e = vaerror(DONE); /* Wait for DMA to complete */ 110 va11.va_wc = 0; 111 va11.va_bufp = 0; 112 113 /* 114 * After printing a line of characters, VPRINTPLOT mode essentially 115 * reverts to VPLOT mode, plotting things until a new mode is set. 116 * This change is indicated by sending a VAAUTOSTEP command to 117 * the va. We also change va_state to reflect this effective 118 * mode change. 119 */ 120 if (va11.va_state & VPRINTPLOT) { 121 va11.va_state = (va11.va_state & ~VPRINTPLOT) | VPLOT; 122 VAADDR->vacsh = VAAUTOSTEP; 123 e |= vaerror(DONE); 124 } 125 (void) spl0(); 126 brkout: 127 ubarelse(&va_ubinfo); 128 va11.va_bp = 0; 129 va11.va_busy = 0; 130 iodone(bp); 131 if (e) 132 u.u_error = EIO; 133 wakeup((caddr_t)&va11); 134 } 135 136 int vablock = 16384; 137 138 unsigned 139 minvaph(bp) 140 struct buf *bp; 141 { 142 if (bp->b_bcount > vablock) 143 bp->b_bcount = vablock; 144 } 145 146 /*ARGSUSED*/ 147 vawrite(dev) 148 { 149 physio(vastrategy, &rvabuf, dev, B_WRITE, minvaph); 150 } 151 152 /* 153 * Vaerror waits until bit or ERROR gets set, then returns non-zero if 154 * if it was ERROR that was set. 155 */ 156 vaerror(bit) 157 { 158 register int e; 159 160 while ((e = VAADDR->vacsw & (bit|ERROR)) == 0) 161 sleep((caddr_t)&va11, VAPRI); 162 return (e & ERROR); 163 } 164 165 vastart() 166 { 167 if (va11.va_wc) { 168 VAADDR->vaba = va11.va_bufp; 169 VAADDR->vacsl = (va11.va_bufp >> 12) & 0x30; 170 VAADDR->vawc = va11.va_wc; 171 return; 172 } 173 } 174 175 /*ARGSUSED*/ 176 vaioctl(dev, cmd, addr, flag) 177 register caddr_t addr; 178 { 179 register int vcmd; 180 181 switch (cmd) { 182 183 case VGETSTATE: 184 (void) suword(addr, va11.va_state); 185 return; 186 187 case VSETSTATE: 188 vcmd = fuword(addr); 189 if (vcmd == -1) { 190 u.u_error = EFAULT; 191 return; 192 } 193 vacmd(vcmd); 194 return; 195 196 default: 197 u.u_error = ENOTTY; /* Not a legal ioctl cmd. */ 198 return; 199 } 200 } 201 202 /* 203 * Send a command code to the va, and wait for it to complete. 204 * If an error occurs, u.u_error is set to EIO. 205 * In any case, update va11.va_state. 206 */ 207 vacmd(vcmd) 208 { 209 (void) spl4(); 210 (void) vaerror(DONE); /* Wait for va to be ready */ 211 switch (vcmd) { 212 213 case VPLOT: 214 /* Must turn on plot AND autostep modes. */ 215 VAADDR->vacsh = VAPLOT; 216 if (vaerror(DONE)) 217 u.u_error = EIO; 218 VAADDR->vacsh = VAAUTOSTEP; 219 break; 220 221 case VPRINT: 222 VAADDR->vacsh = VAPRINT; 223 break; 224 225 case VPRINTPLOT: 226 VAADDR->vacsh = VAPRINTPLOT; 227 break; 228 } 229 va11.va_state = 230 (va11.va_state & ~(VPLOT | VPRINT | VPRINTPLOT)) | vcmd; 231 232 if (vaerror(DONE)) /* Wait for command to complete. */ 233 u.u_error = EIO; 234 (void) spl0(); 235 } 236 237 vatimo() 238 { 239 if (va11.va_open) 240 timeout(vatimo, (caddr_t)0, HZ/10); 241 vaintr(0); 242 } 243 244 /*ARGSUSED*/ 245 vaintr(dev) 246 { 247 wakeup((caddr_t)&va11); 248 } 249 250 vaclose() 251 { 252 253 va11.va_open = 0; 254 va11.va_busy = 0; 255 va11.va_state = 0; 256 va11.va_wc = 0; 257 va11.va_bufp = 0; 258 VAADDR->vacsl = 0; 259 } 260 261 #define DELAY(N) { register int d; d = N; while (--d > 0); } 262 263 vareset() 264 { 265 266 if (va11.va_open == 0) 267 return; 268 printf(" va"); 269 VAADDR->vacsl = IENABLE; 270 if (va11.va_state & VPLOT) { 271 VAADDR->vacsh = VAPLOT; 272 DELAY(10000); 273 VAADDR->vacsh = VAAUTOSTEP; 274 } else if (va11.va_state & VPRINTPLOT) 275 VAADDR->vacsh = VPRINTPLOT; 276 else 277 VAADDR->vacsh = VAPRINTPLOT; 278 DELAY(10000); 279 if (va11.va_busy == 0) 280 return; 281 if (va_ubinfo) { 282 printf("<%d>", (va_ubinfo>>28)&0xf); 283 ubarelse(&va_ubinfo); 284 } 285 /* This code belongs in vastart() */ 286 va_ubinfo = ubasetup(va11.va_bp, vabdp); 287 va11.va_bufp = va_ubinfo & 0x3ffff; 288 va11.va_wc = (-va11.va_bp->b_bcount/2); 289 /* End badly placed code */ 290 vastart(); 291 } 292 #endif 293