summaryrefslogtreecommitdiffstats
path: root/drivers/char/sx.c
diff options
context:
space:
mode:
authorRalf Baechle <ralf@linux-mips.org>2000-04-28 01:09:25 +0000
committerRalf Baechle <ralf@linux-mips.org>2000-04-28 01:09:25 +0000
commitb9ba7aeb165cffecdffb60aec8c3fa8d590d9ca9 (patch)
tree42d07b0c7246ae2536a702e7c5de9e2732341116 /drivers/char/sx.c
parent7406b0a326f2d70ade2671c37d1beef62249db97 (diff)
Merge with 2.3.99-pre6.
Diffstat (limited to 'drivers/char/sx.c')
-rw-r--r--drivers/char/sx.c66
1 files changed, 49 insertions, 17 deletions
diff --git a/drivers/char/sx.c b/drivers/char/sx.c
index 1b8583034..a5c94927a 100644
--- a/drivers/char/sx.c
+++ b/drivers/char/sx.c
@@ -33,7 +33,12 @@
*
* Revision history:
* $Log: sx.c,v $
- * Revision 1.32 2000/03/07 90:00:00 wolff,pvdl
+ * Revision 1.33 2000/03/09 10:00:00 pvdl,wolff
+ * - Fixed module and port counting
+ * - Fixed signal handling
+ * - Fixed an Ooops
+ *
+ * Revision 1.32 2000/03/07 09:00:00 wolff,pvdl
* - Fixed some sx_dprintk typos
* - added detection for an invalid board/module configuration
*
@@ -195,8 +200,8 @@
* */
-#define RCS_ID "$Id: sx.c,v 1.32 2000/03/07 17:01:02 wolff, pvdl Exp $"
-#define RCS_REV "$Revision: 1.32 $"
+#define RCS_ID "$Id: sx.c,v 1.33 2000/03/08 10:01:02 wolff, pvdl Exp $"
+#define RCS_REV "$Revision: 1.33 $"
#include <linux/module.h>
@@ -231,8 +236,9 @@
#include "sxboards.h"
#include "sxwindow.h"
-#include <linux/generic_serial.h>
+
#include <linux/compatmac.h>
+#include <linux/generic_serial.h>
#include "sx.h"
@@ -241,11 +247,11 @@
if you want more than 4 boards. */
-
/* Why the hell am I defining these here? */
#define SX_TYPE_NORMAL 1
#define SX_TYPE_CALLOUT 2
+
#ifndef PCI_DEVICE_ID_SPECIALIX_SX_XIO_IO8
#define PCI_DEVICE_ID_SPECIALIX_SX_XIO_IO8 0x2000
#endif
@@ -767,6 +773,7 @@ static void sx_setsignals (struct sx_port *port, int dtr, int rts)
if (rts >= 0) t = rts? (t | OP_RTS): (t & ~OP_RTS);
sx_write_channel_byte (port, hi_op, t);
sx_dprintk (SX_DEBUG_MODEMSIGNALS, "setsignals: %d/%d\n", dtr, rts);
+
func_exit ();
}
@@ -882,6 +889,9 @@ static int sx_set_real_termios (void *ptr)
func_enter2();
+ if (!port->gs.tty)
+ return 0;
+
/* What is this doing here? -- REW
Ha! figured it out. It is to allow you to get DTR active again
if you've dropped it with stty 0. Moved to set_baud, where it
@@ -1043,7 +1053,7 @@ void sx_transmit_chars (struct sx_port *port)
sx_disable_tx_interrupts (port);
}
- if (port->gs.xmit_cnt <= port->gs.wakeup_chars) {
+ if ((port->gs.xmit_cnt <= port->gs.wakeup_chars) && port->gs.tty) {
if ((port->gs.tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
port->gs.tty->ldisc.write_wakeup)
(port->gs.tty->ldisc.write_wakeup)(port->gs.tty);
@@ -1294,6 +1304,8 @@ static void sx_pollfunc (unsigned long data)
sx_interrupt (0, board, NULL);
+ init_timer(&board->timer);
+
board->timer.expires = jiffies + sx_poll;
add_timer (&board->timer);
func_exit ();
@@ -1389,7 +1401,7 @@ static void sx_shutdown_port (void * ptr)
func_enter();
port->gs.flags &= ~ GS_ACTIVE;
- if (port->gs.tty && port->gs.tty->termios->c_cflag & HUPCL) {
+ if (port->gs.tty && (port->gs.tty->termios->c_cflag & HUPCL)) {
sx_setsignals (port, 0, 0);
sx_reconfigure_port(port);
}
@@ -1452,6 +1464,8 @@ static int sx_open (struct tty_struct * tty, struct file * filp)
tty->driver_data = port;
port->gs.tty = tty;
+ if (!port->gs.count)
+ MOD_INC_USE_COUNT;
port->gs.count++;
sx_dprintk (SX_DEBUG_OPEN, "starting port\n");
@@ -1463,19 +1477,13 @@ static int sx_open (struct tty_struct * tty, struct file * filp)
sx_dprintk (SX_DEBUG_OPEN, "done gs_init\n");
if (retval) {
port->gs.count--;
+ if (port->gs.count) MOD_DEC_USE_COUNT;
return retval;
}
port->gs.flags |= GS_ACTIVE;
sx_setsignals (port, 1,1);
- sx_dprintk (SX_DEBUG_OPEN, "before inc_use_count (count=%d.\n",
- port->gs.count);
- if (port->gs.count == 1) {
- MOD_INC_USE_COUNT;
- }
- sx_dprintk (SX_DEBUG_OPEN, "after inc_use_count\n");
-
#if 0
if (sx_debug & SX_DEBUG_OPEN)
my_hd ((unsigned char *)port, sizeof (*port));
@@ -1487,8 +1495,8 @@ static int sx_open (struct tty_struct * tty, struct file * filp)
if (sx_send_command (port, HS_LOPEN, -1, HS_IDLE_OPEN) != 1) {
printk (KERN_ERR "sx: Card didn't respond to LOPEN command.\n");
- MOD_DEC_USE_COUNT;
port->gs.count--;
+ if (!port->gs.count) MOD_DEC_USE_COUNT;
return -EIO;
}
@@ -1497,8 +1505,10 @@ static int sx_open (struct tty_struct * tty, struct file * filp)
retval, port->gs.count);
if (retval) {
- MOD_DEC_USE_COUNT;
- port->gs.count--;
+ /*
+ * Don't lower gs.count here because sx_close() will be called later
+ */
+
return retval;
}
/* tty->low_latency = 1; */
@@ -1530,7 +1540,21 @@ static int sx_open (struct tty_struct * tty, struct file * filp)
exit minicom. I expect an "oops". -- REW */
static void sx_hungup (void *ptr)
{
+ struct sx_port *port = ptr;
func_enter ();
+
+ sx_setsignals (port, 0, 0);
+ sx_reconfigure_port(port);
+ sx_send_command (port, HS_CLOSE, 0, 0);
+
+ if (sx_read_channel_byte (port, hi_hstat) != HS_IDLE_CLOSED) {
+ if (sx_send_command (port, HS_FORCE_CLOSED, -1, HS_IDLE_CLOSED) != 1) {
+ printk (KERN_ERR
+ "sx: sent the force_close command, but card didn't react\n");
+ } else
+ sx_dprintk (SX_DEBUG_CLOSE, "sent the force_close command.\n");
+ }
+
MOD_DEC_USE_COUNT;
func_exit ();
}
@@ -1543,6 +1567,9 @@ static void sx_close (void *ptr)
int to = 5 * HZ;
func_enter ();
+
+ sx_setsignals (port, 0, 0);
+ sx_reconfigure_port(port);
sx_send_command (port, HS_CLOSE, 0, 0);
while (to-- && (sx_read_channel_byte (port, hi_hstat) != HS_IDLE_CLOSED)) {
@@ -1563,6 +1590,11 @@ static void sx_close (void *ptr)
sx_dprintk (SX_DEBUG_CLOSE, "waited %d jiffies for close. count=%d\n",
5 * HZ - to - 1, port->gs.count);
+ if(port->gs.count) {
+ sx_dprintk(SX_DEBUG_CLOSE, "WARNING port count:%d\n", port->gs.count);
+ port->gs.count = 0;
+ }
+
MOD_DEC_USE_COUNT;
func_exit ();
}