xref: /freebsd/sys/dev/ppbus/ppi.c (revision 2ad872c5794e4c26fdf6ed219ad3f09ca0d5304a)
1 /*-
2  * Copyright (c) 1997, 1998 Nicolas Souchu, Michael Smith
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24  * SUCH DAMAGE.
25  *
26  *	$Id: ppi.c,v 1.8 1998/12/07 21:58:16 archie Exp $
27  *
28  */
29 #include "ppi.h"
30 
31 #if NPPI > 0
32 
33 #include <sys/param.h>
34 #include <sys/systm.h>
35 #include <sys/conf.h>
36 #include <sys/kernel.h>
37 #include <sys/uio.h>
38 #include <sys/malloc.h>
39 #include <sys/fcntl.h>
40 
41 #include <machine/clock.h>
42 
43 #include <dev/ppbus/ppbconf.h>
44 #include <dev/ppbus/ppb_msq.h>
45 
46 #include "opt_ppb_1284.h"
47 
48 #ifdef PERIPH_1284
49 #include <dev/ppbus/ppb_1284.h>
50 #endif
51 
52 #include <dev/ppbus/ppi.h>
53 
54 #define BUFSIZE		512
55 
56 struct ppi_data {
57 
58     int		ppi_unit;
59     int		ppi_flags;
60 #define HAVE_PPBUS	(1<<0)
61 #define HAD_PPBUS	(1<<1)
62 
63     int		ppi_count;
64     int		ppi_mode;			/* IEEE1284 mode */
65     char	ppi_buffer[BUFSIZE];
66 
67     struct ppb_device ppi_dev;
68 };
69 
70 #define MAXPPI		8			/* XXX not much better! */
71 static int 		nppi = 0;
72 static struct ppi_data	*ppidata[MAXPPI];
73 
74 /*
75  * Make ourselves visible as a ppbus driver
76  */
77 
78 static struct ppb_device	*ppiprobe(struct ppb_data *ppb);
79 static int			ppiattach(struct ppb_device *dev);
80 static void			ppiintr(int unit);
81 
82 static struct ppb_driver ppidriver = {
83     ppiprobe, ppiattach, "ppi"
84 };
85 DATA_SET(ppbdriver_set, ppidriver);
86 
87 static	d_open_t	ppiopen;
88 static	d_close_t	ppiclose;
89 static	d_ioctl_t	ppiioctl;
90 static	d_write_t	ppiwrite;
91 static	d_read_t	ppiread;
92 
93 #define CDEV_MAJOR 82
94 static struct cdevsw ppi_cdevsw =
95 	{ ppiopen,	ppiclose,	ppiread,	ppiwrite,	/* 82 */
96 	  ppiioctl,	nullstop,	nullreset,	nodevtotty,
97 	  seltrue,	nommap,		nostrat,	"ppi",	NULL,	-1 };
98 
99 #ifdef PERIPH_1284
100 
101 static void
102 ppi_enable_intr(struct ppi_data *ppi)
103 {
104 	char r;
105 
106 	r = ppb_rctr(&ppi->ppi_dev);
107 	ppb_wctr(&ppi->ppi_dev, r | IRQENABLE);
108 
109 	return;
110 }
111 
112 static void
113 ppi_disable_intr(struct ppi_data *ppi)
114 {
115 	char r;
116 
117 	r = ppb_rctr(&ppi->ppi_dev);
118 	ppb_wctr(&ppi->ppi_dev, r & ~IRQENABLE);
119 
120 	return;
121 }
122 
123 #endif /* PERIPH_1284 */
124 
125 /*
126  * ppiprobe()
127  */
128 static struct ppb_device *
129 ppiprobe(struct ppb_data *ppb)
130 {
131 	struct ppi_data *ppi;
132 
133 	ppi = (struct ppi_data *) malloc(sizeof(struct ppi_data),
134 							M_TEMP, M_NOWAIT);
135 	if (!ppi) {
136 		printf("ppi: cannot malloc!\n");
137 		return 0;
138 	}
139 	bzero(ppi, sizeof(struct ppi_data));
140 
141 	ppidata[nppi] = ppi;
142 
143 	/*
144 	 * ppi dependent initialisation.
145 	 */
146 	ppi->ppi_unit = nppi;
147 
148 	/*
149 	 * ppbus dependent initialisation.
150 	 */
151 	ppi->ppi_dev.id_unit = ppi->ppi_unit;
152 	ppi->ppi_dev.ppb = ppb;
153 	ppi->ppi_dev.intr = ppiintr;
154 
155 	/* Ok, go to next device on next probe */
156 	nppi ++;
157 
158 	return &ppi->ppi_dev;
159 }
160 
161 static int
162 ppiattach(struct ppb_device *dev)
163 {
164 	/*
165 	 * Report ourselves
166 	 */
167 	printf("ppi%d: <generic parallel i/o> on ppbus %d\n",
168 	       dev->id_unit, dev->ppb->ppb_link->adapter_unit);
169 
170 	return (1);
171 }
172 
173 /*
174  * Cable
175  * -----
176  *
177  * Use an IEEE1284 compliant (DB25/DB25) cable with the following tricks:
178  *
179  * nStrobe   <-> nAck		1  <-> 10
180  * nAutofd   <-> Busy		11 <-> 14
181  * nSelectin <-> Select		17 <-> 13
182  * nInit     <-> nFault		15 <-> 16
183  *
184  */
185 static void
186 ppiintr(int unit)
187 {
188 #ifdef PERIPH_1284
189 	struct ppi_data *ppi = ppidata[unit];
190 
191 	ppi_disable_intr(ppi);
192 
193 	switch (ppi->ppi_dev.ppb->state) {
194 
195 	/* accept IEEE1284 negociation then wakeup an waiting process to
196 	 * continue negociation at process level */
197 	case PPB_FORWARD_IDLE:
198 		/* Event 1 */
199 		if ((ppb_rstr(&ppi->ppi_dev) & (SELECT | nBUSY)) ==
200 							(SELECT | nBUSY)) {
201 			/* IEEE1284 negociation */
202 #ifdef DEBUG_1284
203 			printf("N");
204 #endif
205 
206 			/* Event 2 - prepare for reading the ext. value */
207 			ppb_wctr(&ppi->ppi_dev, (PCD | STROBE | nINIT) & ~SELECTIN);
208 
209 			ppi->ppi_dev.ppb->state = PPB_NEGOCIATION;
210 
211 		} else {
212 #ifdef DEBUG_1284
213 			printf("0x%x", ppb_rstr(&ppi->ppi_dev));
214 #endif
215 			ppb_peripheral_terminate(&ppi->ppi_dev, PPB_DONTWAIT);
216 			break;
217 		}
218 
219 		/* wake up any process waiting for negociation from
220 		 * remote master host */
221 
222 		/* XXX should set a variable to warn the process about
223 		 * the interrupt */
224 
225 		wakeup(ppi);
226 		break;
227 	default:
228 #ifdef DEBUG_1284
229 		printf("?%d", ppi->ppi_dev.ppb->state);
230 #endif
231 		ppi->ppi_dev.ppb->state = PPB_FORWARD_IDLE;
232 		ppb_set_mode(&ppi->ppi_dev, PPB_COMPATIBLE);
233 		break;
234 	}
235 
236 	ppi_enable_intr(ppi);
237 #endif /* PERIPH_1284 */
238 
239 	return;
240 }
241 
242 static int
243 ppiopen(dev_t dev, int flags, int fmt, struct proc *p)
244 {
245 	u_int unit = minor(dev);
246 	struct ppi_data *ppi = ppidata[unit];
247 	int res;
248 
249 	if (unit >= nppi)
250 		return (ENXIO);
251 
252 	if (!(ppi->ppi_flags & HAVE_PPBUS)) {
253 		if ((res = ppb_request_bus(&ppi->ppi_dev,
254 			(flags & O_NONBLOCK) ? PPB_DONTWAIT :
255 						(PPB_WAIT | PPB_INTR))))
256 			return (res);
257 
258 		ppi->ppi_flags |= HAVE_PPBUS;
259 	}
260 	ppi->ppi_count += 1;
261 
262 	return (0);
263 }
264 
265 static int
266 ppiclose(dev_t dev, int flags, int fmt, struct proc *p)
267 {
268 	u_int unit = minor(dev);
269 	struct ppi_data *ppi = ppidata[unit];
270 
271 	ppi->ppi_count --;
272 	if (!ppi->ppi_count) {
273 
274 #ifdef PERIPH_1284
275 		switch (ppi->ppi_dev.ppb->state) {
276 		case PPB_PERIPHERAL_IDLE:
277 			ppb_peripheral_terminate(&ppi->ppi_dev, 0);
278 			break;
279 		case PPB_REVERSE_IDLE:
280 		case PPB_EPP_IDLE:
281 		case PPB_ECP_FORWARD_IDLE:
282 		default:
283 			ppb_1284_terminate(&ppi->ppi_dev);
284 			break;
285 		}
286 #endif /* PERIPH_1284 */
287 
288 		ppb_release_bus(&ppi->ppi_dev);
289 		ppi->ppi_flags &= ~HAVE_PPBUS;
290 	}
291 
292 	return (0);
293 }
294 
295 /*
296  * ppiread()
297  *
298  * IEEE1284 compliant read.
299  *
300  * First, try negociation to BYTE then NIBBLE mode
301  * If no data is available, wait for it otherwise transfer as much as possible
302  */
303 static int
304 ppiread(dev_t dev, struct uio *uio, int ioflag)
305 {
306 #ifdef PERIPH_1284
307 	u_int unit = minor(dev);
308 	struct ppi_data *ppi = ppidata[unit];
309 	int len, error = 0;
310 
311 	switch (ppi->ppi_dev.ppb->state) {
312 	case PPB_PERIPHERAL_IDLE:
313 		ppb_peripheral_terminate(&ppi->ppi_dev, 0);
314 		/* fall throught */
315 
316 	case PPB_FORWARD_IDLE:
317 		/* if can't negociate NIBBLE mode then try BYTE mode,
318 		 * the peripheral may be a computer
319 		 */
320 		if ((ppb_1284_negociate(&ppi->ppi_dev,
321 			ppi->ppi_mode = PPB_NIBBLE, 0))) {
322 
323 			/* XXX Wait 2 seconds to let the remote host some
324 			 * time to terminate its interrupt
325 			 */
326 			tsleep(ppi, PPBPRI, "ppiread", 2*hz);
327 
328 			if ((error = ppb_1284_negociate(&ppi->ppi_dev,
329 				ppi->ppi_mode = PPB_BYTE, 0)))
330 				return (error);
331 		}
332 		break;
333 
334 	case PPB_REVERSE_IDLE:
335 	case PPB_EPP_IDLE:
336 	case PPB_ECP_FORWARD_IDLE:
337 	default:
338 		break;
339 	}
340 
341 #ifdef DEBUG_1284
342 	printf("N");
343 #endif
344 	/* read data */
345 	len = 0;
346 	while (uio->uio_resid) {
347 		if ((error = ppb_1284_read(&ppi->ppi_dev, ppi->ppi_mode,
348 			ppi->ppi_buffer, min(BUFSIZE, uio->uio_resid),
349 			&len))) {
350 			goto error;
351 		}
352 
353 		if (!len)
354 			goto error;		/* no more data */
355 
356 #ifdef DEBUG_1284
357 		printf("d");
358 #endif
359 		if ((error = uiomove(ppi->ppi_buffer, len, uio)))
360 			goto error;
361 	}
362 
363 error:
364 
365 #else /* PERIPH_1284 */
366 	int error = ENODEV;
367 #endif
368 
369 	return (error);
370 }
371 
372 /*
373  * ppiwrite()
374  *
375  * IEEE1284 compliant write
376  *
377  * Actually, this is the peripheral side of a remote IEEE1284 read
378  *
379  * The first part of the negociation (IEEE1284 device detection) is
380  * done at interrupt level, then the remaining is done by the writing
381  * process
382  *
383  * Once negociation done, transfer data
384  */
385 static int
386 ppiwrite(dev_t dev, struct uio *uio, int ioflag)
387 {
388 #ifdef PERIPH_1284
389 	u_int unit = minor(dev);
390 	struct ppi_data *ppi = ppidata[unit];
391 	struct ppb_data *ppb = ppi->ppi_dev.ppb;
392 	int len, error = 0, sent;
393 
394 #if 0
395 	int ret;
396 
397 	#define ADDRESS		MS_PARAM(0, 0, MS_TYP_PTR)
398 	#define LENGTH		MS_PARAM(0, 1, MS_TYP_INT)
399 
400 	struct ppb_microseq msq[] = {
401 		  { MS_OP_PUT, { MS_UNKNOWN, MS_UNKNOWN, MS_UNKNOWN } },
402 		  MS_RET(0)
403 	};
404 
405 	/* negociate ECP mode */
406 	if (ppb_1284_negociate(&ppi->ppi_dev, PPB_ECP, 0)) {
407 		printf("ppiwrite: ECP negociation failed\n");
408 	}
409 
410 	while (!error && (len = min(uio->uio_resid, BUFSIZE))) {
411 		uiomove(ppi->ppi_buffer, len, uio);
412 
413 		ppb_MS_init_msq(msq, 2, ADDRESS, ppi->ppi_buffer, LENGTH, len);
414 
415 		error = ppb_MS_microseq(&ppi->ppi_dev, msq, &ret);
416 	}
417 #endif
418 
419 	/* we have to be peripheral to be able to send data, so
420 	 * wait for the appropriate state
421 	 */
422 	if (ppb->state < PPB_PERIPHERAL_NEGOCIATION)
423 		ppb_1284_terminate(&ppi->ppi_dev);
424 
425 	while (ppb->state != PPB_PERIPHERAL_IDLE) {
426 		/* XXX should check a variable before sleeping */
427 #ifdef DEBUG_1284
428 		printf("s");
429 #endif
430 
431 		ppi_enable_intr(ppi);
432 
433 		/* sleep until IEEE1284 negociation starts */
434 		error = tsleep(ppi, PCATCH | PPBPRI, "ppiwrite", 0);
435 
436 		switch (error) {
437 		case 0:
438 			/* negociate peripheral side with BYTE mode */
439 			ppb_peripheral_negociate(&ppi->ppi_dev, PPB_BYTE, 0);
440 			break;
441 		case EWOULDBLOCK:
442 			break;
443 		default:
444 			goto error;
445 		}
446 	}
447 #ifdef DEBUG_1284
448 	printf("N");
449 #endif
450 
451 	/* negociation done, write bytes to master host */
452 	while (len = min(uio->uio_resid, BUFSIZE)) {
453 		uiomove(ppi->ppi_buffer, len, uio);
454 		if ((error = byte_peripheral_write(&ppi->ppi_dev,
455 						ppi->ppi_buffer, len, &sent)))
456 			goto error;
457 #ifdef DEBUG_1284
458 		printf("d");
459 #endif
460 	}
461 
462 error:
463 
464 #else /* PERIPH_1284 */
465 	int error = ENODEV;
466 #endif
467 
468 	return (error);
469 }
470 
471 static int
472 ppiioctl(dev_t dev, u_long cmd, caddr_t data, int flags, struct proc *p)
473 {
474 	u_int unit = minor(dev);
475 	struct ppi_data *ppi = ppidata[unit];
476 	int error = 0;
477 	u_int8_t *val = (u_int8_t *)data;
478 
479 	switch (cmd) {
480 
481 	case PPIGDATA:			/* get data register */
482 		*val = ppb_rdtr(&ppi->ppi_dev);
483 		break;
484 	case PPIGSTATUS:		/* get status bits */
485 		*val = ppb_rstr(&ppi->ppi_dev);
486 		break;
487 	case PPIGCTRL:			/* get control bits */
488 		*val = ppb_rctr(&ppi->ppi_dev);
489 		break;
490 	case PPIGEPP:			/* get EPP bits */
491 		*val = ppb_repp(&ppi->ppi_dev);
492 		break;
493 	case PPIGECR:			/* get ECP bits */
494 		*val = ppb_recr(&ppi->ppi_dev);
495 		break;
496 	case PPIGFIFO:			/* read FIFO */
497 		*val = ppb_rfifo(&ppi->ppi_dev);
498 		break;
499 
500 	case PPISDATA:			/* set data register */
501 		ppb_wdtr(&ppi->ppi_dev, *val);
502 		break;
503 	case PPISSTATUS:		/* set status bits */
504 		ppb_wstr(&ppi->ppi_dev, *val);
505 		break;
506 	case PPISCTRL:			/* set control bits */
507 		ppb_wctr(&ppi->ppi_dev, *val);
508 		break;
509 	case PPISEPP:			/* set EPP bits */
510 		ppb_wepp(&ppi->ppi_dev, *val);
511 		break;
512 	case PPISECR:			/* set ECP bits */
513 		ppb_wecr(&ppi->ppi_dev, *val);
514 		break;
515 	case PPISFIFO:			/* write FIFO */
516 		ppb_wfifo(&ppi->ppi_dev, *val);
517 		break;
518 	default:
519 		error = ENOTTY;
520 		break;
521 	}
522 
523 	return (error);
524 }
525 
526 #ifdef PPI_MODULE
527 
528 MOD_DEV(ppi, LM_DT_CHAR, CDEV_MAJOR, &ppi_cdevsw);
529 
530 static int
531 ppi_load(struct lkm_table *lkmtp, int cmd)
532 {
533 	struct ppb_data *ppb;
534 	struct ppb_device *dev;
535 	int i;
536 
537 	for (ppb = ppb_next_bus(NULL); ppb; ppb = ppb_next_bus(ppb)) {
538 
539 		dev = ppiprobe(ppb);
540 		ppiattach(dev);
541 
542 		ppb_attach_device(dev);
543 	}
544 
545 	return (0);
546 }
547 
548 static int
549 ppi_unload(struct lkm_table *lkmtp, int cmd)
550 {
551 	int i;
552 
553 	for (i = nppi-1; i > 0; i--) {
554 		ppb_remove_device(&ppidata[i]->ppi_dev);
555 		free(ppidata[i], M_TEMP);
556 	}
557 
558 	return (0);
559 }
560 
561 int
562 ppi_mod(struct lkm_table *lkmtp, int cmd, int ver)
563 {
564 	DISPATCH(lkmtp, cmd, ver, ppi_load, ppi_unload, lkm_nullcmd);
565 }
566 
567 #endif /* PPI_MODULE */
568 
569 static ppi_devsw_installed = 0;
570 
571 static void ppi_drvinit(void *unused)
572 {
573 	dev_t dev;
574 
575 	if (!ppi_devsw_installed ) {
576 		dev = makedev(CDEV_MAJOR, 0);
577 		cdevsw_add(&dev, &ppi_cdevsw, NULL);
578 		ppi_devsw_installed = 1;
579     	}
580 }
581 
582 SYSINIT(ppidev,SI_SUB_DRIVERS,SI_ORDER_MIDDLE+CDEV_MAJOR,ppi_drvinit,NULL)
583 
584 #endif /* NPPI */
585