server: use ringbuffer for all handlers
Currently, we use the a ringbuffer within the socket handler to manage
bursts of data to slower clients.
However, we're also seeing cases where the local tty handler becomes
blocking as well. So, we want to implement a buffer within the tty
handler too.
This change moves the ringbuffer 'up a layer' - from the socket handler
to the core console code.
We remove the ->data_in callback from handlers, and work on the
assumption that handlers have registered their own consumer on the
console's ringbuffer (through a new helper function,
console_ringbuffer_consumer_register()).
Change-Id: Ie8f02d6632578c50bb5e2dfb9bee6ece86432135
Signed-off-by: Jeremy Kerr <jk@ozlabs.org>
diff --git a/console-server.h b/console-server.h
index 67cc99e..0831c57 100644
--- a/console-server.h
+++ b/console-server.h
@@ -21,13 +21,8 @@
struct console;
struct config;
-/* handler API */
-enum {
- HANDLER_OK = 0,
- HANDLER_EXIT,
-};
-
-/*
+/* Handler API.
+ *
* Console data handlers: these implement the functions that process
* data coming out of the main tty device.
*
@@ -35,8 +30,9 @@
* macro. We call each handler's ->init() function at startup, and ->fini() at
* exit.
*
- * Incoming data from the tty will be passed to the handler through the
- * ->data_in() function. To send data to the tty, use console_data_out().
+ * Handlers will almost always want to register a ringbuffer consumer, which
+ * provides data coming from the tty. Use cosole_register_ringbuffer_consumer()
+ * for this. To send data to the tty, use console_data_out().
*
* If a handler needs to monitor a separate file descriptor for events, use the
* poller API, through console_poller_register().
@@ -46,8 +42,6 @@
int (*init)(struct handler *handler,
struct console *console,
struct config *config);
- int (*data_in)(struct handler *handler,
- uint8_t *buf, size_t len);
void (*fini)(struct handler *handler);
bool active;
};
@@ -108,6 +102,11 @@
int ringbuffer_dequeue_commit(struct ringbuffer_consumer *rbc, size_t len);
+/* console wrapper around ringbuffer consumer registration */
+struct ringbuffer_consumer *console_ringbuffer_consumer_register(
+ struct console *console,
+ ringbuffer_poll_fn_t poll_fn, void *data);
+
/* config API */
struct config;
const char *config_get_value(struct config *config, const char *name);