xref: /inferno-os/os/mpc/800io.h (revision 74a4d8c26dd3c1e9febcb717cfd6cb6512991a7a)
1 typedef struct BD BD;
2 typedef struct CPMdev CPMdev;
3 typedef struct GTimer GTimer;
4 typedef struct I2Cdev I2Cdev;
5 typedef struct PCMconftab PCMconftab;
6 typedef struct PCMmap	PCMmap;
7 typedef struct PCMslot	PCMslot;
8 typedef struct Ring Ring;
9 
10 /*
11  * MPC800 series IO structures
12  */
13 
14 enum
15 {
16 	/* interrupt vectors (SIU and CPM) */
17 	VectorPIC= 0,	/* level 0 to level 7, assigned by software */
18 		/* vector assignments are determined by the assignments here */
19 		PITlevel=	2,
20 		CPIClevel=	4,
21 		PCMCIAio=	5,
22 		PCMCIAstatus=	6,
23 		RTClevel=	7,
24 	VectorIRQ=	VectorPIC+8,	/* IRQ0 to IRQ7 */
25 	VectorCPIC=	VectorIRQ+8,	/* 32 CPM interrupts: 0 (error) to 0x1F (PC15) */
26 	MaxVector=	VectorCPIC+32,
27 };
28 
29 /*
30  * these are defined to keep the interface compatible with other
31  * architectures, but only BUSUNKNOWN is currently used
32  */
33 #define MKBUS(t,b,d,f)	(((t)<<24)|(((b)&0xFF)<<16)|(((d)&0x1F)<<11)|(((f)&0x07)<<8))
34 #define BUSFNO(tbdf)	(((tbdf)>>8)&0x07)
35 #define BUSDNO(tbdf)	(((tbdf)>>11)&0x1F)
36 #define BUSBNO(tbdf)	(((tbdf)>>16)&0xFF)
37 #define BUSTYPE(tbdf)	((tbdf)>>24)
38 #define BUSBDF(tbdf)	((tbdf)&0x00FFFF00)
39 #define BUSUNKNOWN	(-1)
40 
41 /*
42  * Buffer Descriptors and IO Rings
43  */
44 
45 struct BD {
46 	ushort	status;
47 	ushort	length;
48 	ulong	addr;
49 };
50 
51 BD*	bdalloc(int);
52 void	bdfree(BD*, int);
53 void	dumpbd(char*, BD*, int);
54 
55 enum {
56 	/* Rx BDs, bits common to all protocols */
57 	BDEmpty=	1<<15,
58 	BDWrap=		1<<13,
59 	BDInt=		1<<12,
60 	BDLast=		1<<11,
61 	BDFirst=		1<<10,
62 
63 	/* Tx BDs */
64 	BDReady=		1<<15,
65 	/* BDWrap, BDInt, BDLast */
66 };
67 
68 
69 struct Ring {
70 	BD*	rdr;				/* receive descriptor ring */
71 	void*	rrb;				/* receive ring buffers */
72 	int	rdrx;				/* index into rdr */
73 	int	nrdre;			/* length of rdr */
74 
75 	BD*	tdr;				/* transmit descriptor ring */
76 	Block**	txb;				/* corresponding transmit ring buffers */
77 	int	tdrh;				/* host index into tdr */
78 	int	tdri;				/* interface index into tdr */
79 	int	ntdre;			/* length of tdr */
80 	int	ntq;				/* pending transmit requests */
81 };
82 
83 #define NEXT(x, l)	(((x)+1)%(l))
84 #define PREV(x, l)	(((x) == 0) ? (l)-1: (x)-1)
85 #define	HOWMANY(x, y)	(((x)+((y)-1))/(y))
86 #define ROUNDUP(x, y)	(HOWMANY((x), (y))*(y))
87 
88 int	ioringinit(Ring*, int, int, int);
89 
90 /*
91  * CPM
92  */
93 enum {
94 	/* commands */
95 	InitRxTx =	0,
96 	InitRx =		1,
97 	InitTx =		2,
98 	EnterHunt=	3,
99 	StopTx=		4,
100 	GracefulStopTx = 5,
101 	InitIDMA =	5,
102 	RestartTx =	6,
103 	CloseRxBD =	7,
104 	SetGroupAddr = 8,
105 	SetTimer =	8,
106 	GCITimeout =	9,
107 	GCIAbort =	10,
108 	StopIDMA =	11,
109 	StartDSP = 	12,
110 	ArmIDMA =	13,
111 	InitDSP =		13,
112 	USBCmd =	15,
113 
114 	/* bgcr */
115 	BaudEnable = 1<<16,
116 
117 	/* sicr */
118 	CLK1 = 4,		/* SCC1,2 */
119 	CLK2 = 5,
120 	CLK3 = 6,
121 	CLK4 = 7,
122 	CLK5 = CLK1,	/* SCC3,4 */
123 	CLK6 = CLK2,
124 	CLK7 = CLK3,
125 	CLK8 = CLK4,
126 
127 	/* logical channel IDs mapped to channel ID by cpm.c */
128 	CPnone = 0,
129 	CPscc1,
130 	CPscc2,
131 	CPscc3,
132 	CPscc4,
133 	CPsmc1,
134 	CPsmc2,
135 	CPdsp1,
136 	CPdsp2,
137 	CPidma1,
138 	CPidma2,
139 	CPtimer,
140 	CPspi,
141 	CPi2c,
142 	CPmax,
143 };
144 
145 struct CPMdev {
146 	int	id;	/* CPM channel number */
147 	int	irq;	/* CPIC interrupt number */
148 	int	rbase;	/* register offset in IO mem */
149 	int	pbase;	/* parameter offset in IO mem */
150 	void*	regs;	/* kernel address of registers */
151 	void*	param;	/* kernel address of parameters */
152 };
153 
154 CPMdev*	cpmdev(int);
155 void	cpmop(CPMdev*, int, int);
156 void*	cpmalloc(int, int);
157 void	cpmfree(void*, int);
158 IMM*	ioplock(void);
159 void	iopunlock(void);
160 
161 int	cpmidopen(int, void*);
162 void	cpmidclose(int);
163 void	sccnmsi(int, int, int);
164 void	sccxstop(CPMdev*);
165 void	smcnmsi(int, int);
166 void	smcxstop(CPMdev*);
167 
168 /*
169  * CPM timers
170  */
171 enum {
172 	/* timer modes */
173 	CaptureRise=	1<<6,
174 	CaptureFall=	2<<6,
175 	CaptureEdge=	3<<6,
176 	TimerToggle=	1<<5,	/* toggle TOUTx* pin */
177 	TimerORI=	1<<4,	/* Output Reference Interrupt */
178 	TimerRestart=	1<<3,
179 	TimerSclk=	1<<1,
180 	TimerSclk16=	2<<1,
181 	TimerTIN=	3<<1,	/* clock by falling edge of TINx */
182 	TimerGate=	1<<0,	/* TGATE1* controls timer */
183 
184 	/* timer events */
185 	TimerREF=	1<<1,
186 	TimerCAP=	1<<0
187 };
188 
189 struct GTimer{
190 	int	x;
191 	int	inuse;
192 	int	event;
193 	ushort*	tmr;
194 	ushort*	trr;
195 	ushort*	tcr;
196 	ushort*	tcn;
197 	ushort*	ter;
198 	void*	arg;
199 	void	(*interrupt)(Ureg*, void*, GTimer*);
200 };
201 GTimer*	gtimer(ushort, ushort, void (*)(Ureg*,void*,GTimer*), void*);
202 void	gtimerset(GTimer*, ushort, int);
203 void	gtimerstart(GTimer*);
204 void	gtimerstop(GTimer*);
205 void	gtimerfree(GTimer*);
206 
207 /*
208  * the structures below follow hardware/firmware layouts in the 8xx manuals:
209  * mind the data types, offsets and alignment
210  */
211 
212 /*
213  * basic IO controller parameters (SMC and SCC)
214  */
215 typedef struct IOCparam IOCparam;
216 struct IOCparam {
217 	ushort	rbase;
218 	ushort	tbase;
219 	uchar	rfcr;
220 	uchar	tfcr;
221 	ushort	mrblr;
222 	ulong	rstate;
223 	ulong	rptr;
224 	ushort	rbptr;
225 	ushort	rcnt;
226 	ulong	rtmp;
227 	ulong	tstate;
228 	ulong	tptr;
229 	ushort	tbptr;
230 	ushort	tcnt;
231 	ulong	ttmp;
232 };
233 
234 typedef struct SCCparam SCCparam;
235 struct SCCparam {
236 	IOCparam;
237 	ulong	rcrc;
238 	ulong	tcrc;
239 };
240 
241 typedef struct SCC SCC;
242 struct SCC {
243 	ulong	gsmrl;
244 	ulong	gsmrh;
245 	ushort	psmr;
246 	uchar	rsvscc0[2];
247 	ushort	todr;
248 	ushort	dsr;
249 	ushort	scce;
250 	uchar	rsvscc1[2];
251 	ushort	sccm;
252 	uchar	rsvscc3;
253 	uchar	sccs;
254 	ushort	irmode;
255 	ushort	irsip;
256 };
257 
258 typedef struct SMC SMC;
259 struct SMC {
260 	uchar	pad1[2];
261 	ushort	smcmr;
262 	uchar	pad2[2];
263 	uchar	smce;
264 	uchar	pad3[3];
265 	uchar	smcm;
266 	uchar	pad4[5];
267 };
268 
269 typedef struct SPI SPI;
270 struct SPI {
271 	ushort	spmode;
272 	uchar	res1[4];
273 	uchar	spie;
274 	uchar	res2[3];
275 	uchar	spim;
276 	uchar	res3[2];
277 	uchar	spcom;
278 	uchar	res4[10];
279 };
280 
281 typedef struct USB USB;
282 struct USB {	/* 823 only */
283 	uchar	usmod;
284 	uchar	usadr;
285 	uchar	uscom;
286 	uchar	rsvu1;
287 	ushort	usep[4];
288 	uchar	rsvu2[4];
289 	ushort	usber;
290 	uchar	rsvu3[2];
291 	ushort	usbmr;
292 	uchar	rsvu4;
293 	uchar	usbs;
294 	uchar	rsvu5[8];
295 };
296 
297 typedef struct IMM IMM;
298 struct IMM {
299 	struct {	/* general SIU */
300 		ulong	siumcr;
301 		ulong	sypcr;
302 		uchar	rsv0[0xE-0x8];
303 		ushort	swsr;
304 		ulong	sipend;
305 		ulong	simask;
306 		ulong	siel;
307 		uchar	sivec;
308 		uchar	padv[3];
309 		ulong	tesr;
310 		uchar	rsv1[0x30-0x24];
311 		ulong	sdcr;
312 		uchar	rsv2[0x80-0x34];
313 	};
314 	struct {	/* PCMCIA */
315 		struct {
316 			ulong	base;
317 			ulong	option;
318 		} pcmr[8];
319 		uchar	rsv3[0xe0-0xc0];
320 		ulong	pgcr[2];
321 		ulong	pscr;
322 		uchar	rsv4[0xf0-0xec];
323 		ulong	pipr;
324 		uchar	rsv5[4];
325 		ulong	per;
326 		uchar	rsv6[4];
327 	};
328 	struct {	/* MEMC */
329 		struct {
330 			ulong	base;
331 			ulong	option;
332 		} memc[8];
333 		uchar	rsv7a[0x24];
334 		ulong	mar;
335 		ulong	mcr;
336 		uchar	rsv7b[4];
337 		ulong	mamr;
338 		ulong	mbmr;
339 		ushort	mstat;
340 		ushort	mptpr;
341 		ulong	mdr;
342 		uchar	rsv7c[0x80];
343 	};
344 	struct {	/* system integration timers */
345 		ushort	tbscr;
346 		uchar	rsv8a[2];
347 		ulong	tbrefu;
348 		ulong	tbrefl;
349 		uchar	rsv8b[0x14];
350 		ushort	rtcsc;
351 		uchar	rsv8c[2];
352 		ulong	rtc;
353 		ulong	rtsec;
354 		ulong	rtcal;
355 		uchar	rsv8d[0x10];
356 		ushort	piscr;
357 		ushort	rsv8e;
358 		ulong	pitc;
359 		ulong	pitr;
360 		uchar	rsv8f[0x34];
361 	};
362 	struct {	/* 280: clocks and resets */
363 		ulong	sccr;
364 		ulong	plprcr;
365 		ulong	rsr;
366 		uchar	rsv9[0x300-0x28c];
367 	};
368 	struct {	/* 300: system integration timers keys */
369 		ulong	tbscrk;
370 		ulong	tbrefuk;
371 		ulong	tbreflk;
372 		ulong	tbk;
373 		uchar	rsv10a[0x10];
374 		ulong	rtcsck;
375 		ulong	rtck;
376 		ulong	rtseck;
377 		ulong	rtcalk;
378 		uchar	rsv10b[0x10];
379 		ulong	piscrk;
380 		ulong	pitck;
381 		uchar	rsv10c[0x38];
382 	};
383 	struct {	/* 380: clocks and resets keys */
384 		ulong	sccrk;
385 		ulong	plprcrk;
386 		ulong	rsrk;
387 		uchar	rsv11[0x800-0x38C];
388 	};
389 	struct {	/* 800: video controller */
390 		ushort	vccr;
391 		ushort	pad11a;
392 		uchar	vsr;
393 		uchar	pad11b;
394 		uchar	vcmr;
395 		uchar	pad11c;
396 		ulong	vbcb;
397 		ulong	pad11d;
398 		ulong	vfcr0;
399 		ulong	vfaa0;
400 		ulong	vfba0;
401 		ulong	vfcr1;
402 		ulong	vfaa1;
403 		ulong	vfba1;
404 		uchar	rsv11a[0x840-0x828];
405 	};
406 	struct {	/* 840: LCD */
407 		ulong	lccr;
408 		ulong	lchcr;
409 		ulong	lcvcr;
410 		ulong	rsv11b;
411 		ulong	lcfaa;
412 		ulong	lcfba;
413 		uchar	lcsr;
414 		uchar	rsv11c[0x860-0x859];
415 	};
416 	struct {	/* 860: I2C */
417 		uchar	i2mod;
418 		uchar	rsv12a[3];
419 		uchar	i2add;
420 		uchar	rsv12b[3];
421 		uchar	i2brg;
422 		uchar	rsv12c[3];
423 		uchar	i2com;
424 		uchar	rsv12d[3];
425 		uchar	i2cer;
426 		uchar	rsv12e[3];
427 		uchar	i2cmr;
428 		uchar	rsv12[0x900-0x875];
429 	};
430 	struct {	/* 900: DMA */
431 		uchar	rsv13[4];
432 		ulong	sdar;
433 		uchar	sdsr;
434 		uchar	pad1[3];
435 		uchar	sdmr;
436 		uchar	pad2[3];
437 		uchar	idsr1;
438 		uchar	pad3[3];
439 		uchar	idmr1;
440 		uchar	pad4[3];
441 		uchar	idsr2;
442 		uchar	pad5[3];
443 		uchar	idmr2;
444 		uchar	pad6[0x930-0x91D];
445 	};
446 	struct {	/* CPM interrupt control */
447 		ushort	civr;
448 		uchar	pad7[0x940-0x932];
449 		ulong	cicr;
450 		ulong	cipr;
451 		ulong	cimr;
452 		ulong	cisr;
453 	};
454 	struct {	/* input/output port */
455 		ushort	padir;
456 		ushort	papar;
457 		ushort	paodr;
458 		ushort	padat;
459 		uchar	pad8[8];
460 		ushort	pcdir;
461 		ushort	pcpar;
462 		ushort	pcso;
463 		ushort	pcdat;
464 		ushort	pcint;
465 		uchar	pad9[6];
466 		ushort	pddir;
467 		ushort	pdpar;
468 		ushort	rsv14a;
469 		ushort	pddat;
470 		uchar	rsv14[0x980-0x978];
471 	};
472 	struct {	/* CPM timers */
473 		ushort	tgcr;
474 		uchar	rsv15a[0x990-0x982];
475 		ushort	tmr1;
476 		ushort	tmr2;
477 		ushort	trr1;
478 		ushort	trr2;
479 		ushort	tcr1;
480 		ushort	tcr2;
481 		ushort	tcn1;
482 		ushort	tcn2;
483 		ushort	tmr3;
484 		ushort	tmr4;
485 		ushort	trr3;
486 		ushort	trr4;
487 		ushort	tcr3;
488 		ushort	tcr4;
489 		ushort	tcn3;
490 		ushort	tcn4;
491 		ushort	ter1;
492 		ushort	ter2;
493 		ushort	ter3;
494 		ushort	ter4;
495 		uchar	rsv15[0x9C0-0x9B8];
496 	};
497 	struct {	/* CPM */
498 		ushort	cpcr;
499 		uchar	res0[2];
500 		ushort	rccr;
501 		uchar	res1;
502 		uchar	rmds;
503 		uchar	res2a[4];
504 		ushort	rctr1;
505 		ushort	rctr2;
506 		ushort	rctr3;
507 		ushort	rctr4;
508 		uchar	res2[2];
509 		ushort	rter;
510 		uchar	res3[2];
511 		ushort	rtmr;
512 		uchar	rsv16[0x9F0-0x9DC];
513 	};
514 	union {	/* BRG */
515 		struct {
516 			ulong	brgc1;
517 			ulong	brgc2;
518 			ulong	brgc3;
519 			ulong	brgc4;
520 		};
521 		ulong	brgc[4];
522 	};
523 	uchar	skip0[0xAB2-0xA00];	/* USB, SCC, SMC, SPI: address using cpmdev(CP...)->regs */
524 	struct {	/* PIP */
525 		ushort	pipc;		/* not 823 */
526 		ushort	ptpr;		/* not 823 */
527 		ulong	pbdir;
528 		ulong	pbpar;
529 		uchar	pad10[2];
530 		ushort	pbodr;
531 		ulong	pbdat;
532 		uchar	pad11[0xAE0-0xAC8];
533 	};
534 	struct {	/* SI */
535 		ulong	simode;
536 		uchar	sigmr;
537 		uchar	pad12;
538 		uchar	sistr;
539 		uchar	sicmr;
540 		uchar	pad13[4];
541 		ulong	sicr;
542 		ulong	sirp;
543 		uchar	pad14[0xB00-0xAF4];
544 	};
545 	ulong	vcram[64];
546 	ushort	siram[256];
547 	ushort	lcdmap[256];
548 };
549 
550 /*
551  * PCMCIA structures known by both ../port/cis.c and the pcmcia driver
552  */
553 
554 /*
555  * Map between physical memory space and PCMCIA card memory space.
556  */
557 struct PCMmap {
558 	ulong	ca;			/* card address */
559 	ulong	cea;			/* card end address */
560 	ulong	isa;			/* local virtual address */
561 	int	len;			/* length of the ISA area */
562 	int	attr;			/* attribute memory */
563 	int	slotno;			/* owning slot */
564 	int	ref;
565 };
566 
567 /*
568  *  a PCMCIA configuration entry
569  */
570 struct PCMconftab
571 {
572 	int	index;
573 	ushort	irqs;		/* legal irqs */
574 	uchar	irqtype;
575 	uchar	bit16;		/* true for 16 bit access */
576 	uchar	nlines;
577 	struct {
578 		ulong	start;
579 		ulong	len;
580 		PCMmap*	map;
581 	} io[16];
582 	int	nio;
583 	int	vcc;
584 	int	vpp1;
585 	int	vpp2;
586 	uchar	memwait;
587 	ulong	maxwait;
588 	ulong	readywait;
589 	ulong	otherwait;
590 };
591 
592 /*
593  *  PCMCIA card slot
594  */
595 struct PCMslot
596 {
597 //	RWlock;
598 
599 //	Ref	ref;
600 Ref;
601 
602 	void*	ctlr;	/* controller for this slot */
603 
604 	long	memlen;		/* memory length */
605 	uchar	slotno;		/* slot number */
606 	uchar	slotshift;	/* >> register to meet mask; << mask to meet register */
607 	void	*regs;		/* i/o registers */
608 	void	*mem;		/* memory */
609 	void	*attr;		/* attribute memory */
610 
611 	/* status */
612 	uchar	occupied;	/* card in the slot */
613 	uchar	configed;	/* card configured */
614 	uchar	busy;
615 	uchar	powered;
616 	uchar	battery;
617 	uchar	wrprot;
618 	uchar	enabled;
619 	uchar	special;
620 	uchar	dsize;
621 	uchar	v3_3;
622 	uchar	voltage;
623 
624 	/* cis info */
625 	int	cisread;	/* set when the cis has been read */
626 	char	verstr[512];	/* version string */
627 	uchar	cpresent;	/* config registers present */
628 	ulong	caddr;		/* relative address of config registers */
629 	int	nctab;		/* number of config table entries */
630 	PCMconftab	ctab[8];
631 	PCMconftab	*def;		/* default conftab */
632 
633 	/* maps are fixed */
634 	PCMmap memmap;
635 	PCMmap attrmap;
636 
637 	struct {
638 		void	(*f)(Ureg*, void*);
639 		void	*arg;
640 	} intr;
641 	struct {
642 		void	(*f)(void*, int);
643 		void	*arg;
644 	} notify;
645 };
646 
647 /* ../port/cis.c */
648 void	pcmcisread(PCMslot*);
649 int	pcmcistuple(int, int, int, void*, int);
650 
651 /* devpcmcia.c */
652 PCMmap*	pcmmap(int, ulong, int, int);
653 void	pcmunmap(int, PCMmap*);
654 
655 /*
656  * used by ../port/devi2c.c and i2c.c
657  */
658 struct I2Cdev {
659 	int	addr;
660 	int	salen;	/* length in bytes of subaddress, if used; 0 otherwise */
661 	int	tenbit;	/* 10-bit addresses */
662 };
663 
664 long	i2crecv(I2Cdev*, void*, long, ulong);
665 long	i2csend(I2Cdev*, void*, long, ulong);
666 void	i2csetup(int);
667