Commit 21bed701da009b4192d9e86b3596cf210ac7369c

Authored by Alan Cox
Committed by Linus Torvalds
1 parent c1314a49d7

tty: make rocketport use standard port->flags

We need to this ready for using the standard helpers

Signed-off-by: Alan Cox <alan@redhat.com>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>

Showing 1 changed file with 19 additions and 19 deletions Inline Diff

drivers/char/rocket.c
1 /* 1 /*
2 * RocketPort device driver for Linux 2 * RocketPort device driver for Linux
3 * 3 *
4 * Written by Theodore Ts'o, 1995, 1996, 1997, 1998, 1999, 2000. 4 * Written by Theodore Ts'o, 1995, 1996, 1997, 1998, 1999, 2000.
5 * 5 *
6 * Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2003 by Comtrol, Inc. 6 * Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2003 by Comtrol, Inc.
7 * 7 *
8 * This program is free software; you can redistribute it and/or 8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License as 9 * modify it under the terms of the GNU General Public License as
10 * published by the Free Software Foundation; either version 2 of the 10 * published by the Free Software Foundation; either version 2 of the
11 * License, or (at your option) any later version. 11 * License, or (at your option) any later version.
12 * 12 *
13 * This program is distributed in the hope that it will be useful, but 13 * This program is distributed in the hope that it will be useful, but
14 * WITHOUT ANY WARRANTY; without even the implied warranty of 14 * WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details. 16 * General Public License for more details.
17 * 17 *
18 * You should have received a copy of the GNU General Public License 18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software 19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 20 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 */ 21 */
22 22
23 /* 23 /*
24 * Kernel Synchronization: 24 * Kernel Synchronization:
25 * 25 *
26 * This driver has 2 kernel control paths - exception handlers (calls into the driver 26 * This driver has 2 kernel control paths - exception handlers (calls into the driver
27 * from user mode) and the timer bottom half (tasklet). This is a polled driver, interrupts 27 * from user mode) and the timer bottom half (tasklet). This is a polled driver, interrupts
28 * are not used. 28 * are not used.
29 * 29 *
30 * Critical data: 30 * Critical data:
31 * - rp_table[], accessed through passed "info" pointers, is a global (static) array of 31 * - rp_table[], accessed through passed "info" pointers, is a global (static) array of
32 * serial port state information and the xmit_buf circular buffer. Protected by 32 * serial port state information and the xmit_buf circular buffer. Protected by
33 * a per port spinlock. 33 * a per port spinlock.
34 * - xmit_flags[], an array of ints indexed by line (port) number, indicating that there 34 * - xmit_flags[], an array of ints indexed by line (port) number, indicating that there
35 * is data to be transmitted. Protected by atomic bit operations. 35 * is data to be transmitted. Protected by atomic bit operations.
36 * - rp_num_ports, int indicating number of open ports, protected by atomic operations. 36 * - rp_num_ports, int indicating number of open ports, protected by atomic operations.
37 * 37 *
38 * rp_write() and rp_write_char() functions use a per port semaphore to protect against 38 * rp_write() and rp_write_char() functions use a per port semaphore to protect against
39 * simultaneous access to the same port by more than one process. 39 * simultaneous access to the same port by more than one process.
40 */ 40 */
41 41
42 /****** Defines ******/ 42 /****** Defines ******/
43 #define ROCKET_PARANOIA_CHECK 43 #define ROCKET_PARANOIA_CHECK
44 #define ROCKET_DISABLE_SIMUSAGE 44 #define ROCKET_DISABLE_SIMUSAGE
45 45
46 #undef ROCKET_SOFT_FLOW 46 #undef ROCKET_SOFT_FLOW
47 #undef ROCKET_DEBUG_OPEN 47 #undef ROCKET_DEBUG_OPEN
48 #undef ROCKET_DEBUG_INTR 48 #undef ROCKET_DEBUG_INTR
49 #undef ROCKET_DEBUG_WRITE 49 #undef ROCKET_DEBUG_WRITE
50 #undef ROCKET_DEBUG_FLOW 50 #undef ROCKET_DEBUG_FLOW
51 #undef ROCKET_DEBUG_THROTTLE 51 #undef ROCKET_DEBUG_THROTTLE
52 #undef ROCKET_DEBUG_WAIT_UNTIL_SENT 52 #undef ROCKET_DEBUG_WAIT_UNTIL_SENT
53 #undef ROCKET_DEBUG_RECEIVE 53 #undef ROCKET_DEBUG_RECEIVE
54 #undef ROCKET_DEBUG_HANGUP 54 #undef ROCKET_DEBUG_HANGUP
55 #undef REV_PCI_ORDER 55 #undef REV_PCI_ORDER
56 #undef ROCKET_DEBUG_IO 56 #undef ROCKET_DEBUG_IO
57 57
58 #define POLL_PERIOD HZ/100 /* Polling period .01 seconds (10ms) */ 58 #define POLL_PERIOD HZ/100 /* Polling period .01 seconds (10ms) */
59 59
60 /****** Kernel includes ******/ 60 /****** Kernel includes ******/
61 61
62 #include <linux/module.h> 62 #include <linux/module.h>
63 #include <linux/errno.h> 63 #include <linux/errno.h>
64 #include <linux/major.h> 64 #include <linux/major.h>
65 #include <linux/kernel.h> 65 #include <linux/kernel.h>
66 #include <linux/signal.h> 66 #include <linux/signal.h>
67 #include <linux/slab.h> 67 #include <linux/slab.h>
68 #include <linux/mm.h> 68 #include <linux/mm.h>
69 #include <linux/sched.h> 69 #include <linux/sched.h>
70 #include <linux/timer.h> 70 #include <linux/timer.h>
71 #include <linux/interrupt.h> 71 #include <linux/interrupt.h>
72 #include <linux/tty.h> 72 #include <linux/tty.h>
73 #include <linux/tty_driver.h> 73 #include <linux/tty_driver.h>
74 #include <linux/tty_flip.h> 74 #include <linux/tty_flip.h>
75 #include <linux/serial.h> 75 #include <linux/serial.h>
76 #include <linux/string.h> 76 #include <linux/string.h>
77 #include <linux/fcntl.h> 77 #include <linux/fcntl.h>
78 #include <linux/ptrace.h> 78 #include <linux/ptrace.h>
79 #include <linux/mutex.h> 79 #include <linux/mutex.h>
80 #include <linux/ioport.h> 80 #include <linux/ioport.h>
81 #include <linux/delay.h> 81 #include <linux/delay.h>
82 #include <linux/completion.h> 82 #include <linux/completion.h>
83 #include <linux/wait.h> 83 #include <linux/wait.h>
84 #include <linux/pci.h> 84 #include <linux/pci.h>
85 #include <linux/uaccess.h> 85 #include <linux/uaccess.h>
86 #include <asm/atomic.h> 86 #include <asm/atomic.h>
87 #include <asm/unaligned.h> 87 #include <asm/unaligned.h>
88 #include <linux/bitops.h> 88 #include <linux/bitops.h>
89 #include <linux/spinlock.h> 89 #include <linux/spinlock.h>
90 #include <linux/init.h> 90 #include <linux/init.h>
91 91
92 /****** RocketPort includes ******/ 92 /****** RocketPort includes ******/
93 93
94 #include "rocket_int.h" 94 #include "rocket_int.h"
95 #include "rocket.h" 95 #include "rocket.h"
96 96
97 #define ROCKET_VERSION "2.09" 97 #define ROCKET_VERSION "2.09"
98 #define ROCKET_DATE "12-June-2003" 98 #define ROCKET_DATE "12-June-2003"
99 99
100 /****** RocketPort Local Variables ******/ 100 /****** RocketPort Local Variables ******/
101 101
102 static void rp_do_poll(unsigned long dummy); 102 static void rp_do_poll(unsigned long dummy);
103 103
104 static struct tty_driver *rocket_driver; 104 static struct tty_driver *rocket_driver;
105 105
106 static struct rocket_version driver_version = { 106 static struct rocket_version driver_version = {
107 ROCKET_VERSION, ROCKET_DATE 107 ROCKET_VERSION, ROCKET_DATE
108 }; 108 };
109 109
110 static struct r_port *rp_table[MAX_RP_PORTS]; /* The main repository of serial port state information. */ 110 static struct r_port *rp_table[MAX_RP_PORTS]; /* The main repository of serial port state information. */
111 static unsigned int xmit_flags[NUM_BOARDS]; /* Bit significant, indicates port had data to transmit. */ 111 static unsigned int xmit_flags[NUM_BOARDS]; /* Bit significant, indicates port had data to transmit. */
112 /* eg. Bit 0 indicates port 0 has xmit data, ... */ 112 /* eg. Bit 0 indicates port 0 has xmit data, ... */
113 static atomic_t rp_num_ports_open; /* Number of serial ports open */ 113 static atomic_t rp_num_ports_open; /* Number of serial ports open */
114 static DEFINE_TIMER(rocket_timer, rp_do_poll, 0, 0); 114 static DEFINE_TIMER(rocket_timer, rp_do_poll, 0, 0);
115 115
116 static unsigned long board1; /* ISA addresses, retrieved from rocketport.conf */ 116 static unsigned long board1; /* ISA addresses, retrieved from rocketport.conf */
117 static unsigned long board2; 117 static unsigned long board2;
118 static unsigned long board3; 118 static unsigned long board3;
119 static unsigned long board4; 119 static unsigned long board4;
120 static unsigned long controller; 120 static unsigned long controller;
121 static int support_low_speed; 121 static int support_low_speed;
122 static unsigned long modem1; 122 static unsigned long modem1;
123 static unsigned long modem2; 123 static unsigned long modem2;
124 static unsigned long modem3; 124 static unsigned long modem3;
125 static unsigned long modem4; 125 static unsigned long modem4;
126 static unsigned long pc104_1[8]; 126 static unsigned long pc104_1[8];
127 static unsigned long pc104_2[8]; 127 static unsigned long pc104_2[8];
128 static unsigned long pc104_3[8]; 128 static unsigned long pc104_3[8];
129 static unsigned long pc104_4[8]; 129 static unsigned long pc104_4[8];
130 static unsigned long *pc104[4] = { pc104_1, pc104_2, pc104_3, pc104_4 }; 130 static unsigned long *pc104[4] = { pc104_1, pc104_2, pc104_3, pc104_4 };
131 131
132 static int rp_baud_base[NUM_BOARDS]; /* Board config info (Someday make a per-board structure) */ 132 static int rp_baud_base[NUM_BOARDS]; /* Board config info (Someday make a per-board structure) */
133 static unsigned long rcktpt_io_addr[NUM_BOARDS]; 133 static unsigned long rcktpt_io_addr[NUM_BOARDS];
134 static int rcktpt_type[NUM_BOARDS]; 134 static int rcktpt_type[NUM_BOARDS];
135 static int is_PCI[NUM_BOARDS]; 135 static int is_PCI[NUM_BOARDS];
136 static rocketModel_t rocketModel[NUM_BOARDS]; 136 static rocketModel_t rocketModel[NUM_BOARDS];
137 static int max_board; 137 static int max_board;
138 static const struct tty_port_operations rocket_port_ops; 138 static const struct tty_port_operations rocket_port_ops;
139 139
140 /* 140 /*
141 * The following arrays define the interrupt bits corresponding to each AIOP. 141 * The following arrays define the interrupt bits corresponding to each AIOP.
142 * These bits are different between the ISA and regular PCI boards and the 142 * These bits are different between the ISA and regular PCI boards and the
143 * Universal PCI boards. 143 * Universal PCI boards.
144 */ 144 */
145 145
146 static Word_t aiop_intr_bits[AIOP_CTL_SIZE] = { 146 static Word_t aiop_intr_bits[AIOP_CTL_SIZE] = {
147 AIOP_INTR_BIT_0, 147 AIOP_INTR_BIT_0,
148 AIOP_INTR_BIT_1, 148 AIOP_INTR_BIT_1,
149 AIOP_INTR_BIT_2, 149 AIOP_INTR_BIT_2,
150 AIOP_INTR_BIT_3 150 AIOP_INTR_BIT_3
151 }; 151 };
152 152
153 static Word_t upci_aiop_intr_bits[AIOP_CTL_SIZE] = { 153 static Word_t upci_aiop_intr_bits[AIOP_CTL_SIZE] = {
154 UPCI_AIOP_INTR_BIT_0, 154 UPCI_AIOP_INTR_BIT_0,
155 UPCI_AIOP_INTR_BIT_1, 155 UPCI_AIOP_INTR_BIT_1,
156 UPCI_AIOP_INTR_BIT_2, 156 UPCI_AIOP_INTR_BIT_2,
157 UPCI_AIOP_INTR_BIT_3 157 UPCI_AIOP_INTR_BIT_3
158 }; 158 };
159 159
160 static Byte_t RData[RDATASIZE] = { 160 static Byte_t RData[RDATASIZE] = {
161 0x00, 0x09, 0xf6, 0x82, 161 0x00, 0x09, 0xf6, 0x82,
162 0x02, 0x09, 0x86, 0xfb, 162 0x02, 0x09, 0x86, 0xfb,
163 0x04, 0x09, 0x00, 0x0a, 163 0x04, 0x09, 0x00, 0x0a,
164 0x06, 0x09, 0x01, 0x0a, 164 0x06, 0x09, 0x01, 0x0a,
165 0x08, 0x09, 0x8a, 0x13, 165 0x08, 0x09, 0x8a, 0x13,
166 0x0a, 0x09, 0xc5, 0x11, 166 0x0a, 0x09, 0xc5, 0x11,
167 0x0c, 0x09, 0x86, 0x85, 167 0x0c, 0x09, 0x86, 0x85,
168 0x0e, 0x09, 0x20, 0x0a, 168 0x0e, 0x09, 0x20, 0x0a,
169 0x10, 0x09, 0x21, 0x0a, 169 0x10, 0x09, 0x21, 0x0a,
170 0x12, 0x09, 0x41, 0xff, 170 0x12, 0x09, 0x41, 0xff,
171 0x14, 0x09, 0x82, 0x00, 171 0x14, 0x09, 0x82, 0x00,
172 0x16, 0x09, 0x82, 0x7b, 172 0x16, 0x09, 0x82, 0x7b,
173 0x18, 0x09, 0x8a, 0x7d, 173 0x18, 0x09, 0x8a, 0x7d,
174 0x1a, 0x09, 0x88, 0x81, 174 0x1a, 0x09, 0x88, 0x81,
175 0x1c, 0x09, 0x86, 0x7a, 175 0x1c, 0x09, 0x86, 0x7a,
176 0x1e, 0x09, 0x84, 0x81, 176 0x1e, 0x09, 0x84, 0x81,
177 0x20, 0x09, 0x82, 0x7c, 177 0x20, 0x09, 0x82, 0x7c,
178 0x22, 0x09, 0x0a, 0x0a 178 0x22, 0x09, 0x0a, 0x0a
179 }; 179 };
180 180
181 static Byte_t RRegData[RREGDATASIZE] = { 181 static Byte_t RRegData[RREGDATASIZE] = {
182 0x00, 0x09, 0xf6, 0x82, /* 00: Stop Rx processor */ 182 0x00, 0x09, 0xf6, 0x82, /* 00: Stop Rx processor */
183 0x08, 0x09, 0x8a, 0x13, /* 04: Tx software flow control */ 183 0x08, 0x09, 0x8a, 0x13, /* 04: Tx software flow control */
184 0x0a, 0x09, 0xc5, 0x11, /* 08: XON char */ 184 0x0a, 0x09, 0xc5, 0x11, /* 08: XON char */
185 0x0c, 0x09, 0x86, 0x85, /* 0c: XANY */ 185 0x0c, 0x09, 0x86, 0x85, /* 0c: XANY */
186 0x12, 0x09, 0x41, 0xff, /* 10: Rx mask char */ 186 0x12, 0x09, 0x41, 0xff, /* 10: Rx mask char */
187 0x14, 0x09, 0x82, 0x00, /* 14: Compare/Ignore #0 */ 187 0x14, 0x09, 0x82, 0x00, /* 14: Compare/Ignore #0 */
188 0x16, 0x09, 0x82, 0x7b, /* 18: Compare #1 */ 188 0x16, 0x09, 0x82, 0x7b, /* 18: Compare #1 */
189 0x18, 0x09, 0x8a, 0x7d, /* 1c: Compare #2 */ 189 0x18, 0x09, 0x8a, 0x7d, /* 1c: Compare #2 */
190 0x1a, 0x09, 0x88, 0x81, /* 20: Interrupt #1 */ 190 0x1a, 0x09, 0x88, 0x81, /* 20: Interrupt #1 */
191 0x1c, 0x09, 0x86, 0x7a, /* 24: Ignore/Replace #1 */ 191 0x1c, 0x09, 0x86, 0x7a, /* 24: Ignore/Replace #1 */
192 0x1e, 0x09, 0x84, 0x81, /* 28: Interrupt #2 */ 192 0x1e, 0x09, 0x84, 0x81, /* 28: Interrupt #2 */
193 0x20, 0x09, 0x82, 0x7c, /* 2c: Ignore/Replace #2 */ 193 0x20, 0x09, 0x82, 0x7c, /* 2c: Ignore/Replace #2 */
194 0x22, 0x09, 0x0a, 0x0a /* 30: Rx FIFO Enable */ 194 0x22, 0x09, 0x0a, 0x0a /* 30: Rx FIFO Enable */
195 }; 195 };
196 196
197 static CONTROLLER_T sController[CTL_SIZE] = { 197 static CONTROLLER_T sController[CTL_SIZE] = {
198 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0}, 198 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0},
199 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}}, 199 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}},
200 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0}, 200 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0},
201 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}}, 201 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}},
202 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0}, 202 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0},
203 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}}, 203 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}},
204 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0}, 204 {-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, {0, 0, 0, 0},
205 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}} 205 {0, 0, 0, 0}, {-1, -1, -1, -1}, {0, 0, 0, 0}}
206 }; 206 };
207 207
208 static Byte_t sBitMapClrTbl[8] = { 208 static Byte_t sBitMapClrTbl[8] = {
209 0xfe, 0xfd, 0xfb, 0xf7, 0xef, 0xdf, 0xbf, 0x7f 209 0xfe, 0xfd, 0xfb, 0xf7, 0xef, 0xdf, 0xbf, 0x7f
210 }; 210 };
211 211
212 static Byte_t sBitMapSetTbl[8] = { 212 static Byte_t sBitMapSetTbl[8] = {
213 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80 213 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80
214 }; 214 };
215 215
216 static int sClockPrescale = 0x14; 216 static int sClockPrescale = 0x14;
217 217
218 /* 218 /*
219 * Line number is the ttySIx number (x), the Minor number. We 219 * Line number is the ttySIx number (x), the Minor number. We
220 * assign them sequentially, starting at zero. The following 220 * assign them sequentially, starting at zero. The following
221 * array keeps track of the line number assigned to a given board/aiop/channel. 221 * array keeps track of the line number assigned to a given board/aiop/channel.
222 */ 222 */
223 static unsigned char lineNumbers[MAX_RP_PORTS]; 223 static unsigned char lineNumbers[MAX_RP_PORTS];
224 static unsigned long nextLineNumber; 224 static unsigned long nextLineNumber;
225 225
226 /***** RocketPort Static Prototypes *********/ 226 /***** RocketPort Static Prototypes *********/
227 static int __init init_ISA(int i); 227 static int __init init_ISA(int i);
228 static void rp_wait_until_sent(struct tty_struct *tty, int timeout); 228 static void rp_wait_until_sent(struct tty_struct *tty, int timeout);
229 static void rp_flush_buffer(struct tty_struct *tty); 229 static void rp_flush_buffer(struct tty_struct *tty);
230 static void rmSpeakerReset(CONTROLLER_T * CtlP, unsigned long model); 230 static void rmSpeakerReset(CONTROLLER_T * CtlP, unsigned long model);
231 static unsigned char GetLineNumber(int ctrl, int aiop, int ch); 231 static unsigned char GetLineNumber(int ctrl, int aiop, int ch);
232 static unsigned char SetLineNumber(int ctrl, int aiop, int ch); 232 static unsigned char SetLineNumber(int ctrl, int aiop, int ch);
233 static void rp_start(struct tty_struct *tty); 233 static void rp_start(struct tty_struct *tty);
234 static int sInitChan(CONTROLLER_T * CtlP, CHANNEL_T * ChP, int AiopNum, 234 static int sInitChan(CONTROLLER_T * CtlP, CHANNEL_T * ChP, int AiopNum,
235 int ChanNum); 235 int ChanNum);
236 static void sSetInterfaceMode(CHANNEL_T * ChP, Byte_t mode); 236 static void sSetInterfaceMode(CHANNEL_T * ChP, Byte_t mode);
237 static void sFlushRxFIFO(CHANNEL_T * ChP); 237 static void sFlushRxFIFO(CHANNEL_T * ChP);
238 static void sFlushTxFIFO(CHANNEL_T * ChP); 238 static void sFlushTxFIFO(CHANNEL_T * ChP);
239 static void sEnInterrupts(CHANNEL_T * ChP, Word_t Flags); 239 static void sEnInterrupts(CHANNEL_T * ChP, Word_t Flags);
240 static void sDisInterrupts(CHANNEL_T * ChP, Word_t Flags); 240 static void sDisInterrupts(CHANNEL_T * ChP, Word_t Flags);
241 static void sModemReset(CONTROLLER_T * CtlP, int chan, int on); 241 static void sModemReset(CONTROLLER_T * CtlP, int chan, int on);
242 static void sPCIModemReset(CONTROLLER_T * CtlP, int chan, int on); 242 static void sPCIModemReset(CONTROLLER_T * CtlP, int chan, int on);
243 static int sWriteTxPrioByte(CHANNEL_T * ChP, Byte_t Data); 243 static int sWriteTxPrioByte(CHANNEL_T * ChP, Byte_t Data);
244 static int sPCIInitController(CONTROLLER_T * CtlP, int CtlNum, 244 static int sPCIInitController(CONTROLLER_T * CtlP, int CtlNum,
245 ByteIO_t * AiopIOList, int AiopIOListSize, 245 ByteIO_t * AiopIOList, int AiopIOListSize,
246 WordIO_t ConfigIO, int IRQNum, Byte_t Frequency, 246 WordIO_t ConfigIO, int IRQNum, Byte_t Frequency,
247 int PeriodicOnly, int altChanRingIndicator, 247 int PeriodicOnly, int altChanRingIndicator,
248 int UPCIRingInd); 248 int UPCIRingInd);
249 static int sInitController(CONTROLLER_T * CtlP, int CtlNum, ByteIO_t MudbacIO, 249 static int sInitController(CONTROLLER_T * CtlP, int CtlNum, ByteIO_t MudbacIO,
250 ByteIO_t * AiopIOList, int AiopIOListSize, 250 ByteIO_t * AiopIOList, int AiopIOListSize,
251 int IRQNum, Byte_t Frequency, int PeriodicOnly); 251 int IRQNum, Byte_t Frequency, int PeriodicOnly);
252 static int sReadAiopID(ByteIO_t io); 252 static int sReadAiopID(ByteIO_t io);
253 static int sReadAiopNumChan(WordIO_t io); 253 static int sReadAiopNumChan(WordIO_t io);
254 254
255 MODULE_AUTHOR("Theodore Ts'o"); 255 MODULE_AUTHOR("Theodore Ts'o");
256 MODULE_DESCRIPTION("Comtrol RocketPort driver"); 256 MODULE_DESCRIPTION("Comtrol RocketPort driver");
257 module_param(board1, ulong, 0); 257 module_param(board1, ulong, 0);
258 MODULE_PARM_DESC(board1, "I/O port for (ISA) board #1"); 258 MODULE_PARM_DESC(board1, "I/O port for (ISA) board #1");
259 module_param(board2, ulong, 0); 259 module_param(board2, ulong, 0);
260 MODULE_PARM_DESC(board2, "I/O port for (ISA) board #2"); 260 MODULE_PARM_DESC(board2, "I/O port for (ISA) board #2");
261 module_param(board3, ulong, 0); 261 module_param(board3, ulong, 0);
262 MODULE_PARM_DESC(board3, "I/O port for (ISA) board #3"); 262 MODULE_PARM_DESC(board3, "I/O port for (ISA) board #3");
263 module_param(board4, ulong, 0); 263 module_param(board4, ulong, 0);
264 MODULE_PARM_DESC(board4, "I/O port for (ISA) board #4"); 264 MODULE_PARM_DESC(board4, "I/O port for (ISA) board #4");
265 module_param(controller, ulong, 0); 265 module_param(controller, ulong, 0);
266 MODULE_PARM_DESC(controller, "I/O port for (ISA) rocketport controller"); 266 MODULE_PARM_DESC(controller, "I/O port for (ISA) rocketport controller");
267 module_param(support_low_speed, bool, 0); 267 module_param(support_low_speed, bool, 0);
268 MODULE_PARM_DESC(support_low_speed, "1 means support 50 baud, 0 means support 460400 baud"); 268 MODULE_PARM_DESC(support_low_speed, "1 means support 50 baud, 0 means support 460400 baud");
269 module_param(modem1, ulong, 0); 269 module_param(modem1, ulong, 0);
270 MODULE_PARM_DESC(modem1, "1 means (ISA) board #1 is a RocketModem"); 270 MODULE_PARM_DESC(modem1, "1 means (ISA) board #1 is a RocketModem");
271 module_param(modem2, ulong, 0); 271 module_param(modem2, ulong, 0);
272 MODULE_PARM_DESC(modem2, "1 means (ISA) board #2 is a RocketModem"); 272 MODULE_PARM_DESC(modem2, "1 means (ISA) board #2 is a RocketModem");
273 module_param(modem3, ulong, 0); 273 module_param(modem3, ulong, 0);
274 MODULE_PARM_DESC(modem3, "1 means (ISA) board #3 is a RocketModem"); 274 MODULE_PARM_DESC(modem3, "1 means (ISA) board #3 is a RocketModem");
275 module_param(modem4, ulong, 0); 275 module_param(modem4, ulong, 0);
276 MODULE_PARM_DESC(modem4, "1 means (ISA) board #4 is a RocketModem"); 276 MODULE_PARM_DESC(modem4, "1 means (ISA) board #4 is a RocketModem");
277 module_param_array(pc104_1, ulong, NULL, 0); 277 module_param_array(pc104_1, ulong, NULL, 0);
278 MODULE_PARM_DESC(pc104_1, "set interface types for ISA(PC104) board #1 (e.g. pc104_1=232,232,485,485,..."); 278 MODULE_PARM_DESC(pc104_1, "set interface types for ISA(PC104) board #1 (e.g. pc104_1=232,232,485,485,...");
279 module_param_array(pc104_2, ulong, NULL, 0); 279 module_param_array(pc104_2, ulong, NULL, 0);
280 MODULE_PARM_DESC(pc104_2, "set interface types for ISA(PC104) board #2 (e.g. pc104_2=232,232,485,485,..."); 280 MODULE_PARM_DESC(pc104_2, "set interface types for ISA(PC104) board #2 (e.g. pc104_2=232,232,485,485,...");
281 module_param_array(pc104_3, ulong, NULL, 0); 281 module_param_array(pc104_3, ulong, NULL, 0);
282 MODULE_PARM_DESC(pc104_3, "set interface types for ISA(PC104) board #3 (e.g. pc104_3=232,232,485,485,..."); 282 MODULE_PARM_DESC(pc104_3, "set interface types for ISA(PC104) board #3 (e.g. pc104_3=232,232,485,485,...");
283 module_param_array(pc104_4, ulong, NULL, 0); 283 module_param_array(pc104_4, ulong, NULL, 0);
284 MODULE_PARM_DESC(pc104_4, "set interface types for ISA(PC104) board #4 (e.g. pc104_4=232,232,485,485,..."); 284 MODULE_PARM_DESC(pc104_4, "set interface types for ISA(PC104) board #4 (e.g. pc104_4=232,232,485,485,...");
285 285
286 static int rp_init(void); 286 static int rp_init(void);
287 static void rp_cleanup_module(void); 287 static void rp_cleanup_module(void);
288 288
289 module_init(rp_init); 289 module_init(rp_init);
290 module_exit(rp_cleanup_module); 290 module_exit(rp_cleanup_module);
291 291
292 292
293 MODULE_LICENSE("Dual BSD/GPL"); 293 MODULE_LICENSE("Dual BSD/GPL");
294 294
295 /*************************************************************************/ 295 /*************************************************************************/
296 /* Module code starts here */ 296 /* Module code starts here */
297 297
298 static inline int rocket_paranoia_check(struct r_port *info, 298 static inline int rocket_paranoia_check(struct r_port *info,
299 const char *routine) 299 const char *routine)
300 { 300 {
301 #ifdef ROCKET_PARANOIA_CHECK 301 #ifdef ROCKET_PARANOIA_CHECK
302 if (!info) 302 if (!info)
303 return 1; 303 return 1;
304 if (info->magic != RPORT_MAGIC) { 304 if (info->magic != RPORT_MAGIC) {
305 printk(KERN_WARNING "Warning: bad magic number for rocketport " 305 printk(KERN_WARNING "Warning: bad magic number for rocketport "
306 "struct in %s\n", routine); 306 "struct in %s\n", routine);
307 return 1; 307 return 1;
308 } 308 }
309 #endif 309 #endif
310 return 0; 310 return 0;
311 } 311 }
312 312
313 313
314 /* Serial port receive data function. Called (from timer poll) when an AIOPIC signals 314 /* Serial port receive data function. Called (from timer poll) when an AIOPIC signals
315 * that receive data is present on a serial port. Pulls data from FIFO, moves it into the 315 * that receive data is present on a serial port. Pulls data from FIFO, moves it into the
316 * tty layer. 316 * tty layer.
317 */ 317 */
318 static void rp_do_receive(struct r_port *info, 318 static void rp_do_receive(struct r_port *info,
319 struct tty_struct *tty, 319 struct tty_struct *tty,
320 CHANNEL_t * cp, unsigned int ChanStatus) 320 CHANNEL_t * cp, unsigned int ChanStatus)
321 { 321 {
322 unsigned int CharNStat; 322 unsigned int CharNStat;
323 int ToRecv, wRecv, space; 323 int ToRecv, wRecv, space;
324 unsigned char *cbuf; 324 unsigned char *cbuf;
325 325
326 ToRecv = sGetRxCnt(cp); 326 ToRecv = sGetRxCnt(cp);
327 #ifdef ROCKET_DEBUG_INTR 327 #ifdef ROCKET_DEBUG_INTR
328 printk(KERN_INFO "rp_do_receive(%d)...\n", ToRecv); 328 printk(KERN_INFO "rp_do_receive(%d)...\n", ToRecv);
329 #endif 329 #endif
330 if (ToRecv == 0) 330 if (ToRecv == 0)
331 return; 331 return;
332 332
333 /* 333 /*
334 * if status indicates there are errored characters in the 334 * if status indicates there are errored characters in the
335 * FIFO, then enter status mode (a word in FIFO holds 335 * FIFO, then enter status mode (a word in FIFO holds
336 * character and status). 336 * character and status).
337 */ 337 */
338 if (ChanStatus & (RXFOVERFL | RXBREAK | RXFRAME | RXPARITY)) { 338 if (ChanStatus & (RXFOVERFL | RXBREAK | RXFRAME | RXPARITY)) {
339 if (!(ChanStatus & STATMODE)) { 339 if (!(ChanStatus & STATMODE)) {
340 #ifdef ROCKET_DEBUG_RECEIVE 340 #ifdef ROCKET_DEBUG_RECEIVE
341 printk(KERN_INFO "Entering STATMODE...\n"); 341 printk(KERN_INFO "Entering STATMODE...\n");
342 #endif 342 #endif
343 ChanStatus |= STATMODE; 343 ChanStatus |= STATMODE;
344 sEnRxStatusMode(cp); 344 sEnRxStatusMode(cp);
345 } 345 }
346 } 346 }
347 347
348 /* 348 /*
349 * if we previously entered status mode, then read down the 349 * if we previously entered status mode, then read down the
350 * FIFO one word at a time, pulling apart the character and 350 * FIFO one word at a time, pulling apart the character and
351 * the status. Update error counters depending on status 351 * the status. Update error counters depending on status
352 */ 352 */
353 if (ChanStatus & STATMODE) { 353 if (ChanStatus & STATMODE) {
354 #ifdef ROCKET_DEBUG_RECEIVE 354 #ifdef ROCKET_DEBUG_RECEIVE
355 printk(KERN_INFO "Ignore %x, read %x...\n", 355 printk(KERN_INFO "Ignore %x, read %x...\n",
356 info->ignore_status_mask, info->read_status_mask); 356 info->ignore_status_mask, info->read_status_mask);
357 #endif 357 #endif
358 while (ToRecv) { 358 while (ToRecv) {
359 char flag; 359 char flag;
360 360
361 CharNStat = sInW(sGetTxRxDataIO(cp)); 361 CharNStat = sInW(sGetTxRxDataIO(cp));
362 #ifdef ROCKET_DEBUG_RECEIVE 362 #ifdef ROCKET_DEBUG_RECEIVE
363 printk(KERN_INFO "%x...\n", CharNStat); 363 printk(KERN_INFO "%x...\n", CharNStat);
364 #endif 364 #endif
365 if (CharNStat & STMBREAKH) 365 if (CharNStat & STMBREAKH)
366 CharNStat &= ~(STMFRAMEH | STMPARITYH); 366 CharNStat &= ~(STMFRAMEH | STMPARITYH);
367 if (CharNStat & info->ignore_status_mask) { 367 if (CharNStat & info->ignore_status_mask) {
368 ToRecv--; 368 ToRecv--;
369 continue; 369 continue;
370 } 370 }
371 CharNStat &= info->read_status_mask; 371 CharNStat &= info->read_status_mask;
372 if (CharNStat & STMBREAKH) 372 if (CharNStat & STMBREAKH)
373 flag = TTY_BREAK; 373 flag = TTY_BREAK;
374 else if (CharNStat & STMPARITYH) 374 else if (CharNStat & STMPARITYH)
375 flag = TTY_PARITY; 375 flag = TTY_PARITY;
376 else if (CharNStat & STMFRAMEH) 376 else if (CharNStat & STMFRAMEH)
377 flag = TTY_FRAME; 377 flag = TTY_FRAME;
378 else if (CharNStat & STMRCVROVRH) 378 else if (CharNStat & STMRCVROVRH)
379 flag = TTY_OVERRUN; 379 flag = TTY_OVERRUN;
380 else 380 else
381 flag = TTY_NORMAL; 381 flag = TTY_NORMAL;
382 tty_insert_flip_char(tty, CharNStat & 0xff, flag); 382 tty_insert_flip_char(tty, CharNStat & 0xff, flag);
383 ToRecv--; 383 ToRecv--;
384 } 384 }
385 385
386 /* 386 /*
387 * after we've emptied the FIFO in status mode, turn 387 * after we've emptied the FIFO in status mode, turn
388 * status mode back off 388 * status mode back off
389 */ 389 */
390 if (sGetRxCnt(cp) == 0) { 390 if (sGetRxCnt(cp) == 0) {
391 #ifdef ROCKET_DEBUG_RECEIVE 391 #ifdef ROCKET_DEBUG_RECEIVE
392 printk(KERN_INFO "Status mode off.\n"); 392 printk(KERN_INFO "Status mode off.\n");
393 #endif 393 #endif
394 sDisRxStatusMode(cp); 394 sDisRxStatusMode(cp);
395 } 395 }
396 } else { 396 } else {
397 /* 397 /*
398 * we aren't in status mode, so read down the FIFO two 398 * we aren't in status mode, so read down the FIFO two
399 * characters at time by doing repeated word IO 399 * characters at time by doing repeated word IO
400 * transfer. 400 * transfer.
401 */ 401 */
402 space = tty_prepare_flip_string(tty, &cbuf, ToRecv); 402 space = tty_prepare_flip_string(tty, &cbuf, ToRecv);
403 if (space < ToRecv) { 403 if (space < ToRecv) {
404 #ifdef ROCKET_DEBUG_RECEIVE 404 #ifdef ROCKET_DEBUG_RECEIVE
405 printk(KERN_INFO "rp_do_receive:insufficient space ToRecv=%d space=%d\n", ToRecv, space); 405 printk(KERN_INFO "rp_do_receive:insufficient space ToRecv=%d space=%d\n", ToRecv, space);
406 #endif 406 #endif
407 if (space <= 0) 407 if (space <= 0)
408 return; 408 return;
409 ToRecv = space; 409 ToRecv = space;
410 } 410 }
411 wRecv = ToRecv >> 1; 411 wRecv = ToRecv >> 1;
412 if (wRecv) 412 if (wRecv)
413 sInStrW(sGetTxRxDataIO(cp), (unsigned short *) cbuf, wRecv); 413 sInStrW(sGetTxRxDataIO(cp), (unsigned short *) cbuf, wRecv);
414 if (ToRecv & 1) 414 if (ToRecv & 1)
415 cbuf[ToRecv - 1] = sInB(sGetTxRxDataIO(cp)); 415 cbuf[ToRecv - 1] = sInB(sGetTxRxDataIO(cp));
416 } 416 }
417 /* Push the data up to the tty layer */ 417 /* Push the data up to the tty layer */
418 tty_flip_buffer_push(tty); 418 tty_flip_buffer_push(tty);
419 } 419 }
420 420
421 /* 421 /*
422 * Serial port transmit data function. Called from the timer polling loop as a 422 * Serial port transmit data function. Called from the timer polling loop as a
423 * result of a bit set in xmit_flags[], indicating data (from the tty layer) is ready 423 * result of a bit set in xmit_flags[], indicating data (from the tty layer) is ready
424 * to be sent out the serial port. Data is buffered in rp_table[line].xmit_buf, it is 424 * to be sent out the serial port. Data is buffered in rp_table[line].xmit_buf, it is
425 * moved to the port's xmit FIFO. *info is critical data, protected by spinlocks. 425 * moved to the port's xmit FIFO. *info is critical data, protected by spinlocks.
426 */ 426 */
427 static void rp_do_transmit(struct r_port *info) 427 static void rp_do_transmit(struct r_port *info)
428 { 428 {
429 int c; 429 int c;
430 CHANNEL_t *cp = &info->channel; 430 CHANNEL_t *cp = &info->channel;
431 struct tty_struct *tty; 431 struct tty_struct *tty;
432 unsigned long flags; 432 unsigned long flags;
433 433
434 #ifdef ROCKET_DEBUG_INTR 434 #ifdef ROCKET_DEBUG_INTR
435 printk(KERN_DEBUG "%s\n", __func__); 435 printk(KERN_DEBUG "%s\n", __func__);
436 #endif 436 #endif
437 if (!info) 437 if (!info)
438 return; 438 return;
439 if (!info->port.tty) { 439 if (!info->port.tty) {
440 printk(KERN_WARNING "rp: WARNING %s called with " 440 printk(KERN_WARNING "rp: WARNING %s called with "
441 "info->port.tty==NULL\n", __func__); 441 "info->port.tty==NULL\n", __func__);
442 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 442 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
443 return; 443 return;
444 } 444 }
445 445
446 spin_lock_irqsave(&info->slock, flags); 446 spin_lock_irqsave(&info->slock, flags);
447 tty = info->port.tty; 447 tty = info->port.tty;
448 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp); 448 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp);
449 449
450 /* Loop sending data to FIFO until done or FIFO full */ 450 /* Loop sending data to FIFO until done or FIFO full */
451 while (1) { 451 while (1) {
452 if (tty->stopped || tty->hw_stopped) 452 if (tty->stopped || tty->hw_stopped)
453 break; 453 break;
454 c = min(info->xmit_fifo_room, info->xmit_cnt); 454 c = min(info->xmit_fifo_room, info->xmit_cnt);
455 c = min(c, XMIT_BUF_SIZE - info->xmit_tail); 455 c = min(c, XMIT_BUF_SIZE - info->xmit_tail);
456 if (c <= 0 || info->xmit_fifo_room <= 0) 456 if (c <= 0 || info->xmit_fifo_room <= 0)
457 break; 457 break;
458 sOutStrW(sGetTxRxDataIO(cp), (unsigned short *) (info->xmit_buf + info->xmit_tail), c / 2); 458 sOutStrW(sGetTxRxDataIO(cp), (unsigned short *) (info->xmit_buf + info->xmit_tail), c / 2);
459 if (c & 1) 459 if (c & 1)
460 sOutB(sGetTxRxDataIO(cp), info->xmit_buf[info->xmit_tail + c - 1]); 460 sOutB(sGetTxRxDataIO(cp), info->xmit_buf[info->xmit_tail + c - 1]);
461 info->xmit_tail += c; 461 info->xmit_tail += c;
462 info->xmit_tail &= XMIT_BUF_SIZE - 1; 462 info->xmit_tail &= XMIT_BUF_SIZE - 1;
463 info->xmit_cnt -= c; 463 info->xmit_cnt -= c;
464 info->xmit_fifo_room -= c; 464 info->xmit_fifo_room -= c;
465 #ifdef ROCKET_DEBUG_INTR 465 #ifdef ROCKET_DEBUG_INTR
466 printk(KERN_INFO "tx %d chars...\n", c); 466 printk(KERN_INFO "tx %d chars...\n", c);
467 #endif 467 #endif
468 } 468 }
469 469
470 if (info->xmit_cnt == 0) 470 if (info->xmit_cnt == 0)
471 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 471 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
472 472
473 if (info->xmit_cnt < WAKEUP_CHARS) { 473 if (info->xmit_cnt < WAKEUP_CHARS) {
474 tty_wakeup(tty); 474 tty_wakeup(tty);
475 #ifdef ROCKETPORT_HAVE_POLL_WAIT 475 #ifdef ROCKETPORT_HAVE_POLL_WAIT
476 wake_up_interruptible(&tty->poll_wait); 476 wake_up_interruptible(&tty->poll_wait);
477 #endif 477 #endif
478 } 478 }
479 479
480 spin_unlock_irqrestore(&info->slock, flags); 480 spin_unlock_irqrestore(&info->slock, flags);
481 481
482 #ifdef ROCKET_DEBUG_INTR 482 #ifdef ROCKET_DEBUG_INTR
483 printk(KERN_DEBUG "(%d,%d,%d,%d)...\n", info->xmit_cnt, info->xmit_head, 483 printk(KERN_DEBUG "(%d,%d,%d,%d)...\n", info->xmit_cnt, info->xmit_head,
484 info->xmit_tail, info->xmit_fifo_room); 484 info->xmit_tail, info->xmit_fifo_room);
485 #endif 485 #endif
486 } 486 }
487 487
488 /* 488 /*
489 * Called when a serial port signals it has read data in it's RX FIFO. 489 * Called when a serial port signals it has read data in it's RX FIFO.
490 * It checks what interrupts are pending and services them, including 490 * It checks what interrupts are pending and services them, including
491 * receiving serial data. 491 * receiving serial data.
492 */ 492 */
493 static void rp_handle_port(struct r_port *info) 493 static void rp_handle_port(struct r_port *info)
494 { 494 {
495 CHANNEL_t *cp; 495 CHANNEL_t *cp;
496 struct tty_struct *tty; 496 struct tty_struct *tty;
497 unsigned int IntMask, ChanStatus; 497 unsigned int IntMask, ChanStatus;
498 498
499 if (!info) 499 if (!info)
500 return; 500 return;
501 501
502 if ((info->flags & ASYNC_INITIALIZED) == 0) { 502 if ((info->port.flags & ASYNC_INITIALIZED) == 0) {
503 printk(KERN_WARNING "rp: WARNING: rp_handle_port called with " 503 printk(KERN_WARNING "rp: WARNING: rp_handle_port called with "
504 "info->flags & NOT_INIT\n"); 504 "info->flags & NOT_INIT\n");
505 return; 505 return;
506 } 506 }
507 if (!info->port.tty) { 507 if (!info->port.tty) {
508 printk(KERN_WARNING "rp: WARNING: rp_handle_port called with " 508 printk(KERN_WARNING "rp: WARNING: rp_handle_port called with "
509 "info->port.tty==NULL\n"); 509 "info->port.tty==NULL\n");
510 return; 510 return;
511 } 511 }
512 cp = &info->channel; 512 cp = &info->channel;
513 tty = info->port.tty; 513 tty = info->port.tty;
514 514
515 IntMask = sGetChanIntID(cp) & info->intmask; 515 IntMask = sGetChanIntID(cp) & info->intmask;
516 #ifdef ROCKET_DEBUG_INTR 516 #ifdef ROCKET_DEBUG_INTR
517 printk(KERN_INFO "rp_interrupt %02x...\n", IntMask); 517 printk(KERN_INFO "rp_interrupt %02x...\n", IntMask);
518 #endif 518 #endif
519 ChanStatus = sGetChanStatus(cp); 519 ChanStatus = sGetChanStatus(cp);
520 if (IntMask & RXF_TRIG) { /* Rx FIFO trigger level */ 520 if (IntMask & RXF_TRIG) { /* Rx FIFO trigger level */
521 rp_do_receive(info, tty, cp, ChanStatus); 521 rp_do_receive(info, tty, cp, ChanStatus);
522 } 522 }
523 if (IntMask & DELTA_CD) { /* CD change */ 523 if (IntMask & DELTA_CD) { /* CD change */
524 #if (defined(ROCKET_DEBUG_OPEN) || defined(ROCKET_DEBUG_INTR) || defined(ROCKET_DEBUG_HANGUP)) 524 #if (defined(ROCKET_DEBUG_OPEN) || defined(ROCKET_DEBUG_INTR) || defined(ROCKET_DEBUG_HANGUP))
525 printk(KERN_INFO "ttyR%d CD now %s...\n", info->line, 525 printk(KERN_INFO "ttyR%d CD now %s...\n", info->line,
526 (ChanStatus & CD_ACT) ? "on" : "off"); 526 (ChanStatus & CD_ACT) ? "on" : "off");
527 #endif 527 #endif
528 if (!(ChanStatus & CD_ACT) && info->cd_status) { 528 if (!(ChanStatus & CD_ACT) && info->cd_status) {
529 #ifdef ROCKET_DEBUG_HANGUP 529 #ifdef ROCKET_DEBUG_HANGUP
530 printk(KERN_INFO "CD drop, calling hangup.\n"); 530 printk(KERN_INFO "CD drop, calling hangup.\n");
531 #endif 531 #endif
532 tty_hangup(tty); 532 tty_hangup(tty);
533 } 533 }
534 info->cd_status = (ChanStatus & CD_ACT) ? 1 : 0; 534 info->cd_status = (ChanStatus & CD_ACT) ? 1 : 0;
535 wake_up_interruptible(&info->port.open_wait); 535 wake_up_interruptible(&info->port.open_wait);
536 } 536 }
537 #ifdef ROCKET_DEBUG_INTR 537 #ifdef ROCKET_DEBUG_INTR
538 if (IntMask & DELTA_CTS) { /* CTS change */ 538 if (IntMask & DELTA_CTS) { /* CTS change */
539 printk(KERN_INFO "CTS change...\n"); 539 printk(KERN_INFO "CTS change...\n");
540 } 540 }
541 if (IntMask & DELTA_DSR) { /* DSR change */ 541 if (IntMask & DELTA_DSR) { /* DSR change */
542 printk(KERN_INFO "DSR change...\n"); 542 printk(KERN_INFO "DSR change...\n");
543 } 543 }
544 #endif 544 #endif
545 } 545 }
546 546
547 /* 547 /*
548 * The top level polling routine. Repeats every 1/100 HZ (10ms). 548 * The top level polling routine. Repeats every 1/100 HZ (10ms).
549 */ 549 */
550 static void rp_do_poll(unsigned long dummy) 550 static void rp_do_poll(unsigned long dummy)
551 { 551 {
552 CONTROLLER_t *ctlp; 552 CONTROLLER_t *ctlp;
553 int ctrl, aiop, ch, line; 553 int ctrl, aiop, ch, line;
554 unsigned int xmitmask, i; 554 unsigned int xmitmask, i;
555 unsigned int CtlMask; 555 unsigned int CtlMask;
556 unsigned char AiopMask; 556 unsigned char AiopMask;
557 Word_t bit; 557 Word_t bit;
558 558
559 /* Walk through all the boards (ctrl's) */ 559 /* Walk through all the boards (ctrl's) */
560 for (ctrl = 0; ctrl < max_board; ctrl++) { 560 for (ctrl = 0; ctrl < max_board; ctrl++) {
561 if (rcktpt_io_addr[ctrl] <= 0) 561 if (rcktpt_io_addr[ctrl] <= 0)
562 continue; 562 continue;
563 563
564 /* Get a ptr to the board's control struct */ 564 /* Get a ptr to the board's control struct */
565 ctlp = sCtlNumToCtlPtr(ctrl); 565 ctlp = sCtlNumToCtlPtr(ctrl);
566 566
567 /* Get the interrupt status from the board */ 567 /* Get the interrupt status from the board */
568 #ifdef CONFIG_PCI 568 #ifdef CONFIG_PCI
569 if (ctlp->BusType == isPCI) 569 if (ctlp->BusType == isPCI)
570 CtlMask = sPCIGetControllerIntStatus(ctlp); 570 CtlMask = sPCIGetControllerIntStatus(ctlp);
571 else 571 else
572 #endif 572 #endif
573 CtlMask = sGetControllerIntStatus(ctlp); 573 CtlMask = sGetControllerIntStatus(ctlp);
574 574
575 /* Check if any AIOP read bits are set */ 575 /* Check if any AIOP read bits are set */
576 for (aiop = 0; CtlMask; aiop++) { 576 for (aiop = 0; CtlMask; aiop++) {
577 bit = ctlp->AiopIntrBits[aiop]; 577 bit = ctlp->AiopIntrBits[aiop];
578 if (CtlMask & bit) { 578 if (CtlMask & bit) {
579 CtlMask &= ~bit; 579 CtlMask &= ~bit;
580 AiopMask = sGetAiopIntStatus(ctlp, aiop); 580 AiopMask = sGetAiopIntStatus(ctlp, aiop);
581 581
582 /* Check if any port read bits are set */ 582 /* Check if any port read bits are set */
583 for (ch = 0; AiopMask; AiopMask >>= 1, ch++) { 583 for (ch = 0; AiopMask; AiopMask >>= 1, ch++) {
584 if (AiopMask & 1) { 584 if (AiopMask & 1) {
585 585
586 /* Get the line number (/dev/ttyRx number). */ 586 /* Get the line number (/dev/ttyRx number). */
587 /* Read the data from the port. */ 587 /* Read the data from the port. */
588 line = GetLineNumber(ctrl, aiop, ch); 588 line = GetLineNumber(ctrl, aiop, ch);
589 rp_handle_port(rp_table[line]); 589 rp_handle_port(rp_table[line]);
590 } 590 }
591 } 591 }
592 } 592 }
593 } 593 }
594 594
595 xmitmask = xmit_flags[ctrl]; 595 xmitmask = xmit_flags[ctrl];
596 596
597 /* 597 /*
598 * xmit_flags contains bit-significant flags, indicating there is data 598 * xmit_flags contains bit-significant flags, indicating there is data
599 * to xmit on the port. Bit 0 is port 0 on this board, bit 1 is port 599 * to xmit on the port. Bit 0 is port 0 on this board, bit 1 is port
600 * 1, ... (32 total possible). The variable i has the aiop and ch 600 * 1, ... (32 total possible). The variable i has the aiop and ch
601 * numbers encoded in it (port 0-7 are aiop0, 8-15 are aiop1, etc). 601 * numbers encoded in it (port 0-7 are aiop0, 8-15 are aiop1, etc).
602 */ 602 */
603 if (xmitmask) { 603 if (xmitmask) {
604 for (i = 0; i < rocketModel[ctrl].numPorts; i++) { 604 for (i = 0; i < rocketModel[ctrl].numPorts; i++) {
605 if (xmitmask & (1 << i)) { 605 if (xmitmask & (1 << i)) {
606 aiop = (i & 0x18) >> 3; 606 aiop = (i & 0x18) >> 3;
607 ch = i & 0x07; 607 ch = i & 0x07;
608 line = GetLineNumber(ctrl, aiop, ch); 608 line = GetLineNumber(ctrl, aiop, ch);
609 rp_do_transmit(rp_table[line]); 609 rp_do_transmit(rp_table[line]);
610 } 610 }
611 } 611 }
612 } 612 }
613 } 613 }
614 614
615 /* 615 /*
616 * Reset the timer so we get called at the next clock tick (10ms). 616 * Reset the timer so we get called at the next clock tick (10ms).
617 */ 617 */
618 if (atomic_read(&rp_num_ports_open)) 618 if (atomic_read(&rp_num_ports_open))
619 mod_timer(&rocket_timer, jiffies + POLL_PERIOD); 619 mod_timer(&rocket_timer, jiffies + POLL_PERIOD);
620 } 620 }
621 621
622 /* 622 /*
623 * Initializes the r_port structure for a port, as well as enabling the port on 623 * Initializes the r_port structure for a port, as well as enabling the port on
624 * the board. 624 * the board.
625 * Inputs: board, aiop, chan numbers 625 * Inputs: board, aiop, chan numbers
626 */ 626 */
627 static void init_r_port(int board, int aiop, int chan, struct pci_dev *pci_dev) 627 static void init_r_port(int board, int aiop, int chan, struct pci_dev *pci_dev)
628 { 628 {
629 unsigned rocketMode; 629 unsigned rocketMode;
630 struct r_port *info; 630 struct r_port *info;
631 int line; 631 int line;
632 CONTROLLER_T *ctlp; 632 CONTROLLER_T *ctlp;
633 633
634 /* Get the next available line number */ 634 /* Get the next available line number */
635 line = SetLineNumber(board, aiop, chan); 635 line = SetLineNumber(board, aiop, chan);
636 636
637 ctlp = sCtlNumToCtlPtr(board); 637 ctlp = sCtlNumToCtlPtr(board);
638 638
639 /* Get a r_port struct for the port, fill it in and save it globally, indexed by line number */ 639 /* Get a r_port struct for the port, fill it in and save it globally, indexed by line number */
640 info = kzalloc(sizeof (struct r_port), GFP_KERNEL); 640 info = kzalloc(sizeof (struct r_port), GFP_KERNEL);
641 if (!info) { 641 if (!info) {
642 printk(KERN_ERR "Couldn't allocate info struct for line #%d\n", 642 printk(KERN_ERR "Couldn't allocate info struct for line #%d\n",
643 line); 643 line);
644 return; 644 return;
645 } 645 }
646 646
647 info->magic = RPORT_MAGIC; 647 info->magic = RPORT_MAGIC;
648 info->line = line; 648 info->line = line;
649 info->ctlp = ctlp; 649 info->ctlp = ctlp;
650 info->board = board; 650 info->board = board;
651 info->aiop = aiop; 651 info->aiop = aiop;
652 info->chan = chan; 652 info->chan = chan;
653 tty_port_init(&info->port); 653 tty_port_init(&info->port);
654 info->port.ops = &rocket_port_ops; 654 info->port.ops = &rocket_port_ops;
655 init_completion(&info->close_wait); 655 init_completion(&info->close_wait);
656 info->flags &= ~ROCKET_MODE_MASK; 656 info->flags &= ~ROCKET_MODE_MASK;
657 switch (pc104[board][line]) { 657 switch (pc104[board][line]) {
658 case 422: 658 case 422:
659 info->flags |= ROCKET_MODE_RS422; 659 info->flags |= ROCKET_MODE_RS422;
660 break; 660 break;
661 case 485: 661 case 485:
662 info->flags |= ROCKET_MODE_RS485; 662 info->flags |= ROCKET_MODE_RS485;
663 break; 663 break;
664 case 232: 664 case 232:
665 default: 665 default:
666 info->flags |= ROCKET_MODE_RS232; 666 info->flags |= ROCKET_MODE_RS232;
667 break; 667 break;
668 } 668 }
669 669
670 info->intmask = RXF_TRIG | TXFIFO_MT | SRC_INT | DELTA_CD | DELTA_CTS | DELTA_DSR; 670 info->intmask = RXF_TRIG | TXFIFO_MT | SRC_INT | DELTA_CD | DELTA_CTS | DELTA_DSR;
671 if (sInitChan(ctlp, &info->channel, aiop, chan) == 0) { 671 if (sInitChan(ctlp, &info->channel, aiop, chan) == 0) {
672 printk(KERN_ERR "RocketPort sInitChan(%d, %d, %d) failed!\n", 672 printk(KERN_ERR "RocketPort sInitChan(%d, %d, %d) failed!\n",
673 board, aiop, chan); 673 board, aiop, chan);
674 kfree(info); 674 kfree(info);
675 return; 675 return;
676 } 676 }
677 677
678 rocketMode = info->flags & ROCKET_MODE_MASK; 678 rocketMode = info->flags & ROCKET_MODE_MASK;
679 679
680 if ((info->flags & ROCKET_RTS_TOGGLE) || (rocketMode == ROCKET_MODE_RS485)) 680 if ((info->flags & ROCKET_RTS_TOGGLE) || (rocketMode == ROCKET_MODE_RS485))
681 sEnRTSToggle(&info->channel); 681 sEnRTSToggle(&info->channel);
682 else 682 else
683 sDisRTSToggle(&info->channel); 683 sDisRTSToggle(&info->channel);
684 684
685 if (ctlp->boardType == ROCKET_TYPE_PC104) { 685 if (ctlp->boardType == ROCKET_TYPE_PC104) {
686 switch (rocketMode) { 686 switch (rocketMode) {
687 case ROCKET_MODE_RS485: 687 case ROCKET_MODE_RS485:
688 sSetInterfaceMode(&info->channel, InterfaceModeRS485); 688 sSetInterfaceMode(&info->channel, InterfaceModeRS485);
689 break; 689 break;
690 case ROCKET_MODE_RS422: 690 case ROCKET_MODE_RS422:
691 sSetInterfaceMode(&info->channel, InterfaceModeRS422); 691 sSetInterfaceMode(&info->channel, InterfaceModeRS422);
692 break; 692 break;
693 case ROCKET_MODE_RS232: 693 case ROCKET_MODE_RS232:
694 default: 694 default:
695 if (info->flags & ROCKET_RTS_TOGGLE) 695 if (info->flags & ROCKET_RTS_TOGGLE)
696 sSetInterfaceMode(&info->channel, InterfaceModeRS232T); 696 sSetInterfaceMode(&info->channel, InterfaceModeRS232T);
697 else 697 else
698 sSetInterfaceMode(&info->channel, InterfaceModeRS232); 698 sSetInterfaceMode(&info->channel, InterfaceModeRS232);
699 break; 699 break;
700 } 700 }
701 } 701 }
702 spin_lock_init(&info->slock); 702 spin_lock_init(&info->slock);
703 mutex_init(&info->write_mtx); 703 mutex_init(&info->write_mtx);
704 rp_table[line] = info; 704 rp_table[line] = info;
705 tty_register_device(rocket_driver, line, pci_dev ? &pci_dev->dev : 705 tty_register_device(rocket_driver, line, pci_dev ? &pci_dev->dev :
706 NULL); 706 NULL);
707 } 707 }
708 708
709 /* 709 /*
710 * Configures a rocketport port according to its termio settings. Called from 710 * Configures a rocketport port according to its termio settings. Called from
711 * user mode into the driver (exception handler). *info CD manipulation is spinlock protected. 711 * user mode into the driver (exception handler). *info CD manipulation is spinlock protected.
712 */ 712 */
713 static void configure_r_port(struct r_port *info, 713 static void configure_r_port(struct r_port *info,
714 struct ktermios *old_termios) 714 struct ktermios *old_termios)
715 { 715 {
716 unsigned cflag; 716 unsigned cflag;
717 unsigned long flags; 717 unsigned long flags;
718 unsigned rocketMode; 718 unsigned rocketMode;
719 int bits, baud, divisor; 719 int bits, baud, divisor;
720 CHANNEL_t *cp; 720 CHANNEL_t *cp;
721 struct ktermios *t = info->port.tty->termios; 721 struct ktermios *t = info->port.tty->termios;
722 722
723 cp = &info->channel; 723 cp = &info->channel;
724 cflag = t->c_cflag; 724 cflag = t->c_cflag;
725 725
726 /* Byte size and parity */ 726 /* Byte size and parity */
727 if ((cflag & CSIZE) == CS8) { 727 if ((cflag & CSIZE) == CS8) {
728 sSetData8(cp); 728 sSetData8(cp);
729 bits = 10; 729 bits = 10;
730 } else { 730 } else {
731 sSetData7(cp); 731 sSetData7(cp);
732 bits = 9; 732 bits = 9;
733 } 733 }
734 if (cflag & CSTOPB) { 734 if (cflag & CSTOPB) {
735 sSetStop2(cp); 735 sSetStop2(cp);
736 bits++; 736 bits++;
737 } else { 737 } else {
738 sSetStop1(cp); 738 sSetStop1(cp);
739 } 739 }
740 740
741 if (cflag & PARENB) { 741 if (cflag & PARENB) {
742 sEnParity(cp); 742 sEnParity(cp);
743 bits++; 743 bits++;
744 if (cflag & PARODD) { 744 if (cflag & PARODD) {
745 sSetOddParity(cp); 745 sSetOddParity(cp);
746 } else { 746 } else {
747 sSetEvenParity(cp); 747 sSetEvenParity(cp);
748 } 748 }
749 } else { 749 } else {
750 sDisParity(cp); 750 sDisParity(cp);
751 } 751 }
752 752
753 /* baud rate */ 753 /* baud rate */
754 baud = tty_get_baud_rate(info->port.tty); 754 baud = tty_get_baud_rate(info->port.tty);
755 if (!baud) 755 if (!baud)
756 baud = 9600; 756 baud = 9600;
757 divisor = ((rp_baud_base[info->board] + (baud >> 1)) / baud) - 1; 757 divisor = ((rp_baud_base[info->board] + (baud >> 1)) / baud) - 1;
758 if ((divisor >= 8192 || divisor < 0) && old_termios) { 758 if ((divisor >= 8192 || divisor < 0) && old_termios) {
759 baud = tty_termios_baud_rate(old_termios); 759 baud = tty_termios_baud_rate(old_termios);
760 if (!baud) 760 if (!baud)
761 baud = 9600; 761 baud = 9600;
762 divisor = (rp_baud_base[info->board] / baud) - 1; 762 divisor = (rp_baud_base[info->board] / baud) - 1;
763 } 763 }
764 if (divisor >= 8192 || divisor < 0) { 764 if (divisor >= 8192 || divisor < 0) {
765 baud = 9600; 765 baud = 9600;
766 divisor = (rp_baud_base[info->board] / baud) - 1; 766 divisor = (rp_baud_base[info->board] / baud) - 1;
767 } 767 }
768 info->cps = baud / bits; 768 info->cps = baud / bits;
769 sSetBaud(cp, divisor); 769 sSetBaud(cp, divisor);
770 770
771 /* FIXME: Should really back compute a baud rate from the divisor */ 771 /* FIXME: Should really back compute a baud rate from the divisor */
772 tty_encode_baud_rate(info->port.tty, baud, baud); 772 tty_encode_baud_rate(info->port.tty, baud, baud);
773 773
774 if (cflag & CRTSCTS) { 774 if (cflag & CRTSCTS) {
775 info->intmask |= DELTA_CTS; 775 info->intmask |= DELTA_CTS;
776 sEnCTSFlowCtl(cp); 776 sEnCTSFlowCtl(cp);
777 } else { 777 } else {
778 info->intmask &= ~DELTA_CTS; 778 info->intmask &= ~DELTA_CTS;
779 sDisCTSFlowCtl(cp); 779 sDisCTSFlowCtl(cp);
780 } 780 }
781 if (cflag & CLOCAL) { 781 if (cflag & CLOCAL) {
782 info->intmask &= ~DELTA_CD; 782 info->intmask &= ~DELTA_CD;
783 } else { 783 } else {
784 spin_lock_irqsave(&info->slock, flags); 784 spin_lock_irqsave(&info->slock, flags);
785 if (sGetChanStatus(cp) & CD_ACT) 785 if (sGetChanStatus(cp) & CD_ACT)
786 info->cd_status = 1; 786 info->cd_status = 1;
787 else 787 else
788 info->cd_status = 0; 788 info->cd_status = 0;
789 info->intmask |= DELTA_CD; 789 info->intmask |= DELTA_CD;
790 spin_unlock_irqrestore(&info->slock, flags); 790 spin_unlock_irqrestore(&info->slock, flags);
791 } 791 }
792 792
793 /* 793 /*
794 * Handle software flow control in the board 794 * Handle software flow control in the board
795 */ 795 */
796 #ifdef ROCKET_SOFT_FLOW 796 #ifdef ROCKET_SOFT_FLOW
797 if (I_IXON(info->port.tty)) { 797 if (I_IXON(info->port.tty)) {
798 sEnTxSoftFlowCtl(cp); 798 sEnTxSoftFlowCtl(cp);
799 if (I_IXANY(info->port.tty)) { 799 if (I_IXANY(info->port.tty)) {
800 sEnIXANY(cp); 800 sEnIXANY(cp);
801 } else { 801 } else {
802 sDisIXANY(cp); 802 sDisIXANY(cp);
803 } 803 }
804 sSetTxXONChar(cp, START_CHAR(info->port.tty)); 804 sSetTxXONChar(cp, START_CHAR(info->port.tty));
805 sSetTxXOFFChar(cp, STOP_CHAR(info->port.tty)); 805 sSetTxXOFFChar(cp, STOP_CHAR(info->port.tty));
806 } else { 806 } else {
807 sDisTxSoftFlowCtl(cp); 807 sDisTxSoftFlowCtl(cp);
808 sDisIXANY(cp); 808 sDisIXANY(cp);
809 sClrTxXOFF(cp); 809 sClrTxXOFF(cp);
810 } 810 }
811 #endif 811 #endif
812 812
813 /* 813 /*
814 * Set up ignore/read mask words 814 * Set up ignore/read mask words
815 */ 815 */
816 info->read_status_mask = STMRCVROVRH | 0xFF; 816 info->read_status_mask = STMRCVROVRH | 0xFF;
817 if (I_INPCK(info->port.tty)) 817 if (I_INPCK(info->port.tty))
818 info->read_status_mask |= STMFRAMEH | STMPARITYH; 818 info->read_status_mask |= STMFRAMEH | STMPARITYH;
819 if (I_BRKINT(info->port.tty) || I_PARMRK(info->port.tty)) 819 if (I_BRKINT(info->port.tty) || I_PARMRK(info->port.tty))
820 info->read_status_mask |= STMBREAKH; 820 info->read_status_mask |= STMBREAKH;
821 821
822 /* 822 /*
823 * Characters to ignore 823 * Characters to ignore
824 */ 824 */
825 info->ignore_status_mask = 0; 825 info->ignore_status_mask = 0;
826 if (I_IGNPAR(info->port.tty)) 826 if (I_IGNPAR(info->port.tty))
827 info->ignore_status_mask |= STMFRAMEH | STMPARITYH; 827 info->ignore_status_mask |= STMFRAMEH | STMPARITYH;
828 if (I_IGNBRK(info->port.tty)) { 828 if (I_IGNBRK(info->port.tty)) {
829 info->ignore_status_mask |= STMBREAKH; 829 info->ignore_status_mask |= STMBREAKH;
830 /* 830 /*
831 * If we're ignoring parity and break indicators, 831 * If we're ignoring parity and break indicators,
832 * ignore overruns too. (For real raw support). 832 * ignore overruns too. (For real raw support).
833 */ 833 */
834 if (I_IGNPAR(info->port.tty)) 834 if (I_IGNPAR(info->port.tty))
835 info->ignore_status_mask |= STMRCVROVRH; 835 info->ignore_status_mask |= STMRCVROVRH;
836 } 836 }
837 837
838 rocketMode = info->flags & ROCKET_MODE_MASK; 838 rocketMode = info->flags & ROCKET_MODE_MASK;
839 839
840 if ((info->flags & ROCKET_RTS_TOGGLE) 840 if ((info->flags & ROCKET_RTS_TOGGLE)
841 || (rocketMode == ROCKET_MODE_RS485)) 841 || (rocketMode == ROCKET_MODE_RS485))
842 sEnRTSToggle(cp); 842 sEnRTSToggle(cp);
843 else 843 else
844 sDisRTSToggle(cp); 844 sDisRTSToggle(cp);
845 845
846 sSetRTS(&info->channel); 846 sSetRTS(&info->channel);
847 847
848 if (cp->CtlP->boardType == ROCKET_TYPE_PC104) { 848 if (cp->CtlP->boardType == ROCKET_TYPE_PC104) {
849 switch (rocketMode) { 849 switch (rocketMode) {
850 case ROCKET_MODE_RS485: 850 case ROCKET_MODE_RS485:
851 sSetInterfaceMode(cp, InterfaceModeRS485); 851 sSetInterfaceMode(cp, InterfaceModeRS485);
852 break; 852 break;
853 case ROCKET_MODE_RS422: 853 case ROCKET_MODE_RS422:
854 sSetInterfaceMode(cp, InterfaceModeRS422); 854 sSetInterfaceMode(cp, InterfaceModeRS422);
855 break; 855 break;
856 case ROCKET_MODE_RS232: 856 case ROCKET_MODE_RS232:
857 default: 857 default:
858 if (info->flags & ROCKET_RTS_TOGGLE) 858 if (info->flags & ROCKET_RTS_TOGGLE)
859 sSetInterfaceMode(cp, InterfaceModeRS232T); 859 sSetInterfaceMode(cp, InterfaceModeRS232T);
860 else 860 else
861 sSetInterfaceMode(cp, InterfaceModeRS232); 861 sSetInterfaceMode(cp, InterfaceModeRS232);
862 break; 862 break;
863 } 863 }
864 } 864 }
865 } 865 }
866 866
867 static int carrier_raised(struct tty_port *port) 867 static int carrier_raised(struct tty_port *port)
868 { 868 {
869 struct r_port *info = container_of(port, struct r_port, port); 869 struct r_port *info = container_of(port, struct r_port, port);
870 return (sGetChanStatusLo(&info->channel) & CD_ACT) ? 1 : 0; 870 return (sGetChanStatusLo(&info->channel) & CD_ACT) ? 1 : 0;
871 } 871 }
872 872
873 static void raise_dtr_rts(struct tty_port *port) 873 static void raise_dtr_rts(struct tty_port *port)
874 { 874 {
875 struct r_port *info = container_of(port, struct r_port, port); 875 struct r_port *info = container_of(port, struct r_port, port);
876 sSetDTR(&info->channel); 876 sSetDTR(&info->channel);
877 sSetRTS(&info->channel); 877 sSetRTS(&info->channel);
878 } 878 }
879 879
880 /* info->port.count is considered critical, protected by spinlocks. */ 880 /* info->port.count is considered critical, protected by spinlocks. */
881 static int block_til_ready(struct tty_struct *tty, struct file *filp, 881 static int block_til_ready(struct tty_struct *tty, struct file *filp,
882 struct r_port *info) 882 struct r_port *info)
883 { 883 {
884 DECLARE_WAITQUEUE(wait, current); 884 DECLARE_WAITQUEUE(wait, current);
885 struct tty_port *port = &info->port; 885 struct tty_port *port = &info->port;
886 int retval; 886 int retval;
887 int do_clocal = 0, extra_count = 0; 887 int do_clocal = 0, extra_count = 0;
888 unsigned long flags; 888 unsigned long flags;
889 889
890 /* 890 /*
891 * If the device is in the middle of being closed, then block 891 * If the device is in the middle of being closed, then block
892 * until it's done, and then try again. 892 * until it's done, and then try again.
893 */ 893 */
894 if (tty_hung_up_p(filp)) 894 if (tty_hung_up_p(filp))
895 return ((info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS); 895 return ((info->port.flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS);
896 if (info->flags & ASYNC_CLOSING) { 896 if (info->flags & ASYNC_CLOSING) {
897 if (wait_for_completion_interruptible(&info->close_wait)) 897 if (wait_for_completion_interruptible(&info->close_wait))
898 return -ERESTARTSYS; 898 return -ERESTARTSYS;
899 return ((info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS); 899 return ((info->port.flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS);
900 } 900 }
901 901
902 /* 902 /*
903 * If non-blocking mode is set, or the port is not enabled, 903 * If non-blocking mode is set, or the port is not enabled,
904 * then make the check up front and then exit. 904 * then make the check up front and then exit.
905 */ 905 */
906 if ((filp->f_flags & O_NONBLOCK) || (tty->flags & (1 << TTY_IO_ERROR))) { 906 if ((filp->f_flags & O_NONBLOCK) || (tty->flags & (1 << TTY_IO_ERROR))) {
907 info->flags |= ASYNC_NORMAL_ACTIVE; 907 info->port.flags |= ASYNC_NORMAL_ACTIVE;
908 return 0; 908 return 0;
909 } 909 }
910 if (tty->termios->c_cflag & CLOCAL) 910 if (tty->termios->c_cflag & CLOCAL)
911 do_clocal = 1; 911 do_clocal = 1;
912 912
913 /* 913 /*
914 * Block waiting for the carrier detect and the line to become free. While we are in 914 * Block waiting for the carrier detect and the line to become free. While we are in
915 * this loop, port->count is dropped by one, so that rp_close() knows when to free things. 915 * this loop, port->count is dropped by one, so that rp_close() knows when to free things.
916 * We restore it upon exit, either normal or abnormal. 916 * We restore it upon exit, either normal or abnormal.
917 */ 917 */
918 retval = 0; 918 retval = 0;
919 add_wait_queue(&port->open_wait, &wait); 919 add_wait_queue(&port->open_wait, &wait);
920 #ifdef ROCKET_DEBUG_OPEN 920 #ifdef ROCKET_DEBUG_OPEN
921 printk(KERN_INFO "block_til_ready before block: ttyR%d, count = %d\n", info->line, port->count); 921 printk(KERN_INFO "block_til_ready before block: ttyR%d, count = %d\n", info->line, port->count);
922 #endif 922 #endif
923 spin_lock_irqsave(&port->lock, flags); 923 spin_lock_irqsave(&port->lock, flags);
924 924
925 #ifdef ROCKET_DISABLE_SIMUSAGE 925 #ifdef ROCKET_DISABLE_SIMUSAGE
926 info->flags |= ASYNC_NORMAL_ACTIVE; 926 info->port.flags |= ASYNC_NORMAL_ACTIVE;
927 #else 927 #else
928 if (!tty_hung_up_p(filp)) { 928 if (!tty_hung_up_p(filp)) {
929 extra_count = 1; 929 extra_count = 1;
930 port->count--; 930 port->count--;
931 } 931 }
932 #endif 932 #endif
933 port->blocked_open++; 933 port->blocked_open++;
934 934
935 spin_unlock_irqrestore(&port->lock, flags); 935 spin_unlock_irqrestore(&port->lock, flags);
936 936
937 while (1) { 937 while (1) {
938 if (tty->termios->c_cflag & CBAUD) 938 if (tty->termios->c_cflag & CBAUD)
939 tty_port_raise_dtr_rts(port); 939 tty_port_raise_dtr_rts(port);
940 set_current_state(TASK_INTERRUPTIBLE); 940 set_current_state(TASK_INTERRUPTIBLE);
941 if (tty_hung_up_p(filp) || !(info->flags & ASYNC_INITIALIZED)) { 941 if (tty_hung_up_p(filp) || !(info->port.flags & ASYNC_INITIALIZED)) {
942 if (info->flags & ASYNC_HUP_NOTIFY) 942 if (info->port.flags & ASYNC_HUP_NOTIFY)
943 retval = -EAGAIN; 943 retval = -EAGAIN;
944 else 944 else
945 retval = -ERESTARTSYS; 945 retval = -ERESTARTSYS;
946 break; 946 break;
947 } 947 }
948 if (!(info->flags & ASYNC_CLOSING) && 948 if (!(info->port.flags & ASYNC_CLOSING) &&
949 (do_clocal || tty_port_carrier_raised(port))) 949 (do_clocal || tty_port_carrier_raised(port)))
950 break; 950 break;
951 if (signal_pending(current)) { 951 if (signal_pending(current)) {
952 retval = -ERESTARTSYS; 952 retval = -ERESTARTSYS;
953 break; 953 break;
954 } 954 }
955 #ifdef ROCKET_DEBUG_OPEN 955 #ifdef ROCKET_DEBUG_OPEN
956 printk(KERN_INFO "block_til_ready blocking: ttyR%d, count = %d, flags=0x%0x\n", 956 printk(KERN_INFO "block_til_ready blocking: ttyR%d, count = %d, flags=0x%0x\n",
957 info->line, port->count, info->flags); 957 info->line, port->count, info->port.flags);
958 #endif 958 #endif
959 schedule(); /* Don't hold spinlock here, will hang PC */ 959 schedule(); /* Don't hold spinlock here, will hang PC */
960 } 960 }
961 __set_current_state(TASK_RUNNING); 961 __set_current_state(TASK_RUNNING);
962 remove_wait_queue(&port->open_wait, &wait); 962 remove_wait_queue(&port->open_wait, &wait);
963 963
964 spin_lock_irqsave(&port->lock, flags); 964 spin_lock_irqsave(&port->lock, flags);
965 965
966 if (extra_count) 966 if (extra_count)
967 port->count++; 967 port->count++;
968 port->blocked_open--; 968 port->blocked_open--;
969 969
970 spin_unlock_irqrestore(&port->lock, flags); 970 spin_unlock_irqrestore(&port->lock, flags);
971 971
972 #ifdef ROCKET_DEBUG_OPEN 972 #ifdef ROCKET_DEBUG_OPEN
973 printk(KERN_INFO "block_til_ready after blocking: ttyR%d, count = %d\n", 973 printk(KERN_INFO "block_til_ready after blocking: ttyR%d, count = %d\n",
974 info->line, port->count); 974 info->line, port->count);
975 #endif 975 #endif
976 if (retval) 976 if (retval)
977 return retval; 977 return retval;
978 info->flags |= ASYNC_NORMAL_ACTIVE; 978 info->port.flags |= ASYNC_NORMAL_ACTIVE;
979 return 0; 979 return 0;
980 } 980 }
981 981
982 /* 982 /*
983 * Exception handler that opens a serial port. Creates xmit_buf storage, fills in 983 * Exception handler that opens a serial port. Creates xmit_buf storage, fills in
984 * port's r_port struct. Initializes the port hardware. 984 * port's r_port struct. Initializes the port hardware.
985 */ 985 */
986 static int rp_open(struct tty_struct *tty, struct file *filp) 986 static int rp_open(struct tty_struct *tty, struct file *filp)
987 { 987 {
988 struct r_port *info; 988 struct r_port *info;
989 int line = 0, retval; 989 int line = 0, retval;
990 CHANNEL_t *cp; 990 CHANNEL_t *cp;
991 unsigned long page; 991 unsigned long page;
992 992
993 line = tty->index; 993 line = tty->index;
994 if ((line < 0) || (line >= MAX_RP_PORTS) || ((info = rp_table[line]) == NULL)) 994 if ((line < 0) || (line >= MAX_RP_PORTS) || ((info = rp_table[line]) == NULL))
995 return -ENXIO; 995 return -ENXIO;
996 996
997 page = __get_free_page(GFP_KERNEL); 997 page = __get_free_page(GFP_KERNEL);
998 if (!page) 998 if (!page)
999 return -ENOMEM; 999 return -ENOMEM;
1000 1000
1001 if (info->flags & ASYNC_CLOSING) { 1001 if (info->port.flags & ASYNC_CLOSING) {
1002 retval = wait_for_completion_interruptible(&info->close_wait); 1002 retval = wait_for_completion_interruptible(&info->close_wait);
1003 free_page(page); 1003 free_page(page);
1004 if (retval) 1004 if (retval)
1005 return retval; 1005 return retval;
1006 return ((info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS); 1006 return ((info->port.flags & ASYNC_HUP_NOTIFY) ? -EAGAIN : -ERESTARTSYS);
1007 } 1007 }
1008 1008
1009 /* 1009 /*
1010 * We must not sleep from here until the port is marked fully in use. 1010 * We must not sleep from here until the port is marked fully in use.
1011 */ 1011 */
1012 if (info->xmit_buf) 1012 if (info->xmit_buf)
1013 free_page(page); 1013 free_page(page);
1014 else 1014 else
1015 info->xmit_buf = (unsigned char *) page; 1015 info->xmit_buf = (unsigned char *) page;
1016 1016
1017 tty->driver_data = info; 1017 tty->driver_data = info;
1018 info->port.tty = tty; 1018 info->port.tty = tty;
1019 1019
1020 if (info->port.count++ == 0) { 1020 if (info->port.count++ == 0) {
1021 atomic_inc(&rp_num_ports_open); 1021 atomic_inc(&rp_num_ports_open);
1022 1022
1023 #ifdef ROCKET_DEBUG_OPEN 1023 #ifdef ROCKET_DEBUG_OPEN
1024 printk(KERN_INFO "rocket mod++ = %d...\n", 1024 printk(KERN_INFO "rocket mod++ = %d...\n",
1025 atomic_read(&rp_num_ports_open)); 1025 atomic_read(&rp_num_ports_open));
1026 #endif 1026 #endif
1027 } 1027 }
1028 #ifdef ROCKET_DEBUG_OPEN 1028 #ifdef ROCKET_DEBUG_OPEN
1029 printk(KERN_INFO "rp_open ttyR%d, count=%d\n", info->line, info->port.count); 1029 printk(KERN_INFO "rp_open ttyR%d, count=%d\n", info->line, info->port.count);
1030 #endif 1030 #endif
1031 1031
1032 /* 1032 /*
1033 * Info->count is now 1; so it's safe to sleep now. 1033 * Info->count is now 1; so it's safe to sleep now.
1034 */ 1034 */
1035 if ((info->flags & ASYNC_INITIALIZED) == 0) { 1035 if ((info->port.flags & ASYNC_INITIALIZED) == 0) {
1036 cp = &info->channel; 1036 cp = &info->channel;
1037 sSetRxTrigger(cp, TRIG_1); 1037 sSetRxTrigger(cp, TRIG_1);
1038 if (sGetChanStatus(cp) & CD_ACT) 1038 if (sGetChanStatus(cp) & CD_ACT)
1039 info->cd_status = 1; 1039 info->cd_status = 1;
1040 else 1040 else
1041 info->cd_status = 0; 1041 info->cd_status = 0;
1042 sDisRxStatusMode(cp); 1042 sDisRxStatusMode(cp);
1043 sFlushRxFIFO(cp); 1043 sFlushRxFIFO(cp);
1044 sFlushTxFIFO(cp); 1044 sFlushTxFIFO(cp);
1045 1045
1046 sEnInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN)); 1046 sEnInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN));
1047 sSetRxTrigger(cp, TRIG_1); 1047 sSetRxTrigger(cp, TRIG_1);
1048 1048
1049 sGetChanStatus(cp); 1049 sGetChanStatus(cp);
1050 sDisRxStatusMode(cp); 1050 sDisRxStatusMode(cp);
1051 sClrTxXOFF(cp); 1051 sClrTxXOFF(cp);
1052 1052
1053 sDisCTSFlowCtl(cp); 1053 sDisCTSFlowCtl(cp);
1054 sDisTxSoftFlowCtl(cp); 1054 sDisTxSoftFlowCtl(cp);
1055 1055
1056 sEnRxFIFO(cp); 1056 sEnRxFIFO(cp);
1057 sEnTransmit(cp); 1057 sEnTransmit(cp);
1058 1058
1059 info->flags |= ASYNC_INITIALIZED; 1059 info->port.flags |= ASYNC_INITIALIZED;
1060 1060
1061 /* 1061 /*
1062 * Set up the tty->alt_speed kludge 1062 * Set up the tty->alt_speed kludge
1063 */ 1063 */
1064 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_HI) 1064 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_HI)
1065 info->port.tty->alt_speed = 57600; 1065 info->port.tty->alt_speed = 57600;
1066 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_VHI) 1066 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_VHI)
1067 info->port.tty->alt_speed = 115200; 1067 info->port.tty->alt_speed = 115200;
1068 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_SHI) 1068 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_SHI)
1069 info->port.tty->alt_speed = 230400; 1069 info->port.tty->alt_speed = 230400;
1070 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP) 1070 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP)
1071 info->port.tty->alt_speed = 460800; 1071 info->port.tty->alt_speed = 460800;
1072 1072
1073 configure_r_port(info, NULL); 1073 configure_r_port(info, NULL);
1074 if (tty->termios->c_cflag & CBAUD) { 1074 if (tty->termios->c_cflag & CBAUD) {
1075 sSetDTR(cp); 1075 sSetDTR(cp);
1076 sSetRTS(cp); 1076 sSetRTS(cp);
1077 } 1077 }
1078 } 1078 }
1079 /* Starts (or resets) the maint polling loop */ 1079 /* Starts (or resets) the maint polling loop */
1080 mod_timer(&rocket_timer, jiffies + POLL_PERIOD); 1080 mod_timer(&rocket_timer, jiffies + POLL_PERIOD);
1081 1081
1082 retval = block_til_ready(tty, filp, info); 1082 retval = block_til_ready(tty, filp, info);
1083 if (retval) { 1083 if (retval) {
1084 #ifdef ROCKET_DEBUG_OPEN 1084 #ifdef ROCKET_DEBUG_OPEN
1085 printk(KERN_INFO "rp_open returning after block_til_ready with %d\n", retval); 1085 printk(KERN_INFO "rp_open returning after block_til_ready with %d\n", retval);
1086 #endif 1086 #endif
1087 return retval; 1087 return retval;
1088 } 1088 }
1089 return 0; 1089 return 0;
1090 } 1090 }
1091 1091
1092 /* 1092 /*
1093 * Exception handler that closes a serial port. info->port.count is considered critical. 1093 * Exception handler that closes a serial port. info->port.count is considered critical.
1094 */ 1094 */
1095 static void rp_close(struct tty_struct *tty, struct file *filp) 1095 static void rp_close(struct tty_struct *tty, struct file *filp)
1096 { 1096 {
1097 struct r_port *info = tty->driver_data; 1097 struct r_port *info = tty->driver_data;
1098 struct tty_port *port = &info->port; 1098 struct tty_port *port = &info->port;
1099 unsigned long flags; 1099 unsigned long flags;
1100 int timeout; 1100 int timeout;
1101 CHANNEL_t *cp; 1101 CHANNEL_t *cp;
1102 1102
1103 if (rocket_paranoia_check(info, "rp_close")) 1103 if (rocket_paranoia_check(info, "rp_close"))
1104 return; 1104 return;
1105 1105
1106 #ifdef ROCKET_DEBUG_OPEN 1106 #ifdef ROCKET_DEBUG_OPEN
1107 printk(KERN_INFO "rp_close ttyR%d, count = %d\n", info->line, info->port.count); 1107 printk(KERN_INFO "rp_close ttyR%d, count = %d\n", info->line, info->port.count);
1108 #endif 1108 #endif
1109 1109
1110 if (tty_hung_up_p(filp)) 1110 if (tty_hung_up_p(filp))
1111 return; 1111 return;
1112 spin_lock_irqsave(&port->lock, flags); 1112 spin_lock_irqsave(&port->lock, flags);
1113 1113
1114 if (tty->count == 1 && port->count != 1) { 1114 if (tty->count == 1 && port->count != 1) {
1115 /* 1115 /*
1116 * Uh, oh. tty->count is 1, which means that the tty 1116 * Uh, oh. tty->count is 1, which means that the tty
1117 * structure will be freed. Info->count should always 1117 * structure will be freed. Info->count should always
1118 * be one in these conditions. If it's greater than 1118 * be one in these conditions. If it's greater than
1119 * one, we've got real problems, since it means the 1119 * one, we've got real problems, since it means the
1120 * serial port won't be shutdown. 1120 * serial port won't be shutdown.
1121 */ 1121 */
1122 printk(KERN_WARNING "rp_close: bad serial port count; " 1122 printk(KERN_WARNING "rp_close: bad serial port count; "
1123 "tty->count is 1, info->port.count is %d\n", info->port.count); 1123 "tty->count is 1, info->port.count is %d\n", info->port.count);
1124 port->count = 1; 1124 port->count = 1;
1125 } 1125 }
1126 if (--port->count < 0) { 1126 if (--port->count < 0) {
1127 printk(KERN_WARNING "rp_close: bad serial port count for " 1127 printk(KERN_WARNING "rp_close: bad serial port count for "
1128 "ttyR%d: %d\n", info->line, info->port.count); 1128 "ttyR%d: %d\n", info->line, info->port.count);
1129 port->count = 0; 1129 port->count = 0;
1130 } 1130 }
1131 if (port->count) { 1131 if (port->count) {
1132 spin_unlock_irqrestore(&port->lock, flags); 1132 spin_unlock_irqrestore(&port->lock, flags);
1133 return; 1133 return;
1134 } 1134 }
1135 info->flags |= ASYNC_CLOSING; 1135 info->port.flags |= ASYNC_CLOSING;
1136 spin_unlock_irqrestore(&port->lock, flags); 1136 spin_unlock_irqrestore(&port->lock, flags);
1137 1137
1138 cp = &info->channel; 1138 cp = &info->channel;
1139 1139
1140 /* 1140 /*
1141 * Notify the line discpline to only process XON/XOFF characters 1141 * Notify the line discpline to only process XON/XOFF characters
1142 */ 1142 */
1143 tty->closing = 1; 1143 tty->closing = 1;
1144 1144
1145 /* 1145 /*
1146 * If transmission was throttled by the application request, 1146 * If transmission was throttled by the application request,
1147 * just flush the xmit buffer. 1147 * just flush the xmit buffer.
1148 */ 1148 */
1149 if (tty->flow_stopped) 1149 if (tty->flow_stopped)
1150 rp_flush_buffer(tty); 1150 rp_flush_buffer(tty);
1151 1151
1152 /* 1152 /*
1153 * Wait for the transmit buffer to clear 1153 * Wait for the transmit buffer to clear
1154 */ 1154 */
1155 if (info->port.closing_wait != ASYNC_CLOSING_WAIT_NONE) 1155 if (info->port.closing_wait != ASYNC_CLOSING_WAIT_NONE)
1156 tty_wait_until_sent(tty, port->closing_wait); 1156 tty_wait_until_sent(tty, port->closing_wait);
1157 /* 1157 /*
1158 * Before we drop DTR, make sure the UART transmitter 1158 * Before we drop DTR, make sure the UART transmitter
1159 * has completely drained; this is especially 1159 * has completely drained; this is especially
1160 * important if there is a transmit FIFO! 1160 * important if there is a transmit FIFO!
1161 */ 1161 */
1162 timeout = (sGetTxCnt(cp) + 1) * HZ / info->cps; 1162 timeout = (sGetTxCnt(cp) + 1) * HZ / info->cps;
1163 if (timeout == 0) 1163 if (timeout == 0)
1164 timeout = 1; 1164 timeout = 1;
1165 rp_wait_until_sent(tty, timeout); 1165 rp_wait_until_sent(tty, timeout);
1166 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1166 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1167 1167
1168 sDisTransmit(cp); 1168 sDisTransmit(cp);
1169 sDisInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN)); 1169 sDisInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN));
1170 sDisCTSFlowCtl(cp); 1170 sDisCTSFlowCtl(cp);
1171 sDisTxSoftFlowCtl(cp); 1171 sDisTxSoftFlowCtl(cp);
1172 sClrTxXOFF(cp); 1172 sClrTxXOFF(cp);
1173 sFlushRxFIFO(cp); 1173 sFlushRxFIFO(cp);
1174 sFlushTxFIFO(cp); 1174 sFlushTxFIFO(cp);
1175 sClrRTS(cp); 1175 sClrRTS(cp);
1176 if (C_HUPCL(tty)) 1176 if (C_HUPCL(tty))
1177 sClrDTR(cp); 1177 sClrDTR(cp);
1178 1178
1179 rp_flush_buffer(tty); 1179 rp_flush_buffer(tty);
1180 1180
1181 tty_ldisc_flush(tty); 1181 tty_ldisc_flush(tty);
1182 1182
1183 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1183 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1184 1184
1185 if (port->blocked_open) { 1185 if (port->blocked_open) {
1186 if (port->close_delay) { 1186 if (port->close_delay) {
1187 msleep_interruptible(jiffies_to_msecs(port->close_delay)); 1187 msleep_interruptible(jiffies_to_msecs(port->close_delay));
1188 } 1188 }
1189 wake_up_interruptible(&port->open_wait); 1189 wake_up_interruptible(&port->open_wait);
1190 } else { 1190 } else {
1191 if (info->xmit_buf) { 1191 if (info->xmit_buf) {
1192 free_page((unsigned long) info->xmit_buf); 1192 free_page((unsigned long) info->xmit_buf);
1193 info->xmit_buf = NULL; 1193 info->xmit_buf = NULL;
1194 } 1194 }
1195 } 1195 }
1196 info->flags &= ~(ASYNC_INITIALIZED | ASYNC_CLOSING | ASYNC_NORMAL_ACTIVE); 1196 info->port.flags &= ~(ASYNC_INITIALIZED | ASYNC_CLOSING | ASYNC_NORMAL_ACTIVE);
1197 tty->closing = 0; 1197 tty->closing = 0;
1198 complete_all(&info->close_wait); 1198 complete_all(&info->close_wait);
1199 atomic_dec(&rp_num_ports_open); 1199 atomic_dec(&rp_num_ports_open);
1200 1200
1201 #ifdef ROCKET_DEBUG_OPEN 1201 #ifdef ROCKET_DEBUG_OPEN
1202 printk(KERN_INFO "rocket mod-- = %d...\n", 1202 printk(KERN_INFO "rocket mod-- = %d...\n",
1203 atomic_read(&rp_num_ports_open)); 1203 atomic_read(&rp_num_ports_open));
1204 printk(KERN_INFO "rp_close ttyR%d complete shutdown\n", info->line); 1204 printk(KERN_INFO "rp_close ttyR%d complete shutdown\n", info->line);
1205 #endif 1205 #endif
1206 1206
1207 } 1207 }
1208 1208
1209 static void rp_set_termios(struct tty_struct *tty, 1209 static void rp_set_termios(struct tty_struct *tty,
1210 struct ktermios *old_termios) 1210 struct ktermios *old_termios)
1211 { 1211 {
1212 struct r_port *info = tty->driver_data; 1212 struct r_port *info = tty->driver_data;
1213 CHANNEL_t *cp; 1213 CHANNEL_t *cp;
1214 unsigned cflag; 1214 unsigned cflag;
1215 1215
1216 if (rocket_paranoia_check(info, "rp_set_termios")) 1216 if (rocket_paranoia_check(info, "rp_set_termios"))
1217 return; 1217 return;
1218 1218
1219 cflag = tty->termios->c_cflag; 1219 cflag = tty->termios->c_cflag;
1220 1220
1221 /* 1221 /*
1222 * This driver doesn't support CS5 or CS6 1222 * This driver doesn't support CS5 or CS6
1223 */ 1223 */
1224 if (((cflag & CSIZE) == CS5) || ((cflag & CSIZE) == CS6)) 1224 if (((cflag & CSIZE) == CS5) || ((cflag & CSIZE) == CS6))
1225 tty->termios->c_cflag = 1225 tty->termios->c_cflag =
1226 ((cflag & ~CSIZE) | (old_termios->c_cflag & CSIZE)); 1226 ((cflag & ~CSIZE) | (old_termios->c_cflag & CSIZE));
1227 /* Or CMSPAR */ 1227 /* Or CMSPAR */
1228 tty->termios->c_cflag &= ~CMSPAR; 1228 tty->termios->c_cflag &= ~CMSPAR;
1229 1229
1230 configure_r_port(info, old_termios); 1230 configure_r_port(info, old_termios);
1231 1231
1232 cp = &info->channel; 1232 cp = &info->channel;
1233 1233
1234 /* Handle transition to B0 status */ 1234 /* Handle transition to B0 status */
1235 if ((old_termios->c_cflag & CBAUD) && !(tty->termios->c_cflag & CBAUD)) { 1235 if ((old_termios->c_cflag & CBAUD) && !(tty->termios->c_cflag & CBAUD)) {
1236 sClrDTR(cp); 1236 sClrDTR(cp);
1237 sClrRTS(cp); 1237 sClrRTS(cp);
1238 } 1238 }
1239 1239
1240 /* Handle transition away from B0 status */ 1240 /* Handle transition away from B0 status */
1241 if (!(old_termios->c_cflag & CBAUD) && (tty->termios->c_cflag & CBAUD)) { 1241 if (!(old_termios->c_cflag & CBAUD) && (tty->termios->c_cflag & CBAUD)) {
1242 if (!tty->hw_stopped || !(tty->termios->c_cflag & CRTSCTS)) 1242 if (!tty->hw_stopped || !(tty->termios->c_cflag & CRTSCTS))
1243 sSetRTS(cp); 1243 sSetRTS(cp);
1244 sSetDTR(cp); 1244 sSetDTR(cp);
1245 } 1245 }
1246 1246
1247 if ((old_termios->c_cflag & CRTSCTS) && !(tty->termios->c_cflag & CRTSCTS)) { 1247 if ((old_termios->c_cflag & CRTSCTS) && !(tty->termios->c_cflag & CRTSCTS)) {
1248 tty->hw_stopped = 0; 1248 tty->hw_stopped = 0;
1249 rp_start(tty); 1249 rp_start(tty);
1250 } 1250 }
1251 } 1251 }
1252 1252
1253 static int rp_break(struct tty_struct *tty, int break_state) 1253 static int rp_break(struct tty_struct *tty, int break_state)
1254 { 1254 {
1255 struct r_port *info = tty->driver_data; 1255 struct r_port *info = tty->driver_data;
1256 unsigned long flags; 1256 unsigned long flags;
1257 1257
1258 if (rocket_paranoia_check(info, "rp_break")) 1258 if (rocket_paranoia_check(info, "rp_break"))
1259 return -EINVAL; 1259 return -EINVAL;
1260 1260
1261 spin_lock_irqsave(&info->slock, flags); 1261 spin_lock_irqsave(&info->slock, flags);
1262 if (break_state == -1) 1262 if (break_state == -1)
1263 sSendBreak(&info->channel); 1263 sSendBreak(&info->channel);
1264 else 1264 else
1265 sClrBreak(&info->channel); 1265 sClrBreak(&info->channel);
1266 spin_unlock_irqrestore(&info->slock, flags); 1266 spin_unlock_irqrestore(&info->slock, flags);
1267 return 0; 1267 return 0;
1268 } 1268 }
1269 1269
1270 /* 1270 /*
1271 * sGetChanRI used to be a macro in rocket_int.h. When the functionality for 1271 * sGetChanRI used to be a macro in rocket_int.h. When the functionality for
1272 * the UPCI boards was added, it was decided to make this a function because 1272 * the UPCI boards was added, it was decided to make this a function because
1273 * the macro was getting too complicated. All cases except the first one 1273 * the macro was getting too complicated. All cases except the first one
1274 * (UPCIRingInd) are taken directly from the original macro. 1274 * (UPCIRingInd) are taken directly from the original macro.
1275 */ 1275 */
1276 static int sGetChanRI(CHANNEL_T * ChP) 1276 static int sGetChanRI(CHANNEL_T * ChP)
1277 { 1277 {
1278 CONTROLLER_t *CtlP = ChP->CtlP; 1278 CONTROLLER_t *CtlP = ChP->CtlP;
1279 int ChanNum = ChP->ChanNum; 1279 int ChanNum = ChP->ChanNum;
1280 int RingInd = 0; 1280 int RingInd = 0;
1281 1281
1282 if (CtlP->UPCIRingInd) 1282 if (CtlP->UPCIRingInd)
1283 RingInd = !(sInB(CtlP->UPCIRingInd) & sBitMapSetTbl[ChanNum]); 1283 RingInd = !(sInB(CtlP->UPCIRingInd) & sBitMapSetTbl[ChanNum]);
1284 else if (CtlP->AltChanRingIndicator) 1284 else if (CtlP->AltChanRingIndicator)
1285 RingInd = sInB((ByteIO_t) (ChP->ChanStat + 8)) & DSR_ACT; 1285 RingInd = sInB((ByteIO_t) (ChP->ChanStat + 8)) & DSR_ACT;
1286 else if (CtlP->boardType == ROCKET_TYPE_PC104) 1286 else if (CtlP->boardType == ROCKET_TYPE_PC104)
1287 RingInd = !(sInB(CtlP->AiopIO[3]) & sBitMapSetTbl[ChanNum]); 1287 RingInd = !(sInB(CtlP->AiopIO[3]) & sBitMapSetTbl[ChanNum]);
1288 1288
1289 return RingInd; 1289 return RingInd;
1290 } 1290 }
1291 1291
1292 /********************************************************************************************/ 1292 /********************************************************************************************/
1293 /* Here are the routines used by rp_ioctl. These are all called from exception handlers. */ 1293 /* Here are the routines used by rp_ioctl. These are all called from exception handlers. */
1294 1294
1295 /* 1295 /*
1296 * Returns the state of the serial modem control lines. These next 2 functions 1296 * Returns the state of the serial modem control lines. These next 2 functions
1297 * are the way kernel versions > 2.5 handle modem control lines rather than IOCTLs. 1297 * are the way kernel versions > 2.5 handle modem control lines rather than IOCTLs.
1298 */ 1298 */
1299 static int rp_tiocmget(struct tty_struct *tty, struct file *file) 1299 static int rp_tiocmget(struct tty_struct *tty, struct file *file)
1300 { 1300 {
1301 struct r_port *info = tty->driver_data; 1301 struct r_port *info = tty->driver_data;
1302 unsigned int control, result, ChanStatus; 1302 unsigned int control, result, ChanStatus;
1303 1303
1304 ChanStatus = sGetChanStatusLo(&info->channel); 1304 ChanStatus = sGetChanStatusLo(&info->channel);
1305 control = info->channel.TxControl[3]; 1305 control = info->channel.TxControl[3];
1306 result = ((control & SET_RTS) ? TIOCM_RTS : 0) | 1306 result = ((control & SET_RTS) ? TIOCM_RTS : 0) |
1307 ((control & SET_DTR) ? TIOCM_DTR : 0) | 1307 ((control & SET_DTR) ? TIOCM_DTR : 0) |
1308 ((ChanStatus & CD_ACT) ? TIOCM_CAR : 0) | 1308 ((ChanStatus & CD_ACT) ? TIOCM_CAR : 0) |
1309 (sGetChanRI(&info->channel) ? TIOCM_RNG : 0) | 1309 (sGetChanRI(&info->channel) ? TIOCM_RNG : 0) |
1310 ((ChanStatus & DSR_ACT) ? TIOCM_DSR : 0) | 1310 ((ChanStatus & DSR_ACT) ? TIOCM_DSR : 0) |
1311 ((ChanStatus & CTS_ACT) ? TIOCM_CTS : 0); 1311 ((ChanStatus & CTS_ACT) ? TIOCM_CTS : 0);
1312 1312
1313 return result; 1313 return result;
1314 } 1314 }
1315 1315
1316 /* 1316 /*
1317 * Sets the modem control lines 1317 * Sets the modem control lines
1318 */ 1318 */
1319 static int rp_tiocmset(struct tty_struct *tty, struct file *file, 1319 static int rp_tiocmset(struct tty_struct *tty, struct file *file,
1320 unsigned int set, unsigned int clear) 1320 unsigned int set, unsigned int clear)
1321 { 1321 {
1322 struct r_port *info = tty->driver_data; 1322 struct r_port *info = tty->driver_data;
1323 1323
1324 if (set & TIOCM_RTS) 1324 if (set & TIOCM_RTS)
1325 info->channel.TxControl[3] |= SET_RTS; 1325 info->channel.TxControl[3] |= SET_RTS;
1326 if (set & TIOCM_DTR) 1326 if (set & TIOCM_DTR)
1327 info->channel.TxControl[3] |= SET_DTR; 1327 info->channel.TxControl[3] |= SET_DTR;
1328 if (clear & TIOCM_RTS) 1328 if (clear & TIOCM_RTS)
1329 info->channel.TxControl[3] &= ~SET_RTS; 1329 info->channel.TxControl[3] &= ~SET_RTS;
1330 if (clear & TIOCM_DTR) 1330 if (clear & TIOCM_DTR)
1331 info->channel.TxControl[3] &= ~SET_DTR; 1331 info->channel.TxControl[3] &= ~SET_DTR;
1332 1332
1333 out32(info->channel.IndexAddr, info->channel.TxControl); 1333 out32(info->channel.IndexAddr, info->channel.TxControl);
1334 return 0; 1334 return 0;
1335 } 1335 }
1336 1336
1337 static int get_config(struct r_port *info, struct rocket_config __user *retinfo) 1337 static int get_config(struct r_port *info, struct rocket_config __user *retinfo)
1338 { 1338 {
1339 struct rocket_config tmp; 1339 struct rocket_config tmp;
1340 1340
1341 if (!retinfo) 1341 if (!retinfo)
1342 return -EFAULT; 1342 return -EFAULT;
1343 memset(&tmp, 0, sizeof (tmp)); 1343 memset(&tmp, 0, sizeof (tmp));
1344 tmp.line = info->line; 1344 tmp.line = info->line;
1345 tmp.flags = info->flags; 1345 tmp.flags = info->flags;
1346 tmp.close_delay = info->port.close_delay; 1346 tmp.close_delay = info->port.close_delay;
1347 tmp.closing_wait = info->port.closing_wait; 1347 tmp.closing_wait = info->port.closing_wait;
1348 tmp.port = rcktpt_io_addr[(info->line >> 5) & 3]; 1348 tmp.port = rcktpt_io_addr[(info->line >> 5) & 3];
1349 1349
1350 if (copy_to_user(retinfo, &tmp, sizeof (*retinfo))) 1350 if (copy_to_user(retinfo, &tmp, sizeof (*retinfo)))
1351 return -EFAULT; 1351 return -EFAULT;
1352 return 0; 1352 return 0;
1353 } 1353 }
1354 1354
1355 static int set_config(struct r_port *info, struct rocket_config __user *new_info) 1355 static int set_config(struct r_port *info, struct rocket_config __user *new_info)
1356 { 1356 {
1357 struct rocket_config new_serial; 1357 struct rocket_config new_serial;
1358 1358
1359 if (copy_from_user(&new_serial, new_info, sizeof (new_serial))) 1359 if (copy_from_user(&new_serial, new_info, sizeof (new_serial)))
1360 return -EFAULT; 1360 return -EFAULT;
1361 1361
1362 if (!capable(CAP_SYS_ADMIN)) 1362 if (!capable(CAP_SYS_ADMIN))
1363 { 1363 {
1364 if ((new_serial.flags & ~ROCKET_USR_MASK) != (info->flags & ~ROCKET_USR_MASK)) 1364 if ((new_serial.flags & ~ROCKET_USR_MASK) != (info->flags & ~ROCKET_USR_MASK))
1365 return -EPERM; 1365 return -EPERM;
1366 info->flags = ((info->flags & ~ROCKET_USR_MASK) | (new_serial.flags & ROCKET_USR_MASK)); 1366 info->flags = ((info->flags & ~ROCKET_USR_MASK) | (new_serial.flags & ROCKET_USR_MASK));
1367 configure_r_port(info, NULL); 1367 configure_r_port(info, NULL);
1368 return 0; 1368 return 0;
1369 } 1369 }
1370 1370
1371 info->flags = ((info->flags & ~ROCKET_FLAGS) | (new_serial.flags & ROCKET_FLAGS)); 1371 info->flags = ((info->flags & ~ROCKET_FLAGS) | (new_serial.flags & ROCKET_FLAGS));
1372 info->port.close_delay = new_serial.close_delay; 1372 info->port.close_delay = new_serial.close_delay;
1373 info->port.closing_wait = new_serial.closing_wait; 1373 info->port.closing_wait = new_serial.closing_wait;
1374 1374
1375 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_HI) 1375 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_HI)
1376 info->port.tty->alt_speed = 57600; 1376 info->port.tty->alt_speed = 57600;
1377 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_VHI) 1377 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_VHI)
1378 info->port.tty->alt_speed = 115200; 1378 info->port.tty->alt_speed = 115200;
1379 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_SHI) 1379 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_SHI)
1380 info->port.tty->alt_speed = 230400; 1380 info->port.tty->alt_speed = 230400;
1381 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP) 1381 if ((info->flags & ROCKET_SPD_MASK) == ROCKET_SPD_WARP)
1382 info->port.tty->alt_speed = 460800; 1382 info->port.tty->alt_speed = 460800;
1383 1383
1384 configure_r_port(info, NULL); 1384 configure_r_port(info, NULL);
1385 return 0; 1385 return 0;
1386 } 1386 }
1387 1387
1388 /* 1388 /*
1389 * This function fills in a rocket_ports struct with information 1389 * This function fills in a rocket_ports struct with information
1390 * about what boards/ports are in the system. This info is passed 1390 * about what boards/ports are in the system. This info is passed
1391 * to user space. See setrocket.c where the info is used to create 1391 * to user space. See setrocket.c where the info is used to create
1392 * the /dev/ttyRx ports. 1392 * the /dev/ttyRx ports.
1393 */ 1393 */
1394 static int get_ports(struct r_port *info, struct rocket_ports __user *retports) 1394 static int get_ports(struct r_port *info, struct rocket_ports __user *retports)
1395 { 1395 {
1396 struct rocket_ports tmp; 1396 struct rocket_ports tmp;
1397 int board; 1397 int board;
1398 1398
1399 if (!retports) 1399 if (!retports)
1400 return -EFAULT; 1400 return -EFAULT;
1401 memset(&tmp, 0, sizeof (tmp)); 1401 memset(&tmp, 0, sizeof (tmp));
1402 tmp.tty_major = rocket_driver->major; 1402 tmp.tty_major = rocket_driver->major;
1403 1403
1404 for (board = 0; board < 4; board++) { 1404 for (board = 0; board < 4; board++) {
1405 tmp.rocketModel[board].model = rocketModel[board].model; 1405 tmp.rocketModel[board].model = rocketModel[board].model;
1406 strcpy(tmp.rocketModel[board].modelString, rocketModel[board].modelString); 1406 strcpy(tmp.rocketModel[board].modelString, rocketModel[board].modelString);
1407 tmp.rocketModel[board].numPorts = rocketModel[board].numPorts; 1407 tmp.rocketModel[board].numPorts = rocketModel[board].numPorts;
1408 tmp.rocketModel[board].loadrm2 = rocketModel[board].loadrm2; 1408 tmp.rocketModel[board].loadrm2 = rocketModel[board].loadrm2;
1409 tmp.rocketModel[board].startingPortNumber = rocketModel[board].startingPortNumber; 1409 tmp.rocketModel[board].startingPortNumber = rocketModel[board].startingPortNumber;
1410 } 1410 }
1411 if (copy_to_user(retports, &tmp, sizeof (*retports))) 1411 if (copy_to_user(retports, &tmp, sizeof (*retports)))
1412 return -EFAULT; 1412 return -EFAULT;
1413 return 0; 1413 return 0;
1414 } 1414 }
1415 1415
1416 static int reset_rm2(struct r_port *info, void __user *arg) 1416 static int reset_rm2(struct r_port *info, void __user *arg)
1417 { 1417 {
1418 int reset; 1418 int reset;
1419 1419
1420 if (!capable(CAP_SYS_ADMIN)) 1420 if (!capable(CAP_SYS_ADMIN))
1421 return -EPERM; 1421 return -EPERM;
1422 1422
1423 if (copy_from_user(&reset, arg, sizeof (int))) 1423 if (copy_from_user(&reset, arg, sizeof (int)))
1424 return -EFAULT; 1424 return -EFAULT;
1425 if (reset) 1425 if (reset)
1426 reset = 1; 1426 reset = 1;
1427 1427
1428 if (rcktpt_type[info->board] != ROCKET_TYPE_MODEMII && 1428 if (rcktpt_type[info->board] != ROCKET_TYPE_MODEMII &&
1429 rcktpt_type[info->board] != ROCKET_TYPE_MODEMIII) 1429 rcktpt_type[info->board] != ROCKET_TYPE_MODEMIII)
1430 return -EINVAL; 1430 return -EINVAL;
1431 1431
1432 if (info->ctlp->BusType == isISA) 1432 if (info->ctlp->BusType == isISA)
1433 sModemReset(info->ctlp, info->chan, reset); 1433 sModemReset(info->ctlp, info->chan, reset);
1434 else 1434 else
1435 sPCIModemReset(info->ctlp, info->chan, reset); 1435 sPCIModemReset(info->ctlp, info->chan, reset);
1436 1436
1437 return 0; 1437 return 0;
1438 } 1438 }
1439 1439
1440 static int get_version(struct r_port *info, struct rocket_version __user *retvers) 1440 static int get_version(struct r_port *info, struct rocket_version __user *retvers)
1441 { 1441 {
1442 if (copy_to_user(retvers, &driver_version, sizeof (*retvers))) 1442 if (copy_to_user(retvers, &driver_version, sizeof (*retvers)))
1443 return -EFAULT; 1443 return -EFAULT;
1444 return 0; 1444 return 0;
1445 } 1445 }
1446 1446
1447 /* IOCTL call handler into the driver */ 1447 /* IOCTL call handler into the driver */
1448 static int rp_ioctl(struct tty_struct *tty, struct file *file, 1448 static int rp_ioctl(struct tty_struct *tty, struct file *file,
1449 unsigned int cmd, unsigned long arg) 1449 unsigned int cmd, unsigned long arg)
1450 { 1450 {
1451 struct r_port *info = tty->driver_data; 1451 struct r_port *info = tty->driver_data;
1452 void __user *argp = (void __user *)arg; 1452 void __user *argp = (void __user *)arg;
1453 int ret = 0; 1453 int ret = 0;
1454 1454
1455 if (cmd != RCKP_GET_PORTS && rocket_paranoia_check(info, "rp_ioctl")) 1455 if (cmd != RCKP_GET_PORTS && rocket_paranoia_check(info, "rp_ioctl"))
1456 return -ENXIO; 1456 return -ENXIO;
1457 1457
1458 lock_kernel(); 1458 lock_kernel();
1459 1459
1460 switch (cmd) { 1460 switch (cmd) {
1461 case RCKP_GET_STRUCT: 1461 case RCKP_GET_STRUCT:
1462 if (copy_to_user(argp, info, sizeof (struct r_port))) 1462 if (copy_to_user(argp, info, sizeof (struct r_port)))
1463 ret = -EFAULT; 1463 ret = -EFAULT;
1464 break; 1464 break;
1465 case RCKP_GET_CONFIG: 1465 case RCKP_GET_CONFIG:
1466 ret = get_config(info, argp); 1466 ret = get_config(info, argp);
1467 break; 1467 break;
1468 case RCKP_SET_CONFIG: 1468 case RCKP_SET_CONFIG:
1469 ret = set_config(info, argp); 1469 ret = set_config(info, argp);
1470 break; 1470 break;
1471 case RCKP_GET_PORTS: 1471 case RCKP_GET_PORTS:
1472 ret = get_ports(info, argp); 1472 ret = get_ports(info, argp);
1473 break; 1473 break;
1474 case RCKP_RESET_RM2: 1474 case RCKP_RESET_RM2:
1475 ret = reset_rm2(info, argp); 1475 ret = reset_rm2(info, argp);
1476 break; 1476 break;
1477 case RCKP_GET_VERSION: 1477 case RCKP_GET_VERSION:
1478 ret = get_version(info, argp); 1478 ret = get_version(info, argp);
1479 break; 1479 break;
1480 default: 1480 default:
1481 ret = -ENOIOCTLCMD; 1481 ret = -ENOIOCTLCMD;
1482 } 1482 }
1483 unlock_kernel(); 1483 unlock_kernel();
1484 return ret; 1484 return ret;
1485 } 1485 }
1486 1486
1487 static void rp_send_xchar(struct tty_struct *tty, char ch) 1487 static void rp_send_xchar(struct tty_struct *tty, char ch)
1488 { 1488 {
1489 struct r_port *info = tty->driver_data; 1489 struct r_port *info = tty->driver_data;
1490 CHANNEL_t *cp; 1490 CHANNEL_t *cp;
1491 1491
1492 if (rocket_paranoia_check(info, "rp_send_xchar")) 1492 if (rocket_paranoia_check(info, "rp_send_xchar"))
1493 return; 1493 return;
1494 1494
1495 cp = &info->channel; 1495 cp = &info->channel;
1496 if (sGetTxCnt(cp)) 1496 if (sGetTxCnt(cp))
1497 sWriteTxPrioByte(cp, ch); 1497 sWriteTxPrioByte(cp, ch);
1498 else 1498 else
1499 sWriteTxByte(sGetTxRxDataIO(cp), ch); 1499 sWriteTxByte(sGetTxRxDataIO(cp), ch);
1500 } 1500 }
1501 1501
1502 static void rp_throttle(struct tty_struct *tty) 1502 static void rp_throttle(struct tty_struct *tty)
1503 { 1503 {
1504 struct r_port *info = tty->driver_data; 1504 struct r_port *info = tty->driver_data;
1505 CHANNEL_t *cp; 1505 CHANNEL_t *cp;
1506 1506
1507 #ifdef ROCKET_DEBUG_THROTTLE 1507 #ifdef ROCKET_DEBUG_THROTTLE
1508 printk(KERN_INFO "throttle %s: %d....\n", tty->name, 1508 printk(KERN_INFO "throttle %s: %d....\n", tty->name,
1509 tty->ldisc.chars_in_buffer(tty)); 1509 tty->ldisc.chars_in_buffer(tty));
1510 #endif 1510 #endif
1511 1511
1512 if (rocket_paranoia_check(info, "rp_throttle")) 1512 if (rocket_paranoia_check(info, "rp_throttle"))
1513 return; 1513 return;
1514 1514
1515 cp = &info->channel; 1515 cp = &info->channel;
1516 if (I_IXOFF(tty)) 1516 if (I_IXOFF(tty))
1517 rp_send_xchar(tty, STOP_CHAR(tty)); 1517 rp_send_xchar(tty, STOP_CHAR(tty));
1518 1518
1519 sClrRTS(&info->channel); 1519 sClrRTS(&info->channel);
1520 } 1520 }
1521 1521
1522 static void rp_unthrottle(struct tty_struct *tty) 1522 static void rp_unthrottle(struct tty_struct *tty)
1523 { 1523 {
1524 struct r_port *info = tty->driver_data; 1524 struct r_port *info = tty->driver_data;
1525 CHANNEL_t *cp; 1525 CHANNEL_t *cp;
1526 #ifdef ROCKET_DEBUG_THROTTLE 1526 #ifdef ROCKET_DEBUG_THROTTLE
1527 printk(KERN_INFO "unthrottle %s: %d....\n", tty->name, 1527 printk(KERN_INFO "unthrottle %s: %d....\n", tty->name,
1528 tty->ldisc.chars_in_buffer(tty)); 1528 tty->ldisc.chars_in_buffer(tty));
1529 #endif 1529 #endif
1530 1530
1531 if (rocket_paranoia_check(info, "rp_throttle")) 1531 if (rocket_paranoia_check(info, "rp_throttle"))
1532 return; 1532 return;
1533 1533
1534 cp = &info->channel; 1534 cp = &info->channel;
1535 if (I_IXOFF(tty)) 1535 if (I_IXOFF(tty))
1536 rp_send_xchar(tty, START_CHAR(tty)); 1536 rp_send_xchar(tty, START_CHAR(tty));
1537 1537
1538 sSetRTS(&info->channel); 1538 sSetRTS(&info->channel);
1539 } 1539 }
1540 1540
1541 /* 1541 /*
1542 * ------------------------------------------------------------ 1542 * ------------------------------------------------------------
1543 * rp_stop() and rp_start() 1543 * rp_stop() and rp_start()
1544 * 1544 *
1545 * This routines are called before setting or resetting tty->stopped. 1545 * This routines are called before setting or resetting tty->stopped.
1546 * They enable or disable transmitter interrupts, as necessary. 1546 * They enable or disable transmitter interrupts, as necessary.
1547 * ------------------------------------------------------------ 1547 * ------------------------------------------------------------
1548 */ 1548 */
1549 static void rp_stop(struct tty_struct *tty) 1549 static void rp_stop(struct tty_struct *tty)
1550 { 1550 {
1551 struct r_port *info = tty->driver_data; 1551 struct r_port *info = tty->driver_data;
1552 1552
1553 #ifdef ROCKET_DEBUG_FLOW 1553 #ifdef ROCKET_DEBUG_FLOW
1554 printk(KERN_INFO "stop %s: %d %d....\n", tty->name, 1554 printk(KERN_INFO "stop %s: %d %d....\n", tty->name,
1555 info->xmit_cnt, info->xmit_fifo_room); 1555 info->xmit_cnt, info->xmit_fifo_room);
1556 #endif 1556 #endif
1557 1557
1558 if (rocket_paranoia_check(info, "rp_stop")) 1558 if (rocket_paranoia_check(info, "rp_stop"))
1559 return; 1559 return;
1560 1560
1561 if (sGetTxCnt(&info->channel)) 1561 if (sGetTxCnt(&info->channel))
1562 sDisTransmit(&info->channel); 1562 sDisTransmit(&info->channel);
1563 } 1563 }
1564 1564
1565 static void rp_start(struct tty_struct *tty) 1565 static void rp_start(struct tty_struct *tty)
1566 { 1566 {
1567 struct r_port *info = tty->driver_data; 1567 struct r_port *info = tty->driver_data;
1568 1568
1569 #ifdef ROCKET_DEBUG_FLOW 1569 #ifdef ROCKET_DEBUG_FLOW
1570 printk(KERN_INFO "start %s: %d %d....\n", tty->name, 1570 printk(KERN_INFO "start %s: %d %d....\n", tty->name,
1571 info->xmit_cnt, info->xmit_fifo_room); 1571 info->xmit_cnt, info->xmit_fifo_room);
1572 #endif 1572 #endif
1573 1573
1574 if (rocket_paranoia_check(info, "rp_stop")) 1574 if (rocket_paranoia_check(info, "rp_stop"))
1575 return; 1575 return;
1576 1576
1577 sEnTransmit(&info->channel); 1577 sEnTransmit(&info->channel);
1578 set_bit((info->aiop * 8) + info->chan, 1578 set_bit((info->aiop * 8) + info->chan,
1579 (void *) &xmit_flags[info->board]); 1579 (void *) &xmit_flags[info->board]);
1580 } 1580 }
1581 1581
1582 /* 1582 /*
1583 * rp_wait_until_sent() --- wait until the transmitter is empty 1583 * rp_wait_until_sent() --- wait until the transmitter is empty
1584 */ 1584 */
1585 static void rp_wait_until_sent(struct tty_struct *tty, int timeout) 1585 static void rp_wait_until_sent(struct tty_struct *tty, int timeout)
1586 { 1586 {
1587 struct r_port *info = tty->driver_data; 1587 struct r_port *info = tty->driver_data;
1588 CHANNEL_t *cp; 1588 CHANNEL_t *cp;
1589 unsigned long orig_jiffies; 1589 unsigned long orig_jiffies;
1590 int check_time, exit_time; 1590 int check_time, exit_time;
1591 int txcnt; 1591 int txcnt;
1592 1592
1593 if (rocket_paranoia_check(info, "rp_wait_until_sent")) 1593 if (rocket_paranoia_check(info, "rp_wait_until_sent"))
1594 return; 1594 return;
1595 1595
1596 cp = &info->channel; 1596 cp = &info->channel;
1597 1597
1598 orig_jiffies = jiffies; 1598 orig_jiffies = jiffies;
1599 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT 1599 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT
1600 printk(KERN_INFO "In RP_wait_until_sent(%d) (jiff=%lu)...\n", timeout, 1600 printk(KERN_INFO "In RP_wait_until_sent(%d) (jiff=%lu)...\n", timeout,
1601 jiffies); 1601 jiffies);
1602 printk(KERN_INFO "cps=%d...\n", info->cps); 1602 printk(KERN_INFO "cps=%d...\n", info->cps);
1603 #endif 1603 #endif
1604 lock_kernel(); 1604 lock_kernel();
1605 while (1) { 1605 while (1) {
1606 txcnt = sGetTxCnt(cp); 1606 txcnt = sGetTxCnt(cp);
1607 if (!txcnt) { 1607 if (!txcnt) {
1608 if (sGetChanStatusLo(cp) & TXSHRMT) 1608 if (sGetChanStatusLo(cp) & TXSHRMT)
1609 break; 1609 break;
1610 check_time = (HZ / info->cps) / 5; 1610 check_time = (HZ / info->cps) / 5;
1611 } else { 1611 } else {
1612 check_time = HZ * txcnt / info->cps; 1612 check_time = HZ * txcnt / info->cps;
1613 } 1613 }
1614 if (timeout) { 1614 if (timeout) {
1615 exit_time = orig_jiffies + timeout - jiffies; 1615 exit_time = orig_jiffies + timeout - jiffies;
1616 if (exit_time <= 0) 1616 if (exit_time <= 0)
1617 break; 1617 break;
1618 if (exit_time < check_time) 1618 if (exit_time < check_time)
1619 check_time = exit_time; 1619 check_time = exit_time;
1620 } 1620 }
1621 if (check_time == 0) 1621 if (check_time == 0)
1622 check_time = 1; 1622 check_time = 1;
1623 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT 1623 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT
1624 printk(KERN_INFO "txcnt = %d (jiff=%lu,check=%d)...\n", txcnt, 1624 printk(KERN_INFO "txcnt = %d (jiff=%lu,check=%d)...\n", txcnt,
1625 jiffies, check_time); 1625 jiffies, check_time);
1626 #endif 1626 #endif
1627 msleep_interruptible(jiffies_to_msecs(check_time)); 1627 msleep_interruptible(jiffies_to_msecs(check_time));
1628 if (signal_pending(current)) 1628 if (signal_pending(current))
1629 break; 1629 break;
1630 } 1630 }
1631 __set_current_state(TASK_RUNNING); 1631 __set_current_state(TASK_RUNNING);
1632 unlock_kernel(); 1632 unlock_kernel();
1633 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT 1633 #ifdef ROCKET_DEBUG_WAIT_UNTIL_SENT
1634 printk(KERN_INFO "txcnt = %d (jiff=%lu)...done\n", txcnt, jiffies); 1634 printk(KERN_INFO "txcnt = %d (jiff=%lu)...done\n", txcnt, jiffies);
1635 #endif 1635 #endif
1636 } 1636 }
1637 1637
1638 /* 1638 /*
1639 * rp_hangup() --- called by tty_hangup() when a hangup is signaled. 1639 * rp_hangup() --- called by tty_hangup() when a hangup is signaled.
1640 */ 1640 */
1641 static void rp_hangup(struct tty_struct *tty) 1641 static void rp_hangup(struct tty_struct *tty)
1642 { 1642 {
1643 CHANNEL_t *cp; 1643 CHANNEL_t *cp;
1644 struct r_port *info = tty->driver_data; 1644 struct r_port *info = tty->driver_data;
1645 1645
1646 if (rocket_paranoia_check(info, "rp_hangup")) 1646 if (rocket_paranoia_check(info, "rp_hangup"))
1647 return; 1647 return;
1648 1648
1649 #if (defined(ROCKET_DEBUG_OPEN) || defined(ROCKET_DEBUG_HANGUP)) 1649 #if (defined(ROCKET_DEBUG_OPEN) || defined(ROCKET_DEBUG_HANGUP))
1650 printk(KERN_INFO "rp_hangup of ttyR%d...\n", info->line); 1650 printk(KERN_INFO "rp_hangup of ttyR%d...\n", info->line);
1651 #endif 1651 #endif
1652 rp_flush_buffer(tty); 1652 rp_flush_buffer(tty);
1653 if (info->flags & ASYNC_CLOSING) 1653 if (info->port.flags & ASYNC_CLOSING)
1654 return; 1654 return;
1655 if (info->port.count) 1655 if (info->port.count)
1656 atomic_dec(&rp_num_ports_open); 1656 atomic_dec(&rp_num_ports_open);
1657 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1657 clear_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1658 1658
1659 info->port.count = 0; 1659 info->port.count = 0;
1660 info->flags &= ~ASYNC_NORMAL_ACTIVE; 1660 info->port.flags &= ~ASYNC_NORMAL_ACTIVE;
1661 info->port.tty = NULL; 1661 info->port.tty = NULL;
1662 1662
1663 cp = &info->channel; 1663 cp = &info->channel;
1664 sDisRxFIFO(cp); 1664 sDisRxFIFO(cp);
1665 sDisTransmit(cp); 1665 sDisTransmit(cp);
1666 sDisInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN)); 1666 sDisInterrupts(cp, (TXINT_EN | MCINT_EN | RXINT_EN | SRCINT_EN | CHANINT_EN));
1667 sDisCTSFlowCtl(cp); 1667 sDisCTSFlowCtl(cp);
1668 sDisTxSoftFlowCtl(cp); 1668 sDisTxSoftFlowCtl(cp);
1669 sClrTxXOFF(cp); 1669 sClrTxXOFF(cp);
1670 info->flags &= ~ASYNC_INITIALIZED; 1670 info->port.flags &= ~ASYNC_INITIALIZED;
1671 1671
1672 wake_up_interruptible(&info->port.open_wait); 1672 wake_up_interruptible(&info->port.open_wait);
1673 } 1673 }
1674 1674
1675 /* 1675 /*
1676 * Exception handler - write char routine. The RocketPort driver uses a 1676 * Exception handler - write char routine. The RocketPort driver uses a
1677 * double-buffering strategy, with the twist that if the in-memory CPU 1677 * double-buffering strategy, with the twist that if the in-memory CPU
1678 * buffer is empty, and there's space in the transmit FIFO, the 1678 * buffer is empty, and there's space in the transmit FIFO, the
1679 * writing routines will write directly to transmit FIFO. 1679 * writing routines will write directly to transmit FIFO.
1680 * Write buffer and counters protected by spinlocks 1680 * Write buffer and counters protected by spinlocks
1681 */ 1681 */
1682 static int rp_put_char(struct tty_struct *tty, unsigned char ch) 1682 static int rp_put_char(struct tty_struct *tty, unsigned char ch)
1683 { 1683 {
1684 struct r_port *info = tty->driver_data; 1684 struct r_port *info = tty->driver_data;
1685 CHANNEL_t *cp; 1685 CHANNEL_t *cp;
1686 unsigned long flags; 1686 unsigned long flags;
1687 1687
1688 if (rocket_paranoia_check(info, "rp_put_char")) 1688 if (rocket_paranoia_check(info, "rp_put_char"))
1689 return 0; 1689 return 0;
1690 1690
1691 /* 1691 /*
1692 * Grab the port write mutex, locking out other processes that try to 1692 * Grab the port write mutex, locking out other processes that try to
1693 * write to this port 1693 * write to this port
1694 */ 1694 */
1695 mutex_lock(&info->write_mtx); 1695 mutex_lock(&info->write_mtx);
1696 1696
1697 #ifdef ROCKET_DEBUG_WRITE 1697 #ifdef ROCKET_DEBUG_WRITE
1698 printk(KERN_INFO "rp_put_char %c...\n", ch); 1698 printk(KERN_INFO "rp_put_char %c...\n", ch);
1699 #endif 1699 #endif
1700 1700
1701 spin_lock_irqsave(&info->slock, flags); 1701 spin_lock_irqsave(&info->slock, flags);
1702 cp = &info->channel; 1702 cp = &info->channel;
1703 1703
1704 if (!tty->stopped && !tty->hw_stopped && info->xmit_fifo_room == 0) 1704 if (!tty->stopped && !tty->hw_stopped && info->xmit_fifo_room == 0)
1705 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp); 1705 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp);
1706 1706
1707 if (tty->stopped || tty->hw_stopped || info->xmit_fifo_room == 0 || info->xmit_cnt != 0) { 1707 if (tty->stopped || tty->hw_stopped || info->xmit_fifo_room == 0 || info->xmit_cnt != 0) {
1708 info->xmit_buf[info->xmit_head++] = ch; 1708 info->xmit_buf[info->xmit_head++] = ch;
1709 info->xmit_head &= XMIT_BUF_SIZE - 1; 1709 info->xmit_head &= XMIT_BUF_SIZE - 1;
1710 info->xmit_cnt++; 1710 info->xmit_cnt++;
1711 set_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1711 set_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1712 } else { 1712 } else {
1713 sOutB(sGetTxRxDataIO(cp), ch); 1713 sOutB(sGetTxRxDataIO(cp), ch);
1714 info->xmit_fifo_room--; 1714 info->xmit_fifo_room--;
1715 } 1715 }
1716 spin_unlock_irqrestore(&info->slock, flags); 1716 spin_unlock_irqrestore(&info->slock, flags);
1717 mutex_unlock(&info->write_mtx); 1717 mutex_unlock(&info->write_mtx);
1718 return 1; 1718 return 1;
1719 } 1719 }
1720 1720
1721 /* 1721 /*
1722 * Exception handler - write routine, called when user app writes to the device. 1722 * Exception handler - write routine, called when user app writes to the device.
1723 * A per port write mutex is used to protect from another process writing to 1723 * A per port write mutex is used to protect from another process writing to
1724 * this port at the same time. This other process could be running on the other CPU 1724 * this port at the same time. This other process could be running on the other CPU
1725 * or get control of the CPU if the copy_from_user() blocks due to a page fault (swapped out). 1725 * or get control of the CPU if the copy_from_user() blocks due to a page fault (swapped out).
1726 * Spinlocks protect the info xmit members. 1726 * Spinlocks protect the info xmit members.
1727 */ 1727 */
1728 static int rp_write(struct tty_struct *tty, 1728 static int rp_write(struct tty_struct *tty,
1729 const unsigned char *buf, int count) 1729 const unsigned char *buf, int count)
1730 { 1730 {
1731 struct r_port *info = tty->driver_data; 1731 struct r_port *info = tty->driver_data;
1732 CHANNEL_t *cp; 1732 CHANNEL_t *cp;
1733 const unsigned char *b; 1733 const unsigned char *b;
1734 int c, retval = 0; 1734 int c, retval = 0;
1735 unsigned long flags; 1735 unsigned long flags;
1736 1736
1737 if (count <= 0 || rocket_paranoia_check(info, "rp_write")) 1737 if (count <= 0 || rocket_paranoia_check(info, "rp_write"))
1738 return 0; 1738 return 0;
1739 1739
1740 if (mutex_lock_interruptible(&info->write_mtx)) 1740 if (mutex_lock_interruptible(&info->write_mtx))
1741 return -ERESTARTSYS; 1741 return -ERESTARTSYS;
1742 1742
1743 #ifdef ROCKET_DEBUG_WRITE 1743 #ifdef ROCKET_DEBUG_WRITE
1744 printk(KERN_INFO "rp_write %d chars...\n", count); 1744 printk(KERN_INFO "rp_write %d chars...\n", count);
1745 #endif 1745 #endif
1746 cp = &info->channel; 1746 cp = &info->channel;
1747 1747
1748 if (!tty->stopped && !tty->hw_stopped && info->xmit_fifo_room < count) 1748 if (!tty->stopped && !tty->hw_stopped && info->xmit_fifo_room < count)
1749 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp); 1749 info->xmit_fifo_room = TXFIFO_SIZE - sGetTxCnt(cp);
1750 1750
1751 /* 1751 /*
1752 * If the write queue for the port is empty, and there is FIFO space, stuff bytes 1752 * If the write queue for the port is empty, and there is FIFO space, stuff bytes
1753 * into FIFO. Use the write queue for temp storage. 1753 * into FIFO. Use the write queue for temp storage.
1754 */ 1754 */
1755 if (!tty->stopped && !tty->hw_stopped && info->xmit_cnt == 0 && info->xmit_fifo_room > 0) { 1755 if (!tty->stopped && !tty->hw_stopped && info->xmit_cnt == 0 && info->xmit_fifo_room > 0) {
1756 c = min(count, info->xmit_fifo_room); 1756 c = min(count, info->xmit_fifo_room);
1757 b = buf; 1757 b = buf;
1758 1758
1759 /* Push data into FIFO, 2 bytes at a time */ 1759 /* Push data into FIFO, 2 bytes at a time */
1760 sOutStrW(sGetTxRxDataIO(cp), (unsigned short *) b, c / 2); 1760 sOutStrW(sGetTxRxDataIO(cp), (unsigned short *) b, c / 2);
1761 1761
1762 /* If there is a byte remaining, write it */ 1762 /* If there is a byte remaining, write it */
1763 if (c & 1) 1763 if (c & 1)
1764 sOutB(sGetTxRxDataIO(cp), b[c - 1]); 1764 sOutB(sGetTxRxDataIO(cp), b[c - 1]);
1765 1765
1766 retval += c; 1766 retval += c;
1767 buf += c; 1767 buf += c;
1768 count -= c; 1768 count -= c;
1769 1769
1770 spin_lock_irqsave(&info->slock, flags); 1770 spin_lock_irqsave(&info->slock, flags);
1771 info->xmit_fifo_room -= c; 1771 info->xmit_fifo_room -= c;
1772 spin_unlock_irqrestore(&info->slock, flags); 1772 spin_unlock_irqrestore(&info->slock, flags);
1773 } 1773 }
1774 1774
1775 /* If count is zero, we wrote it all and are done */ 1775 /* If count is zero, we wrote it all and are done */
1776 if (!count) 1776 if (!count)
1777 goto end; 1777 goto end;
1778 1778
1779 /* Write remaining data into the port's xmit_buf */ 1779 /* Write remaining data into the port's xmit_buf */
1780 while (1) { 1780 while (1) {
1781 if (!info->port.tty) /* Seemingly obligatory check... */ 1781 if (!info->port.tty) /* Seemingly obligatory check... */
1782 goto end; 1782 goto end;
1783 c = min(count, XMIT_BUF_SIZE - info->xmit_cnt - 1); 1783 c = min(count, XMIT_BUF_SIZE - info->xmit_cnt - 1);
1784 c = min(c, XMIT_BUF_SIZE - info->xmit_head); 1784 c = min(c, XMIT_BUF_SIZE - info->xmit_head);
1785 if (c <= 0) 1785 if (c <= 0)
1786 break; 1786 break;
1787 1787
1788 b = buf; 1788 b = buf;
1789 memcpy(info->xmit_buf + info->xmit_head, b, c); 1789 memcpy(info->xmit_buf + info->xmit_head, b, c);
1790 1790
1791 spin_lock_irqsave(&info->slock, flags); 1791 spin_lock_irqsave(&info->slock, flags);
1792 info->xmit_head = 1792 info->xmit_head =
1793 (info->xmit_head + c) & (XMIT_BUF_SIZE - 1); 1793 (info->xmit_head + c) & (XMIT_BUF_SIZE - 1);
1794 info->xmit_cnt += c; 1794 info->xmit_cnt += c;
1795 spin_unlock_irqrestore(&info->slock, flags); 1795 spin_unlock_irqrestore(&info->slock, flags);
1796 1796
1797 buf += c; 1797 buf += c;
1798 count -= c; 1798 count -= c;
1799 retval += c; 1799 retval += c;
1800 } 1800 }
1801 1801
1802 if ((retval > 0) && !tty->stopped && !tty->hw_stopped) 1802 if ((retval > 0) && !tty->stopped && !tty->hw_stopped)
1803 set_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]); 1803 set_bit((info->aiop * 8) + info->chan, (void *) &xmit_flags[info->board]);
1804 1804
1805 end: 1805 end:
1806 if (info->xmit_cnt < WAKEUP_CHARS) { 1806 if (info->xmit_cnt < WAKEUP_CHARS) {
1807 tty_wakeup(tty); 1807 tty_wakeup(tty);
1808 #ifdef ROCKETPORT_HAVE_POLL_WAIT 1808 #ifdef ROCKETPORT_HAVE_POLL_WAIT
1809 wake_up_interruptible(&tty->poll_wait); 1809 wake_up_interruptible(&tty->poll_wait);
1810 #endif 1810 #endif
1811 } 1811 }
1812 mutex_unlock(&info->write_mtx); 1812 mutex_unlock(&info->write_mtx);
1813 return retval; 1813 return retval;
1814 } 1814 }
1815 1815
1816 /* 1816 /*
1817 * Return the number of characters that can be sent. We estimate 1817 * Return the number of characters that can be sent. We estimate
1818 * only using the in-memory transmit buffer only, and ignore the 1818 * only using the in-memory transmit buffer only, and ignore the
1819 * potential space in the transmit FIFO. 1819 * potential space in the transmit FIFO.
1820 */ 1820 */
1821 static int rp_write_room(struct tty_struct *tty) 1821 static int rp_write_room(struct tty_struct *tty)
1822 { 1822 {
1823 struct r_port *info = tty->driver_data; 1823 struct r_port *info = tty->driver_data;
1824 int ret; 1824 int ret;
1825 1825
1826 if (rocket_paranoia_check(info, "rp_write_room")) 1826 if (rocket_paranoia_check(info, "rp_write_room"))
1827 return 0; 1827 return 0;
1828 1828
1829 ret = XMIT_BUF_SIZE - info->xmit_cnt - 1; 1829 ret = XMIT_BUF_SIZE - info->xmit_cnt - 1;
1830 if (ret < 0) 1830 if (ret < 0)
1831 ret = 0; 1831 ret = 0;
1832 #ifdef ROCKET_DEBUG_WRITE 1832 #ifdef ROCKET_DEBUG_WRITE
1833 printk(KERN_INFO "rp_write_room returns %d...\n", ret); 1833 printk(KERN_INFO "rp_write_room returns %d...\n", ret);
1834 #endif 1834 #endif
1835 return ret; 1835 return ret;
1836 } 1836 }
1837 1837
1838 /* 1838 /*
1839 * Return the number of characters in the buffer. Again, this only 1839 * Return the number of characters in the buffer. Again, this only
1840 * counts those characters in the in-memory transmit buffer. 1840 * counts those characters in the in-memory transmit buffer.
1841 */ 1841 */
1842 static int rp_chars_in_buffer(struct tty_struct *tty) 1842 static int rp_chars_in_buffer(struct tty_struct *tty)
1843 { 1843 {
1844 struct r_port *info = tty->driver_data; 1844 struct r_port *info = tty->driver_data;
1845 CHANNEL_t *cp; 1845 CHANNEL_t *cp;
1846 1846
1847 if (rocket_paranoia_check(info, "rp_chars_in_buffer")) 1847 if (rocket_paranoia_check(info, "rp_chars_in_buffer"))
1848 return 0; 1848 return 0;
1849 1849
1850 cp = &info->channel; 1850 cp = &info->channel;
1851 1851
1852 #ifdef ROCKET_DEBUG_WRITE 1852 #ifdef ROCKET_DEBUG_WRITE
1853 printk(KERN_INFO "rp_chars_in_buffer returns %d...\n", info->xmit_cnt); 1853 printk(KERN_INFO "rp_chars_in_buffer returns %d...\n", info->xmit_cnt);
1854 #endif 1854 #endif
1855 return info->xmit_cnt; 1855 return info->xmit_cnt;
1856 } 1856 }
1857 1857
1858 /* 1858 /*
1859 * Flushes the TX fifo for a port, deletes data in the xmit_buf stored in the 1859 * Flushes the TX fifo for a port, deletes data in the xmit_buf stored in the
1860 * r_port struct for the port. Note that spinlock are used to protect info members, 1860 * r_port struct for the port. Note that spinlock are used to protect info members,
1861 * do not call this function if the spinlock is already held. 1861 * do not call this function if the spinlock is already held.
1862 */ 1862 */
1863 static void rp_flush_buffer(struct tty_struct *tty) 1863 static void rp_flush_buffer(struct tty_struct *tty)
1864 { 1864 {
1865 struct r_port *info = tty->driver_data; 1865 struct r_port *info = tty->driver_data;
1866 CHANNEL_t *cp; 1866 CHANNEL_t *cp;
1867 unsigned long flags; 1867 unsigned long flags;
1868 1868
1869 if (rocket_paranoia_check(info, "rp_flush_buffer")) 1869 if (rocket_paranoia_check(info, "rp_flush_buffer"))
1870 return; 1870 return;
1871 1871
1872 spin_lock_irqsave(&info->slock, flags); 1872 spin_lock_irqsave(&info->slock, flags);
1873 info->xmit_cnt = info->xmit_head = info->xmit_tail = 0; 1873 info->xmit_cnt = info->xmit_head = info->xmit_tail = 0;
1874 spin_unlock_irqrestore(&info->slock, flags); 1874 spin_unlock_irqrestore(&info->slock, flags);
1875 1875
1876 #ifdef ROCKETPORT_HAVE_POLL_WAIT 1876 #ifdef ROCKETPORT_HAVE_POLL_WAIT
1877 wake_up_interruptible(&tty->poll_wait); 1877 wake_up_interruptible(&tty->poll_wait);
1878 #endif 1878 #endif
1879 tty_wakeup(tty); 1879 tty_wakeup(tty);
1880 1880
1881 cp = &info->channel; 1881 cp = &info->channel;
1882 sFlushTxFIFO(cp); 1882 sFlushTxFIFO(cp);
1883 } 1883 }
1884 1884
1885 #ifdef CONFIG_PCI 1885 #ifdef CONFIG_PCI
1886 1886
1887 static struct pci_device_id __devinitdata rocket_pci_ids[] = { 1887 static struct pci_device_id __devinitdata rocket_pci_ids[] = {
1888 { PCI_DEVICE(PCI_VENDOR_ID_RP, PCI_ANY_ID) }, 1888 { PCI_DEVICE(PCI_VENDOR_ID_RP, PCI_ANY_ID) },
1889 { } 1889 { }
1890 }; 1890 };
1891 MODULE_DEVICE_TABLE(pci, rocket_pci_ids); 1891 MODULE_DEVICE_TABLE(pci, rocket_pci_ids);
1892 1892
1893 /* 1893 /*
1894 * Called when a PCI card is found. Retrieves and stores model information, 1894 * Called when a PCI card is found. Retrieves and stores model information,
1895 * init's aiopic and serial port hardware. 1895 * init's aiopic and serial port hardware.
1896 * Inputs: i is the board number (0-n) 1896 * Inputs: i is the board number (0-n)
1897 */ 1897 */
1898 static __init int register_PCI(int i, struct pci_dev *dev) 1898 static __init int register_PCI(int i, struct pci_dev *dev)
1899 { 1899 {
1900 int num_aiops, aiop, max_num_aiops, num_chan, chan; 1900 int num_aiops, aiop, max_num_aiops, num_chan, chan;
1901 unsigned int aiopio[MAX_AIOPS_PER_BOARD]; 1901 unsigned int aiopio[MAX_AIOPS_PER_BOARD];
1902 char *str, *board_type; 1902 char *str, *board_type;
1903 CONTROLLER_t *ctlp; 1903 CONTROLLER_t *ctlp;
1904 1904
1905 int fast_clock = 0; 1905 int fast_clock = 0;
1906 int altChanRingIndicator = 0; 1906 int altChanRingIndicator = 0;
1907 int ports_per_aiop = 8; 1907 int ports_per_aiop = 8;
1908 WordIO_t ConfigIO = 0; 1908 WordIO_t ConfigIO = 0;
1909 ByteIO_t UPCIRingInd = 0; 1909 ByteIO_t UPCIRingInd = 0;
1910 1910
1911 if (!dev || pci_enable_device(dev)) 1911 if (!dev || pci_enable_device(dev))
1912 return 0; 1912 return 0;
1913 1913
1914 rcktpt_io_addr[i] = pci_resource_start(dev, 0); 1914 rcktpt_io_addr[i] = pci_resource_start(dev, 0);
1915 1915
1916 rcktpt_type[i] = ROCKET_TYPE_NORMAL; 1916 rcktpt_type[i] = ROCKET_TYPE_NORMAL;
1917 rocketModel[i].loadrm2 = 0; 1917 rocketModel[i].loadrm2 = 0;
1918 rocketModel[i].startingPortNumber = nextLineNumber; 1918 rocketModel[i].startingPortNumber = nextLineNumber;
1919 1919
1920 /* Depending on the model, set up some config variables */ 1920 /* Depending on the model, set up some config variables */
1921 switch (dev->device) { 1921 switch (dev->device) {
1922 case PCI_DEVICE_ID_RP4QUAD: 1922 case PCI_DEVICE_ID_RP4QUAD:
1923 str = "Quadcable"; 1923 str = "Quadcable";
1924 max_num_aiops = 1; 1924 max_num_aiops = 1;
1925 ports_per_aiop = 4; 1925 ports_per_aiop = 4;
1926 rocketModel[i].model = MODEL_RP4QUAD; 1926 rocketModel[i].model = MODEL_RP4QUAD;
1927 strcpy(rocketModel[i].modelString, "RocketPort 4 port w/quad cable"); 1927 strcpy(rocketModel[i].modelString, "RocketPort 4 port w/quad cable");
1928 rocketModel[i].numPorts = 4; 1928 rocketModel[i].numPorts = 4;
1929 break; 1929 break;
1930 case PCI_DEVICE_ID_RP8OCTA: 1930 case PCI_DEVICE_ID_RP8OCTA:
1931 str = "Octacable"; 1931 str = "Octacable";
1932 max_num_aiops = 1; 1932 max_num_aiops = 1;
1933 rocketModel[i].model = MODEL_RP8OCTA; 1933 rocketModel[i].model = MODEL_RP8OCTA;
1934 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/octa cable"); 1934 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/octa cable");
1935 rocketModel[i].numPorts = 8; 1935 rocketModel[i].numPorts = 8;
1936 break; 1936 break;
1937 case PCI_DEVICE_ID_URP8OCTA: 1937 case PCI_DEVICE_ID_URP8OCTA:
1938 str = "Octacable"; 1938 str = "Octacable";
1939 max_num_aiops = 1; 1939 max_num_aiops = 1;
1940 rocketModel[i].model = MODEL_UPCI_RP8OCTA; 1940 rocketModel[i].model = MODEL_UPCI_RP8OCTA;
1941 strcpy(rocketModel[i].modelString, "RocketPort UPCI 8 port w/octa cable"); 1941 strcpy(rocketModel[i].modelString, "RocketPort UPCI 8 port w/octa cable");
1942 rocketModel[i].numPorts = 8; 1942 rocketModel[i].numPorts = 8;
1943 break; 1943 break;
1944 case PCI_DEVICE_ID_RP8INTF: 1944 case PCI_DEVICE_ID_RP8INTF:
1945 str = "8"; 1945 str = "8";
1946 max_num_aiops = 1; 1946 max_num_aiops = 1;
1947 rocketModel[i].model = MODEL_RP8INTF; 1947 rocketModel[i].model = MODEL_RP8INTF;
1948 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/external I/F"); 1948 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/external I/F");
1949 rocketModel[i].numPorts = 8; 1949 rocketModel[i].numPorts = 8;
1950 break; 1950 break;
1951 case PCI_DEVICE_ID_URP8INTF: 1951 case PCI_DEVICE_ID_URP8INTF:
1952 str = "8"; 1952 str = "8";
1953 max_num_aiops = 1; 1953 max_num_aiops = 1;
1954 rocketModel[i].model = MODEL_UPCI_RP8INTF; 1954 rocketModel[i].model = MODEL_UPCI_RP8INTF;
1955 strcpy(rocketModel[i].modelString, "RocketPort UPCI 8 port w/external I/F"); 1955 strcpy(rocketModel[i].modelString, "RocketPort UPCI 8 port w/external I/F");
1956 rocketModel[i].numPorts = 8; 1956 rocketModel[i].numPorts = 8;
1957 break; 1957 break;
1958 case PCI_DEVICE_ID_RP8J: 1958 case PCI_DEVICE_ID_RP8J:
1959 str = "8J"; 1959 str = "8J";
1960 max_num_aiops = 1; 1960 max_num_aiops = 1;
1961 rocketModel[i].model = MODEL_RP8J; 1961 rocketModel[i].model = MODEL_RP8J;
1962 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/RJ11 connectors"); 1962 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/RJ11 connectors");
1963 rocketModel[i].numPorts = 8; 1963 rocketModel[i].numPorts = 8;
1964 break; 1964 break;
1965 case PCI_DEVICE_ID_RP4J: 1965 case PCI_DEVICE_ID_RP4J:
1966 str = "4J"; 1966 str = "4J";
1967 max_num_aiops = 1; 1967 max_num_aiops = 1;
1968 ports_per_aiop = 4; 1968 ports_per_aiop = 4;
1969 rocketModel[i].model = MODEL_RP4J; 1969 rocketModel[i].model = MODEL_RP4J;
1970 strcpy(rocketModel[i].modelString, "RocketPort 4 port w/RJ45 connectors"); 1970 strcpy(rocketModel[i].modelString, "RocketPort 4 port w/RJ45 connectors");
1971 rocketModel[i].numPorts = 4; 1971 rocketModel[i].numPorts = 4;
1972 break; 1972 break;
1973 case PCI_DEVICE_ID_RP8SNI: 1973 case PCI_DEVICE_ID_RP8SNI:
1974 str = "8 (DB78 Custom)"; 1974 str = "8 (DB78 Custom)";
1975 max_num_aiops = 1; 1975 max_num_aiops = 1;
1976 rocketModel[i].model = MODEL_RP8SNI; 1976 rocketModel[i].model = MODEL_RP8SNI;
1977 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/ custom DB78"); 1977 strcpy(rocketModel[i].modelString, "RocketPort 8 port w/ custom DB78");
1978 rocketModel[i].numPorts = 8; 1978 rocketModel[i].numPorts = 8;
1979 break; 1979 break;
1980 case PCI_DEVICE_ID_RP16SNI: 1980 case PCI_DEVICE_ID_RP16SNI:
1981 str = "16 (DB78 Custom)"; 1981 str = "16 (DB78 Custom)";
1982 max_num_aiops = 2; 1982 max_num_aiops = 2;
1983 rocketModel[i].model = MODEL_RP16SNI; 1983 rocketModel[i].model = MODEL_RP16SNI;
1984 strcpy(rocketModel[i].modelString, "RocketPort 16 port w/ custom DB78"); 1984 strcpy(rocketModel[i].modelString, "RocketPort 16 port w/ custom DB78");
1985 rocketModel[i].numPorts = 16; 1985 rocketModel[i].numPorts = 16;
1986 break; 1986 break;
1987 case PCI_DEVICE_ID_RP16INTF: 1987 case PCI_DEVICE_ID_RP16INTF:
1988 str = "16"; 1988 str = "16";
1989 max_num_aiops = 2; 1989 max_num_aiops = 2;
1990 rocketModel[i].model = MODEL_RP16INTF; 1990 rocketModel[i].model = MODEL_RP16INTF;
1991 strcpy(rocketModel[i].modelString, "RocketPort 16 port w/external I/F"); 1991 strcpy(rocketModel[i].modelString, "RocketPort 16 port w/external I/F");
1992 rocketModel[i].numPorts = 16; 1992 rocketModel[i].numPorts = 16;
1993 break; 1993 break;
1994 case PCI_DEVICE_ID_URP16INTF: 1994 case PCI_DEVICE_ID_URP16INTF:
1995 str = "16"; 1995 str = "16";
1996 max_num_aiops = 2; 1996 max_num_aiops = 2;
1997 rocketModel[i].model = MODEL_UPCI_RP16INTF; 1997 rocketModel[i].model = MODEL_UPCI_RP16INTF;
1998 strcpy(rocketModel[i].modelString, "RocketPort UPCI 16 port w/external I/F"); 1998 strcpy(rocketModel[i].modelString, "RocketPort UPCI 16 port w/external I/F");
1999 rocketModel[i].numPorts = 16; 1999 rocketModel[i].numPorts = 16;
2000 break; 2000 break;
2001 case PCI_DEVICE_ID_CRP16INTF: 2001 case PCI_DEVICE_ID_CRP16INTF:
2002 str = "16"; 2002 str = "16";
2003 max_num_aiops = 2; 2003 max_num_aiops = 2;
2004 rocketModel[i].model = MODEL_CPCI_RP16INTF; 2004 rocketModel[i].model = MODEL_CPCI_RP16INTF;
2005 strcpy(rocketModel[i].modelString, "RocketPort Compact PCI 16 port w/external I/F"); 2005 strcpy(rocketModel[i].modelString, "RocketPort Compact PCI 16 port w/external I/F");
2006 rocketModel[i].numPorts = 16; 2006 rocketModel[i].numPorts = 16;
2007 break; 2007 break;
2008 case PCI_DEVICE_ID_RP32INTF: 2008 case PCI_DEVICE_ID_RP32INTF:
2009 str = "32"; 2009 str = "32";
2010 max_num_aiops = 4; 2010 max_num_aiops = 4;
2011 rocketModel[i].model = MODEL_RP32INTF; 2011 rocketModel[i].model = MODEL_RP32INTF;
2012 strcpy(rocketModel[i].modelString, "RocketPort 32 port w/external I/F"); 2012 strcpy(rocketModel[i].modelString, "RocketPort 32 port w/external I/F");
2013 rocketModel[i].numPorts = 32; 2013 rocketModel[i].numPorts = 32;
2014 break; 2014 break;
2015 case PCI_DEVICE_ID_URP32INTF: 2015 case PCI_DEVICE_ID_URP32INTF:
2016 str = "32"; 2016 str = "32";
2017 max_num_aiops = 4; 2017 max_num_aiops = 4;
2018 rocketModel[i].model = MODEL_UPCI_RP32INTF; 2018 rocketModel[i].model = MODEL_UPCI_RP32INTF;
2019 strcpy(rocketModel[i].modelString, "RocketPort UPCI 32 port w/external I/F"); 2019 strcpy(rocketModel[i].modelString, "RocketPort UPCI 32 port w/external I/F");
2020 rocketModel[i].numPorts = 32; 2020 rocketModel[i].numPorts = 32;
2021 break; 2021 break;
2022 case PCI_DEVICE_ID_RPP4: 2022 case PCI_DEVICE_ID_RPP4:
2023 str = "Plus Quadcable"; 2023 str = "Plus Quadcable";
2024 max_num_aiops = 1; 2024 max_num_aiops = 1;
2025 ports_per_aiop = 4; 2025 ports_per_aiop = 4;
2026 altChanRingIndicator++; 2026 altChanRingIndicator++;
2027 fast_clock++; 2027 fast_clock++;
2028 rocketModel[i].model = MODEL_RPP4; 2028 rocketModel[i].model = MODEL_RPP4;
2029 strcpy(rocketModel[i].modelString, "RocketPort Plus 4 port"); 2029 strcpy(rocketModel[i].modelString, "RocketPort Plus 4 port");
2030 rocketModel[i].numPorts = 4; 2030 rocketModel[i].numPorts = 4;
2031 break; 2031 break;
2032 case PCI_DEVICE_ID_RPP8: 2032 case PCI_DEVICE_ID_RPP8:
2033 str = "Plus Octacable"; 2033 str = "Plus Octacable";
2034 max_num_aiops = 2; 2034 max_num_aiops = 2;
2035 ports_per_aiop = 4; 2035 ports_per_aiop = 4;
2036 altChanRingIndicator++; 2036 altChanRingIndicator++;
2037 fast_clock++; 2037 fast_clock++;
2038 rocketModel[i].model = MODEL_RPP8; 2038 rocketModel[i].model = MODEL_RPP8;
2039 strcpy(rocketModel[i].modelString, "RocketPort Plus 8 port"); 2039 strcpy(rocketModel[i].modelString, "RocketPort Plus 8 port");
2040 rocketModel[i].numPorts = 8; 2040 rocketModel[i].numPorts = 8;
2041 break; 2041 break;
2042 case PCI_DEVICE_ID_RP2_232: 2042 case PCI_DEVICE_ID_RP2_232:
2043 str = "Plus 2 (RS-232)"; 2043 str = "Plus 2 (RS-232)";
2044 max_num_aiops = 1; 2044 max_num_aiops = 1;
2045 ports_per_aiop = 2; 2045 ports_per_aiop = 2;
2046 altChanRingIndicator++; 2046 altChanRingIndicator++;
2047 fast_clock++; 2047 fast_clock++;
2048 rocketModel[i].model = MODEL_RP2_232; 2048 rocketModel[i].model = MODEL_RP2_232;
2049 strcpy(rocketModel[i].modelString, "RocketPort Plus 2 port RS232"); 2049 strcpy(rocketModel[i].modelString, "RocketPort Plus 2 port RS232");
2050 rocketModel[i].numPorts = 2; 2050 rocketModel[i].numPorts = 2;
2051 break; 2051 break;
2052 case PCI_DEVICE_ID_RP2_422: 2052 case PCI_DEVICE_ID_RP2_422:
2053 str = "Plus 2 (RS-422)"; 2053 str = "Plus 2 (RS-422)";
2054 max_num_aiops = 1; 2054 max_num_aiops = 1;
2055 ports_per_aiop = 2; 2055 ports_per_aiop = 2;
2056 altChanRingIndicator++; 2056 altChanRingIndicator++;
2057 fast_clock++; 2057 fast_clock++;
2058 rocketModel[i].model = MODEL_RP2_422; 2058 rocketModel[i].model = MODEL_RP2_422;
2059 strcpy(rocketModel[i].modelString, "RocketPort Plus 2 port RS422"); 2059 strcpy(rocketModel[i].modelString, "RocketPort Plus 2 port RS422");
2060 rocketModel[i].numPorts = 2; 2060 rocketModel[i].numPorts = 2;
2061 break; 2061 break;
2062 case PCI_DEVICE_ID_RP6M: 2062 case PCI_DEVICE_ID_RP6M:
2063 2063
2064 max_num_aiops = 1; 2064 max_num_aiops = 1;
2065 ports_per_aiop = 6; 2065 ports_per_aiop = 6;
2066 str = "6-port"; 2066 str = "6-port";
2067 2067
2068 /* If revision is 1, the rocketmodem flash must be loaded. 2068 /* If revision is 1, the rocketmodem flash must be loaded.
2069 * If it is 2 it is a "socketed" version. */ 2069 * If it is 2 it is a "socketed" version. */
2070 if (dev->revision == 1) { 2070 if (dev->revision == 1) {
2071 rcktpt_type[i] = ROCKET_TYPE_MODEMII; 2071 rcktpt_type[i] = ROCKET_TYPE_MODEMII;
2072 rocketModel[i].loadrm2 = 1; 2072 rocketModel[i].loadrm2 = 1;
2073 } else { 2073 } else {
2074 rcktpt_type[i] = ROCKET_TYPE_MODEM; 2074 rcktpt_type[i] = ROCKET_TYPE_MODEM;
2075 } 2075 }
2076 2076
2077 rocketModel[i].model = MODEL_RP6M; 2077 rocketModel[i].model = MODEL_RP6M;
2078 strcpy(rocketModel[i].modelString, "RocketModem 6 port"); 2078 strcpy(rocketModel[i].modelString, "RocketModem 6 port");
2079 rocketModel[i].numPorts = 6; 2079 rocketModel[i].numPorts = 6;
2080 break; 2080 break;
2081 case PCI_DEVICE_ID_RP4M: 2081 case PCI_DEVICE_ID_RP4M:
2082 max_num_aiops = 1; 2082 max_num_aiops = 1;
2083 ports_per_aiop = 4; 2083 ports_per_aiop = 4;
2084 str = "4-port"; 2084 str = "4-port";
2085 if (dev->revision == 1) { 2085 if (dev->revision == 1) {
2086 rcktpt_type[i] = ROCKET_TYPE_MODEMII; 2086 rcktpt_type[i] = ROCKET_TYPE_MODEMII;
2087 rocketModel[i].loadrm2 = 1; 2087 rocketModel[i].loadrm2 = 1;
2088 } else { 2088 } else {
2089 rcktpt_type[i] = ROCKET_TYPE_MODEM; 2089 rcktpt_type[i] = ROCKET_TYPE_MODEM;
2090 } 2090 }
2091 2091
2092 rocketModel[i].model = MODEL_RP4M; 2092 rocketModel[i].model = MODEL_RP4M;
2093 strcpy(rocketModel[i].modelString, "RocketModem 4 port"); 2093 strcpy(rocketModel[i].modelString, "RocketModem 4 port");
2094 rocketModel[i].numPorts = 4; 2094 rocketModel[i].numPorts = 4;
2095 break; 2095 break;
2096 default: 2096 default:
2097 str = "(unknown/unsupported)"; 2097 str = "(unknown/unsupported)";
2098 max_num_aiops = 0; 2098 max_num_aiops = 0;
2099 break; 2099 break;
2100 } 2100 }
2101 2101
2102 /* 2102 /*
2103 * Check for UPCI boards. 2103 * Check for UPCI boards.
2104 */ 2104 */
2105 2105
2106 switch (dev->device) { 2106 switch (dev->device) {
2107 case PCI_DEVICE_ID_URP32INTF: 2107 case PCI_DEVICE_ID_URP32INTF:
2108 case PCI_DEVICE_ID_URP8INTF: 2108 case PCI_DEVICE_ID_URP8INTF:
2109 case PCI_DEVICE_ID_URP16INTF: 2109 case PCI_DEVICE_ID_URP16INTF:
2110 case PCI_DEVICE_ID_CRP16INTF: 2110 case PCI_DEVICE_ID_CRP16INTF:
2111 case PCI_DEVICE_ID_URP8OCTA: 2111 case PCI_DEVICE_ID_URP8OCTA:
2112 rcktpt_io_addr[i] = pci_resource_start(dev, 2); 2112 rcktpt_io_addr[i] = pci_resource_start(dev, 2);
2113 ConfigIO = pci_resource_start(dev, 1); 2113 ConfigIO = pci_resource_start(dev, 1);
2114 if (dev->device == PCI_DEVICE_ID_URP8OCTA) { 2114 if (dev->device == PCI_DEVICE_ID_URP8OCTA) {
2115 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND; 2115 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND;
2116 2116
2117 /* 2117 /*
2118 * Check for octa or quad cable. 2118 * Check for octa or quad cable.
2119 */ 2119 */
2120 if (! 2120 if (!
2121 (sInW(ConfigIO + _PCI_9030_GPIO_CTRL) & 2121 (sInW(ConfigIO + _PCI_9030_GPIO_CTRL) &
2122 PCI_GPIO_CTRL_8PORT)) { 2122 PCI_GPIO_CTRL_8PORT)) {
2123 str = "Quadcable"; 2123 str = "Quadcable";
2124 ports_per_aiop = 4; 2124 ports_per_aiop = 4;
2125 rocketModel[i].numPorts = 4; 2125 rocketModel[i].numPorts = 4;
2126 } 2126 }
2127 } 2127 }
2128 break; 2128 break;
2129 case PCI_DEVICE_ID_UPCI_RM3_8PORT: 2129 case PCI_DEVICE_ID_UPCI_RM3_8PORT:
2130 str = "8 ports"; 2130 str = "8 ports";
2131 max_num_aiops = 1; 2131 max_num_aiops = 1;
2132 rocketModel[i].model = MODEL_UPCI_RM3_8PORT; 2132 rocketModel[i].model = MODEL_UPCI_RM3_8PORT;
2133 strcpy(rocketModel[i].modelString, "RocketModem III 8 port"); 2133 strcpy(rocketModel[i].modelString, "RocketModem III 8 port");
2134 rocketModel[i].numPorts = 8; 2134 rocketModel[i].numPorts = 8;
2135 rcktpt_io_addr[i] = pci_resource_start(dev, 2); 2135 rcktpt_io_addr[i] = pci_resource_start(dev, 2);
2136 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND; 2136 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND;
2137 ConfigIO = pci_resource_start(dev, 1); 2137 ConfigIO = pci_resource_start(dev, 1);
2138 rcktpt_type[i] = ROCKET_TYPE_MODEMIII; 2138 rcktpt_type[i] = ROCKET_TYPE_MODEMIII;
2139 break; 2139 break;
2140 case PCI_DEVICE_ID_UPCI_RM3_4PORT: 2140 case PCI_DEVICE_ID_UPCI_RM3_4PORT:
2141 str = "4 ports"; 2141 str = "4 ports";
2142 max_num_aiops = 1; 2142 max_num_aiops = 1;
2143 rocketModel[i].model = MODEL_UPCI_RM3_4PORT; 2143 rocketModel[i].model = MODEL_UPCI_RM3_4PORT;
2144 strcpy(rocketModel[i].modelString, "RocketModem III 4 port"); 2144 strcpy(rocketModel[i].modelString, "RocketModem III 4 port");
2145 rocketModel[i].numPorts = 4; 2145 rocketModel[i].numPorts = 4;
2146 rcktpt_io_addr[i] = pci_resource_start(dev, 2); 2146 rcktpt_io_addr[i] = pci_resource_start(dev, 2);
2147 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND; 2147 UPCIRingInd = rcktpt_io_addr[i] + _PCI_9030_RING_IND;
2148 ConfigIO = pci_resource_start(dev, 1); 2148 ConfigIO = pci_resource_start(dev, 1);
2149 rcktpt_type[i] = ROCKET_TYPE_MODEMIII; 2149 rcktpt_type[i] = ROCKET_TYPE_MODEMIII;
2150 break; 2150 break;
2151 default: 2151 default:
2152 break; 2152 break;
2153 } 2153 }
2154 2154
2155 switch (rcktpt_type[i]) { 2155 switch (rcktpt_type[i]) {
2156 case ROCKET_TYPE_MODEM: 2156 case ROCKET_TYPE_MODEM:
2157 board_type = "RocketModem"; 2157 board_type = "RocketModem";
2158 break; 2158 break;
2159 case ROCKET_TYPE_MODEMII: 2159 case ROCKET_TYPE_MODEMII:
2160 board_type = "RocketModem II"; 2160 board_type = "RocketModem II";
2161 break; 2161 break;
2162 case ROCKET_TYPE_MODEMIII: 2162 case ROCKET_TYPE_MODEMIII:
2163 board_type = "RocketModem III"; 2163 board_type = "RocketModem III";
2164 break; 2164 break;
2165 default: 2165 default:
2166 board_type = "RocketPort"; 2166 board_type = "RocketPort";
2167 break; 2167 break;
2168 } 2168 }
2169 2169
2170 if (fast_clock) { 2170 if (fast_clock) {
2171 sClockPrescale = 0x12; /* mod 2 (divide by 3) */ 2171 sClockPrescale = 0x12; /* mod 2 (divide by 3) */
2172 rp_baud_base[i] = 921600; 2172 rp_baud_base[i] = 921600;
2173 } else { 2173 } else {
2174 /* 2174 /*
2175 * If support_low_speed is set, use the slow clock 2175 * If support_low_speed is set, use the slow clock
2176 * prescale, which supports 50 bps 2176 * prescale, which supports 50 bps
2177 */ 2177 */
2178 if (support_low_speed) { 2178 if (support_low_speed) {
2179 /* mod 9 (divide by 10) prescale */ 2179 /* mod 9 (divide by 10) prescale */
2180 sClockPrescale = 0x19; 2180 sClockPrescale = 0x19;
2181 rp_baud_base[i] = 230400; 2181 rp_baud_base[i] = 230400;
2182 } else { 2182 } else {
2183 /* mod 4 (devide by 5) prescale */ 2183 /* mod 4 (devide by 5) prescale */
2184 sClockPrescale = 0x14; 2184 sClockPrescale = 0x14;
2185 rp_baud_base[i] = 460800; 2185 rp_baud_base[i] = 460800;
2186 } 2186 }
2187 } 2187 }
2188 2188
2189 for (aiop = 0; aiop < max_num_aiops; aiop++) 2189 for (aiop = 0; aiop < max_num_aiops; aiop++)
2190 aiopio[aiop] = rcktpt_io_addr[i] + (aiop * 0x40); 2190 aiopio[aiop] = rcktpt_io_addr[i] + (aiop * 0x40);
2191 ctlp = sCtlNumToCtlPtr(i); 2191 ctlp = sCtlNumToCtlPtr(i);
2192 num_aiops = sPCIInitController(ctlp, i, aiopio, max_num_aiops, ConfigIO, 0, FREQ_DIS, 0, altChanRingIndicator, UPCIRingInd); 2192 num_aiops = sPCIInitController(ctlp, i, aiopio, max_num_aiops, ConfigIO, 0, FREQ_DIS, 0, altChanRingIndicator, UPCIRingInd);
2193 for (aiop = 0; aiop < max_num_aiops; aiop++) 2193 for (aiop = 0; aiop < max_num_aiops; aiop++)
2194 ctlp->AiopNumChan[aiop] = ports_per_aiop; 2194 ctlp->AiopNumChan[aiop] = ports_per_aiop;
2195 2195
2196 dev_info(&dev->dev, "comtrol PCI controller #%d found at " 2196 dev_info(&dev->dev, "comtrol PCI controller #%d found at "
2197 "address %04lx, %d AIOP(s) (%s), creating ttyR%d - %ld\n", 2197 "address %04lx, %d AIOP(s) (%s), creating ttyR%d - %ld\n",
2198 i, rcktpt_io_addr[i], num_aiops, rocketModel[i].modelString, 2198 i, rcktpt_io_addr[i], num_aiops, rocketModel[i].modelString,
2199 rocketModel[i].startingPortNumber, 2199 rocketModel[i].startingPortNumber,
2200 rocketModel[i].startingPortNumber + rocketModel[i].numPorts-1); 2200 rocketModel[i].startingPortNumber + rocketModel[i].numPorts-1);
2201 2201
2202 if (num_aiops <= 0) { 2202 if (num_aiops <= 0) {
2203 rcktpt_io_addr[i] = 0; 2203 rcktpt_io_addr[i] = 0;
2204 return (0); 2204 return (0);
2205 } 2205 }
2206 is_PCI[i] = 1; 2206 is_PCI[i] = 1;
2207 2207
2208 /* Reset the AIOPIC, init the serial ports */ 2208 /* Reset the AIOPIC, init the serial ports */
2209 for (aiop = 0; aiop < num_aiops; aiop++) { 2209 for (aiop = 0; aiop < num_aiops; aiop++) {
2210 sResetAiopByNum(ctlp, aiop); 2210 sResetAiopByNum(ctlp, aiop);
2211 num_chan = ports_per_aiop; 2211 num_chan = ports_per_aiop;
2212 for (chan = 0; chan < num_chan; chan++) 2212 for (chan = 0; chan < num_chan; chan++)
2213 init_r_port(i, aiop, chan, dev); 2213 init_r_port(i, aiop, chan, dev);
2214 } 2214 }
2215 2215
2216 /* Rocket modems must be reset */ 2216 /* Rocket modems must be reset */
2217 if ((rcktpt_type[i] == ROCKET_TYPE_MODEM) || 2217 if ((rcktpt_type[i] == ROCKET_TYPE_MODEM) ||
2218 (rcktpt_type[i] == ROCKET_TYPE_MODEMII) || 2218 (rcktpt_type[i] == ROCKET_TYPE_MODEMII) ||
2219 (rcktpt_type[i] == ROCKET_TYPE_MODEMIII)) { 2219 (rcktpt_type[i] == ROCKET_TYPE_MODEMIII)) {
2220 num_chan = ports_per_aiop; 2220 num_chan = ports_per_aiop;
2221 for (chan = 0; chan < num_chan; chan++) 2221 for (chan = 0; chan < num_chan; chan++)
2222 sPCIModemReset(ctlp, chan, 1); 2222 sPCIModemReset(ctlp, chan, 1);
2223 msleep(500); 2223 msleep(500);
2224 for (chan = 0; chan < num_chan; chan++) 2224 for (chan = 0; chan < num_chan; chan++)
2225 sPCIModemReset(ctlp, chan, 0); 2225 sPCIModemReset(ctlp, chan, 0);
2226 msleep(500); 2226 msleep(500);
2227 rmSpeakerReset(ctlp, rocketModel[i].model); 2227 rmSpeakerReset(ctlp, rocketModel[i].model);
2228 } 2228 }
2229 return (1); 2229 return (1);
2230 } 2230 }
2231 2231
2232 /* 2232 /*
2233 * Probes for PCI cards, inits them if found 2233 * Probes for PCI cards, inits them if found
2234 * Input: board_found = number of ISA boards already found, or the 2234 * Input: board_found = number of ISA boards already found, or the
2235 * starting board number 2235 * starting board number
2236 * Returns: Number of PCI boards found 2236 * Returns: Number of PCI boards found
2237 */ 2237 */
2238 static int __init init_PCI(int boards_found) 2238 static int __init init_PCI(int boards_found)
2239 { 2239 {
2240 struct pci_dev *dev = NULL; 2240 struct pci_dev *dev = NULL;
2241 int count = 0; 2241 int count = 0;
2242 2242
2243 /* Work through the PCI device list, pulling out ours */ 2243 /* Work through the PCI device list, pulling out ours */
2244 while ((dev = pci_get_device(PCI_VENDOR_ID_RP, PCI_ANY_ID, dev))) { 2244 while ((dev = pci_get_device(PCI_VENDOR_ID_RP, PCI_ANY_ID, dev))) {
2245 if (register_PCI(count + boards_found, dev)) 2245 if (register_PCI(count + boards_found, dev))
2246 count++; 2246 count++;
2247 } 2247 }
2248 return (count); 2248 return (count);
2249 } 2249 }
2250 2250
2251 #endif /* CONFIG_PCI */ 2251 #endif /* CONFIG_PCI */
2252 2252
2253 /* 2253 /*
2254 * Probes for ISA cards 2254 * Probes for ISA cards
2255 * Input: i = the board number to look for 2255 * Input: i = the board number to look for
2256 * Returns: 1 if board found, 0 else 2256 * Returns: 1 if board found, 0 else
2257 */ 2257 */
2258 static int __init init_ISA(int i) 2258 static int __init init_ISA(int i)
2259 { 2259 {
2260 int num_aiops, num_chan = 0, total_num_chan = 0; 2260 int num_aiops, num_chan = 0, total_num_chan = 0;
2261 int aiop, chan; 2261 int aiop, chan;
2262 unsigned int aiopio[MAX_AIOPS_PER_BOARD]; 2262 unsigned int aiopio[MAX_AIOPS_PER_BOARD];
2263 CONTROLLER_t *ctlp; 2263 CONTROLLER_t *ctlp;
2264 char *type_string; 2264 char *type_string;
2265 2265
2266 /* If io_addr is zero, no board configured */ 2266 /* If io_addr is zero, no board configured */
2267 if (rcktpt_io_addr[i] == 0) 2267 if (rcktpt_io_addr[i] == 0)
2268 return (0); 2268 return (0);
2269 2269
2270 /* Reserve the IO region */ 2270 /* Reserve the IO region */
2271 if (!request_region(rcktpt_io_addr[i], 64, "Comtrol RocketPort")) { 2271 if (!request_region(rcktpt_io_addr[i], 64, "Comtrol RocketPort")) {
2272 printk(KERN_ERR "Unable to reserve IO region for configured " 2272 printk(KERN_ERR "Unable to reserve IO region for configured "
2273 "ISA RocketPort at address 0x%lx, board not " 2273 "ISA RocketPort at address 0x%lx, board not "
2274 "installed...\n", rcktpt_io_addr[i]); 2274 "installed...\n", rcktpt_io_addr[i]);
2275 rcktpt_io_addr[i] = 0; 2275 rcktpt_io_addr[i] = 0;
2276 return (0); 2276 return (0);
2277 } 2277 }
2278 2278
2279 ctlp = sCtlNumToCtlPtr(i); 2279 ctlp = sCtlNumToCtlPtr(i);
2280 2280
2281 ctlp->boardType = rcktpt_type[i]; 2281 ctlp->boardType = rcktpt_type[i];
2282 2282
2283 switch (rcktpt_type[i]) { 2283 switch (rcktpt_type[i]) {
2284 case ROCKET_TYPE_PC104: 2284 case ROCKET_TYPE_PC104:
2285 type_string = "(PC104)"; 2285 type_string = "(PC104)";
2286 break; 2286 break;
2287 case ROCKET_TYPE_MODEM: 2287 case ROCKET_TYPE_MODEM:
2288 type_string = "(RocketModem)"; 2288 type_string = "(RocketModem)";
2289 break; 2289 break;
2290 case ROCKET_TYPE_MODEMII: 2290 case ROCKET_TYPE_MODEMII:
2291 type_string = "(RocketModem II)"; 2291 type_string = "(RocketModem II)";
2292 break; 2292 break;
2293 default: 2293 default:
2294 type_string = ""; 2294 type_string = "";
2295 break; 2295 break;
2296 } 2296 }
2297 2297
2298 /* 2298 /*
2299 * If support_low_speed is set, use the slow clock prescale, 2299 * If support_low_speed is set, use the slow clock prescale,
2300 * which supports 50 bps 2300 * which supports 50 bps
2301 */ 2301 */
2302 if (support_low_speed) { 2302 if (support_low_speed) {
2303 sClockPrescale = 0x19; /* mod 9 (divide by 10) prescale */ 2303 sClockPrescale = 0x19; /* mod 9 (divide by 10) prescale */
2304 rp_baud_base[i] = 230400; 2304 rp_baud_base[i] = 230400;
2305 } else { 2305 } else {
2306 sClockPrescale = 0x14; /* mod 4 (devide by 5) prescale */ 2306 sClockPrescale = 0x14; /* mod 4 (devide by 5) prescale */
2307 rp_baud_base[i] = 460800; 2307 rp_baud_base[i] = 460800;
2308 } 2308 }
2309 2309
2310 for (aiop = 0; aiop < MAX_AIOPS_PER_BOARD; aiop++) 2310 for (aiop = 0; aiop < MAX_AIOPS_PER_BOARD; aiop++)
2311 aiopio[aiop] = rcktpt_io_addr[i] + (aiop * 0x400); 2311 aiopio[aiop] = rcktpt_io_addr[i] + (aiop * 0x400);
2312 2312
2313 num_aiops = sInitController(ctlp, i, controller + (i * 0x400), aiopio, MAX_AIOPS_PER_BOARD, 0, FREQ_DIS, 0); 2313 num_aiops = sInitController(ctlp, i, controller + (i * 0x400), aiopio, MAX_AIOPS_PER_BOARD, 0, FREQ_DIS, 0);
2314 2314
2315 if (ctlp->boardType == ROCKET_TYPE_PC104) { 2315 if (ctlp->boardType == ROCKET_TYPE_PC104) {
2316 sEnAiop(ctlp, 2); /* only one AIOPIC, but these */ 2316 sEnAiop(ctlp, 2); /* only one AIOPIC, but these */
2317 sEnAiop(ctlp, 3); /* CSels used for other stuff */ 2317 sEnAiop(ctlp, 3); /* CSels used for other stuff */
2318 } 2318 }
2319 2319
2320 /* If something went wrong initing the AIOP's release the ISA IO memory */ 2320 /* If something went wrong initing the AIOP's release the ISA IO memory */
2321 if (num_aiops <= 0) { 2321 if (num_aiops <= 0) {
2322 release_region(rcktpt_io_addr[i], 64); 2322 release_region(rcktpt_io_addr[i], 64);
2323 rcktpt_io_addr[i] = 0; 2323 rcktpt_io_addr[i] = 0;
2324 return (0); 2324 return (0);
2325 } 2325 }
2326 2326
2327 rocketModel[i].startingPortNumber = nextLineNumber; 2327 rocketModel[i].startingPortNumber = nextLineNumber;
2328 2328
2329 for (aiop = 0; aiop < num_aiops; aiop++) { 2329 for (aiop = 0; aiop < num_aiops; aiop++) {
2330 sResetAiopByNum(ctlp, aiop); 2330 sResetAiopByNum(ctlp, aiop);
2331 sEnAiop(ctlp, aiop); 2331 sEnAiop(ctlp, aiop);
2332 num_chan = sGetAiopNumChan(ctlp, aiop); 2332 num_chan = sGetAiopNumChan(ctlp, aiop);
2333 total_num_chan += num_chan; 2333 total_num_chan += num_chan;
2334 for (chan = 0; chan < num_chan; chan++) 2334 for (chan = 0; chan < num_chan; chan++)
2335 init_r_port(i, aiop, chan, NULL); 2335 init_r_port(i, aiop, chan, NULL);
2336 } 2336 }
2337 is_PCI[i] = 0; 2337 is_PCI[i] = 0;
2338 if ((rcktpt_type[i] == ROCKET_TYPE_MODEM) || (rcktpt_type[i] == ROCKET_TYPE_MODEMII)) { 2338 if ((rcktpt_type[i] == ROCKET_TYPE_MODEM) || (rcktpt_type[i] == ROCKET_TYPE_MODEMII)) {
2339 num_chan = sGetAiopNumChan(ctlp, 0); 2339 num_chan = sGetAiopNumChan(ctlp, 0);
2340 total_num_chan = num_chan; 2340 total_num_chan = num_chan;
2341 for (chan = 0; chan < num_chan; chan++) 2341 for (chan = 0; chan < num_chan; chan++)
2342 sModemReset(ctlp, chan, 1); 2342 sModemReset(ctlp, chan, 1);
2343 msleep(500); 2343 msleep(500);
2344 for (chan = 0; chan < num_chan; chan++) 2344 for (chan = 0; chan < num_chan; chan++)
2345 sModemReset(ctlp, chan, 0); 2345 sModemReset(ctlp, chan, 0);
2346 msleep(500); 2346 msleep(500);
2347 strcpy(rocketModel[i].modelString, "RocketModem ISA"); 2347 strcpy(rocketModel[i].modelString, "RocketModem ISA");
2348 } else { 2348 } else {
2349 strcpy(rocketModel[i].modelString, "RocketPort ISA"); 2349 strcpy(rocketModel[i].modelString, "RocketPort ISA");
2350 } 2350 }
2351 rocketModel[i].numPorts = total_num_chan; 2351 rocketModel[i].numPorts = total_num_chan;
2352 rocketModel[i].model = MODEL_ISA; 2352 rocketModel[i].model = MODEL_ISA;
2353 2353
2354 printk(KERN_INFO "RocketPort ISA card #%d found at 0x%lx - %d AIOPs %s\n", 2354 printk(KERN_INFO "RocketPort ISA card #%d found at 0x%lx - %d AIOPs %s\n",
2355 i, rcktpt_io_addr[i], num_aiops, type_string); 2355 i, rcktpt_io_addr[i], num_aiops, type_string);
2356 2356
2357 printk(KERN_INFO "Installing %s, creating /dev/ttyR%d - %ld\n", 2357 printk(KERN_INFO "Installing %s, creating /dev/ttyR%d - %ld\n",
2358 rocketModel[i].modelString, 2358 rocketModel[i].modelString,
2359 rocketModel[i].startingPortNumber, 2359 rocketModel[i].startingPortNumber,
2360 rocketModel[i].startingPortNumber + 2360 rocketModel[i].startingPortNumber +
2361 rocketModel[i].numPorts - 1); 2361 rocketModel[i].numPorts - 1);
2362 2362
2363 return (1); 2363 return (1);
2364 } 2364 }
2365 2365
2366 static const struct tty_operations rocket_ops = { 2366 static const struct tty_operations rocket_ops = {
2367 .open = rp_open, 2367 .open = rp_open,
2368 .close = rp_close, 2368 .close = rp_close,
2369 .write = rp_write, 2369 .write = rp_write,
2370 .put_char = rp_put_char, 2370 .put_char = rp_put_char,
2371 .write_room = rp_write_room, 2371 .write_room = rp_write_room,
2372 .chars_in_buffer = rp_chars_in_buffer, 2372 .chars_in_buffer = rp_chars_in_buffer,
2373 .flush_buffer = rp_flush_buffer, 2373 .flush_buffer = rp_flush_buffer,
2374 .ioctl = rp_ioctl, 2374 .ioctl = rp_ioctl,
2375 .throttle = rp_throttle, 2375 .throttle = rp_throttle,
2376 .unthrottle = rp_unthrottle, 2376 .unthrottle = rp_unthrottle,
2377 .set_termios = rp_set_termios, 2377 .set_termios = rp_set_termios,
2378 .stop = rp_stop, 2378 .stop = rp_stop,
2379 .start = rp_start, 2379 .start = rp_start,
2380 .hangup = rp_hangup, 2380 .hangup = rp_hangup,
2381 .break_ctl = rp_break, 2381 .break_ctl = rp_break,
2382 .send_xchar = rp_send_xchar, 2382 .send_xchar = rp_send_xchar,
2383 .wait_until_sent = rp_wait_until_sent, 2383 .wait_until_sent = rp_wait_until_sent,
2384 .tiocmget = rp_tiocmget, 2384 .tiocmget = rp_tiocmget,
2385 .tiocmset = rp_tiocmset, 2385 .tiocmset = rp_tiocmset,
2386 }; 2386 };
2387 2387
2388 static const struct tty_port_operations rocket_port_ops = { 2388 static const struct tty_port_operations rocket_port_ops = {
2389 .carrier_raised = carrier_raised, 2389 .carrier_raised = carrier_raised,
2390 .raise_dtr_rts = raise_dtr_rts, 2390 .raise_dtr_rts = raise_dtr_rts,
2391 }; 2391 };
2392 2392
2393 /* 2393 /*
2394 * The module "startup" routine; it's run when the module is loaded. 2394 * The module "startup" routine; it's run when the module is loaded.
2395 */ 2395 */
2396 static int __init rp_init(void) 2396 static int __init rp_init(void)
2397 { 2397 {
2398 int ret = -ENOMEM, pci_boards_found, isa_boards_found, i; 2398 int ret = -ENOMEM, pci_boards_found, isa_boards_found, i;
2399 2399
2400 printk(KERN_INFO "RocketPort device driver module, version %s, %s\n", 2400 printk(KERN_INFO "RocketPort device driver module, version %s, %s\n",
2401 ROCKET_VERSION, ROCKET_DATE); 2401 ROCKET_VERSION, ROCKET_DATE);
2402 2402
2403 rocket_driver = alloc_tty_driver(MAX_RP_PORTS); 2403 rocket_driver = alloc_tty_driver(MAX_RP_PORTS);
2404 if (!rocket_driver) 2404 if (!rocket_driver)
2405 goto err; 2405 goto err;
2406 2406
2407 /* 2407 /*
2408 * If board 1 is non-zero, there is at least one ISA configured. If controller is 2408 * If board 1 is non-zero, there is at least one ISA configured. If controller is
2409 * zero, use the default controller IO address of board1 + 0x40. 2409 * zero, use the default controller IO address of board1 + 0x40.
2410 */ 2410 */
2411 if (board1) { 2411 if (board1) {
2412 if (controller == 0) 2412 if (controller == 0)
2413 controller = board1 + 0x40; 2413 controller = board1 + 0x40;
2414 } else { 2414 } else {
2415 controller = 0; /* Used as a flag, meaning no ISA boards */ 2415 controller = 0; /* Used as a flag, meaning no ISA boards */
2416 } 2416 }
2417 2417
2418 /* If an ISA card is configured, reserve the 4 byte IO space for the Mudbac controller */ 2418 /* If an ISA card is configured, reserve the 4 byte IO space for the Mudbac controller */
2419 if (controller && (!request_region(controller, 4, "Comtrol RocketPort"))) { 2419 if (controller && (!request_region(controller, 4, "Comtrol RocketPort"))) {
2420 printk(KERN_ERR "Unable to reserve IO region for first " 2420 printk(KERN_ERR "Unable to reserve IO region for first "
2421 "configured ISA RocketPort controller 0x%lx. " 2421 "configured ISA RocketPort controller 0x%lx. "
2422 "Driver exiting\n", controller); 2422 "Driver exiting\n", controller);
2423 ret = -EBUSY; 2423 ret = -EBUSY;
2424 goto err_tty; 2424 goto err_tty;
2425 } 2425 }
2426 2426
2427 /* Store ISA variable retrieved from command line or .conf file. */ 2427 /* Store ISA variable retrieved from command line or .conf file. */
2428 rcktpt_io_addr[0] = board1; 2428 rcktpt_io_addr[0] = board1;
2429 rcktpt_io_addr[1] = board2; 2429 rcktpt_io_addr[1] = board2;
2430 rcktpt_io_addr[2] = board3; 2430 rcktpt_io_addr[2] = board3;
2431 rcktpt_io_addr[3] = board4; 2431 rcktpt_io_addr[3] = board4;
2432 2432
2433 rcktpt_type[0] = modem1 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL; 2433 rcktpt_type[0] = modem1 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL;
2434 rcktpt_type[0] = pc104_1[0] ? ROCKET_TYPE_PC104 : rcktpt_type[0]; 2434 rcktpt_type[0] = pc104_1[0] ? ROCKET_TYPE_PC104 : rcktpt_type[0];
2435 rcktpt_type[1] = modem2 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL; 2435 rcktpt_type[1] = modem2 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL;
2436 rcktpt_type[1] = pc104_2[0] ? ROCKET_TYPE_PC104 : rcktpt_type[1]; 2436 rcktpt_type[1] = pc104_2[0] ? ROCKET_TYPE_PC104 : rcktpt_type[1];
2437 rcktpt_type[2] = modem3 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL; 2437 rcktpt_type[2] = modem3 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL;
2438 rcktpt_type[2] = pc104_3[0] ? ROCKET_TYPE_PC104 : rcktpt_type[2]; 2438 rcktpt_type[2] = pc104_3[0] ? ROCKET_TYPE_PC104 : rcktpt_type[2];
2439 rcktpt_type[3] = modem4 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL; 2439 rcktpt_type[3] = modem4 ? ROCKET_TYPE_MODEM : ROCKET_TYPE_NORMAL;
2440 rcktpt_type[3] = pc104_4[0] ? ROCKET_TYPE_PC104 : rcktpt_type[3]; 2440 rcktpt_type[3] = pc104_4[0] ? ROCKET_TYPE_PC104 : rcktpt_type[3];
2441 2441
2442 /* 2442 /*
2443 * Set up the tty driver structure and then register this 2443 * Set up the tty driver structure and then register this
2444 * driver with the tty layer. 2444 * driver with the tty layer.
2445 */ 2445 */
2446 2446
2447 rocket_driver->owner = THIS_MODULE; 2447 rocket_driver->owner = THIS_MODULE;
2448 rocket_driver->flags = TTY_DRIVER_DYNAMIC_DEV; 2448 rocket_driver->flags = TTY_DRIVER_DYNAMIC_DEV;
2449 rocket_driver->name = "ttyR"; 2449 rocket_driver->name = "ttyR";
2450 rocket_driver->driver_name = "Comtrol RocketPort"; 2450 rocket_driver->driver_name = "Comtrol RocketPort";
2451 rocket_driver->major = TTY_ROCKET_MAJOR; 2451 rocket_driver->major = TTY_ROCKET_MAJOR;
2452 rocket_driver->minor_start = 0; 2452 rocket_driver->minor_start = 0;
2453 rocket_driver->type = TTY_DRIVER_TYPE_SERIAL; 2453 rocket_driver->type = TTY_DRIVER_TYPE_SERIAL;
2454 rocket_driver->subtype = SERIAL_TYPE_NORMAL; 2454 rocket_driver->subtype = SERIAL_TYPE_NORMAL;
2455 rocket_driver->init_termios = tty_std_termios; 2455 rocket_driver->init_termios = tty_std_termios;
2456 rocket_driver->init_termios.c_cflag = 2456 rocket_driver->init_termios.c_cflag =
2457 B9600 | CS8 | CREAD | HUPCL | CLOCAL; 2457 B9600 | CS8 | CREAD | HUPCL | CLOCAL;
2458 rocket_driver->init_termios.c_ispeed = 9600; 2458 rocket_driver->init_termios.c_ispeed = 9600;
2459 rocket_driver->init_termios.c_ospeed = 9600; 2459 rocket_driver->init_termios.c_ospeed = 9600;
2460 #ifdef ROCKET_SOFT_FLOW 2460 #ifdef ROCKET_SOFT_FLOW
2461 rocket_driver->flags |= TTY_DRIVER_REAL_RAW; 2461 rocket_driver->flags |= TTY_DRIVER_REAL_RAW;
2462 #endif 2462 #endif
2463 tty_set_operations(rocket_driver, &rocket_ops); 2463 tty_set_operations(rocket_driver, &rocket_ops);
2464 2464
2465 ret = tty_register_driver(rocket_driver); 2465 ret = tty_register_driver(rocket_driver);
2466 if (ret < 0) { 2466 if (ret < 0) {
2467 printk(KERN_ERR "Couldn't install tty RocketPort driver\n"); 2467 printk(KERN_ERR "Couldn't install tty RocketPort driver\n");
2468 goto err_tty; 2468 goto err_tty;
2469 } 2469 }
2470 2470
2471 #ifdef ROCKET_DEBUG_OPEN 2471 #ifdef ROCKET_DEBUG_OPEN
2472 printk(KERN_INFO "RocketPort driver is major %d\n", rocket_driver.major); 2472 printk(KERN_INFO "RocketPort driver is major %d\n", rocket_driver.major);
2473 #endif 2473 #endif
2474 2474
2475 /* 2475 /*
2476 * OK, let's probe each of the controllers looking for boards. Any boards found 2476 * OK, let's probe each of the controllers looking for boards. Any boards found
2477 * will be initialized here. 2477 * will be initialized here.
2478 */ 2478 */
2479 isa_boards_found = 0; 2479 isa_boards_found = 0;
2480 pci_boards_found = 0; 2480 pci_boards_found = 0;
2481 2481
2482 for (i = 0; i < NUM_BOARDS; i++) { 2482 for (i = 0; i < NUM_BOARDS; i++) {
2483 if (init_ISA(i)) 2483 if (init_ISA(i))
2484 isa_boards_found++; 2484 isa_boards_found++;
2485 } 2485 }
2486 2486
2487 #ifdef CONFIG_PCI 2487 #ifdef CONFIG_PCI
2488 if (isa_boards_found < NUM_BOARDS) 2488 if (isa_boards_found < NUM_BOARDS)
2489 pci_boards_found = init_PCI(isa_boards_found); 2489 pci_boards_found = init_PCI(isa_boards_found);
2490 #endif 2490 #endif
2491 2491
2492 max_board = pci_boards_found + isa_boards_found; 2492 max_board = pci_boards_found + isa_boards_found;
2493 2493
2494 if (max_board == 0) { 2494 if (max_board == 0) {
2495 printk(KERN_ERR "No rocketport ports found; unloading driver\n"); 2495 printk(KERN_ERR "No rocketport ports found; unloading driver\n");
2496 ret = -ENXIO; 2496 ret = -ENXIO;
2497 goto err_ttyu; 2497 goto err_ttyu;
2498 } 2498 }
2499 2499
2500 return 0; 2500 return 0;
2501 err_ttyu: 2501 err_ttyu:
2502 tty_unregister_driver(rocket_driver); 2502 tty_unregister_driver(rocket_driver);
2503 err_tty: 2503 err_tty:
2504 put_tty_driver(rocket_driver); 2504 put_tty_driver(rocket_driver);
2505 err: 2505 err:
2506 return ret; 2506 return ret;
2507 } 2507 }
2508 2508
2509 2509
2510 static void rp_cleanup_module(void) 2510 static void rp_cleanup_module(void)
2511 { 2511 {
2512 int retval; 2512 int retval;
2513 int i; 2513 int i;
2514 2514
2515 del_timer_sync(&rocket_timer); 2515 del_timer_sync(&rocket_timer);
2516 2516
2517 retval = tty_unregister_driver(rocket_driver); 2517 retval = tty_unregister_driver(rocket_driver);
2518 if (retval) 2518 if (retval)
2519 printk(KERN_ERR "Error %d while trying to unregister " 2519 printk(KERN_ERR "Error %d while trying to unregister "
2520 "rocketport driver\n", -retval); 2520 "rocketport driver\n", -retval);
2521 2521
2522 for (i = 0; i < MAX_RP_PORTS; i++) 2522 for (i = 0; i < MAX_RP_PORTS; i++)
2523 if (rp_table[i]) { 2523 if (rp_table[i]) {
2524 tty_unregister_device(rocket_driver, i); 2524 tty_unregister_device(rocket_driver, i);
2525 kfree(rp_table[i]); 2525 kfree(rp_table[i]);
2526 } 2526 }
2527 2527
2528 put_tty_driver(rocket_driver); 2528 put_tty_driver(rocket_driver);
2529 2529
2530 for (i = 0; i < NUM_BOARDS; i++) { 2530 for (i = 0; i < NUM_BOARDS; i++) {
2531 if (rcktpt_io_addr[i] <= 0 || is_PCI[i]) 2531 if (rcktpt_io_addr[i] <= 0 || is_PCI[i])
2532 continue; 2532 continue;
2533 release_region(rcktpt_io_addr[i], 64); 2533 release_region(rcktpt_io_addr[i], 64);
2534 } 2534 }
2535 if (controller) 2535 if (controller)
2536 release_region(controller, 4); 2536 release_region(controller, 4);
2537 } 2537 }
2538 2538
2539 /*************************************************************************** 2539 /***************************************************************************
2540 Function: sInitController 2540 Function: sInitController
2541 Purpose: Initialization of controller global registers and controller 2541 Purpose: Initialization of controller global registers and controller
2542 structure. 2542 structure.
2543 Call: sInitController(CtlP,CtlNum,MudbacIO,AiopIOList,AiopIOListSize, 2543 Call: sInitController(CtlP,CtlNum,MudbacIO,AiopIOList,AiopIOListSize,
2544 IRQNum,Frequency,PeriodicOnly) 2544 IRQNum,Frequency,PeriodicOnly)
2545 CONTROLLER_T *CtlP; Ptr to controller structure 2545 CONTROLLER_T *CtlP; Ptr to controller structure
2546 int CtlNum; Controller number 2546 int CtlNum; Controller number
2547 ByteIO_t MudbacIO; Mudbac base I/O address. 2547 ByteIO_t MudbacIO; Mudbac base I/O address.
2548 ByteIO_t *AiopIOList; List of I/O addresses for each AIOP. 2548 ByteIO_t *AiopIOList; List of I/O addresses for each AIOP.
2549 This list must be in the order the AIOPs will be found on the 2549 This list must be in the order the AIOPs will be found on the
2550 controller. Once an AIOP in the list is not found, it is 2550 controller. Once an AIOP in the list is not found, it is
2551 assumed that there are no more AIOPs on the controller. 2551 assumed that there are no more AIOPs on the controller.
2552 int AiopIOListSize; Number of addresses in AiopIOList 2552 int AiopIOListSize; Number of addresses in AiopIOList
2553 int IRQNum; Interrupt Request number. Can be any of the following: 2553 int IRQNum; Interrupt Request number. Can be any of the following:
2554 0: Disable global interrupts 2554 0: Disable global interrupts
2555 3: IRQ 3 2555 3: IRQ 3
2556 4: IRQ 4 2556 4: IRQ 4
2557 5: IRQ 5 2557 5: IRQ 5
2558 9: IRQ 9 2558 9: IRQ 9
2559 10: IRQ 10 2559 10: IRQ 10
2560 11: IRQ 11 2560 11: IRQ 11
2561 12: IRQ 12 2561 12: IRQ 12
2562 15: IRQ 15 2562 15: IRQ 15
2563 Byte_t Frequency: A flag identifying the frequency 2563 Byte_t Frequency: A flag identifying the frequency
2564 of the periodic interrupt, can be any one of the following: 2564 of the periodic interrupt, can be any one of the following:
2565 FREQ_DIS - periodic interrupt disabled 2565 FREQ_DIS - periodic interrupt disabled
2566 FREQ_137HZ - 137 Hertz 2566 FREQ_137HZ - 137 Hertz
2567 FREQ_69HZ - 69 Hertz 2567 FREQ_69HZ - 69 Hertz
2568 FREQ_34HZ - 34 Hertz 2568 FREQ_34HZ - 34 Hertz
2569 FREQ_17HZ - 17 Hertz 2569 FREQ_17HZ - 17 Hertz
2570 FREQ_9HZ - 9 Hertz 2570 FREQ_9HZ - 9 Hertz
2571 FREQ_4HZ - 4 Hertz 2571 FREQ_4HZ - 4 Hertz
2572 If IRQNum is set to 0 the Frequency parameter is 2572 If IRQNum is set to 0 the Frequency parameter is
2573 overidden, it is forced to a value of FREQ_DIS. 2573 overidden, it is forced to a value of FREQ_DIS.
2574 int PeriodicOnly: 1 if all interrupts except the periodic 2574 int PeriodicOnly: 1 if all interrupts except the periodic
2575 interrupt are to be blocked. 2575 interrupt are to be blocked.
2576 0 is both the periodic interrupt and 2576 0 is both the periodic interrupt and
2577 other channel interrupts are allowed. 2577 other channel interrupts are allowed.
2578 If IRQNum is set to 0 the PeriodicOnly parameter is 2578 If IRQNum is set to 0 the PeriodicOnly parameter is
2579 overidden, it is forced to a value of 0. 2579 overidden, it is forced to a value of 0.
2580 Return: int: Number of AIOPs on the controller, or CTLID_NULL if controller 2580 Return: int: Number of AIOPs on the controller, or CTLID_NULL if controller
2581 initialization failed. 2581 initialization failed.
2582 2582
2583 Comments: 2583 Comments:
2584 If periodic interrupts are to be disabled but AIOP interrupts 2584 If periodic interrupts are to be disabled but AIOP interrupts
2585 are allowed, set Frequency to FREQ_DIS and PeriodicOnly to 0. 2585 are allowed, set Frequency to FREQ_DIS and PeriodicOnly to 0.
2586 2586
2587 If interrupts are to be completely disabled set IRQNum to 0. 2587 If interrupts are to be completely disabled set IRQNum to 0.
2588 2588
2589 Setting Frequency to FREQ_DIS and PeriodicOnly to 1 is an 2589 Setting Frequency to FREQ_DIS and PeriodicOnly to 1 is an
2590 invalid combination. 2590 invalid combination.
2591 2591
2592 This function performs initialization of global interrupt modes, 2592 This function performs initialization of global interrupt modes,
2593 but it does not actually enable global interrupts. To enable 2593 but it does not actually enable global interrupts. To enable
2594 and disable global interrupts use functions sEnGlobalInt() and 2594 and disable global interrupts use functions sEnGlobalInt() and
2595 sDisGlobalInt(). Enabling of global interrupts is normally not 2595 sDisGlobalInt(). Enabling of global interrupts is normally not
2596 done until all other initializations are complete. 2596 done until all other initializations are complete.
2597 2597
2598 Even if interrupts are globally enabled, they must also be 2598 Even if interrupts are globally enabled, they must also be
2599 individually enabled for each channel that is to generate 2599 individually enabled for each channel that is to generate
2600 interrupts. 2600 interrupts.
2601 2601
2602 Warnings: No range checking on any of the parameters is done. 2602 Warnings: No range checking on any of the parameters is done.
2603 2603
2604 No context switches are allowed while executing this function. 2604 No context switches are allowed while executing this function.
2605 2605
2606 After this function all AIOPs on the controller are disabled, 2606 After this function all AIOPs on the controller are disabled,
2607 they can be enabled with sEnAiop(). 2607 they can be enabled with sEnAiop().
2608 */ 2608 */
2609 static int sInitController(CONTROLLER_T * CtlP, int CtlNum, ByteIO_t MudbacIO, 2609 static int sInitController(CONTROLLER_T * CtlP, int CtlNum, ByteIO_t MudbacIO,
2610 ByteIO_t * AiopIOList, int AiopIOListSize, 2610 ByteIO_t * AiopIOList, int AiopIOListSize,
2611 int IRQNum, Byte_t Frequency, int PeriodicOnly) 2611 int IRQNum, Byte_t Frequency, int PeriodicOnly)
2612 { 2612 {
2613 int i; 2613 int i;
2614 ByteIO_t io; 2614 ByteIO_t io;
2615 int done; 2615 int done;
2616 2616
2617 CtlP->AiopIntrBits = aiop_intr_bits; 2617 CtlP->AiopIntrBits = aiop_intr_bits;
2618 CtlP->AltChanRingIndicator = 0; 2618 CtlP->AltChanRingIndicator = 0;
2619 CtlP->CtlNum = CtlNum; 2619 CtlP->CtlNum = CtlNum;
2620 CtlP->CtlID = CTLID_0001; /* controller release 1 */ 2620 CtlP->CtlID = CTLID_0001; /* controller release 1 */
2621 CtlP->BusType = isISA; 2621 CtlP->BusType = isISA;
2622 CtlP->MBaseIO = MudbacIO; 2622 CtlP->MBaseIO = MudbacIO;
2623 CtlP->MReg1IO = MudbacIO + 1; 2623 CtlP->MReg1IO = MudbacIO + 1;
2624 CtlP->MReg2IO = MudbacIO + 2; 2624 CtlP->MReg2IO = MudbacIO + 2;
2625 CtlP->MReg3IO = MudbacIO + 3; 2625 CtlP->MReg3IO = MudbacIO + 3;
2626 #if 1 2626 #if 1
2627 CtlP->MReg2 = 0; /* interrupt disable */ 2627 CtlP->MReg2 = 0; /* interrupt disable */
2628 CtlP->MReg3 = 0; /* no periodic interrupts */ 2628 CtlP->MReg3 = 0; /* no periodic interrupts */
2629 #else 2629 #else
2630 if (sIRQMap[IRQNum] == 0) { /* interrupts globally disabled */ 2630 if (sIRQMap[IRQNum] == 0) { /* interrupts globally disabled */
2631 CtlP->MReg2 = 0; /* interrupt disable */ 2631 CtlP->MReg2 = 0; /* interrupt disable */
2632 CtlP->MReg3 = 0; /* no periodic interrupts */ 2632 CtlP->MReg3 = 0; /* no periodic interrupts */
2633 } else { 2633 } else {
2634 CtlP->MReg2 = sIRQMap[IRQNum]; /* set IRQ number */ 2634 CtlP->MReg2 = sIRQMap[IRQNum]; /* set IRQ number */
2635 CtlP->MReg3 = Frequency; /* set frequency */ 2635 CtlP->MReg3 = Frequency; /* set frequency */
2636 if (PeriodicOnly) { /* periodic interrupt only */ 2636 if (PeriodicOnly) { /* periodic interrupt only */
2637 CtlP->MReg3 |= PERIODIC_ONLY; 2637 CtlP->MReg3 |= PERIODIC_ONLY;
2638 } 2638 }
2639 } 2639 }
2640 #endif 2640 #endif
2641 sOutB(CtlP->MReg2IO, CtlP->MReg2); 2641 sOutB(CtlP->MReg2IO, CtlP->MReg2);
2642 sOutB(CtlP->MReg3IO, CtlP->MReg3); 2642 sOutB(CtlP->MReg3IO, CtlP->MReg3);
2643 sControllerEOI(CtlP); /* clear EOI if warm init */ 2643 sControllerEOI(CtlP); /* clear EOI if warm init */
2644 /* Init AIOPs */ 2644 /* Init AIOPs */
2645 CtlP->NumAiop = 0; 2645 CtlP->NumAiop = 0;
2646 for (i = done = 0; i < AiopIOListSize; i++) { 2646 for (i = done = 0; i < AiopIOListSize; i++) {
2647 io = AiopIOList[i]; 2647 io = AiopIOList[i];
2648 CtlP->AiopIO[i] = (WordIO_t) io; 2648 CtlP->AiopIO[i] = (WordIO_t) io;
2649 CtlP->AiopIntChanIO[i] = io + _INT_CHAN; 2649 CtlP->AiopIntChanIO[i] = io + _INT_CHAN;
2650 sOutB(CtlP->MReg2IO, CtlP->MReg2 | (i & 0x03)); /* AIOP index */ 2650 sOutB(CtlP->MReg2IO, CtlP->MReg2 | (i & 0x03)); /* AIOP index */
2651 sOutB(MudbacIO, (Byte_t) (io >> 6)); /* set up AIOP I/O in MUDBAC */ 2651 sOutB(MudbacIO, (Byte_t) (io >> 6)); /* set up AIOP I/O in MUDBAC */
2652 if (done) 2652 if (done)
2653 continue; 2653 continue;
2654 sEnAiop(CtlP, i); /* enable the AIOP */ 2654 sEnAiop(CtlP, i); /* enable the AIOP */
2655 CtlP->AiopID[i] = sReadAiopID(io); /* read AIOP ID */ 2655 CtlP->AiopID[i] = sReadAiopID(io); /* read AIOP ID */
2656 if (CtlP->AiopID[i] == AIOPID_NULL) /* if AIOP does not exist */ 2656 if (CtlP->AiopID[i] == AIOPID_NULL) /* if AIOP does not exist */
2657 done = 1; /* done looking for AIOPs */ 2657 done = 1; /* done looking for AIOPs */
2658 else { 2658 else {
2659 CtlP->AiopNumChan[i] = sReadAiopNumChan((WordIO_t) io); /* num channels in AIOP */ 2659 CtlP->AiopNumChan[i] = sReadAiopNumChan((WordIO_t) io); /* num channels in AIOP */
2660 sOutW((WordIO_t) io + _INDX_ADDR, _CLK_PRE); /* clock prescaler */ 2660 sOutW((WordIO_t) io + _INDX_ADDR, _CLK_PRE); /* clock prescaler */
2661 sOutB(io + _INDX_DATA, sClockPrescale); 2661 sOutB(io + _INDX_DATA, sClockPrescale);
2662 CtlP->NumAiop++; /* bump count of AIOPs */ 2662 CtlP->NumAiop++; /* bump count of AIOPs */
2663 } 2663 }
2664 sDisAiop(CtlP, i); /* disable AIOP */ 2664 sDisAiop(CtlP, i); /* disable AIOP */
2665 } 2665 }
2666 2666
2667 if (CtlP->NumAiop == 0) 2667 if (CtlP->NumAiop == 0)
2668 return (-1); 2668 return (-1);
2669 else 2669 else
2670 return (CtlP->NumAiop); 2670 return (CtlP->NumAiop);
2671 } 2671 }
2672 2672
2673 /*************************************************************************** 2673 /***************************************************************************
2674 Function: sPCIInitController 2674 Function: sPCIInitController
2675 Purpose: Initialization of controller global registers and controller 2675 Purpose: Initialization of controller global registers and controller
2676 structure. 2676 structure.
2677 Call: sPCIInitController(CtlP,CtlNum,AiopIOList,AiopIOListSize, 2677 Call: sPCIInitController(CtlP,CtlNum,AiopIOList,AiopIOListSize,
2678 IRQNum,Frequency,PeriodicOnly) 2678 IRQNum,Frequency,PeriodicOnly)
2679 CONTROLLER_T *CtlP; Ptr to controller structure 2679 CONTROLLER_T *CtlP; Ptr to controller structure
2680 int CtlNum; Controller number 2680 int CtlNum; Controller number
2681 ByteIO_t *AiopIOList; List of I/O addresses for each AIOP. 2681 ByteIO_t *AiopIOList; List of I/O addresses for each AIOP.
2682 This list must be in the order the AIOPs will be found on the 2682 This list must be in the order the AIOPs will be found on the
2683 controller. Once an AIOP in the list is not found, it is 2683 controller. Once an AIOP in the list is not found, it is
2684 assumed that there are no more AIOPs on the controller. 2684 assumed that there are no more AIOPs on the controller.
2685 int AiopIOListSize; Number of addresses in AiopIOList 2685 int AiopIOListSize; Number of addresses in AiopIOList
2686 int IRQNum; Interrupt Request number. Can be any of the following: 2686 int IRQNum; Interrupt Request number. Can be any of the following:
2687 0: Disable global interrupts 2687 0: Disable global interrupts
2688 3: IRQ 3 2688 3: IRQ 3
2689 4: IRQ 4 2689 4: IRQ 4
2690 5: IRQ 5 2690 5: IRQ 5
2691 9: IRQ 9 2691 9: IRQ 9
2692 10: IRQ 10 2692 10: IRQ 10
2693 11: IRQ 11 2693 11: IRQ 11
2694 12: IRQ 12 2694 12: IRQ 12
2695 15: IRQ 15 2695 15: IRQ 15
2696 Byte_t Frequency: A flag identifying the frequency 2696 Byte_t Frequency: A flag identifying the frequency
2697 of the periodic interrupt, can be any one of the following: 2697 of the periodic interrupt, can be any one of the following:
2698 FREQ_DIS - periodic interrupt disabled 2698 FREQ_DIS - periodic interrupt disabled
2699 FREQ_137HZ - 137 Hertz 2699 FREQ_137HZ - 137 Hertz
2700 FREQ_69HZ - 69 Hertz 2700 FREQ_69HZ - 69 Hertz
2701 FREQ_34HZ - 34 Hertz 2701 FREQ_34HZ - 34 Hertz
2702 FREQ_17HZ - 17 Hertz 2702 FREQ_17HZ - 17 Hertz
2703 FREQ_9HZ - 9 Hertz 2703 FREQ_9HZ - 9 Hertz
2704 FREQ_4HZ - 4 Hertz 2704 FREQ_4HZ - 4 Hertz
2705 If IRQNum is set to 0 the Frequency parameter is 2705 If IRQNum is set to 0 the Frequency parameter is
2706 overidden, it is forced to a value of FREQ_DIS. 2706 overidden, it is forced to a value of FREQ_DIS.
2707 int PeriodicOnly: 1 if all interrupts except the periodic 2707 int PeriodicOnly: 1 if all interrupts except the periodic
2708 interrupt are to be blocked. 2708 interrupt are to be blocked.
2709 0 is both the periodic interrupt and 2709 0 is both the periodic interrupt and
2710 other channel interrupts are allowed. 2710 other channel interrupts are allowed.
2711 If IRQNum is set to 0 the PeriodicOnly parameter is 2711 If IRQNum is set to 0 the PeriodicOnly parameter is
2712 overidden, it is forced to a value of 0. 2712 overidden, it is forced to a value of 0.
2713 Return: int: Number of AIOPs on the controller, or CTLID_NULL if controller 2713 Return: int: Number of AIOPs on the controller, or CTLID_NULL if controller
2714 initialization failed. 2714 initialization failed.
2715 2715
2716 Comments: 2716 Comments:
2717 If periodic interrupts are to be disabled but AIOP interrupts 2717 If periodic interrupts are to be disabled but AIOP interrupts
2718 are allowed, set Frequency to FREQ_DIS and PeriodicOnly to 0. 2718 are allowed, set Frequency to FREQ_DIS and PeriodicOnly to 0.
2719 2719
2720 If interrupts are to be completely disabled set IRQNum to 0. 2720 If interrupts are to be completely disabled set IRQNum to 0.
2721 2721
2722 Setting Frequency to FREQ_DIS and PeriodicOnly to 1 is an 2722 Setting Frequency to FREQ_DIS and PeriodicOnly to 1 is an
2723 invalid combination. 2723 invalid combination.
2724 2724
2725 This function performs initialization of global interrupt modes, 2725 This function performs initialization of global interrupt modes,
2726 but it does not actually enable global interrupts. To enable 2726 but it does not actually enable global interrupts. To enable
2727 and disable global interrupts use functions sEnGlobalInt() and 2727 and disable global interrupts use functions sEnGlobalInt() and
2728 sDisGlobalInt(). Enabling of global interrupts is normally not 2728 sDisGlobalInt(). Enabling of global interrupts is normally not
2729 done until all other initializations are complete. 2729 done until all other initializations are complete.
2730 2730
2731 Even if interrupts are globally enabled, they must also be 2731 Even if interrupts are globally enabled, they must also be
2732 individually enabled for each channel that is to generate 2732 individually enabled for each channel that is to generate
2733 interrupts. 2733 interrupts.
2734 2734
2735 Warnings: No range checking on any of the parameters is done. 2735 Warnings: No range checking on any of the parameters is done.
2736 2736
2737 No context switches are allowed while executing this function. 2737 No context switches are allowed while executing this function.
2738 2738
2739 After this function all AIOPs on the controller are disabled, 2739 After this function all AIOPs on the controller are disabled,
2740 they can be enabled with sEnAiop(). 2740 they can be enabled with sEnAiop().
2741 */ 2741 */
2742 static int sPCIInitController(CONTROLLER_T * CtlP, int CtlNum, 2742 static int sPCIInitController(CONTROLLER_T * CtlP, int CtlNum,
2743 ByteIO_t * AiopIOList, int AiopIOListSize, 2743 ByteIO_t * AiopIOList, int AiopIOListSize,
2744 WordIO_t ConfigIO, int IRQNum, Byte_t Frequency, 2744 WordIO_t ConfigIO, int IRQNum, Byte_t Frequency,
2745 int PeriodicOnly, int altChanRingIndicator, 2745 int PeriodicOnly, int altChanRingIndicator,
2746 int UPCIRingInd) 2746 int UPCIRingInd)
2747 { 2747 {
2748 int i; 2748 int i;
2749 ByteIO_t io; 2749 ByteIO_t io;
2750 2750
2751 CtlP->AltChanRingIndicator = altChanRingIndicator; 2751 CtlP->AltChanRingIndicator = altChanRingIndicator;
2752 CtlP->UPCIRingInd = UPCIRingInd; 2752 CtlP->UPCIRingInd = UPCIRingInd;
2753 CtlP->CtlNum = CtlNum; 2753 CtlP->CtlNum = CtlNum;
2754 CtlP->CtlID = CTLID_0001; /* controller release 1 */ 2754 CtlP->CtlID = CTLID_0001; /* controller release 1 */
2755 CtlP->BusType = isPCI; /* controller release 1 */ 2755 CtlP->BusType = isPCI; /* controller release 1 */
2756 2756
2757 if (ConfigIO) { 2757 if (ConfigIO) {
2758 CtlP->isUPCI = 1; 2758 CtlP->isUPCI = 1;
2759 CtlP->PCIIO = ConfigIO + _PCI_9030_INT_CTRL; 2759 CtlP->PCIIO = ConfigIO + _PCI_9030_INT_CTRL;
2760 CtlP->PCIIO2 = ConfigIO + _PCI_9030_GPIO_CTRL; 2760 CtlP->PCIIO2 = ConfigIO + _PCI_9030_GPIO_CTRL;
2761 CtlP->AiopIntrBits = upci_aiop_intr_bits; 2761 CtlP->AiopIntrBits = upci_aiop_intr_bits;
2762 } else { 2762 } else {
2763 CtlP->isUPCI = 0; 2763 CtlP->isUPCI = 0;
2764 CtlP->PCIIO = 2764 CtlP->PCIIO =
2765 (WordIO_t) ((ByteIO_t) AiopIOList[0] + _PCI_INT_FUNC); 2765 (WordIO_t) ((ByteIO_t) AiopIOList[0] + _PCI_INT_FUNC);
2766 CtlP->AiopIntrBits = aiop_intr_bits; 2766 CtlP->AiopIntrBits = aiop_intr_bits;
2767 } 2767 }
2768 2768
2769 sPCIControllerEOI(CtlP); /* clear EOI if warm init */ 2769 sPCIControllerEOI(CtlP); /* clear EOI if warm init */
2770 /* Init AIOPs */ 2770 /* Init AIOPs */
2771 CtlP->NumAiop = 0; 2771 CtlP->NumAiop = 0;
2772 for (i = 0; i < AiopIOListSize; i++) { 2772 for (i = 0; i < AiopIOListSize; i++) {
2773 io = AiopIOList[i]; 2773 io = AiopIOList[i];
2774 CtlP->AiopIO[i] = (WordIO_t) io; 2774 CtlP->AiopIO[i] = (WordIO_t) io;
2775 CtlP->AiopIntChanIO[i] = io + _INT_CHAN; 2775 CtlP->AiopIntChanIO[i] = io + _INT_CHAN;
2776 2776
2777 CtlP->AiopID[i] = sReadAiopID(io); /* read AIOP ID */ 2777 CtlP->AiopID[i] = sReadAiopID(io); /* read AIOP ID */
2778 if (CtlP->AiopID[i] == AIOPID_NULL) /* if AIOP does not exist */ 2778 if (CtlP->AiopID[i] == AIOPID_NULL) /* if AIOP does not exist */
2779 break; /* done looking for AIOPs */ 2779 break; /* done looking for AIOPs */
2780 2780
2781 CtlP->AiopNumChan[i] = sReadAiopNumChan((WordIO_t) io); /* num channels in AIOP */ 2781 CtlP->AiopNumChan[i] = sReadAiopNumChan((WordIO_t) io); /* num channels in AIOP */
2782 sOutW((WordIO_t) io + _INDX_ADDR, _CLK_PRE); /* clock prescaler */ 2782 sOutW((WordIO_t) io + _INDX_ADDR, _CLK_PRE); /* clock prescaler */
2783 sOutB(io + _INDX_DATA, sClockPrescale); 2783 sOutB(io + _INDX_DATA, sClockPrescale);
2784 CtlP->NumAiop++; /* bump count of AIOPs */ 2784 CtlP->NumAiop++; /* bump count of AIOPs */
2785 } 2785 }
2786 2786
2787 if (CtlP->NumAiop == 0) 2787 if (CtlP->NumAiop == 0)
2788 return (-1); 2788 return (-1);
2789 else 2789 else
2790 return (CtlP->NumAiop); 2790 return (CtlP->NumAiop);
2791 } 2791 }
2792 2792
2793 /*************************************************************************** 2793 /***************************************************************************
2794 Function: sReadAiopID 2794 Function: sReadAiopID
2795 Purpose: Read the AIOP idenfication number directly from an AIOP. 2795 Purpose: Read the AIOP idenfication number directly from an AIOP.
2796 Call: sReadAiopID(io) 2796 Call: sReadAiopID(io)
2797 ByteIO_t io: AIOP base I/O address 2797 ByteIO_t io: AIOP base I/O address
2798 Return: int: Flag AIOPID_XXXX if a valid AIOP is found, where X 2798 Return: int: Flag AIOPID_XXXX if a valid AIOP is found, where X
2799 is replace by an identifying number. 2799 is replace by an identifying number.
2800 Flag AIOPID_NULL if no valid AIOP is found 2800 Flag AIOPID_NULL if no valid AIOP is found
2801 Warnings: No context switches are allowed while executing this function. 2801 Warnings: No context switches are allowed while executing this function.
2802 2802
2803 */ 2803 */
2804 static int sReadAiopID(ByteIO_t io) 2804 static int sReadAiopID(ByteIO_t io)
2805 { 2805 {
2806 Byte_t AiopID; /* ID byte from AIOP */ 2806 Byte_t AiopID; /* ID byte from AIOP */
2807 2807
2808 sOutB(io + _CMD_REG, RESET_ALL); /* reset AIOP */ 2808 sOutB(io + _CMD_REG, RESET_ALL); /* reset AIOP */
2809 sOutB(io + _CMD_REG, 0x0); 2809 sOutB(io + _CMD_REG, 0x0);
2810 AiopID = sInW(io + _CHN_STAT0) & 0x07; 2810 AiopID = sInW(io + _CHN_STAT0) & 0x07;
2811 if (AiopID == 0x06) 2811 if (AiopID == 0x06)
2812 return (1); 2812 return (1);
2813 else /* AIOP does not exist */ 2813 else /* AIOP does not exist */
2814 return (-1); 2814 return (-1);
2815 } 2815 }
2816 2816
2817 /*************************************************************************** 2817 /***************************************************************************
2818 Function: sReadAiopNumChan 2818 Function: sReadAiopNumChan
2819 Purpose: Read the number of channels available in an AIOP directly from 2819 Purpose: Read the number of channels available in an AIOP directly from
2820 an AIOP. 2820 an AIOP.
2821 Call: sReadAiopNumChan(io) 2821 Call: sReadAiopNumChan(io)
2822 WordIO_t io: AIOP base I/O address 2822 WordIO_t io: AIOP base I/O address
2823 Return: int: The number of channels available 2823 Return: int: The number of channels available
2824 Comments: The number of channels is determined by write/reads from identical 2824 Comments: The number of channels is determined by write/reads from identical
2825 offsets within the SRAM address spaces for channels 0 and 4. 2825 offsets within the SRAM address spaces for channels 0 and 4.
2826 If the channel 4 space is mirrored to channel 0 it is a 4 channel 2826 If the channel 4 space is mirrored to channel 0 it is a 4 channel
2827 AIOP, otherwise it is an 8 channel. 2827 AIOP, otherwise it is an 8 channel.
2828 Warnings: No context switches are allowed while executing this function. 2828 Warnings: No context switches are allowed while executing this function.
2829 */ 2829 */
2830 static int sReadAiopNumChan(WordIO_t io) 2830 static int sReadAiopNumChan(WordIO_t io)
2831 { 2831 {
2832 Word_t x; 2832 Word_t x;
2833 static Byte_t R[4] = { 0x00, 0x00, 0x34, 0x12 }; 2833 static Byte_t R[4] = { 0x00, 0x00, 0x34, 0x12 };
2834 2834
2835 /* write to chan 0 SRAM */ 2835 /* write to chan 0 SRAM */
2836 out32((DWordIO_t) io + _INDX_ADDR, R); 2836 out32((DWordIO_t) io + _INDX_ADDR, R);
2837 sOutW(io + _INDX_ADDR, 0); /* read from SRAM, chan 0 */ 2837 sOutW(io + _INDX_ADDR, 0); /* read from SRAM, chan 0 */
2838 x = sInW(io + _INDX_DATA); 2838 x = sInW(io + _INDX_DATA);
2839 sOutW(io + _INDX_ADDR, 0x4000); /* read from SRAM, chan 4 */ 2839 sOutW(io + _INDX_ADDR, 0x4000); /* read from SRAM, chan 4 */
2840 if (x != sInW(io + _INDX_DATA)) /* if different must be 8 chan */ 2840 if (x != sInW(io + _INDX_DATA)) /* if different must be 8 chan */
2841 return (8); 2841 return (8);
2842 else 2842 else
2843 return (4); 2843 return (4);
2844 } 2844 }
2845 2845
2846 /*************************************************************************** 2846 /***************************************************************************
2847 Function: sInitChan 2847 Function: sInitChan
2848 Purpose: Initialization of a channel and channel structure 2848 Purpose: Initialization of a channel and channel structure
2849 Call: sInitChan(CtlP,ChP,AiopNum,ChanNum) 2849 Call: sInitChan(CtlP,ChP,AiopNum,ChanNum)
2850 CONTROLLER_T *CtlP; Ptr to controller structure 2850 CONTROLLER_T *CtlP; Ptr to controller structure
2851 CHANNEL_T *ChP; Ptr to channel structure 2851 CHANNEL_T *ChP; Ptr to channel structure
2852 int AiopNum; AIOP number within controller 2852 int AiopNum; AIOP number within controller
2853 int ChanNum; Channel number within AIOP 2853 int ChanNum; Channel number within AIOP
2854 Return: int: 1 if initialization succeeded, 0 if it fails because channel 2854 Return: int: 1 if initialization succeeded, 0 if it fails because channel
2855 number exceeds number of channels available in AIOP. 2855 number exceeds number of channels available in AIOP.
2856 Comments: This function must be called before a channel can be used. 2856 Comments: This function must be called before a channel can be used.
2857 Warnings: No range checking on any of the parameters is done. 2857 Warnings: No range checking on any of the parameters is done.
2858 2858
2859 No context switches are allowed while executing this function. 2859 No context switches are allowed while executing this function.
2860 */ 2860 */
2861 static int sInitChan(CONTROLLER_T * CtlP, CHANNEL_T * ChP, int AiopNum, 2861 static int sInitChan(CONTROLLER_T * CtlP, CHANNEL_T * ChP, int AiopNum,
2862 int ChanNum) 2862 int ChanNum)
2863 { 2863 {
2864 int i; 2864 int i;
2865 WordIO_t AiopIO; 2865 WordIO_t AiopIO;
2866 WordIO_t ChIOOff; 2866 WordIO_t ChIOOff;
2867 Byte_t *ChR; 2867 Byte_t *ChR;
2868 Word_t ChOff; 2868 Word_t ChOff;
2869 static Byte_t R[4]; 2869 static Byte_t R[4];
2870 int brd9600; 2870 int brd9600;
2871 2871
2872 if (ChanNum >= CtlP->AiopNumChan[AiopNum]) 2872 if (ChanNum >= CtlP->AiopNumChan[AiopNum])
2873 return 0; /* exceeds num chans in AIOP */ 2873 return 0; /* exceeds num chans in AIOP */
2874 2874
2875 /* Channel, AIOP, and controller identifiers */ 2875 /* Channel, AIOP, and controller identifiers */
2876 ChP->CtlP = CtlP; 2876 ChP->CtlP = CtlP;
2877 ChP->ChanID = CtlP->AiopID[AiopNum]; 2877 ChP->ChanID = CtlP->AiopID[AiopNum];
2878 ChP->AiopNum = AiopNum; 2878 ChP->AiopNum = AiopNum;
2879 ChP->ChanNum = ChanNum; 2879 ChP->ChanNum = ChanNum;
2880 2880
2881 /* Global direct addresses */ 2881 /* Global direct addresses */
2882 AiopIO = CtlP->AiopIO[AiopNum]; 2882 AiopIO = CtlP->AiopIO[AiopNum];
2883 ChP->Cmd = (ByteIO_t) AiopIO + _CMD_REG; 2883 ChP->Cmd = (ByteIO_t) AiopIO + _CMD_REG;
2884 ChP->IntChan = (ByteIO_t) AiopIO + _INT_CHAN; 2884 ChP->IntChan = (ByteIO_t) AiopIO + _INT_CHAN;
2885 ChP->IntMask = (ByteIO_t) AiopIO + _INT_MASK; 2885 ChP->IntMask = (ByteIO_t) AiopIO + _INT_MASK;
2886 ChP->IndexAddr = (DWordIO_t) AiopIO + _INDX_ADDR; 2886 ChP->IndexAddr = (DWordIO_t) AiopIO + _INDX_ADDR;
2887 ChP->IndexData = AiopIO + _INDX_DATA; 2887 ChP->IndexData = AiopIO + _INDX_DATA;
2888 2888
2889 /* Channel direct addresses */ 2889 /* Channel direct addresses */
2890 ChIOOff = AiopIO + ChP->ChanNum * 2; 2890 ChIOOff = AiopIO + ChP->ChanNum * 2;
2891 ChP->TxRxData = ChIOOff + _TD0; 2891 ChP->TxRxData = ChIOOff + _TD0;
2892 ChP->ChanStat = ChIOOff + _CHN_STAT0; 2892 ChP->ChanStat = ChIOOff + _CHN_STAT0;
2893 ChP->TxRxCount = ChIOOff + _FIFO_CNT0; 2893 ChP->TxRxCount = ChIOOff + _FIFO_CNT0;
2894 ChP->IntID = (ByteIO_t) AiopIO + ChP->ChanNum + _INT_ID0; 2894 ChP->IntID = (ByteIO_t) AiopIO + ChP->ChanNum + _INT_ID0;
2895 2895
2896 /* Initialize the channel from the RData array */ 2896 /* Initialize the channel from the RData array */
2897 for (i = 0; i < RDATASIZE; i += 4) { 2897 for (i = 0; i < RDATASIZE; i += 4) {
2898 R[0] = RData[i]; 2898 R[0] = RData[i];
2899 R[1] = RData[i + 1] + 0x10 * ChanNum; 2899 R[1] = RData[i + 1] + 0x10 * ChanNum;
2900 R[2] = RData[i + 2]; 2900 R[2] = RData[i + 2];
2901 R[3] = RData[i + 3]; 2901 R[3] = RData[i + 3];
2902 out32(ChP->IndexAddr, R); 2902 out32(ChP->IndexAddr, R);
2903 } 2903 }
2904 2904
2905 ChR = ChP->R; 2905 ChR = ChP->R;
2906 for (i = 0; i < RREGDATASIZE; i += 4) { 2906 for (i = 0; i < RREGDATASIZE; i += 4) {
2907 ChR[i] = RRegData[i]; 2907 ChR[i] = RRegData[i];
2908 ChR[i + 1] = RRegData[i + 1] + 0x10 * ChanNum; 2908 ChR[i + 1] = RRegData[i + 1] + 0x10 * ChanNum;
2909 ChR[i + 2] = RRegData[i + 2]; 2909 ChR[i + 2] = RRegData[i + 2];
2910 ChR[i + 3] = RRegData[i + 3]; 2910 ChR[i + 3] = RRegData[i + 3];
2911 } 2911 }
2912 2912
2913 /* Indexed registers */ 2913 /* Indexed registers */
2914 ChOff = (Word_t) ChanNum *0x1000; 2914 ChOff = (Word_t) ChanNum *0x1000;
2915 2915
2916 if (sClockPrescale == 0x14) 2916 if (sClockPrescale == 0x14)
2917 brd9600 = 47; 2917 brd9600 = 47;
2918 else 2918 else
2919 brd9600 = 23; 2919 brd9600 = 23;
2920 2920
2921 ChP->BaudDiv[0] = (Byte_t) (ChOff + _BAUD); 2921 ChP->BaudDiv[0] = (Byte_t) (ChOff + _BAUD);
2922 ChP->BaudDiv[1] = (Byte_t) ((ChOff + _BAUD) >> 8); 2922 ChP->BaudDiv[1] = (Byte_t) ((ChOff + _BAUD) >> 8);
2923 ChP->BaudDiv[2] = (Byte_t) brd9600; 2923 ChP->BaudDiv[2] = (Byte_t) brd9600;
2924 ChP->BaudDiv[3] = (Byte_t) (brd9600 >> 8); 2924 ChP->BaudDiv[3] = (Byte_t) (brd9600 >> 8);
2925 out32(ChP->IndexAddr, ChP->BaudDiv); 2925 out32(ChP->IndexAddr, ChP->BaudDiv);
2926 2926
2927 ChP->TxControl[0] = (Byte_t) (ChOff + _TX_CTRL); 2927 ChP->TxControl[0] = (Byte_t) (ChOff + _TX_CTRL);
2928 ChP->TxControl[1] = (Byte_t) ((ChOff + _TX_CTRL) >> 8); 2928 ChP->TxControl[1] = (Byte_t) ((ChOff + _TX_CTRL) >> 8);
2929 ChP->TxControl[2] = 0; 2929 ChP->TxControl[2] = 0;
2930 ChP->TxControl[3] = 0; 2930 ChP->TxControl[3] = 0;
2931 out32(ChP->IndexAddr, ChP->TxControl); 2931 out32(ChP->IndexAddr, ChP->TxControl);
2932 2932
2933 ChP->RxControl[0] = (Byte_t) (ChOff + _RX_CTRL); 2933 ChP->RxControl[0] = (Byte_t) (ChOff + _RX_CTRL);
2934 ChP->RxControl[1] = (Byte_t) ((ChOff + _RX_CTRL) >> 8); 2934 ChP->RxControl[1] = (Byte_t) ((ChOff + _RX_CTRL) >> 8);
2935 ChP->RxControl[2] = 0; 2935 ChP->RxControl[2] = 0;
2936 ChP->RxControl[3] = 0; 2936 ChP->RxControl[3] = 0;
2937 out32(ChP->IndexAddr, ChP->RxControl); 2937 out32(ChP->IndexAddr, ChP->RxControl);
2938 2938
2939 ChP->TxEnables[0] = (Byte_t) (ChOff + _TX_ENBLS); 2939 ChP->TxEnables[0] = (Byte_t) (ChOff + _TX_ENBLS);
2940 ChP->TxEnables[1] = (Byte_t) ((ChOff + _TX_ENBLS) >> 8); 2940 ChP->TxEnables[1] = (Byte_t) ((ChOff + _TX_ENBLS) >> 8);
2941 ChP->TxEnables[2] = 0; 2941 ChP->TxEnables[2] = 0;
2942 ChP->TxEnables[3] = 0; 2942 ChP->TxEnables[3] = 0;
2943 out32(ChP->IndexAddr, ChP->TxEnables); 2943 out32(ChP->IndexAddr, ChP->TxEnables);
2944 2944
2945 ChP->TxCompare[0] = (Byte_t) (ChOff + _TXCMP1); 2945 ChP->TxCompare[0] = (Byte_t) (ChOff + _TXCMP1);
2946 ChP->TxCompare[1] = (Byte_t) ((ChOff + _TXCMP1) >> 8); 2946 ChP->TxCompare[1] = (Byte_t) ((ChOff + _TXCMP1) >> 8);
2947 ChP->TxCompare[2] = 0; 2947 ChP->TxCompare[2] = 0;
2948 ChP->TxCompare[3] = 0; 2948 ChP->TxCompare[3] = 0;
2949 out32(ChP->IndexAddr, ChP->TxCompare); 2949 out32(ChP->IndexAddr, ChP->TxCompare);
2950 2950
2951 ChP->TxReplace1[0] = (Byte_t) (ChOff + _TXREP1B1); 2951 ChP->TxReplace1[0] = (Byte_t) (ChOff + _TXREP1B1);
2952 ChP->TxReplace1[1] = (Byte_t) ((ChOff + _TXREP1B1) >> 8); 2952 ChP->TxReplace1[1] = (Byte_t) ((ChOff + _TXREP1B1) >> 8);
2953 ChP->TxReplace1[2] = 0; 2953 ChP->TxReplace1[2] = 0;
2954 ChP->TxReplace1[3] = 0; 2954 ChP->TxReplace1[3] = 0;
2955 out32(ChP->IndexAddr, ChP->TxReplace1); 2955 out32(ChP->IndexAddr, ChP->TxReplace1);
2956 2956
2957 ChP->TxReplace2[0] = (Byte_t) (ChOff + _TXREP2); 2957 ChP->TxReplace2[0] = (Byte_t) (ChOff + _TXREP2);
2958 ChP->TxReplace2[1] = (Byte_t) ((ChOff + _TXREP2) >> 8); 2958 ChP->TxReplace2[1] = (Byte_t) ((ChOff + _TXREP2) >> 8);
2959 ChP->TxReplace2[2] = 0; 2959 ChP->TxReplace2[2] = 0;
2960 ChP->TxReplace2[3] = 0; 2960 ChP->TxReplace2[3] = 0;
2961 out32(ChP->IndexAddr, ChP->TxReplace2); 2961 out32(ChP->IndexAddr, ChP->TxReplace2);
2962 2962
2963 ChP->TxFIFOPtrs = ChOff + _TXF_OUTP; 2963 ChP->TxFIFOPtrs = ChOff + _TXF_OUTP;
2964 ChP->TxFIFO = ChOff + _TX_FIFO; 2964 ChP->TxFIFO = ChOff + _TX_FIFO;
2965 2965
2966 sOutB(ChP->Cmd, (Byte_t) ChanNum | RESTXFCNT); /* apply reset Tx FIFO count */ 2966 sOutB(ChP->Cmd, (Byte_t) ChanNum | RESTXFCNT); /* apply reset Tx FIFO count */
2967 sOutB(ChP->Cmd, (Byte_t) ChanNum); /* remove reset Tx FIFO count */ 2967 sOutB(ChP->Cmd, (Byte_t) ChanNum); /* remove reset Tx FIFO count */
2968 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxFIFOPtrs); /* clear Tx in/out ptrs */ 2968 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxFIFOPtrs); /* clear Tx in/out ptrs */
2969 sOutW(ChP->IndexData, 0); 2969 sOutW(ChP->IndexData, 0);
2970 ChP->RxFIFOPtrs = ChOff + _RXF_OUTP; 2970 ChP->RxFIFOPtrs = ChOff + _RXF_OUTP;
2971 ChP->RxFIFO = ChOff + _RX_FIFO; 2971 ChP->RxFIFO = ChOff + _RX_FIFO;
2972 2972
2973 sOutB(ChP->Cmd, (Byte_t) ChanNum | RESRXFCNT); /* apply reset Rx FIFO count */ 2973 sOutB(ChP->Cmd, (Byte_t) ChanNum | RESRXFCNT); /* apply reset Rx FIFO count */
2974 sOutB(ChP->Cmd, (Byte_t) ChanNum); /* remove reset Rx FIFO count */ 2974 sOutB(ChP->Cmd, (Byte_t) ChanNum); /* remove reset Rx FIFO count */
2975 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs); /* clear Rx out ptr */ 2975 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs); /* clear Rx out ptr */
2976 sOutW(ChP->IndexData, 0); 2976 sOutW(ChP->IndexData, 0);
2977 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs + 2); /* clear Rx in ptr */ 2977 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs + 2); /* clear Rx in ptr */
2978 sOutW(ChP->IndexData, 0); 2978 sOutW(ChP->IndexData, 0);
2979 ChP->TxPrioCnt = ChOff + _TXP_CNT; 2979 ChP->TxPrioCnt = ChOff + _TXP_CNT;
2980 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxPrioCnt); 2980 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxPrioCnt);
2981 sOutB(ChP->IndexData, 0); 2981 sOutB(ChP->IndexData, 0);
2982 ChP->TxPrioPtr = ChOff + _TXP_PNTR; 2982 ChP->TxPrioPtr = ChOff + _TXP_PNTR;
2983 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxPrioPtr); 2983 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxPrioPtr);
2984 sOutB(ChP->IndexData, 0); 2984 sOutB(ChP->IndexData, 0);
2985 ChP->TxPrioBuf = ChOff + _TXP_BUF; 2985 ChP->TxPrioBuf = ChOff + _TXP_BUF;
2986 sEnRxProcessor(ChP); /* start the Rx processor */ 2986 sEnRxProcessor(ChP); /* start the Rx processor */
2987 2987
2988 return 1; 2988 return 1;
2989 } 2989 }
2990 2990
2991 /*************************************************************************** 2991 /***************************************************************************
2992 Function: sStopRxProcessor 2992 Function: sStopRxProcessor
2993 Purpose: Stop the receive processor from processing a channel. 2993 Purpose: Stop the receive processor from processing a channel.
2994 Call: sStopRxProcessor(ChP) 2994 Call: sStopRxProcessor(ChP)
2995 CHANNEL_T *ChP; Ptr to channel structure 2995 CHANNEL_T *ChP; Ptr to channel structure
2996 2996
2997 Comments: The receive processor can be started again with sStartRxProcessor(). 2997 Comments: The receive processor can be started again with sStartRxProcessor().
2998 This function causes the receive processor to skip over the 2998 This function causes the receive processor to skip over the
2999 stopped channel. It does not stop it from processing other channels. 2999 stopped channel. It does not stop it from processing other channels.
3000 3000
3001 Warnings: No context switches are allowed while executing this function. 3001 Warnings: No context switches are allowed while executing this function.
3002 3002
3003 Do not leave the receive processor stopped for more than one 3003 Do not leave the receive processor stopped for more than one
3004 character time. 3004 character time.
3005 3005
3006 After calling this function a delay of 4 uS is required to ensure 3006 After calling this function a delay of 4 uS is required to ensure
3007 that the receive processor is no longer processing this channel. 3007 that the receive processor is no longer processing this channel.
3008 */ 3008 */
3009 static void sStopRxProcessor(CHANNEL_T * ChP) 3009 static void sStopRxProcessor(CHANNEL_T * ChP)
3010 { 3010 {
3011 Byte_t R[4]; 3011 Byte_t R[4];
3012 3012
3013 R[0] = ChP->R[0]; 3013 R[0] = ChP->R[0];
3014 R[1] = ChP->R[1]; 3014 R[1] = ChP->R[1];
3015 R[2] = 0x0a; 3015 R[2] = 0x0a;
3016 R[3] = ChP->R[3]; 3016 R[3] = ChP->R[3];
3017 out32(ChP->IndexAddr, R); 3017 out32(ChP->IndexAddr, R);
3018 } 3018 }
3019 3019
3020 /*************************************************************************** 3020 /***************************************************************************
3021 Function: sFlushRxFIFO 3021 Function: sFlushRxFIFO
3022 Purpose: Flush the Rx FIFO 3022 Purpose: Flush the Rx FIFO
3023 Call: sFlushRxFIFO(ChP) 3023 Call: sFlushRxFIFO(ChP)
3024 CHANNEL_T *ChP; Ptr to channel structure 3024 CHANNEL_T *ChP; Ptr to channel structure
3025 Return: void 3025 Return: void
3026 Comments: To prevent data from being enqueued or dequeued in the Tx FIFO 3026 Comments: To prevent data from being enqueued or dequeued in the Tx FIFO
3027 while it is being flushed the receive processor is stopped 3027 while it is being flushed the receive processor is stopped
3028 and the transmitter is disabled. After these operations a 3028 and the transmitter is disabled. After these operations a
3029 4 uS delay is done before clearing the pointers to allow 3029 4 uS delay is done before clearing the pointers to allow
3030 the receive processor to stop. These items are handled inside 3030 the receive processor to stop. These items are handled inside
3031 this function. 3031 this function.
3032 Warnings: No context switches are allowed while executing this function. 3032 Warnings: No context switches are allowed while executing this function.
3033 */ 3033 */
3034 static void sFlushRxFIFO(CHANNEL_T * ChP) 3034 static void sFlushRxFIFO(CHANNEL_T * ChP)
3035 { 3035 {
3036 int i; 3036 int i;
3037 Byte_t Ch; /* channel number within AIOP */ 3037 Byte_t Ch; /* channel number within AIOP */
3038 int RxFIFOEnabled; /* 1 if Rx FIFO enabled */ 3038 int RxFIFOEnabled; /* 1 if Rx FIFO enabled */
3039 3039
3040 if (sGetRxCnt(ChP) == 0) /* Rx FIFO empty */ 3040 if (sGetRxCnt(ChP) == 0) /* Rx FIFO empty */
3041 return; /* don't need to flush */ 3041 return; /* don't need to flush */
3042 3042
3043 RxFIFOEnabled = 0; 3043 RxFIFOEnabled = 0;
3044 if (ChP->R[0x32] == 0x08) { /* Rx FIFO is enabled */ 3044 if (ChP->R[0x32] == 0x08) { /* Rx FIFO is enabled */
3045 RxFIFOEnabled = 1; 3045 RxFIFOEnabled = 1;
3046 sDisRxFIFO(ChP); /* disable it */ 3046 sDisRxFIFO(ChP); /* disable it */
3047 for (i = 0; i < 2000 / 200; i++) /* delay 2 uS to allow proc to disable FIFO */ 3047 for (i = 0; i < 2000 / 200; i++) /* delay 2 uS to allow proc to disable FIFO */
3048 sInB(ChP->IntChan); /* depends on bus i/o timing */ 3048 sInB(ChP->IntChan); /* depends on bus i/o timing */
3049 } 3049 }
3050 sGetChanStatus(ChP); /* clear any pending Rx errors in chan stat */ 3050 sGetChanStatus(ChP); /* clear any pending Rx errors in chan stat */
3051 Ch = (Byte_t) sGetChanNum(ChP); 3051 Ch = (Byte_t) sGetChanNum(ChP);
3052 sOutB(ChP->Cmd, Ch | RESRXFCNT); /* apply reset Rx FIFO count */ 3052 sOutB(ChP->Cmd, Ch | RESRXFCNT); /* apply reset Rx FIFO count */
3053 sOutB(ChP->Cmd, Ch); /* remove reset Rx FIFO count */ 3053 sOutB(ChP->Cmd, Ch); /* remove reset Rx FIFO count */
3054 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs); /* clear Rx out ptr */ 3054 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs); /* clear Rx out ptr */
3055 sOutW(ChP->IndexData, 0); 3055 sOutW(ChP->IndexData, 0);
3056 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs + 2); /* clear Rx in ptr */ 3056 sOutW((WordIO_t) ChP->IndexAddr, ChP->RxFIFOPtrs + 2); /* clear Rx in ptr */
3057 sOutW(ChP->IndexData, 0); 3057 sOutW(ChP->IndexData, 0);
3058 if (RxFIFOEnabled) 3058 if (RxFIFOEnabled)
3059 sEnRxFIFO(ChP); /* enable Rx FIFO */ 3059 sEnRxFIFO(ChP); /* enable Rx FIFO */
3060 } 3060 }
3061 3061
3062 /*************************************************************************** 3062 /***************************************************************************
3063 Function: sFlushTxFIFO 3063 Function: sFlushTxFIFO
3064 Purpose: Flush the Tx FIFO 3064 Purpose: Flush the Tx FIFO
3065 Call: sFlushTxFIFO(ChP) 3065 Call: sFlushTxFIFO(ChP)
3066 CHANNEL_T *ChP; Ptr to channel structure 3066 CHANNEL_T *ChP; Ptr to channel structure
3067 Return: void 3067 Return: void
3068 Comments: To prevent data from being enqueued or dequeued in the Tx FIFO 3068 Comments: To prevent data from being enqueued or dequeued in the Tx FIFO
3069 while it is being flushed the receive processor is stopped 3069 while it is being flushed the receive processor is stopped
3070 and the transmitter is disabled. After these operations a 3070 and the transmitter is disabled. After these operations a
3071 4 uS delay is done before clearing the pointers to allow 3071 4 uS delay is done before clearing the pointers to allow
3072 the receive processor to stop. These items are handled inside 3072 the receive processor to stop. These items are handled inside
3073 this function. 3073 this function.
3074 Warnings: No context switches are allowed while executing this function. 3074 Warnings: No context switches are allowed while executing this function.
3075 */ 3075 */
3076 static void sFlushTxFIFO(CHANNEL_T * ChP) 3076 static void sFlushTxFIFO(CHANNEL_T * ChP)
3077 { 3077 {
3078 int i; 3078 int i;
3079 Byte_t Ch; /* channel number within AIOP */ 3079 Byte_t Ch; /* channel number within AIOP */
3080 int TxEnabled; /* 1 if transmitter enabled */ 3080 int TxEnabled; /* 1 if transmitter enabled */
3081 3081
3082 if (sGetTxCnt(ChP) == 0) /* Tx FIFO empty */ 3082 if (sGetTxCnt(ChP) == 0) /* Tx FIFO empty */
3083 return; /* don't need to flush */ 3083 return; /* don't need to flush */
3084 3084
3085 TxEnabled = 0; 3085 TxEnabled = 0;
3086 if (ChP->TxControl[3] & TX_ENABLE) { 3086 if (ChP->TxControl[3] & TX_ENABLE) {
3087 TxEnabled = 1; 3087 TxEnabled = 1;
3088 sDisTransmit(ChP); /* disable transmitter */ 3088 sDisTransmit(ChP); /* disable transmitter */
3089 } 3089 }
3090 sStopRxProcessor(ChP); /* stop Rx processor */ 3090 sStopRxProcessor(ChP); /* stop Rx processor */
3091 for (i = 0; i < 4000 / 200; i++) /* delay 4 uS to allow proc to stop */ 3091 for (i = 0; i < 4000 / 200; i++) /* delay 4 uS to allow proc to stop */
3092 sInB(ChP->IntChan); /* depends on bus i/o timing */ 3092 sInB(ChP->IntChan); /* depends on bus i/o timing */
3093 Ch = (Byte_t) sGetChanNum(ChP); 3093 Ch = (Byte_t) sGetChanNum(ChP);
3094 sOutB(ChP->Cmd, Ch | RESTXFCNT); /* apply reset Tx FIFO count */ 3094 sOutB(ChP->Cmd, Ch | RESTXFCNT); /* apply reset Tx FIFO count */
3095 sOutB(ChP->Cmd, Ch); /* remove reset Tx FIFO count */ 3095 sOutB(ChP->Cmd, Ch); /* remove reset Tx FIFO count */
3096 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxFIFOPtrs); /* clear Tx in/out ptrs */ 3096 sOutW((WordIO_t) ChP->IndexAddr, ChP->TxFIFOPtrs); /* clear Tx in/out ptrs */
3097 sOutW(ChP->IndexData, 0); 3097 sOutW(ChP->IndexData, 0);
3098 if (TxEnabled) 3098 if (TxEnabled)
3099 sEnTransmit(ChP); /* enable transmitter */ 3099 sEnTransmit(ChP); /* enable transmitter */
3100 sStartRxProcessor(ChP); /* restart Rx processor */ 3100 sStartRxProcessor(ChP); /* restart Rx processor */
3101 } 3101 }
3102 3102
3103 /*************************************************************************** 3103 /***************************************************************************
3104 Function: sWriteTxPrioByte 3104 Function: sWriteTxPrioByte
3105 Purpose: Write a byte of priority transmit data to a channel 3105 Purpose: Write a byte of priority transmit data to a channel
3106 Call: sWriteTxPrioByte(ChP,Data) 3106 Call: sWriteTxPrioByte(ChP,Data)
3107 CHANNEL_T *ChP; Ptr to channel structure 3107 CHANNEL_T *ChP; Ptr to channel structure
3108 Byte_t Data; The transmit data byte 3108 Byte_t Data; The transmit data byte
3109 3109
3110 Return: int: 1 if the bytes is successfully written, otherwise 0. 3110 Return: int: 1 if the bytes is successfully written, otherwise 0.
3111 3111
3112 Comments: The priority byte is transmitted before any data in the Tx FIFO. 3112 Comments: The priority byte is transmitted before any data in the Tx FIFO.
3113 3113
3114 Warnings: No context switches are allowed while executing this function. 3114 Warnings: No context switches are allowed while executing this function.
3115 */ 3115 */
3116 static int sWriteTxPrioByte(CHANNEL_T * ChP, Byte_t Data) 3116 static int sWriteTxPrioByte(CHANNEL_T * ChP, Byte_t Data)
3117 { 3117 {
3118 Byte_t DWBuf[4]; /* buffer for double word writes */ 3118 Byte_t DWBuf[4]; /* buffer for double word writes */
3119 Word_t *WordPtr; /* must be far because Win SS != DS */ 3119 Word_t *WordPtr; /* must be far because Win SS != DS */
3120 register DWordIO_t IndexAddr; 3120 register DWordIO_t IndexAddr;
3121 3121
3122 if (sGetTxCnt(ChP) > 1) { /* write it to Tx priority buffer */ 3122 if (sGetTxCnt(ChP) > 1) { /* write it to Tx priority buffer */
3123 IndexAddr = ChP->IndexAddr; 3123 IndexAddr = ChP->IndexAddr;
3124 sOutW((WordIO_t) IndexAddr, ChP->TxPrioCnt); /* get priority buffer status */ 3124 sOutW((WordIO_t) IndexAddr, ChP->TxPrioCnt); /* get priority buffer status */
3125 if (sInB((ByteIO_t) ChP->IndexData) & PRI_PEND) /* priority buffer busy */ 3125 if (sInB((ByteIO_t) ChP->IndexData) & PRI_PEND) /* priority buffer busy */
3126 return (0); /* nothing sent */ 3126 return (0); /* nothing sent */
3127 3127
3128 WordPtr = (Word_t *) (&DWBuf[0]); 3128 WordPtr = (Word_t *) (&DWBuf[0]);
3129 *WordPtr = ChP->TxPrioBuf; /* data byte address */ 3129 *WordPtr = ChP->TxPrioBuf; /* data byte address */
3130 3130
3131 DWBuf[2] = Data; /* data byte value */ 3131 DWBuf[2] = Data; /* data byte value */
3132 out32(IndexAddr, DWBuf); /* write it out */ 3132 out32(IndexAddr, DWBuf); /* write it out */
3133 3133
3134 *WordPtr = ChP->TxPrioCnt; /* Tx priority count address */ 3134 *WordPtr = ChP->TxPrioCnt; /* Tx priority count address */
3135 3135
3136 DWBuf[2] = PRI_PEND + 1; /* indicate 1 byte pending */ 3136 DWBuf[2] = PRI_PEND + 1; /* indicate 1 byte pending */
3137 DWBuf[3] = 0; /* priority buffer pointer */ 3137 DWBuf[3] = 0; /* priority buffer pointer */
3138 out32(IndexAddr, DWBuf); /* write it out */ 3138 out32(IndexAddr, DWBuf); /* write it out */
3139 } else { /* write it to Tx FIFO */ 3139 } else { /* write it to Tx FIFO */
3140 3140
3141 sWriteTxByte(sGetTxRxDataIO(ChP), Data); 3141 sWriteTxByte(sGetTxRxDataIO(ChP), Data);
3142 } 3142 }
3143 return (1); /* 1 byte sent */ 3143 return (1); /* 1 byte sent */
3144 } 3144 }
3145 3145
3146 /*************************************************************************** 3146 /***************************************************************************
3147 Function: sEnInterrupts 3147 Function: sEnInterrupts
3148 Purpose: Enable one or more interrupts for a channel 3148 Purpose: Enable one or more interrupts for a channel
3149 Call: sEnInterrupts(ChP,Flags) 3149 Call: sEnInterrupts(ChP,Flags)
3150 CHANNEL_T *ChP; Ptr to channel structure 3150 CHANNEL_T *ChP; Ptr to channel structure
3151 Word_t Flags: Interrupt enable flags, can be any combination 3151 Word_t Flags: Interrupt enable flags, can be any combination
3152 of the following flags: 3152 of the following flags:
3153 TXINT_EN: Interrupt on Tx FIFO empty 3153 TXINT_EN: Interrupt on Tx FIFO empty
3154 RXINT_EN: Interrupt on Rx FIFO at trigger level (see 3154 RXINT_EN: Interrupt on Rx FIFO at trigger level (see
3155 sSetRxTrigger()) 3155 sSetRxTrigger())
3156 SRCINT_EN: Interrupt on SRC (Special Rx Condition) 3156 SRCINT_EN: Interrupt on SRC (Special Rx Condition)
3157 MCINT_EN: Interrupt on modem input change 3157 MCINT_EN: Interrupt on modem input change
3158 CHANINT_EN: Allow channel interrupt signal to the AIOP's 3158 CHANINT_EN: Allow channel interrupt signal to the AIOP's
3159 Interrupt Channel Register. 3159 Interrupt Channel Register.
3160 Return: void 3160 Return: void
3161 Comments: If an interrupt enable flag is set in Flags, that interrupt will be 3161 Comments: If an interrupt enable flag is set in Flags, that interrupt will be
3162 enabled. If an interrupt enable flag is not set in Flags, that 3162 enabled. If an interrupt enable flag is not set in Flags, that
3163 interrupt will not be changed. Interrupts can be disabled with 3163 interrupt will not be changed. Interrupts can be disabled with
3164 function sDisInterrupts(). 3164 function sDisInterrupts().
3165 3165
3166 This function sets the appropriate bit for the channel in the AIOP's 3166 This function sets the appropriate bit for the channel in the AIOP's
3167 Interrupt Mask Register if the CHANINT_EN flag is set. This allows 3167 Interrupt Mask Register if the CHANINT_EN flag is set. This allows
3168 this channel's bit to be set in the AIOP's Interrupt Channel Register. 3168 this channel's bit to be set in the AIOP's Interrupt Channel Register.
3169 3169
3170 Interrupts must also be globally enabled before channel interrupts 3170 Interrupts must also be globally enabled before channel interrupts
3171 will be passed on to the host. This is done with function 3171 will be passed on to the host. This is done with function
3172 sEnGlobalInt(). 3172 sEnGlobalInt().
3173 3173
3174 In some cases it may be desirable to disable interrupts globally but 3174 In some cases it may be desirable to disable interrupts globally but
3175 enable channel interrupts. This would allow the global interrupt 3175 enable channel interrupts. This would allow the global interrupt
3176 status register to be used to determine which AIOPs need service. 3176 status register to be used to determine which AIOPs need service.
3177 */ 3177 */
3178 static void sEnInterrupts(CHANNEL_T * ChP, Word_t Flags) 3178 static void sEnInterrupts(CHANNEL_T * ChP, Word_t Flags)
3179 { 3179 {
3180 Byte_t Mask; /* Interrupt Mask Register */ 3180 Byte_t Mask; /* Interrupt Mask Register */
3181 3181
3182 ChP->RxControl[2] |= 3182 ChP->RxControl[2] |=
3183 ((Byte_t) Flags & (RXINT_EN | SRCINT_EN | MCINT_EN)); 3183 ((Byte_t) Flags & (RXINT_EN | SRCINT_EN | MCINT_EN));
3184 3184
3185 out32(ChP->IndexAddr, ChP->RxControl); 3185 out32(ChP->IndexAddr, ChP->RxControl);
3186 3186
3187 ChP->TxControl[2] |= ((Byte_t) Flags & TXINT_EN); 3187 ChP->TxControl[2] |= ((Byte_t) Flags & TXINT_EN);
3188 3188
3189 out32(ChP->IndexAddr, ChP->TxControl); 3189 out32(ChP->IndexAddr, ChP->TxControl);
3190 3190
3191 if (Flags & CHANINT_EN) { 3191 if (Flags & CHANINT_EN) {
3192 Mask = sInB(ChP->IntMask) | sBitMapSetTbl[ChP->ChanNum]; 3192 Mask = sInB(ChP->IntMask) | sBitMapSetTbl[ChP->ChanNum];
3193 sOutB(ChP->IntMask, Mask); 3193 sOutB(ChP->IntMask, Mask);
3194 } 3194 }
3195 } 3195 }
3196 3196
3197 /*************************************************************************** 3197 /***************************************************************************
3198 Function: sDisInterrupts 3198 Function: sDisInterrupts
3199 Purpose: Disable one or more interrupts for a channel 3199 Purpose: Disable one or more interrupts for a channel
3200 Call: sDisInterrupts(ChP,Flags) 3200 Call: sDisInterrupts(ChP,Flags)
3201 CHANNEL_T *ChP; Ptr to channel structure 3201 CHANNEL_T *ChP; Ptr to channel structure
3202 Word_t Flags: Interrupt flags, can be any combination 3202 Word_t Flags: Interrupt flags, can be any combination
3203 of the following flags: 3203 of the following flags:
3204 TXINT_EN: Interrupt on Tx FIFO empty 3204 TXINT_EN: Interrupt on Tx FIFO empty
3205 RXINT_EN: Interrupt on Rx FIFO at trigger level (see 3205 RXINT_EN: Interrupt on Rx FIFO at trigger level (see
3206 sSetRxTrigger()) 3206 sSetRxTrigger())
3207 SRCINT_EN: Interrupt on SRC (Special Rx Condition) 3207 SRCINT_EN: Interrupt on SRC (Special Rx Condition)
3208 MCINT_EN: Interrupt on modem input change 3208 MCINT_EN: Interrupt on modem input change
3209 CHANINT_EN: Disable channel interrupt signal to the 3209 CHANINT_EN: Disable channel interrupt signal to the
3210 AIOP's Interrupt Channel Register. 3210 AIOP's Interrupt Channel Register.
3211 Return: void 3211 Return: void
3212 Comments: If an interrupt flag is set in Flags, that interrupt will be 3212 Comments: If an interrupt flag is set in Flags, that interrupt will be
3213 disabled. If an interrupt flag is not set in Flags, that 3213 disabled. If an interrupt flag is not set in Flags, that
3214 interrupt will not be changed. Interrupts can be enabled with 3214 interrupt will not be changed. Interrupts can be enabled with
3215 function sEnInterrupts(). 3215 function sEnInterrupts().
3216 3216
3217 This function clears the appropriate bit for the channel in the AIOP's 3217 This function clears the appropriate bit for the channel in the AIOP's
3218 Interrupt Mask Register if the CHANINT_EN flag is set. This blocks 3218 Interrupt Mask Register if the CHANINT_EN flag is set. This blocks
3219 this channel's bit from being set in the AIOP's Interrupt Channel 3219 this channel's bit from being set in the AIOP's Interrupt Channel
3220 Register. 3220 Register.
3221 */ 3221 */
3222 static void sDisInterrupts(CHANNEL_T * ChP, Word_t Flags) 3222 static void sDisInterrupts(CHANNEL_T * ChP, Word_t Flags)
3223 { 3223 {
3224 Byte_t Mask; /* Interrupt Mask Register */ 3224 Byte_t Mask; /* Interrupt Mask Register */
3225 3225
3226 ChP->RxControl[2] &= 3226 ChP->RxControl[2] &=
3227 ~((Byte_t) Flags & (RXINT_EN | SRCINT_EN | MCINT_EN)); 3227 ~((Byte_t) Flags & (RXINT_EN | SRCINT_EN | MCINT_EN));
3228 out32(ChP->IndexAddr, ChP->RxControl); 3228 out32(ChP->IndexAddr, ChP->RxControl);
3229 ChP->TxControl[2] &= ~((Byte_t) Flags & TXINT_EN); 3229 ChP->TxControl[2] &= ~((Byte_t) Flags & TXINT_EN);
3230 out32(ChP->IndexAddr, ChP->TxControl); 3230 out32(ChP->IndexAddr, ChP->TxControl);
3231 3231
3232 if (Flags & CHANINT_EN) { 3232 if (Flags & CHANINT_EN) {
3233 Mask = sInB(ChP->IntMask) & sBitMapClrTbl[ChP->ChanNum]; 3233 Mask = sInB(ChP->IntMask) & sBitMapClrTbl[ChP->ChanNum];
3234 sOutB(ChP->IntMask, Mask); 3234 sOutB(ChP->IntMask, Mask);
3235 } 3235 }
3236 } 3236 }
3237 3237
3238 static void sSetInterfaceMode(CHANNEL_T * ChP, Byte_t mode) 3238 static void sSetInterfaceMode(CHANNEL_T * ChP, Byte_t mode)
3239 { 3239 {
3240 sOutB(ChP->CtlP->AiopIO[2], (mode & 0x18) | ChP->ChanNum); 3240 sOutB(ChP->CtlP->AiopIO[2], (mode & 0x18) | ChP->ChanNum);
3241 } 3241 }
3242 3242
3243 /* 3243 /*
3244 * Not an official SSCI function, but how to reset RocketModems. 3244 * Not an official SSCI function, but how to reset RocketModems.
3245 * ISA bus version 3245 * ISA bus version
3246 */ 3246 */
3247 static void sModemReset(CONTROLLER_T * CtlP, int chan, int on) 3247 static void sModemReset(CONTROLLER_T * CtlP, int chan, int on)
3248 { 3248 {
3249 ByteIO_t addr; 3249 ByteIO_t addr;
3250 Byte_t val; 3250 Byte_t val;
3251 3251
3252 addr = CtlP->AiopIO[0] + 0x400; 3252 addr = CtlP->AiopIO[0] + 0x400;
3253 val = sInB(CtlP->MReg3IO); 3253 val = sInB(CtlP->MReg3IO);
3254 /* if AIOP[1] is not enabled, enable it */ 3254 /* if AIOP[1] is not enabled, enable it */
3255 if ((val & 2) == 0) { 3255 if ((val & 2) == 0) {
3256 val = sInB(CtlP->MReg2IO); 3256 val = sInB(CtlP->MReg2IO);
3257 sOutB(CtlP->MReg2IO, (val & 0xfc) | (1 & 0x03)); 3257 sOutB(CtlP->MReg2IO, (val & 0xfc) | (1 & 0x03));
3258 sOutB(CtlP->MBaseIO, (unsigned char) (addr >> 6)); 3258 sOutB(CtlP->MBaseIO, (unsigned char) (addr >> 6));
3259 } 3259 }
3260 3260
3261 sEnAiop(CtlP, 1); 3261 sEnAiop(CtlP, 1);
3262 if (!on) 3262 if (!on)
3263 addr += 8; 3263 addr += 8;
3264 sOutB(addr + chan, 0); /* apply or remove reset */ 3264 sOutB(addr + chan, 0); /* apply or remove reset */
3265 sDisAiop(CtlP, 1); 3265 sDisAiop(CtlP, 1);
3266 } 3266 }
3267 3267
3268 /* 3268 /*
3269 * Not an official SSCI function, but how to reset RocketModems. 3269 * Not an official SSCI function, but how to reset RocketModems.
3270 * PCI bus version 3270 * PCI bus version
3271 */ 3271 */
3272 static void sPCIModemReset(CONTROLLER_T * CtlP, int chan, int on) 3272 static void sPCIModemReset(CONTROLLER_T * CtlP, int chan, int on)
3273 { 3273 {
3274 ByteIO_t addr; 3274 ByteIO_t addr;
3275 3275
3276 addr = CtlP->AiopIO[0] + 0x40; /* 2nd AIOP */ 3276 addr = CtlP->AiopIO[0] + 0x40; /* 2nd AIOP */
3277 if (!on) 3277 if (!on)
3278 addr += 8; 3278 addr += 8;
3279 sOutB(addr + chan, 0); /* apply or remove reset */ 3279 sOutB(addr + chan, 0); /* apply or remove reset */
3280 } 3280 }
3281 3281
3282 /* Resets the speaker controller on RocketModem II and III devices */ 3282 /* Resets the speaker controller on RocketModem II and III devices */
3283 static void rmSpeakerReset(CONTROLLER_T * CtlP, unsigned long model) 3283 static void rmSpeakerReset(CONTROLLER_T * CtlP, unsigned long model)
3284 { 3284 {
3285 ByteIO_t addr; 3285 ByteIO_t addr;
3286 3286
3287 /* RocketModem II speaker control is at the 8th port location of offset 0x40 */ 3287 /* RocketModem II speaker control is at the 8th port location of offset 0x40 */
3288 if ((model == MODEL_RP4M) || (model == MODEL_RP6M)) { 3288 if ((model == MODEL_RP4M) || (model == MODEL_RP6M)) {
3289 addr = CtlP->AiopIO[0] + 0x4F; 3289 addr = CtlP->AiopIO[0] + 0x4F;
3290 sOutB(addr, 0); 3290 sOutB(addr, 0);
3291 } 3291 }
3292 3292
3293 /* RocketModem III speaker control is at the 1st port location of offset 0x80 */ 3293 /* RocketModem III speaker control is at the 1st port location of offset 0x80 */
3294 if ((model == MODEL_UPCI_RM3_8PORT) 3294 if ((model == MODEL_UPCI_RM3_8PORT)
3295 || (model == MODEL_UPCI_RM3_4PORT)) { 3295 || (model == MODEL_UPCI_RM3_4PORT)) {
3296 addr = CtlP->AiopIO[0] + 0x88; 3296 addr = CtlP->AiopIO[0] + 0x88;
3297 sOutB(addr, 0); 3297 sOutB(addr, 0);
3298 } 3298 }
3299 } 3299 }
3300 3300
3301 /* Returns the line number given the controller (board), aiop and channel number */ 3301 /* Returns the line number given the controller (board), aiop and channel number */
3302 static unsigned char GetLineNumber(int ctrl, int aiop, int ch) 3302 static unsigned char GetLineNumber(int ctrl, int aiop, int ch)
3303 { 3303 {
3304 return lineNumbers[(ctrl << 5) | (aiop << 3) | ch]; 3304 return lineNumbers[(ctrl << 5) | (aiop << 3) | ch];
3305 } 3305 }
3306 3306
3307 /* 3307 /*
3308 * Stores the line number associated with a given controller (board), aiop 3308 * Stores the line number associated with a given controller (board), aiop
3309 * and channel number. 3309 * and channel number.
3310 * Returns: The line number assigned 3310 * Returns: The line number assigned
3311 */ 3311 */
3312 static unsigned char SetLineNumber(int ctrl, int aiop, int ch) 3312 static unsigned char SetLineNumber(int ctrl, int aiop, int ch)
3313 { 3313 {
3314 lineNumbers[(ctrl << 5) | (aiop << 3) | ch] = nextLineNumber++; 3314 lineNumbers[(ctrl << 5) | (aiop << 3) | ch] = nextLineNumber++;
3315 return (nextLineNumber - 1); 3315 return (nextLineNumber - 1);
3316 } 3316 }
3317 3317