TTY: introduce tty_port_destroy
authorJiri Slaby <jslaby@suse.cz>
Thu, 15 Nov 2012 08:49:54 +0000 (09:49 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Fri, 16 Nov 2012 01:20:58 +0000 (17:20 -0800)
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.

Those using refcounting are safe now, but for those which do not we
introduce a function to be called right before the tty_port is freed
by the drivers.

Signed-off-by: Jiri Slaby <jslaby@suse.cz>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
drivers/tty/tty_port.c
include/linux/tty.h

index fdc42c2d565f4f70fc9495b99a025a37894e9215..b7ff59d3db88f85d5f37027e2adf44d036c1e0a2 100644 (file)
@@ -122,12 +122,26 @@ void tty_port_free_xmit_buf(struct tty_port *port)
 }
 EXPORT_SYMBOL(tty_port_free_xmit_buf);
 
+/**
+ * tty_port_destroy -- destroy inited port
+ * @port: tty port to be doestroyed
+ *
+ * When a port was initialized using tty_port_init, one has to destroy the
+ * port by this function. Either indirectly by using tty_port refcounting
+ * (tty_port_put) or directly if refcounting is not used.
+ */
+void tty_port_destroy(struct tty_port *port)
+{
+       tty_buffer_free_all(port);
+}
+EXPORT_SYMBOL(tty_port_destroy);
+
 static void tty_port_destructor(struct kref *kref)
 {
        struct tty_port *port = container_of(kref, struct tty_port, kref);
        if (port->xmit_buf)
                free_page((unsigned long)port->xmit_buf);
-       tty_buffer_free_all(port);
+       tty_port_destroy(port);
        if (port->ops && port->ops->destruct)
                port->ops->destruct(port);
        else
index d7ff88fb896715ba58838fe89d329ed0821439bb..8db1b569c37a4cb5bb6965adc420bff2030fb47c 100644 (file)
@@ -455,6 +455,7 @@ extern struct device *tty_port_register_device_attr(struct tty_port *port,
                const struct attribute_group **attr_grp);
 extern int tty_port_alloc_xmit_buf(struct tty_port *port);
 extern void tty_port_free_xmit_buf(struct tty_port *port);
+extern void tty_port_destroy(struct tty_port *port);
 extern void tty_port_put(struct tty_port *port);
 
 static inline struct tty_port *tty_port_get(struct tty_port *port)