summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJiri Slaby <jslaby@suse.cz>2012-11-15 12:49:55 +0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2012-11-16 05:20:58 +0400
commitd0f59141ca40159c9d142c0f62e9aea61f846539 (patch)
tree0d1a37909ac7157b8f38eb94d9a285224dcc383a
parentde274bfe0fc81def6ddb8a17020a9a4b56477cc4 (diff)
downloadlinux-d0f59141ca40159c9d142c0f62e9aea61f846539.tar.xz
TTY: isicom, fix tty buffers memory leak
After commit "TTY: move tty buffers to tty_port", the tty buffers are not freed in some drivers. This is because tty_port_destructor is not called whenever a tty_port is freed. This was an assumption I counted with but was unfortunately untrue. So fix the drivers to fulfil this assumption. This one is special as we need more work to be done. Previously, the tty_port was initialized at module load time, but to be able to destroy the port and init it again, we now do the initialization in probe and destroy in remove. I.e. at more appropriate places for that. Signed-off-by: Jiri Slaby <jslaby@suse.cz> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--drivers/tty/isicom.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/drivers/tty/isicom.c b/drivers/tty/isicom.c
index 5f3ecbc2713e..67f288d7e76a 100644
--- a/drivers/tty/isicom.c
+++ b/drivers/tty/isicom.c
@@ -1610,10 +1610,15 @@ static int __devinit isicom_probe(struct pci_dev *pdev,
if (retval < 0)
goto errunri;
- for (index = 0; index < board->port_count; index++)
- tty_port_register_device(&board->ports[index].port,
- isicom_normal, board->index * 16 + index,
- &pdev->dev);
+ for (index = 0; index < board->port_count; index++) {
+ struct tty_port *tport = &board->ports[index].port;
+ tty_port_init(tport);
+ tport->ops = &isicom_port_ops;
+ tport->close_delay = 50 * HZ/100;
+ tport->closing_wait = 3000 * HZ/100;
+ tty_port_register_device(tport, isicom_normal,
+ board->index * 16 + index, &pdev->dev);
+ }
return 0;
@@ -1635,8 +1640,10 @@ static void __devexit isicom_remove(struct pci_dev *pdev)
struct isi_board *board = pci_get_drvdata(pdev);
unsigned int i;
- for (i = 0; i < board->port_count; i++)
+ for (i = 0; i < board->port_count; i++) {
tty_unregister_device(isicom_normal, board->index * 16 + i);
+ tty_port_destroy(&board->ports[i].port);
+ }
free_irq(board->irq, board);
pci_release_region(pdev, 3);
@@ -1655,13 +1662,9 @@ static int __init isicom_init(void)
isi_card[idx].ports = port;
spin_lock_init(&isi_card[idx].card_lock);
for (channel = 0; channel < 16; channel++, port++) {
- tty_port_init(&port->port);
- port->port.ops = &isicom_port_ops;
port->magic = ISICOM_MAGIC;
port->card = &isi_card[idx];
port->channel = channel;
- port->port.close_delay = 50 * HZ/100;
- port->port.closing_wait = 3000 * HZ/100;
port->status = 0;
/* . . . */
}