From b4cbca161a1638e96d9e0a6fe12a29ed43173e43 Mon Sep 17 00:00:00 2001 From: Jon Bergli Heier Date: Mon, 16 Aug 2010 00:51:20 +0200 Subject: Committed some work. --- httpd.c | 92 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 92 insertions(+) create mode 100644 httpd.c (limited to 'httpd.c') diff --git a/httpd.c b/httpd.c new file mode 100644 index 0000000..49b6b1e --- /dev/null +++ b/httpd.c @@ -0,0 +1,92 @@ +#include "httpd.h" +#include "commands.h" + +#include +#include + +GSocketService *ss = NULL; + +static gboolean service_incoming(GSocketService *service, + GSocketConnection *connection, GObject *source_object, + gpointer user_data) { + GSocket *socket; + GError *error = NULL; + + g_debug("incoming connection to service"); + + socket = g_socket_connection_get_socket(connection); + if(socket == NULL) { + g_error("g_socket_connection_get_socket() returned NULL"); + return FALSE; + } + + GString *string = g_string_new(NULL); + gboolean done = FALSE; + gssize tot = 0; + + while(done == FALSE) { + gchar buffer[0x400]; + gssize len = g_socket_receive(socket, buffer, 0x400, NULL, &error); + if(len == -1) { + g_error(error->message); + g_error_free(error); + return FALSE; + } + tot += len; + g_string_append_len(string, buffer, len); + + /* TODO: find a more sane way to stop reading */ + if(string->len >= 4 && g_strcmp0(string->str + string->len - 4, "\r\n\r\n") == 0) { + done = TRUE; + } + } + g_debug("read %lu bytes", tot); + g_debug("HTTP header:\n%s", string->str); + + /* split headers */ + gchar **data = g_strsplit(string->str, "\r\n", 0); + + g_string_free(string, TRUE); + + gchar **firstline = g_strsplit(data[0], " ", 0); + /* this sets the first character of the last string in + * firstline to \0 (HTTP version) */ + firstline[g_strv_length(firstline)-1] = '\0'; + /* now join from the second string to get the request path */ + gchar *path = g_strjoinv(" ", firstline + 1); + + g_strfreev(firstline); + + for(gint i = 1; strlen(data[i]); i++) { + g_debug("data[%d] = %s", i, data[i]); + } + + g_strfreev(data); + + commands_handle(connection, path); + + if(g_socket_close(socket, &error) == FALSE) { + g_error(error->message); + g_error_free(error); + return FALSE; + } + + return FALSE; +} + +gboolean httpd_start() { + ss = g_threaded_socket_service_new(10); + + g_socket_listener_add_inet_port((GSocketListener*)ss, 8000, NULL, NULL); + + g_signal_connect(ss, "incoming", (GCallback)service_incoming, NULL); + g_socket_service_start(ss); + + return TRUE; +} + +void httpd_stop() { + g_socket_service_stop(ss); + g_free(ss); + ss = NULL; +} -- cgit v1.2.3