regfree (&self->rx);
char ebuf[256];
size_t len = regerror (err, NULL, ebuf, 256);
- self->string = malloc(len + strlen(buf) + 9);
+ self->string = malloc(len + strlen(buf) + 14);
if (!self->string) abort();
- strcpy (self->string, "# ");
+ strcpy (self->string, "#ERROR ");
strcat (self->string, ebuf);
strcat (self->string, " in '");
strcat (self->string, buf);
int
rxpd_file_load (struct rxpd_base* base, const char* filename)
{
- char buf[2048];
+ char buf[4096];
// TODO better filenname validation / error handling
if (!filename ||
strchr (filename, '/') ||
- strlen (filename) + strlen (base->rulesdir) > 2047)
+ strlen (filename) + strlen (base->rulesdir) > 4097)
abort();
strcpy (buf, base->rulesdir);
if (!f) abort();
// TODO test excess line length = error
- while (fgets (buf, 2048, f))
+ while (fgets (buf, 4096, f))
{
size_t last = strlen(buf);
if (buf[last-1] == '\n')
if (bind (self->fd, (struct sockaddr*)&listen_addr, sizeof (listen_addr)) == -1)
abort();
- static int yes=1;
+ static int yes = 1;
if (setsockopt (self->fd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(int)) == -1)
abort ();
rxpd_connection_activate (conn);
}
+///
+
+struct rxpd_buffer*
+rxpd_buffer_init (struct rxpd_buffer* self, struct rxpd_connection* conn)
+{
+ self->conn = conn;
+ self->state = RXPD_OK;
+ self->eol = self->eob = self->buffer;
+ self->buffer [4095] = '\0';
+ return self;
+}
+
+
+char*
+rxpd_buffer_readline (struct rxpd_buffer* self, int again)
+{
+ int fd = self->conn->fd;
+
+ if (self->eol != self->buffer)
+ {
+ //there was a line pending, discard it now
+ memmove (self->buffer, self->eol+1, self->eob - self->eol - 1);
+ self->eob = (char*)(self->eob - (self->eol - self->buffer + 1));
+ self->eol = self->buffer;
+ // TODO handle \r's
+ }
+
+ if (!again && self->state == RXPD_OK) // we only read when again is 0, first iteration
+ {
+ ssize_t r = 0;
+ do
+ {
+ r = read(fd, self->eob, 4096 - (self->eob - self->buffer));
+ }
+ while (r == -1 && errno == EINTR);
+
+ if (r == -1)
+ self->state = RXPD_ERROR;
+
+ if (r == 0)
+ {
+ shutdown (fd, SHUT_RD);
+ self->state = RXPD_EOF;
+ }
+
+ self->eob += r;
+ }
+
+ // find next newline, terminate string there
+ for (char* i = self->buffer; i < self->eob; ++i)
+ {
+ if (*i == '\n')
+ {
+ *i = '\0';
+ self->eol = i;
+ break;
+ }
+ }
+
+ // TODO handle buffer overfulls
+
+ return self->eol == self->buffer ? NULL : self->buffer;
+}
+
+
+
+
///
struct rxpd_connection*
if (self->fd == -1)
abort ();
+ static int yes = 1;
+ if (setsockopt (self->fd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(int)) == -1)
+ abort ();
+
+
self->base = base;
self->file = NULL;
- self->eol = self->eob = self->buffer;
+ rxpd_buffer_init (&self->in, self);
+ rxpd_buffer_init (&self->out, self);
event_set (&self->ev, self->fd, EV_READ, rxpd_connection_parse_cmd, self);
}
-
-
-int
-rxpd_connection_readline (struct rxpd_connection* self)
-{
-}
-
void
rxpd_connection_parse_cmd (int sock, short event, void* ptr)
{
printf ("parse cmd\n");
+ struct rxpd_connection* self = (struct rxpd_connection*) ptr;
+
+ char* line;
+ line = rxpd_buffer_readline (&self->in, 0);
+ printf ("got line '%s'\n", line);
+
+
// TODO policy check
+
+ //if (rxpd_buffer_state (&self->in) != RXPD_EOF)
+ // event_add (&self->ev, NULL);
}
void
#include "llist.h"
#include "psplay.h"
+#include <errno.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
struct rxpd_file;
struct rxpd_rule;
struct rxpd_socket;
+struct rxpd_buffer;
struct rxpd_connection;
struct rxpd_base
//
+enum rxpd_buffer_state_e
+ {
+ RXPD_OK, // operational
+ RXPD_EOF, // connection closed
+ RXPD_ERROR // some other error
+ };
+
+struct rxpd_buffer
+{
+ struct rxpd_connection* conn;
+ enum rxpd_buffer_state_e state;
+ char* eol;
+ char* eob;
+ char buffer[4096];
+};
+
+struct rxpd_buffer*
+rxpd_buffer_init (struct rxpd_buffer* self, struct rxpd_connection* conn);
+
+char*
+rxpd_buffer_readline (struct rxpd_buffer* self, int again);
+
+inline static enum rxpd_buffer_state_e
+rxpd_buffer_state (struct rxpd_buffer* self)
+{
+ return self->state;
+}
+
+
+//
struct rxpd_connection
{
llist node;
struct sockaddr peer_addr;
- char* eol;
- char* eob;
- char buffer[4096];
+ struct rxpd_buffer in;
+ struct rxpd_buffer out;
};