summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: 2a0f3c8)
raw | patch | inline | side by side (parent: 2a0f3c8)
author | Sebastian Harl <sh@tokkee.org> | |
Sat, 23 Nov 2013 08:50:50 +0000 (09:50 +0100) | ||
committer | Sebastian Harl <sh@tokkee.org> | |
Sat, 23 Nov 2013 08:52:39 +0000 (09:52 +0100) |
Implemented an initial, trivial "framework" for session handling /
authentication. Simply send back OK status for now.
Fixed preconditions for initialization and handling of commands.
authentication. Simply send back OK status for now.
Fixed preconditions for initialization and handling of commands.
src/Makefile.am | patch | blob | history | |
src/frontend/connection.c | patch | blob | history | |
src/frontend/session.c | [new file with mode: 0644] | patch | blob |
src/include/frontend/connection.h | patch | blob | history |
diff --git a/src/Makefile.am b/src/Makefile.am
index 24b41ae51bedb40ba510eccb7f0f75d1731ce792..32c493e56900702d702838f4473825d5a4a582c6 100644 (file)
--- a/src/Makefile.am
+++ b/src/Makefile.am
core/error.c include/core/error.h \
frontend/connection.c include/frontend/connection.h \
frontend/sock.c include/frontend/sock.h \
+ frontend/session.c \
utils/channel.c include/utils/channel.h \
utils/llist.c include/utils/llist.h \
utils/strbuf.c include/utils/strbuf.h \
index f235dc7a84e09d2697010276c089dfc6422270a6..23bbb33920f2186b56004c5b3d8d52d5730a6b01 100644 (file)
static int
command_handle(sdb_conn_t *conn)
{
- assert(conn && conn->cmd && conn->cmd_len);
- /* XXX */
- sdb_strbuf_skip(conn->buf, conn->cmd_len);
- conn->cmd = conn->cmd_len = 0;
- return 0;
+ int status = -1;
+
+ assert(conn && (conn->cmd != CONNECTION_IDLE));
+
+ sdb_log(SDB_LOG_DEBUG, "frontend: Handling command %u (len: %u)",
+ conn->cmd, conn->cmd_len);
+
+ switch (conn->cmd) {
+ case CONNECTION_PING:
+ status = sdb_connection_ping(conn);
+ break;
+ case CONNECTION_STARTUP:
+ status = sdb_session_start(conn);
+ break;
+ default:
+ sdb_log(SDB_LOG_WARNING, "frontend: Ignoring invalid command");
+ status = -1;
+ break;
+ }
+
+ /* remove the command from the buffer */
+ if (conn->cmd_len)
+ sdb_strbuf_skip(conn->buf, conn->cmd_len);
+ conn->cmd = CONNECTION_IDLE;
+ conn->cmd_len = 0;
+ return status;
} /* command_handle */
/* initialize the connection state information */
static int
command_init(sdb_conn_t *conn)
{
- assert(conn && (! conn->cmd) && (! conn->cmd_len));
+ size_t len;
+
+ assert(conn && (conn->cmd == CONNECTION_IDLE) && (! conn->cmd_len));
conn->cmd = connection_get_int32(conn, 0);
conn->cmd_len = connection_get_int32(conn, sizeof(uint32_t));
- sdb_strbuf_skip(conn->buf, 2 * sizeof(uint32_t));
+
+ len = 2 * sizeof(uint32_t);
+ if (conn->cmd == CONNECTION_IDLE)
+ len += conn->cmd_len;
+ sdb_strbuf_skip(conn->buf, len);
return 0;
} /* command_init */
return -1;
}
- conn->cmd = conn->cmd_len = 0;
+ conn->cmd = CONNECTION_IDLE;
+ conn->cmd_len = 0;
conn->fd = -1;
return 0;
} /* sdb_connection_init */
while (42) {
ssize_t status = connection_read(conn);
- if ((! conn->cmd) && (! conn->cmd_len)
+ if ((conn->cmd == CONNECTION_IDLE) && (! conn->cmd_len)
&& (sdb_strbuf_len(conn->buf) >= 2 * sizeof(int32_t)))
command_init(conn);
- if (conn->cmd_len && (sdb_strbuf_len(conn->buf) >= conn->cmd_len))
+ if ((conn->cmd != CONNECTION_IDLE)
+ && (sdb_strbuf_len(conn->buf) >= conn->cmd_len))
command_handle(conn);
if (status <= 0)
return n;
} /* sdb_connection_read */
+ssize_t
+sdb_connection_send(sdb_conn_t *conn, uint32_t code,
+ uint32_t msg_len, char *msg)
+{
+ size_t len = 2 * sizeof(uint32_t) + msg_len;
+ char buffer[len];
+ char *buf;
+
+ uint32_t tmp;
+
+ if ((! conn) || (conn->fd < 0))
+ return -1;
+
+ tmp = htonl(code);
+ memcpy(buffer, &tmp, sizeof(uint32_t));
+
+ tmp = htonl(msg_len);
+ memcpy(buffer + sizeof(uint32_t), &tmp, sizeof(uint32_t));
+
+ if (msg_len)
+ memcpy(buffer + 2 * sizeof(uint32_t), msg, msg_len);
+
+ buf = buffer;
+ while (len > 0) {
+ ssize_t status;
+
+ /* XXX: use select() */
+
+ errno = 0;
+ status = write(conn->fd, buf, len);
+ if (status < 0) {
+ char errbuf[1024];
+
+ if ((errno == EAGAIN) || (errno == EWOULDBLOCK))
+ continue;
+ if (errno == EINTR)
+ continue;
+
+ sdb_log(SDB_LOG_ERR, "frontend: Failed to send msg "
+ "(code: %u, len: %u) to client: %s", code, msg_len,
+ sdb_strerror(errno, errbuf, sizeof(errbuf)));
+ return status;
+ }
+
+ len -= (size_t)status;
+ buf += status;
+ }
+ return (ssize_t)len;
+} /* sdb_connection_send */
+
+int
+sdb_connection_ping(sdb_conn_t *conn)
+{
+ if ((! conn) || (conn->cmd != CONNECTION_PING))
+ return -1;
+
+ /* we're alive */
+ sdb_connection_send(conn, CONNECTION_OK, 0, NULL);
+ return 0;
+} /* sdb_connection_ping */
+
/* vim: set tw=78 sw=4 ts=4 noexpandtab : */
diff --git a/src/frontend/session.c b/src/frontend/session.c
--- /dev/null
+++ b/src/frontend/session.c
@@ -0,0 +1,51 @@
+/*
+ * SysDB - src/frontend/session.c
+ * Copyright (C) 2013 Sebastian 'tokkee' Harl <sh@tokkee.org>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "sysdb.h"
+
+#include "frontend/connection.h"
+
+/*
+ * public API
+ */
+
+int
+sdb_session_start(sdb_conn_t *conn)
+{
+ if ((! conn) || (conn->username))
+ return -1;
+
+ if (conn->cmd != CONNECTION_STARTUP)
+ return -1;
+
+ /* XXX: for now, simply accept all connections */
+ sdb_connection_send(conn, CONNECTION_OK, 0, NULL);
+ return 0;
+} /* session_start */
+
+/* vim: set tw=78 sw=4 ts=4 noexpandtab : */
+
index 5748211f4c1d5c78f367eb1fc9672c825f757c2c..a5ea092c425d65f570af2b838f2febbdf9e64611 100644 (file)
extern "C" {
#endif
+/* status codes returned to a client */
+typedef enum {
+ CONNECTION_OK = 0,
+ CONNECTION_ERROR
+} sdb_conn_status_t;
+
+/* accepted commands / state of the connection */
+typedef enum {
+ CONNECTION_IDLE = 0,
+ CONNECTION_PING,
+ CONNECTION_STARTUP,
+} sdb_conn_state_t;
+
/* a generic connection object */
typedef struct {
/* file-descriptor of the open connection */
/* connection / protocol state information */
uint32_t cmd;
uint32_t cmd_len;
+
+ /* user information */
+ char *username; /* NULL if the user has not been authenticated */
} sdb_conn_t;
/*
ssize_t
sdb_connection_read(sdb_conn_t *conn);
+/*
+ * sdb_connection_send:
+ * Send to an open connection.
+ *
+ * Returns:
+ * - the number of bytes written
+ * - a negative value on error
+ */
+ssize_t
+sdb_connection_send(sdb_conn_t *conn, uint32_t code,
+ uint32_t msg_len, char *msg);
+
+/*
+ * sdb_connection_ping:
+ * Send back a backend status indicator to the connected client.
+ *
+ * Returns:
+ * - 0 on success
+ * - a negative value else
+ */
+int
+sdb_connection_ping(sdb_conn_t *conn);
+
+/*
+ * session handling
+ */
+
+/*
+ * sdb_session_start:
+ * Start a new user session on the specified connection.
+ *
+ * Returns:
+ * - 0 on success
+ * - a negative value else
+ */
+int
+sdb_session_start(sdb_conn_t *conn);
+
#ifdef __cplusplus
} /* extern "C" */
#endif