mirror of
https://github.com/torvalds/linux.git
synced 2024-11-07 04:32:03 +00:00
USB: cypress_m8: fix port-data memory leak
Fix port-data memory leak by replacing attach and release with
port_probe and port_remove.
Since commit 0998d06310
(device-core: Ensure drvdata = NULL when no
driver is bound) the port private data is no longer freed at release as
it is no longer accessible.
Compile-only tested.
Cc: <stable@vger.kernel.org>
Signed-off-by: Johan Hovold <jhovold@gmail.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
parent
301a29da6e
commit
5c1a0f418d
@ -123,10 +123,10 @@ struct cypress_private {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/* function prototypes for the Cypress USB to serial device */
|
/* function prototypes for the Cypress USB to serial device */
|
||||||
static int cypress_earthmate_startup(struct usb_serial *serial);
|
static int cypress_earthmate_port_probe(struct usb_serial_port *port);
|
||||||
static int cypress_hidcom_startup(struct usb_serial *serial);
|
static int cypress_hidcom_port_probe(struct usb_serial_port *port);
|
||||||
static int cypress_ca42v2_startup(struct usb_serial *serial);
|
static int cypress_ca42v2_port_probe(struct usb_serial_port *port);
|
||||||
static void cypress_release(struct usb_serial *serial);
|
static int cypress_port_remove(struct usb_serial_port *port);
|
||||||
static int cypress_open(struct tty_struct *tty, struct usb_serial_port *port);
|
static int cypress_open(struct tty_struct *tty, struct usb_serial_port *port);
|
||||||
static void cypress_close(struct usb_serial_port *port);
|
static void cypress_close(struct usb_serial_port *port);
|
||||||
static void cypress_dtr_rts(struct usb_serial_port *port, int on);
|
static void cypress_dtr_rts(struct usb_serial_port *port, int on);
|
||||||
@ -156,8 +156,8 @@ static struct usb_serial_driver cypress_earthmate_device = {
|
|||||||
.description = "DeLorme Earthmate USB",
|
.description = "DeLorme Earthmate USB",
|
||||||
.id_table = id_table_earthmate,
|
.id_table = id_table_earthmate,
|
||||||
.num_ports = 1,
|
.num_ports = 1,
|
||||||
.attach = cypress_earthmate_startup,
|
.port_probe = cypress_earthmate_port_probe,
|
||||||
.release = cypress_release,
|
.port_remove = cypress_port_remove,
|
||||||
.open = cypress_open,
|
.open = cypress_open,
|
||||||
.close = cypress_close,
|
.close = cypress_close,
|
||||||
.dtr_rts = cypress_dtr_rts,
|
.dtr_rts = cypress_dtr_rts,
|
||||||
@ -182,8 +182,8 @@ static struct usb_serial_driver cypress_hidcom_device = {
|
|||||||
.description = "HID->COM RS232 Adapter",
|
.description = "HID->COM RS232 Adapter",
|
||||||
.id_table = id_table_cyphidcomrs232,
|
.id_table = id_table_cyphidcomrs232,
|
||||||
.num_ports = 1,
|
.num_ports = 1,
|
||||||
.attach = cypress_hidcom_startup,
|
.port_probe = cypress_hidcom_port_probe,
|
||||||
.release = cypress_release,
|
.port_remove = cypress_port_remove,
|
||||||
.open = cypress_open,
|
.open = cypress_open,
|
||||||
.close = cypress_close,
|
.close = cypress_close,
|
||||||
.dtr_rts = cypress_dtr_rts,
|
.dtr_rts = cypress_dtr_rts,
|
||||||
@ -208,8 +208,8 @@ static struct usb_serial_driver cypress_ca42v2_device = {
|
|||||||
.description = "Nokia CA-42 V2 Adapter",
|
.description = "Nokia CA-42 V2 Adapter",
|
||||||
.id_table = id_table_nokiaca42v2,
|
.id_table = id_table_nokiaca42v2,
|
||||||
.num_ports = 1,
|
.num_ports = 1,
|
||||||
.attach = cypress_ca42v2_startup,
|
.port_probe = cypress_ca42v2_port_probe,
|
||||||
.release = cypress_release,
|
.port_remove = cypress_port_remove,
|
||||||
.open = cypress_open,
|
.open = cypress_open,
|
||||||
.close = cypress_close,
|
.close = cypress_close,
|
||||||
.dtr_rts = cypress_dtr_rts,
|
.dtr_rts = cypress_dtr_rts,
|
||||||
@ -438,10 +438,10 @@ static void cypress_set_dead(struct usb_serial_port *port)
|
|||||||
*****************************************************************************/
|
*****************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
static int generic_startup(struct usb_serial *serial)
|
static int cypress_generic_port_probe(struct usb_serial_port *port)
|
||||||
{
|
{
|
||||||
|
struct usb_serial *serial = port->serial;
|
||||||
struct cypress_private *priv;
|
struct cypress_private *priv;
|
||||||
struct usb_serial_port *port = serial->port[0];
|
|
||||||
|
|
||||||
priv = kzalloc(sizeof(struct cypress_private), GFP_KERNEL);
|
priv = kzalloc(sizeof(struct cypress_private), GFP_KERNEL);
|
||||||
if (!priv)
|
if (!priv)
|
||||||
@ -490,14 +490,16 @@ static int generic_startup(struct usb_serial *serial)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static int cypress_earthmate_startup(struct usb_serial *serial)
|
static int cypress_earthmate_port_probe(struct usb_serial_port *port)
|
||||||
{
|
{
|
||||||
|
struct usb_serial *serial = port->serial;
|
||||||
struct cypress_private *priv;
|
struct cypress_private *priv;
|
||||||
struct usb_serial_port *port = serial->port[0];
|
int ret;
|
||||||
|
|
||||||
if (generic_startup(serial)) {
|
ret = cypress_generic_port_probe(port);
|
||||||
|
if (ret) {
|
||||||
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
||||||
return 1;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
priv = usb_get_serial_port_data(port);
|
priv = usb_get_serial_port_data(port);
|
||||||
@ -518,57 +520,54 @@ static int cypress_earthmate_startup(struct usb_serial *serial)
|
|||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
} /* cypress_earthmate_startup */
|
}
|
||||||
|
|
||||||
|
static int cypress_hidcom_port_probe(struct usb_serial_port *port)
|
||||||
static int cypress_hidcom_startup(struct usb_serial *serial)
|
|
||||||
{
|
{
|
||||||
struct cypress_private *priv;
|
struct cypress_private *priv;
|
||||||
struct usb_serial_port *port = serial->port[0];
|
int ret;
|
||||||
|
|
||||||
if (generic_startup(serial)) {
|
ret = cypress_generic_port_probe(port);
|
||||||
|
if (ret) {
|
||||||
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
||||||
return 1;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
priv = usb_get_serial_port_data(port);
|
priv = usb_get_serial_port_data(port);
|
||||||
priv->chiptype = CT_CYPHIDCOM;
|
priv->chiptype = CT_CYPHIDCOM;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
} /* cypress_hidcom_startup */
|
}
|
||||||
|
|
||||||
|
static int cypress_ca42v2_port_probe(struct usb_serial_port *port)
|
||||||
static int cypress_ca42v2_startup(struct usb_serial *serial)
|
|
||||||
{
|
{
|
||||||
struct cypress_private *priv;
|
struct cypress_private *priv;
|
||||||
struct usb_serial_port *port = serial->port[0];
|
int ret;
|
||||||
|
|
||||||
if (generic_startup(serial)) {
|
ret = cypress_generic_port_probe(port);
|
||||||
|
if (ret) {
|
||||||
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
dev_dbg(&port->dev, "%s - Failed setting up port\n", __func__);
|
||||||
return 1;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
priv = usb_get_serial_port_data(port);
|
priv = usb_get_serial_port_data(port);
|
||||||
priv->chiptype = CT_CA42V2;
|
priv->chiptype = CT_CA42V2;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
} /* cypress_ca42v2_startup */
|
}
|
||||||
|
|
||||||
|
static int cypress_port_remove(struct usb_serial_port *port)
|
||||||
static void cypress_release(struct usb_serial *serial)
|
|
||||||
{
|
{
|
||||||
struct cypress_private *priv;
|
struct cypress_private *priv;
|
||||||
|
|
||||||
/* all open ports are closed at this point */
|
priv = usb_get_serial_port_data(port);
|
||||||
priv = usb_get_serial_port_data(serial->port[0]);
|
|
||||||
|
|
||||||
if (priv) {
|
kfifo_free(&priv->write_fifo);
|
||||||
kfifo_free(&priv->write_fifo);
|
kfree(priv);
|
||||||
kfree(priv);
|
|
||||||
}
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static int cypress_open(struct tty_struct *tty, struct usb_serial_port *port)
|
static int cypress_open(struct tty_struct *tty, struct usb_serial_port *port)
|
||||||
{
|
{
|
||||||
struct cypress_private *priv = usb_get_serial_port_data(port);
|
struct cypress_private *priv = usb_get_serial_port_data(port);
|
||||||
|
Loading…
Reference in New Issue
Block a user