xref: /OK3568_Linux_fs/kernel/drivers/tty/rocket_int.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0 */
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * rocket_int.h --- internal header file for rocket.c
4*4882a593Smuzhiyun  *
5*4882a593Smuzhiyun  * Written by Theodore Ts'o, Copyright 1997.
6*4882a593Smuzhiyun  * Copyright 1997 Comtrol Corporation.
7*4882a593Smuzhiyun  *
8*4882a593Smuzhiyun  */
9*4882a593Smuzhiyun 
10*4882a593Smuzhiyun /*
11*4882a593Smuzhiyun  * Definition of the types in rcktpt_type
12*4882a593Smuzhiyun  */
13*4882a593Smuzhiyun #define ROCKET_TYPE_NORMAL	0
14*4882a593Smuzhiyun #define ROCKET_TYPE_MODEM	1
15*4882a593Smuzhiyun #define ROCKET_TYPE_MODEMII	2
16*4882a593Smuzhiyun #define ROCKET_TYPE_MODEMIII	3
17*4882a593Smuzhiyun #define ROCKET_TYPE_PC104       4
18*4882a593Smuzhiyun 
19*4882a593Smuzhiyun #include <linux/mutex.h>
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun #include <asm/io.h>
22*4882a593Smuzhiyun #include <asm/byteorder.h>
23*4882a593Smuzhiyun 
24*4882a593Smuzhiyun typedef unsigned char Byte_t;
25*4882a593Smuzhiyun typedef unsigned int ByteIO_t;
26*4882a593Smuzhiyun 
27*4882a593Smuzhiyun typedef unsigned int Word_t;
28*4882a593Smuzhiyun typedef unsigned int WordIO_t;
29*4882a593Smuzhiyun 
30*4882a593Smuzhiyun typedef unsigned int DWordIO_t;
31*4882a593Smuzhiyun 
32*4882a593Smuzhiyun /*
33*4882a593Smuzhiyun  * Note!  Normally the Linux I/O macros already take care of
34*4882a593Smuzhiyun  * byte-swapping the I/O instructions.  However, all accesses using
35*4882a593Smuzhiyun  * sOutDW aren't really 32-bit accesses, but should be handled in byte
36*4882a593Smuzhiyun  * order.  Hence the use of the cpu_to_le32() macro to byte-swap
37*4882a593Smuzhiyun  * things to no-op the byte swapping done by the big-endian outl()
38*4882a593Smuzhiyun  * instruction.
39*4882a593Smuzhiyun  */
40*4882a593Smuzhiyun 
sOutB(unsigned short port,unsigned char value)41*4882a593Smuzhiyun static inline void sOutB(unsigned short port, unsigned char value)
42*4882a593Smuzhiyun {
43*4882a593Smuzhiyun #ifdef ROCKET_DEBUG_IO
44*4882a593Smuzhiyun 	printk(KERN_DEBUG "sOutB(%x, %x)...\n", port, value);
45*4882a593Smuzhiyun #endif
46*4882a593Smuzhiyun 	outb_p(value, port);
47*4882a593Smuzhiyun }
48*4882a593Smuzhiyun 
sOutW(unsigned short port,unsigned short value)49*4882a593Smuzhiyun static inline void sOutW(unsigned short port, unsigned short value)
50*4882a593Smuzhiyun {
51*4882a593Smuzhiyun #ifdef ROCKET_DEBUG_IO
52*4882a593Smuzhiyun 	printk(KERN_DEBUG "sOutW(%x, %x)...\n", port, value);
53*4882a593Smuzhiyun #endif
54*4882a593Smuzhiyun 	outw_p(value, port);
55*4882a593Smuzhiyun }
56*4882a593Smuzhiyun 
out32(unsigned short port,Byte_t * p)57*4882a593Smuzhiyun static inline void out32(unsigned short port, Byte_t *p)
58*4882a593Smuzhiyun {
59*4882a593Smuzhiyun 	u32 value = get_unaligned_le32(p);
60*4882a593Smuzhiyun #ifdef ROCKET_DEBUG_IO
61*4882a593Smuzhiyun 	printk(KERN_DEBUG "out32(%x, %lx)...\n", port, value);
62*4882a593Smuzhiyun #endif
63*4882a593Smuzhiyun 	outl_p(value, port);
64*4882a593Smuzhiyun }
65*4882a593Smuzhiyun 
sInB(unsigned short port)66*4882a593Smuzhiyun static inline unsigned char sInB(unsigned short port)
67*4882a593Smuzhiyun {
68*4882a593Smuzhiyun 	return inb_p(port);
69*4882a593Smuzhiyun }
70*4882a593Smuzhiyun 
sInW(unsigned short port)71*4882a593Smuzhiyun static inline unsigned short sInW(unsigned short port)
72*4882a593Smuzhiyun {
73*4882a593Smuzhiyun 	return inw_p(port);
74*4882a593Smuzhiyun }
75*4882a593Smuzhiyun 
76*4882a593Smuzhiyun /* This is used to move arrays of bytes so byte swapping isn't appropriate. */
77*4882a593Smuzhiyun #define sOutStrW(port, addr, count) if (count) outsw(port, addr, count)
78*4882a593Smuzhiyun #define sInStrW(port, addr, count) if (count) insw(port, addr, count)
79*4882a593Smuzhiyun 
80*4882a593Smuzhiyun #define CTL_SIZE 8
81*4882a593Smuzhiyun #define AIOP_CTL_SIZE 4
82*4882a593Smuzhiyun #define CHAN_AIOP_SIZE 8
83*4882a593Smuzhiyun #define MAX_PORTS_PER_AIOP 8
84*4882a593Smuzhiyun #define MAX_AIOPS_PER_BOARD 4
85*4882a593Smuzhiyun #define MAX_PORTS_PER_BOARD 32
86*4882a593Smuzhiyun 
87*4882a593Smuzhiyun /* Bus type ID */
88*4882a593Smuzhiyun #define	isISA	0
89*4882a593Smuzhiyun #define	isPCI	1
90*4882a593Smuzhiyun #define	isMC	2
91*4882a593Smuzhiyun 
92*4882a593Smuzhiyun /* Controller ID numbers */
93*4882a593Smuzhiyun #define CTLID_NULL  -1		/* no controller exists */
94*4882a593Smuzhiyun #define CTLID_0001  0x0001	/* controller release 1 */
95*4882a593Smuzhiyun 
96*4882a593Smuzhiyun /* AIOP ID numbers, identifies AIOP type implementing channel */
97*4882a593Smuzhiyun #define AIOPID_NULL -1		/* no AIOP or channel exists */
98*4882a593Smuzhiyun #define AIOPID_0001 0x0001	/* AIOP release 1 */
99*4882a593Smuzhiyun 
100*4882a593Smuzhiyun /************************************************************************
101*4882a593Smuzhiyun  Global Register Offsets - Direct Access - Fixed values
102*4882a593Smuzhiyun ************************************************************************/
103*4882a593Smuzhiyun 
104*4882a593Smuzhiyun #define _CMD_REG   0x38		/* Command Register            8    Write */
105*4882a593Smuzhiyun #define _INT_CHAN  0x39		/* Interrupt Channel Register  8    Read */
106*4882a593Smuzhiyun #define _INT_MASK  0x3A		/* Interrupt Mask Register     8    Read / Write */
107*4882a593Smuzhiyun #define _UNUSED    0x3B		/* Unused                      8 */
108*4882a593Smuzhiyun #define _INDX_ADDR 0x3C		/* Index Register Address      16   Write */
109*4882a593Smuzhiyun #define _INDX_DATA 0x3E		/* Index Register Data         8/16 Read / Write */
110*4882a593Smuzhiyun 
111*4882a593Smuzhiyun /************************************************************************
112*4882a593Smuzhiyun  Channel Register Offsets for 1st channel in AIOP - Direct Access
113*4882a593Smuzhiyun ************************************************************************/
114*4882a593Smuzhiyun #define _TD0       0x00		/* Transmit Data               16   Write */
115*4882a593Smuzhiyun #define _RD0       0x00		/* Receive Data                16   Read */
116*4882a593Smuzhiyun #define _CHN_STAT0 0x20		/* Channel Status              8/16 Read / Write */
117*4882a593Smuzhiyun #define _FIFO_CNT0 0x10		/* Transmit/Receive FIFO Count 16   Read */
118*4882a593Smuzhiyun #define _INT_ID0   0x30		/* Interrupt Identification    8    Read */
119*4882a593Smuzhiyun 
120*4882a593Smuzhiyun /************************************************************************
121*4882a593Smuzhiyun  Tx Control Register Offsets - Indexed - External - Fixed
122*4882a593Smuzhiyun ************************************************************************/
123*4882a593Smuzhiyun #define _TX_ENBLS  0x980	/* Tx Processor Enables Register 8 Read / Write */
124*4882a593Smuzhiyun #define _TXCMP1    0x988	/* Transmit Compare Value #1     8 Read / Write */
125*4882a593Smuzhiyun #define _TXCMP2    0x989	/* Transmit Compare Value #2     8 Read / Write */
126*4882a593Smuzhiyun #define _TXREP1B1  0x98A	/* Tx Replace Value #1 - Byte 1  8 Read / Write */
127*4882a593Smuzhiyun #define _TXREP1B2  0x98B	/* Tx Replace Value #1 - Byte 2  8 Read / Write */
128*4882a593Smuzhiyun #define _TXREP2    0x98C	/* Transmit Replace Value #2     8 Read / Write */
129*4882a593Smuzhiyun 
130*4882a593Smuzhiyun /************************************************************************
131*4882a593Smuzhiyun Memory Controller Register Offsets - Indexed - External - Fixed
132*4882a593Smuzhiyun ************************************************************************/
133*4882a593Smuzhiyun #define _RX_FIFO    0x000	/* Rx FIFO */
134*4882a593Smuzhiyun #define _TX_FIFO    0x800	/* Tx FIFO */
135*4882a593Smuzhiyun #define _RXF_OUTP   0x990	/* Rx FIFO OUT pointer        16 Read / Write */
136*4882a593Smuzhiyun #define _RXF_INP    0x992	/* Rx FIFO IN pointer         16 Read / Write */
137*4882a593Smuzhiyun #define _TXF_OUTP   0x994	/* Tx FIFO OUT pointer        8  Read / Write */
138*4882a593Smuzhiyun #define _TXF_INP    0x995	/* Tx FIFO IN pointer         8  Read / Write */
139*4882a593Smuzhiyun #define _TXP_CNT    0x996	/* Tx Priority Count          8  Read / Write */
140*4882a593Smuzhiyun #define _TXP_PNTR   0x997	/* Tx Priority Pointer        8  Read / Write */
141*4882a593Smuzhiyun 
142*4882a593Smuzhiyun #define PRI_PEND    0x80	/* Priority data pending (bit7, Tx pri cnt) */
143*4882a593Smuzhiyun #define TXFIFO_SIZE 255		/* size of Tx FIFO */
144*4882a593Smuzhiyun #define RXFIFO_SIZE 1023	/* size of Rx FIFO */
145*4882a593Smuzhiyun 
146*4882a593Smuzhiyun /************************************************************************
147*4882a593Smuzhiyun Tx Priority Buffer - Indexed - External - Fixed
148*4882a593Smuzhiyun ************************************************************************/
149*4882a593Smuzhiyun #define _TXP_BUF    0x9C0	/* Tx Priority Buffer  32  Bytes   Read / Write */
150*4882a593Smuzhiyun #define TXP_SIZE    0x20	/* 32 bytes */
151*4882a593Smuzhiyun 
152*4882a593Smuzhiyun /************************************************************************
153*4882a593Smuzhiyun Channel Register Offsets - Indexed - Internal - Fixed
154*4882a593Smuzhiyun ************************************************************************/
155*4882a593Smuzhiyun 
156*4882a593Smuzhiyun #define _TX_CTRL    0xFF0	/* Transmit Control               16  Write */
157*4882a593Smuzhiyun #define _RX_CTRL    0xFF2	/* Receive Control                 8  Write */
158*4882a593Smuzhiyun #define _BAUD       0xFF4	/* Baud Rate                      16  Write */
159*4882a593Smuzhiyun #define _CLK_PRE    0xFF6	/* Clock Prescaler                 8  Write */
160*4882a593Smuzhiyun 
161*4882a593Smuzhiyun #define STMBREAK   0x08		/* BREAK */
162*4882a593Smuzhiyun #define STMFRAME   0x04		/* framing error */
163*4882a593Smuzhiyun #define STMRCVROVR 0x02		/* receiver over run error */
164*4882a593Smuzhiyun #define STMPARITY  0x01		/* parity error */
165*4882a593Smuzhiyun #define STMERROR   (STMBREAK | STMFRAME | STMPARITY)
166*4882a593Smuzhiyun #define STMBREAKH   0x800	/* BREAK */
167*4882a593Smuzhiyun #define STMFRAMEH   0x400	/* framing error */
168*4882a593Smuzhiyun #define STMRCVROVRH 0x200	/* receiver over run error */
169*4882a593Smuzhiyun #define STMPARITYH  0x100	/* parity error */
170*4882a593Smuzhiyun #define STMERRORH   (STMBREAKH | STMFRAMEH | STMPARITYH)
171*4882a593Smuzhiyun 
172*4882a593Smuzhiyun #define CTS_ACT   0x20		/* CTS input asserted */
173*4882a593Smuzhiyun #define DSR_ACT   0x10		/* DSR input asserted */
174*4882a593Smuzhiyun #define CD_ACT    0x08		/* CD input asserted */
175*4882a593Smuzhiyun #define TXFIFOMT  0x04		/* Tx FIFO is empty */
176*4882a593Smuzhiyun #define TXSHRMT   0x02		/* Tx shift register is empty */
177*4882a593Smuzhiyun #define RDA       0x01		/* Rx data available */
178*4882a593Smuzhiyun #define DRAINED (TXFIFOMT | TXSHRMT)	/* indicates Tx is drained */
179*4882a593Smuzhiyun 
180*4882a593Smuzhiyun #define STATMODE  0x8000	/* status mode enable bit */
181*4882a593Smuzhiyun #define RXFOVERFL 0x2000	/* receive FIFO overflow */
182*4882a593Smuzhiyun #define RX2MATCH  0x1000	/* receive compare byte 2 match */
183*4882a593Smuzhiyun #define RX1MATCH  0x0800	/* receive compare byte 1 match */
184*4882a593Smuzhiyun #define RXBREAK   0x0400	/* received BREAK */
185*4882a593Smuzhiyun #define RXFRAME   0x0200	/* received framing error */
186*4882a593Smuzhiyun #define RXPARITY  0x0100	/* received parity error */
187*4882a593Smuzhiyun #define STATERROR (RXBREAK | RXFRAME | RXPARITY)
188*4882a593Smuzhiyun 
189*4882a593Smuzhiyun #define CTSFC_EN  0x80		/* CTS flow control enable bit */
190*4882a593Smuzhiyun #define RTSTOG_EN 0x40		/* RTS toggle enable bit */
191*4882a593Smuzhiyun #define TXINT_EN  0x10		/* transmit interrupt enable */
192*4882a593Smuzhiyun #define STOP2     0x08		/* enable 2 stop bits (0 = 1 stop) */
193*4882a593Smuzhiyun #define PARITY_EN 0x04		/* enable parity (0 = no parity) */
194*4882a593Smuzhiyun #define EVEN_PAR  0x02		/* even parity (0 = odd parity) */
195*4882a593Smuzhiyun #define DATA8BIT  0x01		/* 8 bit data (0 = 7 bit data) */
196*4882a593Smuzhiyun 
197*4882a593Smuzhiyun #define SETBREAK  0x10		/* send break condition (must clear) */
198*4882a593Smuzhiyun #define LOCALLOOP 0x08		/* local loopback set for test */
199*4882a593Smuzhiyun #define SET_DTR   0x04		/* assert DTR */
200*4882a593Smuzhiyun #define SET_RTS   0x02		/* assert RTS */
201*4882a593Smuzhiyun #define TX_ENABLE 0x01		/* enable transmitter */
202*4882a593Smuzhiyun 
203*4882a593Smuzhiyun #define RTSFC_EN  0x40		/* RTS flow control enable */
204*4882a593Smuzhiyun #define RXPROC_EN 0x20		/* receive processor enable */
205*4882a593Smuzhiyun #define TRIG_NO   0x00		/* Rx FIFO trigger level 0 (no trigger) */
206*4882a593Smuzhiyun #define TRIG_1    0x08		/* trigger level 1 char */
207*4882a593Smuzhiyun #define TRIG_1_2  0x10		/* trigger level 1/2 */
208*4882a593Smuzhiyun #define TRIG_7_8  0x18		/* trigger level 7/8 */
209*4882a593Smuzhiyun #define TRIG_MASK 0x18		/* trigger level mask */
210*4882a593Smuzhiyun #define SRCINT_EN 0x04		/* special Rx condition interrupt enable */
211*4882a593Smuzhiyun #define RXINT_EN  0x02		/* Rx interrupt enable */
212*4882a593Smuzhiyun #define MCINT_EN  0x01		/* modem change interrupt enable */
213*4882a593Smuzhiyun 
214*4882a593Smuzhiyun #define RXF_TRIG  0x20		/* Rx FIFO trigger level interrupt */
215*4882a593Smuzhiyun #define TXFIFO_MT 0x10		/* Tx FIFO empty interrupt */
216*4882a593Smuzhiyun #define SRC_INT   0x08		/* special receive condition interrupt */
217*4882a593Smuzhiyun #define DELTA_CD  0x04		/* CD change interrupt */
218*4882a593Smuzhiyun #define DELTA_CTS 0x02		/* CTS change interrupt */
219*4882a593Smuzhiyun #define DELTA_DSR 0x01		/* DSR change interrupt */
220*4882a593Smuzhiyun 
221*4882a593Smuzhiyun #define REP1W2_EN 0x10		/* replace byte 1 with 2 bytes enable */
222*4882a593Smuzhiyun #define IGN2_EN   0x08		/* ignore byte 2 enable */
223*4882a593Smuzhiyun #define IGN1_EN   0x04		/* ignore byte 1 enable */
224*4882a593Smuzhiyun #define COMP2_EN  0x02		/* compare byte 2 enable */
225*4882a593Smuzhiyun #define COMP1_EN  0x01		/* compare byte 1 enable */
226*4882a593Smuzhiyun 
227*4882a593Smuzhiyun #define RESET_ALL 0x80		/* reset AIOP (all channels) */
228*4882a593Smuzhiyun #define TXOVERIDE 0x40		/* Transmit software off override */
229*4882a593Smuzhiyun #define RESETUART 0x20		/* reset channel's UART */
230*4882a593Smuzhiyun #define RESTXFCNT 0x10		/* reset channel's Tx FIFO count register */
231*4882a593Smuzhiyun #define RESRXFCNT 0x08		/* reset channel's Rx FIFO count register */
232*4882a593Smuzhiyun 
233*4882a593Smuzhiyun #define INTSTAT0  0x01		/* AIOP 0 interrupt status */
234*4882a593Smuzhiyun #define INTSTAT1  0x02		/* AIOP 1 interrupt status */
235*4882a593Smuzhiyun #define INTSTAT2  0x04		/* AIOP 2 interrupt status */
236*4882a593Smuzhiyun #define INTSTAT3  0x08		/* AIOP 3 interrupt status */
237*4882a593Smuzhiyun 
238*4882a593Smuzhiyun #define INTR_EN   0x08		/* allow interrupts to host */
239*4882a593Smuzhiyun #define INT_STROB 0x04		/* strobe and clear interrupt line (EOI) */
240*4882a593Smuzhiyun 
241*4882a593Smuzhiyun /**************************************************************************
242*4882a593Smuzhiyun  MUDBAC remapped for PCI
243*4882a593Smuzhiyun **************************************************************************/
244*4882a593Smuzhiyun 
245*4882a593Smuzhiyun #define _CFG_INT_PCI  0x40
246*4882a593Smuzhiyun #define _PCI_INT_FUNC 0x3A
247*4882a593Smuzhiyun 
248*4882a593Smuzhiyun #define PCI_STROB 0x2000	/* bit 13 of int aiop register */
249*4882a593Smuzhiyun #define INTR_EN_PCI   0x0010	/* allow interrupts to host */
250*4882a593Smuzhiyun 
251*4882a593Smuzhiyun /*
252*4882a593Smuzhiyun  * Definitions for Universal PCI board registers
253*4882a593Smuzhiyun  */
254*4882a593Smuzhiyun #define _PCI_9030_INT_CTRL	0x4c          /* Offsets from BAR1 */
255*4882a593Smuzhiyun #define _PCI_9030_GPIO_CTRL	0x54
256*4882a593Smuzhiyun #define PCI_INT_CTRL_AIOP	0x0001
257*4882a593Smuzhiyun #define PCI_GPIO_CTRL_8PORT	0x4000
258*4882a593Smuzhiyun #define _PCI_9030_RING_IND	0xc0          /* Offsets from BAR1 */
259*4882a593Smuzhiyun 
260*4882a593Smuzhiyun #define CHAN3_EN  0x08		/* enable AIOP 3 */
261*4882a593Smuzhiyun #define CHAN2_EN  0x04		/* enable AIOP 2 */
262*4882a593Smuzhiyun #define CHAN1_EN  0x02		/* enable AIOP 1 */
263*4882a593Smuzhiyun #define CHAN0_EN  0x01		/* enable AIOP 0 */
264*4882a593Smuzhiyun #define FREQ_DIS  0x00
265*4882a593Smuzhiyun #define FREQ_274HZ 0x60
266*4882a593Smuzhiyun #define FREQ_137HZ 0x50
267*4882a593Smuzhiyun #define FREQ_69HZ  0x40
268*4882a593Smuzhiyun #define FREQ_34HZ  0x30
269*4882a593Smuzhiyun #define FREQ_17HZ  0x20
270*4882a593Smuzhiyun #define FREQ_9HZ   0x10
271*4882a593Smuzhiyun #define PERIODIC_ONLY 0x80	/* only PERIODIC interrupt */
272*4882a593Smuzhiyun 
273*4882a593Smuzhiyun #define CHANINT_EN 0x0100	/* flags to enable/disable channel ints */
274*4882a593Smuzhiyun 
275*4882a593Smuzhiyun #define RDATASIZE 72
276*4882a593Smuzhiyun #define RREGDATASIZE 52
277*4882a593Smuzhiyun 
278*4882a593Smuzhiyun /*
279*4882a593Smuzhiyun  * AIOP interrupt bits for ISA/PCI boards and UPCI boards.
280*4882a593Smuzhiyun  */
281*4882a593Smuzhiyun #define AIOP_INTR_BIT_0		0x0001
282*4882a593Smuzhiyun #define AIOP_INTR_BIT_1		0x0002
283*4882a593Smuzhiyun #define AIOP_INTR_BIT_2		0x0004
284*4882a593Smuzhiyun #define AIOP_INTR_BIT_3		0x0008
285*4882a593Smuzhiyun 
286*4882a593Smuzhiyun #define AIOP_INTR_BITS ( \
287*4882a593Smuzhiyun 	AIOP_INTR_BIT_0 \
288*4882a593Smuzhiyun 	| AIOP_INTR_BIT_1 \
289*4882a593Smuzhiyun 	| AIOP_INTR_BIT_2 \
290*4882a593Smuzhiyun 	| AIOP_INTR_BIT_3)
291*4882a593Smuzhiyun 
292*4882a593Smuzhiyun #define UPCI_AIOP_INTR_BIT_0	0x0004
293*4882a593Smuzhiyun #define UPCI_AIOP_INTR_BIT_1	0x0020
294*4882a593Smuzhiyun #define UPCI_AIOP_INTR_BIT_2	0x0100
295*4882a593Smuzhiyun #define UPCI_AIOP_INTR_BIT_3	0x0800
296*4882a593Smuzhiyun 
297*4882a593Smuzhiyun #define UPCI_AIOP_INTR_BITS ( \
298*4882a593Smuzhiyun 	UPCI_AIOP_INTR_BIT_0 \
299*4882a593Smuzhiyun 	| UPCI_AIOP_INTR_BIT_1 \
300*4882a593Smuzhiyun 	| UPCI_AIOP_INTR_BIT_2 \
301*4882a593Smuzhiyun 	| UPCI_AIOP_INTR_BIT_3)
302*4882a593Smuzhiyun 
303*4882a593Smuzhiyun /* Controller level information structure */
304*4882a593Smuzhiyun typedef struct {
305*4882a593Smuzhiyun 	int CtlID;
306*4882a593Smuzhiyun 	int CtlNum;
307*4882a593Smuzhiyun 	int BusType;
308*4882a593Smuzhiyun 	int boardType;
309*4882a593Smuzhiyun 	int isUPCI;
310*4882a593Smuzhiyun 	WordIO_t PCIIO;
311*4882a593Smuzhiyun 	WordIO_t PCIIO2;
312*4882a593Smuzhiyun 	ByteIO_t MBaseIO;
313*4882a593Smuzhiyun 	ByteIO_t MReg1IO;
314*4882a593Smuzhiyun 	ByteIO_t MReg2IO;
315*4882a593Smuzhiyun 	ByteIO_t MReg3IO;
316*4882a593Smuzhiyun 	Byte_t MReg2;
317*4882a593Smuzhiyun 	Byte_t MReg3;
318*4882a593Smuzhiyun 	int NumAiop;
319*4882a593Smuzhiyun 	int AltChanRingIndicator;
320*4882a593Smuzhiyun 	ByteIO_t UPCIRingInd;
321*4882a593Smuzhiyun 	WordIO_t AiopIO[AIOP_CTL_SIZE];
322*4882a593Smuzhiyun 	ByteIO_t AiopIntChanIO[AIOP_CTL_SIZE];
323*4882a593Smuzhiyun 	int AiopID[AIOP_CTL_SIZE];
324*4882a593Smuzhiyun 	int AiopNumChan[AIOP_CTL_SIZE];
325*4882a593Smuzhiyun 	Word_t *AiopIntrBits;
326*4882a593Smuzhiyun } CONTROLLER_T;
327*4882a593Smuzhiyun 
328*4882a593Smuzhiyun typedef CONTROLLER_T CONTROLLER_t;
329*4882a593Smuzhiyun 
330*4882a593Smuzhiyun /* Channel level information structure */
331*4882a593Smuzhiyun typedef struct {
332*4882a593Smuzhiyun 	CONTROLLER_T *CtlP;
333*4882a593Smuzhiyun 	int AiopNum;
334*4882a593Smuzhiyun 	int ChanID;
335*4882a593Smuzhiyun 	int ChanNum;
336*4882a593Smuzhiyun 	int rtsToggle;
337*4882a593Smuzhiyun 
338*4882a593Smuzhiyun 	ByteIO_t Cmd;
339*4882a593Smuzhiyun 	ByteIO_t IntChan;
340*4882a593Smuzhiyun 	ByteIO_t IntMask;
341*4882a593Smuzhiyun 	DWordIO_t IndexAddr;
342*4882a593Smuzhiyun 	WordIO_t IndexData;
343*4882a593Smuzhiyun 
344*4882a593Smuzhiyun 	WordIO_t TxRxData;
345*4882a593Smuzhiyun 	WordIO_t ChanStat;
346*4882a593Smuzhiyun 	WordIO_t TxRxCount;
347*4882a593Smuzhiyun 	ByteIO_t IntID;
348*4882a593Smuzhiyun 
349*4882a593Smuzhiyun 	Word_t TxFIFO;
350*4882a593Smuzhiyun 	Word_t TxFIFOPtrs;
351*4882a593Smuzhiyun 	Word_t RxFIFO;
352*4882a593Smuzhiyun 	Word_t RxFIFOPtrs;
353*4882a593Smuzhiyun 	Word_t TxPrioCnt;
354*4882a593Smuzhiyun 	Word_t TxPrioPtr;
355*4882a593Smuzhiyun 	Word_t TxPrioBuf;
356*4882a593Smuzhiyun 
357*4882a593Smuzhiyun 	Byte_t R[RREGDATASIZE];
358*4882a593Smuzhiyun 
359*4882a593Smuzhiyun 	Byte_t BaudDiv[4];
360*4882a593Smuzhiyun 	Byte_t TxControl[4];
361*4882a593Smuzhiyun 	Byte_t RxControl[4];
362*4882a593Smuzhiyun 	Byte_t TxEnables[4];
363*4882a593Smuzhiyun 	Byte_t TxCompare[4];
364*4882a593Smuzhiyun 	Byte_t TxReplace1[4];
365*4882a593Smuzhiyun 	Byte_t TxReplace2[4];
366*4882a593Smuzhiyun } CHANNEL_T;
367*4882a593Smuzhiyun 
368*4882a593Smuzhiyun typedef CHANNEL_T CHANNEL_t;
369*4882a593Smuzhiyun typedef CHANNEL_T *CHANPTR_T;
370*4882a593Smuzhiyun 
371*4882a593Smuzhiyun #define InterfaceModeRS232  0x00
372*4882a593Smuzhiyun #define InterfaceModeRS422  0x08
373*4882a593Smuzhiyun #define InterfaceModeRS485  0x10
374*4882a593Smuzhiyun #define InterfaceModeRS232T 0x18
375*4882a593Smuzhiyun 
376*4882a593Smuzhiyun /***************************************************************************
377*4882a593Smuzhiyun Function: sClrBreak
378*4882a593Smuzhiyun Purpose:  Stop sending a transmit BREAK signal
379*4882a593Smuzhiyun Call:     sClrBreak(ChP)
380*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
381*4882a593Smuzhiyun */
382*4882a593Smuzhiyun #define sClrBreak(ChP) \
383*4882a593Smuzhiyun do { \
384*4882a593Smuzhiyun    (ChP)->TxControl[3] &= ~SETBREAK; \
385*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
386*4882a593Smuzhiyun } while (0)
387*4882a593Smuzhiyun 
388*4882a593Smuzhiyun /***************************************************************************
389*4882a593Smuzhiyun Function: sClrDTR
390*4882a593Smuzhiyun Purpose:  Clr the DTR output
391*4882a593Smuzhiyun Call:     sClrDTR(ChP)
392*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
393*4882a593Smuzhiyun */
394*4882a593Smuzhiyun #define sClrDTR(ChP) \
395*4882a593Smuzhiyun do { \
396*4882a593Smuzhiyun    (ChP)->TxControl[3] &= ~SET_DTR; \
397*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
398*4882a593Smuzhiyun } while (0)
399*4882a593Smuzhiyun 
400*4882a593Smuzhiyun /***************************************************************************
401*4882a593Smuzhiyun Function: sClrRTS
402*4882a593Smuzhiyun Purpose:  Clr the RTS output
403*4882a593Smuzhiyun Call:     sClrRTS(ChP)
404*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
405*4882a593Smuzhiyun */
406*4882a593Smuzhiyun #define sClrRTS(ChP) \
407*4882a593Smuzhiyun do { \
408*4882a593Smuzhiyun    if ((ChP)->rtsToggle) break; \
409*4882a593Smuzhiyun    (ChP)->TxControl[3] &= ~SET_RTS; \
410*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
411*4882a593Smuzhiyun } while (0)
412*4882a593Smuzhiyun 
413*4882a593Smuzhiyun /***************************************************************************
414*4882a593Smuzhiyun Function: sClrTxXOFF
415*4882a593Smuzhiyun Purpose:  Clear any existing transmit software flow control off condition
416*4882a593Smuzhiyun Call:     sClrTxXOFF(ChP)
417*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
418*4882a593Smuzhiyun */
419*4882a593Smuzhiyun #define sClrTxXOFF(ChP) \
420*4882a593Smuzhiyun do { \
421*4882a593Smuzhiyun    sOutB((ChP)->Cmd,TXOVERIDE | (Byte_t)(ChP)->ChanNum); \
422*4882a593Smuzhiyun    sOutB((ChP)->Cmd,(Byte_t)(ChP)->ChanNum); \
423*4882a593Smuzhiyun } while (0)
424*4882a593Smuzhiyun 
425*4882a593Smuzhiyun /***************************************************************************
426*4882a593Smuzhiyun Function: sCtlNumToCtlPtr
427*4882a593Smuzhiyun Purpose:  Convert a controller number to controller structure pointer
428*4882a593Smuzhiyun Call:     sCtlNumToCtlPtr(CtlNum)
429*4882a593Smuzhiyun           int CtlNum; Controller number
430*4882a593Smuzhiyun Return:   CONTROLLER_T *: Ptr to controller structure
431*4882a593Smuzhiyun */
432*4882a593Smuzhiyun #define sCtlNumToCtlPtr(CTLNUM) &sController[CTLNUM]
433*4882a593Smuzhiyun 
434*4882a593Smuzhiyun /***************************************************************************
435*4882a593Smuzhiyun Function: sControllerEOI
436*4882a593Smuzhiyun Purpose:  Strobe the MUDBAC's End Of Interrupt bit.
437*4882a593Smuzhiyun Call:     sControllerEOI(CtlP)
438*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
439*4882a593Smuzhiyun */
440*4882a593Smuzhiyun #define sControllerEOI(CTLP) sOutB((CTLP)->MReg2IO,(CTLP)->MReg2 | INT_STROB)
441*4882a593Smuzhiyun 
442*4882a593Smuzhiyun /***************************************************************************
443*4882a593Smuzhiyun Function: sPCIControllerEOI
444*4882a593Smuzhiyun Purpose:  Strobe the PCI End Of Interrupt bit.
445*4882a593Smuzhiyun           For the UPCI boards, toggle the AIOP interrupt enable bit
446*4882a593Smuzhiyun 	  (this was taken from the Windows driver).
447*4882a593Smuzhiyun Call:     sPCIControllerEOI(CtlP)
448*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
449*4882a593Smuzhiyun */
450*4882a593Smuzhiyun #define sPCIControllerEOI(CTLP) \
451*4882a593Smuzhiyun do { \
452*4882a593Smuzhiyun     if ((CTLP)->isUPCI) { \
453*4882a593Smuzhiyun 	Word_t w = sInW((CTLP)->PCIIO); \
454*4882a593Smuzhiyun 	sOutW((CTLP)->PCIIO, (w ^ PCI_INT_CTRL_AIOP)); \
455*4882a593Smuzhiyun 	sOutW((CTLP)->PCIIO, w); \
456*4882a593Smuzhiyun     } \
457*4882a593Smuzhiyun     else { \
458*4882a593Smuzhiyun 	sOutW((CTLP)->PCIIO, PCI_STROB); \
459*4882a593Smuzhiyun     } \
460*4882a593Smuzhiyun } while (0)
461*4882a593Smuzhiyun 
462*4882a593Smuzhiyun /***************************************************************************
463*4882a593Smuzhiyun Function: sDisAiop
464*4882a593Smuzhiyun Purpose:  Disable I/O access to an AIOP
465*4882a593Smuzhiyun Call:     sDisAiop(CltP)
466*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
467*4882a593Smuzhiyun           int AiopNum; Number of AIOP on controller
468*4882a593Smuzhiyun */
469*4882a593Smuzhiyun #define sDisAiop(CTLP,AIOPNUM) \
470*4882a593Smuzhiyun do { \
471*4882a593Smuzhiyun    (CTLP)->MReg3 &= sBitMapClrTbl[AIOPNUM]; \
472*4882a593Smuzhiyun    sOutB((CTLP)->MReg3IO,(CTLP)->MReg3); \
473*4882a593Smuzhiyun } while (0)
474*4882a593Smuzhiyun 
475*4882a593Smuzhiyun /***************************************************************************
476*4882a593Smuzhiyun Function: sDisCTSFlowCtl
477*4882a593Smuzhiyun Purpose:  Disable output flow control using CTS
478*4882a593Smuzhiyun Call:     sDisCTSFlowCtl(ChP)
479*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
480*4882a593Smuzhiyun */
481*4882a593Smuzhiyun #define sDisCTSFlowCtl(ChP) \
482*4882a593Smuzhiyun do { \
483*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~CTSFC_EN; \
484*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
485*4882a593Smuzhiyun } while (0)
486*4882a593Smuzhiyun 
487*4882a593Smuzhiyun /***************************************************************************
488*4882a593Smuzhiyun Function: sDisIXANY
489*4882a593Smuzhiyun Purpose:  Disable IXANY Software Flow Control
490*4882a593Smuzhiyun Call:     sDisIXANY(ChP)
491*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
492*4882a593Smuzhiyun */
493*4882a593Smuzhiyun #define sDisIXANY(ChP) \
494*4882a593Smuzhiyun do { \
495*4882a593Smuzhiyun    (ChP)->R[0x0e] = 0x86; \
496*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x0c]); \
497*4882a593Smuzhiyun } while (0)
498*4882a593Smuzhiyun 
499*4882a593Smuzhiyun /***************************************************************************
500*4882a593Smuzhiyun Function: DisParity
501*4882a593Smuzhiyun Purpose:  Disable parity
502*4882a593Smuzhiyun Call:     sDisParity(ChP)
503*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
504*4882a593Smuzhiyun Comments: Function sSetParity() can be used in place of functions sEnParity(),
505*4882a593Smuzhiyun           sDisParity(), sSetOddParity(), and sSetEvenParity().
506*4882a593Smuzhiyun */
507*4882a593Smuzhiyun #define sDisParity(ChP) \
508*4882a593Smuzhiyun do { \
509*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~PARITY_EN; \
510*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
511*4882a593Smuzhiyun } while (0)
512*4882a593Smuzhiyun 
513*4882a593Smuzhiyun /***************************************************************************
514*4882a593Smuzhiyun Function: sDisRTSToggle
515*4882a593Smuzhiyun Purpose:  Disable RTS toggle
516*4882a593Smuzhiyun Call:     sDisRTSToggle(ChP)
517*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
518*4882a593Smuzhiyun */
519*4882a593Smuzhiyun #define sDisRTSToggle(ChP) \
520*4882a593Smuzhiyun do { \
521*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~RTSTOG_EN; \
522*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
523*4882a593Smuzhiyun    (ChP)->rtsToggle = 0; \
524*4882a593Smuzhiyun } while (0)
525*4882a593Smuzhiyun 
526*4882a593Smuzhiyun /***************************************************************************
527*4882a593Smuzhiyun Function: sDisRxFIFO
528*4882a593Smuzhiyun Purpose:  Disable Rx FIFO
529*4882a593Smuzhiyun Call:     sDisRxFIFO(ChP)
530*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
531*4882a593Smuzhiyun */
532*4882a593Smuzhiyun #define sDisRxFIFO(ChP) \
533*4882a593Smuzhiyun do { \
534*4882a593Smuzhiyun    (ChP)->R[0x32] = 0x0a; \
535*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x30]); \
536*4882a593Smuzhiyun } while (0)
537*4882a593Smuzhiyun 
538*4882a593Smuzhiyun /***************************************************************************
539*4882a593Smuzhiyun Function: sDisRxStatusMode
540*4882a593Smuzhiyun Purpose:  Disable the Rx status mode
541*4882a593Smuzhiyun Call:     sDisRxStatusMode(ChP)
542*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
543*4882a593Smuzhiyun Comments: This takes the channel out of the receive status mode.  All
544*4882a593Smuzhiyun           subsequent reads of receive data using sReadRxWord() will return
545*4882a593Smuzhiyun           two data bytes.
546*4882a593Smuzhiyun */
547*4882a593Smuzhiyun #define sDisRxStatusMode(ChP) sOutW((ChP)->ChanStat,0)
548*4882a593Smuzhiyun 
549*4882a593Smuzhiyun /***************************************************************************
550*4882a593Smuzhiyun Function: sDisTransmit
551*4882a593Smuzhiyun Purpose:  Disable transmit
552*4882a593Smuzhiyun Call:     sDisTransmit(ChP)
553*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
554*4882a593Smuzhiyun           This disables movement of Tx data from the Tx FIFO into the 1 byte
555*4882a593Smuzhiyun           Tx buffer.  Therefore there could be up to a 2 byte latency
556*4882a593Smuzhiyun           between the time sDisTransmit() is called and the transmit buffer
557*4882a593Smuzhiyun           and transmit shift register going completely empty.
558*4882a593Smuzhiyun */
559*4882a593Smuzhiyun #define sDisTransmit(ChP) \
560*4882a593Smuzhiyun do { \
561*4882a593Smuzhiyun    (ChP)->TxControl[3] &= ~TX_ENABLE; \
562*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
563*4882a593Smuzhiyun } while (0)
564*4882a593Smuzhiyun 
565*4882a593Smuzhiyun /***************************************************************************
566*4882a593Smuzhiyun Function: sDisTxSoftFlowCtl
567*4882a593Smuzhiyun Purpose:  Disable Tx Software Flow Control
568*4882a593Smuzhiyun Call:     sDisTxSoftFlowCtl(ChP)
569*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
570*4882a593Smuzhiyun */
571*4882a593Smuzhiyun #define sDisTxSoftFlowCtl(ChP) \
572*4882a593Smuzhiyun do { \
573*4882a593Smuzhiyun    (ChP)->R[0x06] = 0x8a; \
574*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x04]); \
575*4882a593Smuzhiyun } while (0)
576*4882a593Smuzhiyun 
577*4882a593Smuzhiyun /***************************************************************************
578*4882a593Smuzhiyun Function: sEnAiop
579*4882a593Smuzhiyun Purpose:  Enable I/O access to an AIOP
580*4882a593Smuzhiyun Call:     sEnAiop(CltP)
581*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
582*4882a593Smuzhiyun           int AiopNum; Number of AIOP on controller
583*4882a593Smuzhiyun */
584*4882a593Smuzhiyun #define sEnAiop(CTLP,AIOPNUM) \
585*4882a593Smuzhiyun do { \
586*4882a593Smuzhiyun    (CTLP)->MReg3 |= sBitMapSetTbl[AIOPNUM]; \
587*4882a593Smuzhiyun    sOutB((CTLP)->MReg3IO,(CTLP)->MReg3); \
588*4882a593Smuzhiyun } while (0)
589*4882a593Smuzhiyun 
590*4882a593Smuzhiyun /***************************************************************************
591*4882a593Smuzhiyun Function: sEnCTSFlowCtl
592*4882a593Smuzhiyun Purpose:  Enable output flow control using CTS
593*4882a593Smuzhiyun Call:     sEnCTSFlowCtl(ChP)
594*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
595*4882a593Smuzhiyun */
596*4882a593Smuzhiyun #define sEnCTSFlowCtl(ChP) \
597*4882a593Smuzhiyun do { \
598*4882a593Smuzhiyun    (ChP)->TxControl[2] |= CTSFC_EN; \
599*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
600*4882a593Smuzhiyun } while (0)
601*4882a593Smuzhiyun 
602*4882a593Smuzhiyun /***************************************************************************
603*4882a593Smuzhiyun Function: sEnIXANY
604*4882a593Smuzhiyun Purpose:  Enable IXANY Software Flow Control
605*4882a593Smuzhiyun Call:     sEnIXANY(ChP)
606*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
607*4882a593Smuzhiyun */
608*4882a593Smuzhiyun #define sEnIXANY(ChP) \
609*4882a593Smuzhiyun do { \
610*4882a593Smuzhiyun    (ChP)->R[0x0e] = 0x21; \
611*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x0c]); \
612*4882a593Smuzhiyun } while (0)
613*4882a593Smuzhiyun 
614*4882a593Smuzhiyun /***************************************************************************
615*4882a593Smuzhiyun Function: EnParity
616*4882a593Smuzhiyun Purpose:  Enable parity
617*4882a593Smuzhiyun Call:     sEnParity(ChP)
618*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
619*4882a593Smuzhiyun Comments: Function sSetParity() can be used in place of functions sEnParity(),
620*4882a593Smuzhiyun           sDisParity(), sSetOddParity(), and sSetEvenParity().
621*4882a593Smuzhiyun 
622*4882a593Smuzhiyun Warnings: Before enabling parity odd or even parity should be chosen using
623*4882a593Smuzhiyun           functions sSetOddParity() or sSetEvenParity().
624*4882a593Smuzhiyun */
625*4882a593Smuzhiyun #define sEnParity(ChP) \
626*4882a593Smuzhiyun do { \
627*4882a593Smuzhiyun    (ChP)->TxControl[2] |= PARITY_EN; \
628*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
629*4882a593Smuzhiyun } while (0)
630*4882a593Smuzhiyun 
631*4882a593Smuzhiyun /***************************************************************************
632*4882a593Smuzhiyun Function: sEnRTSToggle
633*4882a593Smuzhiyun Purpose:  Enable RTS toggle
634*4882a593Smuzhiyun Call:     sEnRTSToggle(ChP)
635*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
636*4882a593Smuzhiyun Comments: This function will disable RTS flow control and clear the RTS
637*4882a593Smuzhiyun           line to allow operation of RTS toggle.
638*4882a593Smuzhiyun */
639*4882a593Smuzhiyun #define sEnRTSToggle(ChP) \
640*4882a593Smuzhiyun do { \
641*4882a593Smuzhiyun    (ChP)->RxControl[2] &= ~RTSFC_EN; \
642*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->RxControl); \
643*4882a593Smuzhiyun    (ChP)->TxControl[2] |= RTSTOG_EN; \
644*4882a593Smuzhiyun    (ChP)->TxControl[3] &= ~SET_RTS; \
645*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
646*4882a593Smuzhiyun    (ChP)->rtsToggle = 1; \
647*4882a593Smuzhiyun } while (0)
648*4882a593Smuzhiyun 
649*4882a593Smuzhiyun /***************************************************************************
650*4882a593Smuzhiyun Function: sEnRxFIFO
651*4882a593Smuzhiyun Purpose:  Enable Rx FIFO
652*4882a593Smuzhiyun Call:     sEnRxFIFO(ChP)
653*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
654*4882a593Smuzhiyun */
655*4882a593Smuzhiyun #define sEnRxFIFO(ChP) \
656*4882a593Smuzhiyun do { \
657*4882a593Smuzhiyun    (ChP)->R[0x32] = 0x08; \
658*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x30]); \
659*4882a593Smuzhiyun } while (0)
660*4882a593Smuzhiyun 
661*4882a593Smuzhiyun /***************************************************************************
662*4882a593Smuzhiyun Function: sEnRxProcessor
663*4882a593Smuzhiyun Purpose:  Enable the receive processor
664*4882a593Smuzhiyun Call:     sEnRxProcessor(ChP)
665*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
666*4882a593Smuzhiyun Comments: This function is used to start the receive processor.  When
667*4882a593Smuzhiyun           the channel is in the reset state the receive processor is not
668*4882a593Smuzhiyun           running.  This is done to prevent the receive processor from
669*4882a593Smuzhiyun           executing invalid microcode instructions prior to the
670*4882a593Smuzhiyun           downloading of the microcode.
671*4882a593Smuzhiyun 
672*4882a593Smuzhiyun Warnings: This function must be called after valid microcode has been
673*4882a593Smuzhiyun           downloaded to the AIOP, and it must not be called before the
674*4882a593Smuzhiyun           microcode has been downloaded.
675*4882a593Smuzhiyun */
676*4882a593Smuzhiyun #define sEnRxProcessor(ChP) \
677*4882a593Smuzhiyun do { \
678*4882a593Smuzhiyun    (ChP)->RxControl[2] |= RXPROC_EN; \
679*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->RxControl); \
680*4882a593Smuzhiyun } while (0)
681*4882a593Smuzhiyun 
682*4882a593Smuzhiyun /***************************************************************************
683*4882a593Smuzhiyun Function: sEnRxStatusMode
684*4882a593Smuzhiyun Purpose:  Enable the Rx status mode
685*4882a593Smuzhiyun Call:     sEnRxStatusMode(ChP)
686*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
687*4882a593Smuzhiyun Comments: This places the channel in the receive status mode.  All subsequent
688*4882a593Smuzhiyun           reads of receive data using sReadRxWord() will return a data byte
689*4882a593Smuzhiyun           in the low word and a status byte in the high word.
690*4882a593Smuzhiyun 
691*4882a593Smuzhiyun */
692*4882a593Smuzhiyun #define sEnRxStatusMode(ChP) sOutW((ChP)->ChanStat,STATMODE)
693*4882a593Smuzhiyun 
694*4882a593Smuzhiyun /***************************************************************************
695*4882a593Smuzhiyun Function: sEnTransmit
696*4882a593Smuzhiyun Purpose:  Enable transmit
697*4882a593Smuzhiyun Call:     sEnTransmit(ChP)
698*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
699*4882a593Smuzhiyun */
700*4882a593Smuzhiyun #define sEnTransmit(ChP) \
701*4882a593Smuzhiyun do { \
702*4882a593Smuzhiyun    (ChP)->TxControl[3] |= TX_ENABLE; \
703*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
704*4882a593Smuzhiyun } while (0)
705*4882a593Smuzhiyun 
706*4882a593Smuzhiyun /***************************************************************************
707*4882a593Smuzhiyun Function: sEnTxSoftFlowCtl
708*4882a593Smuzhiyun Purpose:  Enable Tx Software Flow Control
709*4882a593Smuzhiyun Call:     sEnTxSoftFlowCtl(ChP)
710*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
711*4882a593Smuzhiyun */
712*4882a593Smuzhiyun #define sEnTxSoftFlowCtl(ChP) \
713*4882a593Smuzhiyun do { \
714*4882a593Smuzhiyun    (ChP)->R[0x06] = 0xc5; \
715*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x04]); \
716*4882a593Smuzhiyun } while (0)
717*4882a593Smuzhiyun 
718*4882a593Smuzhiyun /***************************************************************************
719*4882a593Smuzhiyun Function: sGetAiopIntStatus
720*4882a593Smuzhiyun Purpose:  Get the AIOP interrupt status
721*4882a593Smuzhiyun Call:     sGetAiopIntStatus(CtlP,AiopNum)
722*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
723*4882a593Smuzhiyun           int AiopNum; AIOP number
724*4882a593Smuzhiyun Return:   Byte_t: The AIOP interrupt status.  Bits 0 through 7
725*4882a593Smuzhiyun                          represent channels 0 through 7 respectively.  If a
726*4882a593Smuzhiyun                          bit is set that channel is interrupting.
727*4882a593Smuzhiyun */
728*4882a593Smuzhiyun #define sGetAiopIntStatus(CTLP,AIOPNUM) sInB((CTLP)->AiopIntChanIO[AIOPNUM])
729*4882a593Smuzhiyun 
730*4882a593Smuzhiyun /***************************************************************************
731*4882a593Smuzhiyun Function: sGetAiopNumChan
732*4882a593Smuzhiyun Purpose:  Get the number of channels supported by an AIOP
733*4882a593Smuzhiyun Call:     sGetAiopNumChan(CtlP,AiopNum)
734*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
735*4882a593Smuzhiyun           int AiopNum; AIOP number
736*4882a593Smuzhiyun Return:   int: The number of channels supported by the AIOP
737*4882a593Smuzhiyun */
738*4882a593Smuzhiyun #define sGetAiopNumChan(CTLP,AIOPNUM) (CTLP)->AiopNumChan[AIOPNUM]
739*4882a593Smuzhiyun 
740*4882a593Smuzhiyun /***************************************************************************
741*4882a593Smuzhiyun Function: sGetChanIntID
742*4882a593Smuzhiyun Purpose:  Get a channel's interrupt identification byte
743*4882a593Smuzhiyun Call:     sGetChanIntID(ChP)
744*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
745*4882a593Smuzhiyun Return:   Byte_t: The channel interrupt ID.  Can be any
746*4882a593Smuzhiyun              combination of the following flags:
747*4882a593Smuzhiyun                 RXF_TRIG:     Rx FIFO trigger level interrupt
748*4882a593Smuzhiyun                 TXFIFO_MT:    Tx FIFO empty interrupt
749*4882a593Smuzhiyun                 SRC_INT:      Special receive condition interrupt
750*4882a593Smuzhiyun                 DELTA_CD:     CD change interrupt
751*4882a593Smuzhiyun                 DELTA_CTS:    CTS change interrupt
752*4882a593Smuzhiyun                 DELTA_DSR:    DSR change interrupt
753*4882a593Smuzhiyun */
754*4882a593Smuzhiyun #define sGetChanIntID(ChP) (sInB((ChP)->IntID) & (RXF_TRIG | TXFIFO_MT | SRC_INT | DELTA_CD | DELTA_CTS | DELTA_DSR))
755*4882a593Smuzhiyun 
756*4882a593Smuzhiyun /***************************************************************************
757*4882a593Smuzhiyun Function: sGetChanNum
758*4882a593Smuzhiyun Purpose:  Get the number of a channel within an AIOP
759*4882a593Smuzhiyun Call:     sGetChanNum(ChP)
760*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
761*4882a593Smuzhiyun Return:   int: Channel number within AIOP, or NULLCHAN if channel does
762*4882a593Smuzhiyun                not exist.
763*4882a593Smuzhiyun */
764*4882a593Smuzhiyun #define sGetChanNum(ChP) (ChP)->ChanNum
765*4882a593Smuzhiyun 
766*4882a593Smuzhiyun /***************************************************************************
767*4882a593Smuzhiyun Function: sGetChanStatus
768*4882a593Smuzhiyun Purpose:  Get the channel status
769*4882a593Smuzhiyun Call:     sGetChanStatus(ChP)
770*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
771*4882a593Smuzhiyun Return:   Word_t: The channel status.  Can be any combination of
772*4882a593Smuzhiyun              the following flags:
773*4882a593Smuzhiyun                 LOW BYTE FLAGS
774*4882a593Smuzhiyun                 CTS_ACT:      CTS input asserted
775*4882a593Smuzhiyun                 DSR_ACT:      DSR input asserted
776*4882a593Smuzhiyun                 CD_ACT:       CD input asserted
777*4882a593Smuzhiyun                 TXFIFOMT:     Tx FIFO is empty
778*4882a593Smuzhiyun                 TXSHRMT:      Tx shift register is empty
779*4882a593Smuzhiyun                 RDA:          Rx data available
780*4882a593Smuzhiyun 
781*4882a593Smuzhiyun                 HIGH BYTE FLAGS
782*4882a593Smuzhiyun                 STATMODE:     status mode enable bit
783*4882a593Smuzhiyun                 RXFOVERFL:    receive FIFO overflow
784*4882a593Smuzhiyun                 RX2MATCH:     receive compare byte 2 match
785*4882a593Smuzhiyun                 RX1MATCH:     receive compare byte 1 match
786*4882a593Smuzhiyun                 RXBREAK:      received BREAK
787*4882a593Smuzhiyun                 RXFRAME:      received framing error
788*4882a593Smuzhiyun                 RXPARITY:     received parity error
789*4882a593Smuzhiyun Warnings: This function will clear the high byte flags in the Channel
790*4882a593Smuzhiyun           Status Register.
791*4882a593Smuzhiyun */
792*4882a593Smuzhiyun #define sGetChanStatus(ChP) sInW((ChP)->ChanStat)
793*4882a593Smuzhiyun 
794*4882a593Smuzhiyun /***************************************************************************
795*4882a593Smuzhiyun Function: sGetChanStatusLo
796*4882a593Smuzhiyun Purpose:  Get the low byte only of the channel status
797*4882a593Smuzhiyun Call:     sGetChanStatusLo(ChP)
798*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
799*4882a593Smuzhiyun Return:   Byte_t: The channel status low byte.  Can be any combination
800*4882a593Smuzhiyun              of the following flags:
801*4882a593Smuzhiyun                 CTS_ACT:      CTS input asserted
802*4882a593Smuzhiyun                 DSR_ACT:      DSR input asserted
803*4882a593Smuzhiyun                 CD_ACT:       CD input asserted
804*4882a593Smuzhiyun                 TXFIFOMT:     Tx FIFO is empty
805*4882a593Smuzhiyun                 TXSHRMT:      Tx shift register is empty
806*4882a593Smuzhiyun                 RDA:          Rx data available
807*4882a593Smuzhiyun */
808*4882a593Smuzhiyun #define sGetChanStatusLo(ChP) sInB((ByteIO_t)(ChP)->ChanStat)
809*4882a593Smuzhiyun 
810*4882a593Smuzhiyun /**********************************************************************
811*4882a593Smuzhiyun  * Get RI status of channel
812*4882a593Smuzhiyun  * Defined as a function in rocket.c   -aes
813*4882a593Smuzhiyun  */
814*4882a593Smuzhiyun #if 0
815*4882a593Smuzhiyun #define sGetChanRI(ChP) ((ChP)->CtlP->AltChanRingIndicator ? \
816*4882a593Smuzhiyun                           (sInB((ByteIO_t)((ChP)->ChanStat+8)) & DSR_ACT) : \
817*4882a593Smuzhiyun                             (((ChP)->CtlP->boardType == ROCKET_TYPE_PC104) ? \
818*4882a593Smuzhiyun                                (!(sInB((ChP)->CtlP->AiopIO[3]) & sBitMapSetTbl[(ChP)->ChanNum])) : \
819*4882a593Smuzhiyun                              0))
820*4882a593Smuzhiyun #endif
821*4882a593Smuzhiyun 
822*4882a593Smuzhiyun /***************************************************************************
823*4882a593Smuzhiyun Function: sGetControllerIntStatus
824*4882a593Smuzhiyun Purpose:  Get the controller interrupt status
825*4882a593Smuzhiyun Call:     sGetControllerIntStatus(CtlP)
826*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
827*4882a593Smuzhiyun Return:   Byte_t: The controller interrupt status in the lower 4
828*4882a593Smuzhiyun                          bits.  Bits 0 through 3 represent AIOP's 0
829*4882a593Smuzhiyun                          through 3 respectively.  If a bit is set that
830*4882a593Smuzhiyun                          AIOP is interrupting.  Bits 4 through 7 will
831*4882a593Smuzhiyun                          always be cleared.
832*4882a593Smuzhiyun */
833*4882a593Smuzhiyun #define sGetControllerIntStatus(CTLP) (sInB((CTLP)->MReg1IO) & 0x0f)
834*4882a593Smuzhiyun 
835*4882a593Smuzhiyun /***************************************************************************
836*4882a593Smuzhiyun Function: sPCIGetControllerIntStatus
837*4882a593Smuzhiyun Purpose:  Get the controller interrupt status
838*4882a593Smuzhiyun Call:     sPCIGetControllerIntStatus(CtlP)
839*4882a593Smuzhiyun           CONTROLLER_T *CtlP; Ptr to controller structure
840*4882a593Smuzhiyun Return:   unsigned char: The controller interrupt status in the lower 4
841*4882a593Smuzhiyun                          bits and bit 4.  Bits 0 through 3 represent AIOP's 0
842*4882a593Smuzhiyun                          through 3 respectively. Bit 4 is set if the int
843*4882a593Smuzhiyun 			 was generated from periodic. If a bit is set the
844*4882a593Smuzhiyun 			 AIOP is interrupting.
845*4882a593Smuzhiyun */
846*4882a593Smuzhiyun #define sPCIGetControllerIntStatus(CTLP) \
847*4882a593Smuzhiyun 	((CTLP)->isUPCI ? \
848*4882a593Smuzhiyun 	  (sInW((CTLP)->PCIIO2) & UPCI_AIOP_INTR_BITS) : \
849*4882a593Smuzhiyun 	  ((sInW((CTLP)->PCIIO) >> 8) & AIOP_INTR_BITS))
850*4882a593Smuzhiyun 
851*4882a593Smuzhiyun /***************************************************************************
852*4882a593Smuzhiyun 
853*4882a593Smuzhiyun Function: sGetRxCnt
854*4882a593Smuzhiyun Purpose:  Get the number of data bytes in the Rx FIFO
855*4882a593Smuzhiyun Call:     sGetRxCnt(ChP)
856*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
857*4882a593Smuzhiyun Return:   int: The number of data bytes in the Rx FIFO.
858*4882a593Smuzhiyun Comments: Byte read of count register is required to obtain Rx count.
859*4882a593Smuzhiyun 
860*4882a593Smuzhiyun */
861*4882a593Smuzhiyun #define sGetRxCnt(ChP) sInW((ChP)->TxRxCount)
862*4882a593Smuzhiyun 
863*4882a593Smuzhiyun /***************************************************************************
864*4882a593Smuzhiyun Function: sGetTxCnt
865*4882a593Smuzhiyun Purpose:  Get the number of data bytes in the Tx FIFO
866*4882a593Smuzhiyun Call:     sGetTxCnt(ChP)
867*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
868*4882a593Smuzhiyun Return:   Byte_t: The number of data bytes in the Tx FIFO.
869*4882a593Smuzhiyun Comments: Byte read of count register is required to obtain Tx count.
870*4882a593Smuzhiyun 
871*4882a593Smuzhiyun */
872*4882a593Smuzhiyun #define sGetTxCnt(ChP) sInB((ByteIO_t)(ChP)->TxRxCount)
873*4882a593Smuzhiyun 
874*4882a593Smuzhiyun /*****************************************************************************
875*4882a593Smuzhiyun Function: sGetTxRxDataIO
876*4882a593Smuzhiyun Purpose:  Get the I/O address of a channel's TxRx Data register
877*4882a593Smuzhiyun Call:     sGetTxRxDataIO(ChP)
878*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
879*4882a593Smuzhiyun Return:   WordIO_t: I/O address of a channel's TxRx Data register
880*4882a593Smuzhiyun */
881*4882a593Smuzhiyun #define sGetTxRxDataIO(ChP) (ChP)->TxRxData
882*4882a593Smuzhiyun 
883*4882a593Smuzhiyun /***************************************************************************
884*4882a593Smuzhiyun Function: sInitChanDefaults
885*4882a593Smuzhiyun Purpose:  Initialize a channel structure to it's default state.
886*4882a593Smuzhiyun Call:     sInitChanDefaults(ChP)
887*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to the channel structure
888*4882a593Smuzhiyun Comments: This function must be called once for every channel structure
889*4882a593Smuzhiyun           that exists before any other SSCI calls can be made.
890*4882a593Smuzhiyun 
891*4882a593Smuzhiyun */
892*4882a593Smuzhiyun #define sInitChanDefaults(ChP) \
893*4882a593Smuzhiyun do { \
894*4882a593Smuzhiyun    (ChP)->CtlP = NULLCTLPTR; \
895*4882a593Smuzhiyun    (ChP)->AiopNum = NULLAIOP; \
896*4882a593Smuzhiyun    (ChP)->ChanID = AIOPID_NULL; \
897*4882a593Smuzhiyun    (ChP)->ChanNum = NULLCHAN; \
898*4882a593Smuzhiyun } while (0)
899*4882a593Smuzhiyun 
900*4882a593Smuzhiyun /***************************************************************************
901*4882a593Smuzhiyun Function: sResetAiopByNum
902*4882a593Smuzhiyun Purpose:  Reset the AIOP by number
903*4882a593Smuzhiyun Call:     sResetAiopByNum(CTLP,AIOPNUM)
904*4882a593Smuzhiyun 	CONTROLLER_T CTLP; Ptr to controller structure
905*4882a593Smuzhiyun 	AIOPNUM; AIOP index
906*4882a593Smuzhiyun */
907*4882a593Smuzhiyun #define sResetAiopByNum(CTLP,AIOPNUM) \
908*4882a593Smuzhiyun do { \
909*4882a593Smuzhiyun    sOutB((CTLP)->AiopIO[(AIOPNUM)]+_CMD_REG,RESET_ALL); \
910*4882a593Smuzhiyun    sOutB((CTLP)->AiopIO[(AIOPNUM)]+_CMD_REG,0x0); \
911*4882a593Smuzhiyun } while (0)
912*4882a593Smuzhiyun 
913*4882a593Smuzhiyun /***************************************************************************
914*4882a593Smuzhiyun Function: sSendBreak
915*4882a593Smuzhiyun Purpose:  Send a transmit BREAK signal
916*4882a593Smuzhiyun Call:     sSendBreak(ChP)
917*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
918*4882a593Smuzhiyun */
919*4882a593Smuzhiyun #define sSendBreak(ChP) \
920*4882a593Smuzhiyun do { \
921*4882a593Smuzhiyun    (ChP)->TxControl[3] |= SETBREAK; \
922*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
923*4882a593Smuzhiyun } while (0)
924*4882a593Smuzhiyun 
925*4882a593Smuzhiyun /***************************************************************************
926*4882a593Smuzhiyun Function: sSetBaud
927*4882a593Smuzhiyun Purpose:  Set baud rate
928*4882a593Smuzhiyun Call:     sSetBaud(ChP,Divisor)
929*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
930*4882a593Smuzhiyun           Word_t Divisor; 16 bit baud rate divisor for channel
931*4882a593Smuzhiyun */
932*4882a593Smuzhiyun #define sSetBaud(ChP,DIVISOR) \
933*4882a593Smuzhiyun do { \
934*4882a593Smuzhiyun    (ChP)->BaudDiv[2] = (Byte_t)(DIVISOR); \
935*4882a593Smuzhiyun    (ChP)->BaudDiv[3] = (Byte_t)((DIVISOR) >> 8); \
936*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->BaudDiv); \
937*4882a593Smuzhiyun } while (0)
938*4882a593Smuzhiyun 
939*4882a593Smuzhiyun /***************************************************************************
940*4882a593Smuzhiyun Function: sSetData7
941*4882a593Smuzhiyun Purpose:  Set data bits to 7
942*4882a593Smuzhiyun Call:     sSetData7(ChP)
943*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
944*4882a593Smuzhiyun */
945*4882a593Smuzhiyun #define sSetData7(ChP) \
946*4882a593Smuzhiyun do { \
947*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~DATA8BIT; \
948*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
949*4882a593Smuzhiyun } while (0)
950*4882a593Smuzhiyun 
951*4882a593Smuzhiyun /***************************************************************************
952*4882a593Smuzhiyun Function: sSetData8
953*4882a593Smuzhiyun Purpose:  Set data bits to 8
954*4882a593Smuzhiyun Call:     sSetData8(ChP)
955*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
956*4882a593Smuzhiyun */
957*4882a593Smuzhiyun #define sSetData8(ChP) \
958*4882a593Smuzhiyun do { \
959*4882a593Smuzhiyun    (ChP)->TxControl[2] |= DATA8BIT; \
960*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
961*4882a593Smuzhiyun } while (0)
962*4882a593Smuzhiyun 
963*4882a593Smuzhiyun /***************************************************************************
964*4882a593Smuzhiyun Function: sSetDTR
965*4882a593Smuzhiyun Purpose:  Set the DTR output
966*4882a593Smuzhiyun Call:     sSetDTR(ChP)
967*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
968*4882a593Smuzhiyun */
969*4882a593Smuzhiyun #define sSetDTR(ChP) \
970*4882a593Smuzhiyun do { \
971*4882a593Smuzhiyun    (ChP)->TxControl[3] |= SET_DTR; \
972*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
973*4882a593Smuzhiyun } while (0)
974*4882a593Smuzhiyun 
975*4882a593Smuzhiyun /***************************************************************************
976*4882a593Smuzhiyun Function: sSetEvenParity
977*4882a593Smuzhiyun Purpose:  Set even parity
978*4882a593Smuzhiyun Call:     sSetEvenParity(ChP)
979*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
980*4882a593Smuzhiyun Comments: Function sSetParity() can be used in place of functions sEnParity(),
981*4882a593Smuzhiyun           sDisParity(), sSetOddParity(), and sSetEvenParity().
982*4882a593Smuzhiyun 
983*4882a593Smuzhiyun Warnings: This function has no effect unless parity is enabled with function
984*4882a593Smuzhiyun           sEnParity().
985*4882a593Smuzhiyun */
986*4882a593Smuzhiyun #define sSetEvenParity(ChP) \
987*4882a593Smuzhiyun do { \
988*4882a593Smuzhiyun    (ChP)->TxControl[2] |= EVEN_PAR; \
989*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
990*4882a593Smuzhiyun } while (0)
991*4882a593Smuzhiyun 
992*4882a593Smuzhiyun /***************************************************************************
993*4882a593Smuzhiyun Function: sSetOddParity
994*4882a593Smuzhiyun Purpose:  Set odd parity
995*4882a593Smuzhiyun Call:     sSetOddParity(ChP)
996*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
997*4882a593Smuzhiyun Comments: Function sSetParity() can be used in place of functions sEnParity(),
998*4882a593Smuzhiyun           sDisParity(), sSetOddParity(), and sSetEvenParity().
999*4882a593Smuzhiyun 
1000*4882a593Smuzhiyun Warnings: This function has no effect unless parity is enabled with function
1001*4882a593Smuzhiyun           sEnParity().
1002*4882a593Smuzhiyun */
1003*4882a593Smuzhiyun #define sSetOddParity(ChP) \
1004*4882a593Smuzhiyun do { \
1005*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~EVEN_PAR; \
1006*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
1007*4882a593Smuzhiyun } while (0)
1008*4882a593Smuzhiyun 
1009*4882a593Smuzhiyun /***************************************************************************
1010*4882a593Smuzhiyun Function: sSetRTS
1011*4882a593Smuzhiyun Purpose:  Set the RTS output
1012*4882a593Smuzhiyun Call:     sSetRTS(ChP)
1013*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1014*4882a593Smuzhiyun */
1015*4882a593Smuzhiyun #define sSetRTS(ChP) \
1016*4882a593Smuzhiyun do { \
1017*4882a593Smuzhiyun    if ((ChP)->rtsToggle) break; \
1018*4882a593Smuzhiyun    (ChP)->TxControl[3] |= SET_RTS; \
1019*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
1020*4882a593Smuzhiyun } while (0)
1021*4882a593Smuzhiyun 
1022*4882a593Smuzhiyun /***************************************************************************
1023*4882a593Smuzhiyun Function: sSetRxTrigger
1024*4882a593Smuzhiyun Purpose:  Set the Rx FIFO trigger level
1025*4882a593Smuzhiyun Call:     sSetRxProcessor(ChP,Level)
1026*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1027*4882a593Smuzhiyun           Byte_t Level; Number of characters in Rx FIFO at which the
1028*4882a593Smuzhiyun              interrupt will be generated.  Can be any of the following flags:
1029*4882a593Smuzhiyun 
1030*4882a593Smuzhiyun              TRIG_NO:   no trigger
1031*4882a593Smuzhiyun              TRIG_1:    1 character in FIFO
1032*4882a593Smuzhiyun              TRIG_1_2:  FIFO 1/2 full
1033*4882a593Smuzhiyun              TRIG_7_8:  FIFO 7/8 full
1034*4882a593Smuzhiyun Comments: An interrupt will be generated when the trigger level is reached
1035*4882a593Smuzhiyun           only if function sEnInterrupt() has been called with flag
1036*4882a593Smuzhiyun           RXINT_EN set.  The RXF_TRIG flag in the Interrupt Idenfification
1037*4882a593Smuzhiyun           register will be set whenever the trigger level is reached
1038*4882a593Smuzhiyun           regardless of the setting of RXINT_EN.
1039*4882a593Smuzhiyun 
1040*4882a593Smuzhiyun */
1041*4882a593Smuzhiyun #define sSetRxTrigger(ChP,LEVEL) \
1042*4882a593Smuzhiyun do { \
1043*4882a593Smuzhiyun    (ChP)->RxControl[2] &= ~TRIG_MASK; \
1044*4882a593Smuzhiyun    (ChP)->RxControl[2] |= LEVEL; \
1045*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->RxControl); \
1046*4882a593Smuzhiyun } while (0)
1047*4882a593Smuzhiyun 
1048*4882a593Smuzhiyun /***************************************************************************
1049*4882a593Smuzhiyun Function: sSetStop1
1050*4882a593Smuzhiyun Purpose:  Set stop bits to 1
1051*4882a593Smuzhiyun Call:     sSetStop1(ChP)
1052*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1053*4882a593Smuzhiyun */
1054*4882a593Smuzhiyun #define sSetStop1(ChP) \
1055*4882a593Smuzhiyun do { \
1056*4882a593Smuzhiyun    (ChP)->TxControl[2] &= ~STOP2; \
1057*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
1058*4882a593Smuzhiyun } while (0)
1059*4882a593Smuzhiyun 
1060*4882a593Smuzhiyun /***************************************************************************
1061*4882a593Smuzhiyun Function: sSetStop2
1062*4882a593Smuzhiyun Purpose:  Set stop bits to 2
1063*4882a593Smuzhiyun Call:     sSetStop2(ChP)
1064*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1065*4882a593Smuzhiyun */
1066*4882a593Smuzhiyun #define sSetStop2(ChP) \
1067*4882a593Smuzhiyun do { \
1068*4882a593Smuzhiyun    (ChP)->TxControl[2] |= STOP2; \
1069*4882a593Smuzhiyun    out32((ChP)->IndexAddr,(ChP)->TxControl); \
1070*4882a593Smuzhiyun } while (0)
1071*4882a593Smuzhiyun 
1072*4882a593Smuzhiyun /***************************************************************************
1073*4882a593Smuzhiyun Function: sSetTxXOFFChar
1074*4882a593Smuzhiyun Purpose:  Set the Tx XOFF flow control character
1075*4882a593Smuzhiyun Call:     sSetTxXOFFChar(ChP,Ch)
1076*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1077*4882a593Smuzhiyun           Byte_t Ch; The value to set the Tx XOFF character to
1078*4882a593Smuzhiyun */
1079*4882a593Smuzhiyun #define sSetTxXOFFChar(ChP,CH) \
1080*4882a593Smuzhiyun do { \
1081*4882a593Smuzhiyun    (ChP)->R[0x07] = (CH); \
1082*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x04]); \
1083*4882a593Smuzhiyun } while (0)
1084*4882a593Smuzhiyun 
1085*4882a593Smuzhiyun /***************************************************************************
1086*4882a593Smuzhiyun Function: sSetTxXONChar
1087*4882a593Smuzhiyun Purpose:  Set the Tx XON flow control character
1088*4882a593Smuzhiyun Call:     sSetTxXONChar(ChP,Ch)
1089*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1090*4882a593Smuzhiyun           Byte_t Ch; The value to set the Tx XON character to
1091*4882a593Smuzhiyun */
1092*4882a593Smuzhiyun #define sSetTxXONChar(ChP,CH) \
1093*4882a593Smuzhiyun do { \
1094*4882a593Smuzhiyun    (ChP)->R[0x0b] = (CH); \
1095*4882a593Smuzhiyun    out32((ChP)->IndexAddr,&(ChP)->R[0x08]); \
1096*4882a593Smuzhiyun } while (0)
1097*4882a593Smuzhiyun 
1098*4882a593Smuzhiyun /***************************************************************************
1099*4882a593Smuzhiyun Function: sStartRxProcessor
1100*4882a593Smuzhiyun Purpose:  Start a channel's receive processor
1101*4882a593Smuzhiyun Call:     sStartRxProcessor(ChP)
1102*4882a593Smuzhiyun           CHANNEL_T *ChP; Ptr to channel structure
1103*4882a593Smuzhiyun Comments: This function is used to start a Rx processor after it was
1104*4882a593Smuzhiyun           stopped with sStopRxProcessor() or sStopSWInFlowCtl().  It
1105*4882a593Smuzhiyun           will restart both the Rx processor and software input flow control.
1106*4882a593Smuzhiyun 
1107*4882a593Smuzhiyun */
1108*4882a593Smuzhiyun #define sStartRxProcessor(ChP) out32((ChP)->IndexAddr,&(ChP)->R[0])
1109*4882a593Smuzhiyun 
1110*4882a593Smuzhiyun /***************************************************************************
1111*4882a593Smuzhiyun Function: sWriteTxByte
1112*4882a593Smuzhiyun Purpose:  Write a transmit data byte to a channel.
1113*4882a593Smuzhiyun           ByteIO_t io: Channel transmit register I/O address.  This can
1114*4882a593Smuzhiyun                            be obtained with sGetTxRxDataIO().
1115*4882a593Smuzhiyun           Byte_t Data; The transmit data byte.
1116*4882a593Smuzhiyun Warnings: This function writes the data byte without checking to see if
1117*4882a593Smuzhiyun           sMaxTxSize is exceeded in the Tx FIFO.
1118*4882a593Smuzhiyun */
1119*4882a593Smuzhiyun #define sWriteTxByte(IO,DATA) sOutB(IO,DATA)
1120*4882a593Smuzhiyun 
1121*4882a593Smuzhiyun /*
1122*4882a593Smuzhiyun  * Begin Linux specific definitions for the Rocketport driver
1123*4882a593Smuzhiyun  *
1124*4882a593Smuzhiyun  * This code is Copyright Theodore Ts'o, 1995-1997
1125*4882a593Smuzhiyun  */
1126*4882a593Smuzhiyun 
1127*4882a593Smuzhiyun struct r_port {
1128*4882a593Smuzhiyun 	int magic;
1129*4882a593Smuzhiyun 	struct tty_port port;
1130*4882a593Smuzhiyun 	int line;
1131*4882a593Smuzhiyun 	int flags;		/* Don't yet match the ASY_ flags!! */
1132*4882a593Smuzhiyun 	unsigned int board:3;
1133*4882a593Smuzhiyun 	unsigned int aiop:2;
1134*4882a593Smuzhiyun 	unsigned int chan:3;
1135*4882a593Smuzhiyun 	CONTROLLER_t *ctlp;
1136*4882a593Smuzhiyun 	CHANNEL_t channel;
1137*4882a593Smuzhiyun 	int intmask;
1138*4882a593Smuzhiyun 	int xmit_fifo_room;	/* room in xmit fifo */
1139*4882a593Smuzhiyun 	unsigned char *xmit_buf;
1140*4882a593Smuzhiyun 	int xmit_head;
1141*4882a593Smuzhiyun 	int xmit_tail;
1142*4882a593Smuzhiyun 	int xmit_cnt;
1143*4882a593Smuzhiyun 	int cd_status;
1144*4882a593Smuzhiyun 	int ignore_status_mask;
1145*4882a593Smuzhiyun 	int read_status_mask;
1146*4882a593Smuzhiyun 	int cps;
1147*4882a593Smuzhiyun 
1148*4882a593Smuzhiyun 	spinlock_t slock;
1149*4882a593Smuzhiyun 	struct mutex write_mtx;
1150*4882a593Smuzhiyun };
1151*4882a593Smuzhiyun 
1152*4882a593Smuzhiyun #define RPORT_MAGIC 0x525001
1153*4882a593Smuzhiyun 
1154*4882a593Smuzhiyun #define NUM_BOARDS 8
1155*4882a593Smuzhiyun #define MAX_RP_PORTS (32*NUM_BOARDS)
1156*4882a593Smuzhiyun 
1157*4882a593Smuzhiyun /*
1158*4882a593Smuzhiyun  * The size of the xmit buffer is 1 page, or 4096 bytes
1159*4882a593Smuzhiyun  */
1160*4882a593Smuzhiyun #define XMIT_BUF_SIZE 4096
1161*4882a593Smuzhiyun 
1162*4882a593Smuzhiyun /* number of characters left in xmit buffer before we ask for more */
1163*4882a593Smuzhiyun #define WAKEUP_CHARS 256
1164*4882a593Smuzhiyun 
1165*4882a593Smuzhiyun /*
1166*4882a593Smuzhiyun  * Assigned major numbers for the Comtrol Rocketport
1167*4882a593Smuzhiyun  */
1168*4882a593Smuzhiyun #define TTY_ROCKET_MAJOR	46
1169*4882a593Smuzhiyun #define CUA_ROCKET_MAJOR	47
1170*4882a593Smuzhiyun 
1171*4882a593Smuzhiyun #ifdef PCI_VENDOR_ID_RP
1172*4882a593Smuzhiyun #undef PCI_VENDOR_ID_RP
1173*4882a593Smuzhiyun #undef PCI_DEVICE_ID_RP8OCTA
1174*4882a593Smuzhiyun #undef PCI_DEVICE_ID_RP8INTF
1175*4882a593Smuzhiyun #undef PCI_DEVICE_ID_RP16INTF
1176*4882a593Smuzhiyun #undef PCI_DEVICE_ID_RP32INTF
1177*4882a593Smuzhiyun #undef PCI_DEVICE_ID_URP8OCTA
1178*4882a593Smuzhiyun #undef PCI_DEVICE_ID_URP8INTF
1179*4882a593Smuzhiyun #undef PCI_DEVICE_ID_URP16INTF
1180*4882a593Smuzhiyun #undef PCI_DEVICE_ID_CRP16INTF
1181*4882a593Smuzhiyun #undef PCI_DEVICE_ID_URP32INTF
1182*4882a593Smuzhiyun #endif
1183*4882a593Smuzhiyun 
1184*4882a593Smuzhiyun /*  Comtrol PCI Vendor ID */
1185*4882a593Smuzhiyun #define PCI_VENDOR_ID_RP		0x11fe
1186*4882a593Smuzhiyun 
1187*4882a593Smuzhiyun /*  Comtrol Device ID's */
1188*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP32INTF		0x0001	/* Rocketport 32 port w/external I/F     */
1189*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP8INTF		0x0002	/* Rocketport 8 port w/external I/F      */
1190*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP16INTF		0x0003	/* Rocketport 16 port w/external I/F     */
1191*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP4QUAD		0x0004	/* Rocketport 4 port w/quad cable        */
1192*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP8OCTA		0x0005	/* Rocketport 8 port w/octa cable        */
1193*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP8J		0x0006	/* Rocketport 8 port w/RJ11 connectors   */
1194*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP4J		0x0007	/* Rocketport 4 port w/RJ11 connectors   */
1195*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP8SNI		0x0008	/* Rocketport 8 port w/ DB78 SNI (Siemens) connector */
1196*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP16SNI		0x0009	/* Rocketport 16 port w/ DB78 SNI (Siemens) connector   */
1197*4882a593Smuzhiyun #define PCI_DEVICE_ID_RPP4		0x000A	/* Rocketport Plus 4 port                */
1198*4882a593Smuzhiyun #define PCI_DEVICE_ID_RPP8		0x000B	/* Rocketport Plus 8 port                */
1199*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP6M		0x000C	/* RocketModem 6 port                    */
1200*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP4M		0x000D	/* RocketModem 4 port                    */
1201*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP2_232           0x000E	/* Rocketport Plus 2 port RS232          */
1202*4882a593Smuzhiyun #define PCI_DEVICE_ID_RP2_422           0x000F	/* Rocketport Plus 2 port RS422          */
1203*4882a593Smuzhiyun 
1204*4882a593Smuzhiyun /* Universal PCI boards  */
1205*4882a593Smuzhiyun #define PCI_DEVICE_ID_URP32INTF		0x0801	/* Rocketport UPCI 32 port w/external I/F */
1206*4882a593Smuzhiyun #define PCI_DEVICE_ID_URP8INTF		0x0802	/* Rocketport UPCI 8 port w/external I/F  */
1207*4882a593Smuzhiyun #define PCI_DEVICE_ID_URP16INTF		0x0803	/* Rocketport UPCI 16 port w/external I/F */
1208*4882a593Smuzhiyun #define PCI_DEVICE_ID_URP8OCTA		0x0805	/* Rocketport UPCI 8 port w/octa cable    */
1209*4882a593Smuzhiyun #define PCI_DEVICE_ID_UPCI_RM3_8PORT    0x080C	/* Rocketmodem III 8 port                 */
1210*4882a593Smuzhiyun #define PCI_DEVICE_ID_UPCI_RM3_4PORT    0x080D	/* Rocketmodem III 4 port                 */
1211*4882a593Smuzhiyun 
1212*4882a593Smuzhiyun /* Compact PCI device */
1213*4882a593Smuzhiyun #define PCI_DEVICE_ID_CRP16INTF		0x0903	/* Rocketport Compact PCI 16 port w/external I/F */
1214*4882a593Smuzhiyun 
1215