USB: ftdi_sio: Fix locking for change_speed() function
The change_speed() function should be serialized against multiple calls. Use the cfg_lock mutex to do this. Signed-off-by: Alessio Igor Bogani <abogani@texware.it> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
This commit is contained in:
parent
11b10d9994
commit
9c67d28e4e
|
@ -91,7 +91,7 @@ struct ftdi_private {
|
||||||
unsigned long tx_outstanding_bytes;
|
unsigned long tx_outstanding_bytes;
|
||||||
unsigned long tx_outstanding_urbs;
|
unsigned long tx_outstanding_urbs;
|
||||||
unsigned short max_packet_size;
|
unsigned short max_packet_size;
|
||||||
struct mutex cfg_lock; /* Avoid mess by parallel calls of config ioctl() */
|
struct mutex cfg_lock; /* Avoid mess by parallel calls of config ioctl() and change_speed() */
|
||||||
};
|
};
|
||||||
|
|
||||||
/* struct ftdi_sio_quirk is used by devices requiring special attention. */
|
/* struct ftdi_sio_quirk is used by devices requiring special attention. */
|
||||||
|
@ -1273,8 +1273,8 @@ check_and_exit:
|
||||||
(priv->flags & ASYNC_SPD_MASK)) ||
|
(priv->flags & ASYNC_SPD_MASK)) ||
|
||||||
(((priv->flags & ASYNC_SPD_MASK) == ASYNC_SPD_CUST) &&
|
(((priv->flags & ASYNC_SPD_MASK) == ASYNC_SPD_CUST) &&
|
||||||
(old_priv.custom_divisor != priv->custom_divisor))) {
|
(old_priv.custom_divisor != priv->custom_divisor))) {
|
||||||
mutex_unlock(&priv->cfg_lock);
|
|
||||||
change_speed(tty, port);
|
change_speed(tty, port);
|
||||||
|
mutex_unlock(&priv->cfg_lock);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
mutex_unlock(&priv->cfg_lock);
|
mutex_unlock(&priv->cfg_lock);
|
||||||
|
@ -2265,9 +2265,11 @@ static void ftdi_set_termios(struct tty_struct *tty,
|
||||||
clear_mctrl(port, TIOCM_DTR | TIOCM_RTS);
|
clear_mctrl(port, TIOCM_DTR | TIOCM_RTS);
|
||||||
} else {
|
} else {
|
||||||
/* set the baudrate determined before */
|
/* set the baudrate determined before */
|
||||||
|
mutex_lock(&priv->cfg_lock);
|
||||||
if (change_speed(tty, port))
|
if (change_speed(tty, port))
|
||||||
dev_err(&port->dev, "%s urb failed to set baudrate\n",
|
dev_err(&port->dev, "%s urb failed to set baudrate\n",
|
||||||
__func__);
|
__func__);
|
||||||
|
mutex_unlock(&priv->cfg_lock);
|
||||||
/* Ensure RTS and DTR are raised when baudrate changed from 0 */
|
/* Ensure RTS and DTR are raised when baudrate changed from 0 */
|
||||||
if (!old_termios || (old_termios->c_cflag & CBAUD) == B0)
|
if (!old_termios || (old_termios->c_cflag & CBAUD) == B0)
|
||||||
set_mctrl(port, TIOCM_DTR | TIOCM_RTS);
|
set_mctrl(port, TIOCM_DTR | TIOCM_RTS);
|
||||||
|
|
Loading…
Reference in New Issue