Message ID | E1TKTlL-0002ni-MB@rmk-PC.arm.linux.org.uk (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
On Sat, 06 Oct 2012 13:45:47 +0100 Russell King <rmk+kernel@arm.linux.org.uk> wrote: > This allows drivers (such as OMAP serial) to allocate and free their > transmit buffers in a sane manner, rather than working around the > buffer allocation provided by serial_core. I think this just illustrates how broken the serial_core layering is in that drivers can't treat it as a library but get constrained by it. Fine for now and actually probably a useful hook to begin removing the circ buffers for the kernel generic kfifo and other work that needs doing eventually. Alan
On Sat, Oct 06, 2012 at 04:49:56PM +0100, Alan Cox wrote: > On Sat, 06 Oct 2012 13:45:47 +0100 > Russell King <rmk+kernel@arm.linux.org.uk> wrote: > > > This allows drivers (such as OMAP serial) to allocate and free their > > transmit buffers in a sane manner, rather than working around the > > buffer allocation provided by serial_core. > > I think this just illustrates how broken the serial_core layering is in > that drivers can't treat it as a library but get constrained by it. > > Fine for now and actually probably a useful hook to begin removing the > circ buffers for the kernel generic kfifo and other work that needs doing > eventually. Yes, I was thinking about turning the 'default' buffer allocation into a library call which drivers would set, but I felt that's just asking for a big patch and problems with new drivers appearing. We could transition it by providing a default buffer allocation call, converting all the drivers, and then making that call mandatory. That probably would then give us a better path to convert to kfifo. The view that serial_core should be a library is one that Ted mentioned when I created serial_core originally - I disagreed at the time, and I still believe it would've ended up being much more complex - and hairy - to go that route at that time. Maybe as things have moved forward in the tty layer that's changed, but I've been out of tty stuff for too long to properly comment.
diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c index 4dd609e..53274ae 100644 --- a/drivers/tty/serial/serial_core.c +++ b/drivers/tty/serial/serial_core.c @@ -147,12 +147,18 @@ static int uart_port_startup(struct tty_struct *tty, struct uart_state *state, * buffer. */ if (!state->xmit.buf) { - /* This is protected by the per port mutex */ - page = get_zeroed_page(GFP_KERNEL); - if (!page) - return -ENOMEM; + if (uport->ops->alloc_xmit) { + retval = uport->ops->alloc_xmit(uport, &state->xmit); + if (retval) + return retval; + } else { + /* This is protected by the per port mutex */ + page = get_zeroed_page(GFP_KERNEL); + if (!page) + return -ENOMEM; - state->xmit.buf = (unsigned char *) page; + state->xmit.buf = (unsigned char *) page; + } uart_circ_clear(&state->xmit); } @@ -257,7 +263,10 @@ static void uart_shutdown(struct tty_struct *tty, struct uart_state *state) * Free the transmit buffer page. */ if (state->xmit.buf) { - free_page((unsigned long)state->xmit.buf); + if (uport->ops->free_xmit) + uport->ops->free_xmit(uport, &state->xmit); + else + free_page((unsigned long)state->xmit.buf); state->xmit.buf = NULL; } } diff --git a/include/linux/serial_core.h b/include/linux/serial_core.h index b17d4c9..ebe9af1 100644 --- a/include/linux/serial_core.h +++ b/include/linux/serial_core.h @@ -248,6 +248,8 @@ struct uart_ops { void (*break_ctl)(struct uart_port *, int ctl); int (*startup)(struct uart_port *); void (*shutdown)(struct uart_port *); + int (*alloc_xmit)(struct uart_port *, struct circ_buf *); + void (*free_xmit)(struct uart_port *, struct circ_buf *); void (*flush_buffer)(struct uart_port *); void (*set_termios)(struct uart_port *, struct ktermios *new, struct ktermios *old);
This allows drivers (such as OMAP serial) to allocate and free their transmit buffers in a sane manner, rather than working around the buffer allocation provided by serial_core. Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk> --- drivers/tty/serial/serial_core.c | 23 ++++++++++++++++------- include/linux/serial_core.h | 2 ++ 2 files changed, 18 insertions(+), 7 deletions(-)