Commit dccb973c authored by Max Kellermann's avatar Max Kellermann

client: use the new fifo_buffer library

parent c76d3596
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
*/ */
#include "client.h" #include "client.h"
#include "fifo_buffer.h"
#include "command.h" #include "command.h"
#include "conf.h" #include "conf.h"
#include "listen.h" #include "listen.h"
...@@ -71,13 +72,12 @@ struct deferred_buffer { ...@@ -71,13 +72,12 @@ struct deferred_buffer {
}; };
struct client { struct client {
char buffer[4096];
size_t bufferLength;
size_t bufferPos;
GIOChannel *channel; GIOChannel *channel;
guint source_id; guint source_id;
/** the buffer for reading lines from the #channel */
struct fifo_buffer *input;
unsigned permission; unsigned permission;
/** the uid of the client process, or -1 if unknown */ /** the uid of the client process, or -1 if unknown */
...@@ -176,8 +176,6 @@ static void client_init(struct client *client, int fd) ...@@ -176,8 +176,6 @@ static void client_init(struct client *client, int fd)
client->cmd_list_size = 0; client->cmd_list_size = 0;
client->cmd_list_OK = -1; client->cmd_list_OK = -1;
client->bufferLength = 0;
client->bufferPos = 0;
#ifndef G_OS_WIN32 #ifndef G_OS_WIN32
client->channel = g_io_channel_unix_new(fd); client->channel = g_io_channel_unix_new(fd);
...@@ -197,6 +195,8 @@ static void client_init(struct client *client, int fd) ...@@ -197,6 +195,8 @@ static void client_init(struct client *client, int fd)
G_IO_IN|G_IO_ERR|G_IO_HUP, G_IO_IN|G_IO_ERR|G_IO_HUP,
client_in_event, client); client_in_event, client);
client->input = fifo_buffer_new(4096);
client->lastTime = time(NULL); client->lastTime = time(NULL);
client->cmd_list = NULL; client->cmd_list = NULL;
client->deferred_send = g_queue_new(); client->deferred_send = g_queue_new();
...@@ -370,54 +370,45 @@ static int client_process_line(struct client *client, char *line) ...@@ -370,54 +370,45 @@ static int client_process_line(struct client *client, char *line)
return ret; return ret;
} }
static char *
client_read_line(struct client *client)
{
const char *p, *newline;
size_t length;
char *line;
p = fifo_buffer_read(client->input, &length);
if (p == NULL)
return NULL;
newline = memchr(p, '\n', length);
if (newline == NULL)
return NULL;
line = g_strndup(p, newline - p);
fifo_buffer_consume(client->input, newline - p + 1);
return g_strchomp(line);
}
static int client_input_received(struct client *client, size_t bytesRead) static int client_input_received(struct client *client, size_t bytesRead)
{ {
char *start = client->buffer + client->bufferPos, *end; char *line;
char *newline, *next;
int ret; int ret;
assert(client->bufferPos <= client->bufferLength); fifo_buffer_append(client->input, bytesRead);
assert(client->bufferLength + bytesRead <= sizeof(client->buffer));
client->bufferLength += bytesRead;
end = client->buffer + client->bufferLength;
/* process all lines */ /* process all lines */
while ((newline = memchr(start, '\n', end - start)) != NULL) {
next = newline + 1;
if (newline > start && newline[-1] == '\r') while ((line = client_read_line(client)) != NULL) {
--newline; ret = client_process_line(client, line);
*newline = 0; g_free(line);
ret = client_process_line(client, start);
if (ret == COMMAND_RETURN_KILL || if (ret == COMMAND_RETURN_KILL ||
ret == COMMAND_RETURN_CLOSE) ret == COMMAND_RETURN_CLOSE)
return ret; return ret;
if (client_is_expired(client)) if (client_is_expired(client))
return COMMAND_RETURN_CLOSE; return COMMAND_RETURN_CLOSE;
start = next;
}
/* mark consumed lines */
client->bufferPos = start - client->buffer;
/* if we're have reached the buffer's end, close the gab at
the beginning */
if (client->bufferLength == sizeof(client->buffer)) {
if (client->bufferPos == 0) {
g_warning("[%u] buffer overflow",
client->num);
return COMMAND_RETURN_CLOSE;
}
assert(client->bufferLength >= client->bufferPos
&& "bufferLength >= bufferPos");
client->bufferLength -= client->bufferPos;
memmove(client->buffer,
client->buffer + client->bufferPos,
client->bufferLength);
client->bufferPos = 0;
} }
return 0; return 0;
...@@ -425,18 +416,20 @@ static int client_input_received(struct client *client, size_t bytesRead) ...@@ -425,18 +416,20 @@ static int client_input_received(struct client *client, size_t bytesRead)
static int client_read(struct client *client) static int client_read(struct client *client)
{ {
char *p;
size_t max_length;
GError *error = NULL; GError *error = NULL;
GIOStatus status; GIOStatus status;
gsize bytes_read; gsize bytes_read;
assert(client->bufferPos <= client->bufferLength); p = fifo_buffer_write(client->input, &max_length);
assert(client->bufferLength < sizeof(client->buffer)); if (p == NULL) {
g_warning("[%u] buffer overflow", client->num);
return COMMAND_RETURN_CLOSE;
}
status = g_io_channel_read_chars status = g_io_channel_read_chars(client->channel, p, max_length,
(client->channel, &bytes_read, &error);
client->buffer + client->bufferLength,
sizeof(client->buffer) - client->bufferLength,
&bytes_read, &error);
switch (status) { switch (status) {
case G_IO_STATUS_NORMAL: case G_IO_STATUS_NORMAL:
return client_input_received(client, bytes_read); return client_input_received(client, bytes_read);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment