summaryrefslogtreecommitdiff
path: root/src/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/main.c')
-rw-r--r--src/main.c102
1 files changed, 46 insertions, 56 deletions
diff --git a/src/main.c b/src/main.c
index 420490c..8e4101f 100644
--- a/src/main.c
+++ b/src/main.c
@@ -55,6 +55,7 @@ static int server_timeout = 5;
static char *token_server_addrmask = NULL;
static gboolean conflict_is_restart = FALSE;
static GInetAddressMask *stp_inet_addrmask = NULL;
+static GMainLoop *loop = NULL;
static GOptionEntry entries[] =
{
@@ -93,20 +94,21 @@ get_server_ctx_from_msg (SoupMessage *msg,
static STPStreamToken*
stp_validate_fetch_token_from_query (GHashTable *tokens,
const char *sessionid,
- const char *query_string,
+ GHashTable *query,
guint *http_status_code)
{
- GHashTable *query;
- char *type, *udp_clients;
+ char *query_string, *type, *udp_clients;
STPStreamToken *token, *perms_token;
- if (!query_string) {
- g_debug ("Rejecting stream: no query string specified");
+ if (!query) {
+ g_debug ("Rejecting stream: no query specified");
*http_status_code = SOUP_STATUS_BAD_REQUEST;
return NULL;
}
+ query_string = soup_form_encode_hash (query);
g_debug ("Recv query string: %s\n", query_string);
+ g_free (query_string);
if (stp_inet_addrmask &&
!g_hash_table_contains (tokens, sessionid)) {
@@ -115,8 +117,6 @@ stp_validate_fetch_token_from_query (GHashTable *tokens,
return NULL;
}
- query = soup_form_decode (query_string);
-
token = g_new0 (STPStreamToken, 1);
type = g_hash_table_lookup (query, "type");
@@ -318,12 +318,12 @@ stream_finished_cb (SoupMessage *msg,
/* This is called when the entire request body has been read */
static void
-handle_request_cb (SoupServer *server,
- SoupMessage *msg,
- const char *path,
- GHashTable *query,
- SoupClientContext *client,
- STPHashTables *tables)
+handle_request_with_body_cb (SoupServer *server,
+ SoupMessage *msg,
+ const char *path,
+ GHashTable *query,
+ SoupClientContext *client,
+ STPHashTables *tables)
{
STPServerCtx *server_ctx;
@@ -431,7 +431,7 @@ GET:
/* Add to pipeline and sync state */
gst_bin_add (GST_BIN (server_ctx->pipeline), bin);
-
+
if (!gst_element_sync_state_with_parent (bin)) {
g_critical ("Unable to sync appsink bin with parent pipeline\n");
goto err;
@@ -444,7 +444,7 @@ GET:
/* Send the WebM stream header through the src pad first */
caps = gst_pad_get_current_caps (srcpad);
-
+
buffer = stp_get_streamheader_from_caps (caps);
if (!buffer) {
g_critical ("Unable to get streamheader from caps");
@@ -616,11 +616,14 @@ got_first_request_body_chunk (SoupMessage *msg,
}
static void
-got_request_headers (SoupMessage *msg,
- STPHashTables *tables)
+handle_request_with_headers_cb (SoupServer *server,
+ SoupMessage *msg,
+ const char *path,
+ GHashTable *query,
+ SoupClientContext *client,
+ STPHashTables *tables)
{
- SoupURI *uri;
- const char *path, *sessionid, *query;
+ const char *sessionid;
#ifdef HEADERS_DEBUG
SoupMessageHeadersIter iter;
@@ -630,9 +633,6 @@ got_request_headers (SoupMessage *msg,
g_debug ("%s: %s", name, value);
#endif
- g_object_get (msg, "uri", &uri, NULL);
- path = soup_uri_get_path (uri);
- query = soup_uri_get_query (uri);
g_debug ("%s on uri %s", msg->method, path);
/* Token API methods are handled in the server callbacks,
@@ -759,7 +759,7 @@ PUT: {
goto PUT_out;
}
-new_conn:
+ new_conn:
/* This is a new connection; treat it as such */
ctx = g_new0 (STPServerCtx, 1);
ctx->stream_type = token->stream_type;
@@ -807,25 +807,10 @@ GET: {
}
out:
- soup_uri_free (uri);
return;
}
static void
-request_started_cb (SoupServer *server,
- SoupMessage *msg,
- SoupClientContext *client,
- STPHashTables *tables)
-{
- g_debug ("New %s request started", msg->method);
-
- /* SoupMessage is useful only once we have headers,
- * so we do all initialization there */
- g_signal_connect (msg, "got-headers",
- G_CALLBACK (got_request_headers), tables);
-}
-
-static void
handle_add_token_cb (SoupServer *server,
SoupMessage *msg,
const char *path,
@@ -857,7 +842,7 @@ POST: {
soup_message_set_status (msg, SOUP_STATUS_FORBIDDEN);
goto out;
}
-
+
if (!query ||
!g_hash_table_contains (query, "sessionid") ||
!g_hash_table_contains (query, "type")) {
@@ -923,7 +908,7 @@ DELETE: {
soup_message_set_status (msg, SOUP_STATUS_FORBIDDEN);
goto out;
}
-
+
if (!query ||
!g_hash_table_contains (query, "sessionid")) {
soup_message_set_status (msg, SOUP_STATUS_BAD_REQUEST);
@@ -1091,7 +1076,7 @@ GET: {
json_builder_set_member_name (b, "status");
json_builder_add_string_value (b, ctx->status);
-
+
json_builder_end_object (b);
}
json_builder_end_array (b);
@@ -1170,8 +1155,9 @@ out:
gboolean
exit_on_signal_cb (SoupServer *server)
{
- soup_server_quit (server);
+ soup_server_disconnect (server);
g_object_unref (server);
+ g_main_loop_quit (loop);
return G_SOURCE_REMOVE;
}
@@ -1216,16 +1202,18 @@ main (int argc,
/* TODO: Accept command-line argument for host */
server = soup_server_new (SOUP_SERVER_SERVER_HEADER,
- "soup-transcode-proxy ",
- SOUP_SERVER_PORT, port, NULL);
-
- /* Handle the end of POST/PUT, and all GET requests */
+ "soup-transcode-proxy ", NULL);
+
+ /* Handle streaming (chunked) requests when we recv headers */
+ soup_server_add_early_handler (server, NULL,
+ (SoupServerCallback)handle_request_with_headers_cb,
+ tables, NULL);
+ /* Handle completed requests; i.e. the end of POST/PUT and all GET requests */
soup_server_add_handler (server, NULL,
- (SoupServerCallback)handle_request_cb,
+ (SoupServerCallback)handle_request_with_body_cb,
tables, NULL);
- /* NOTE: When adding a new path handler, an exception must be made in
- * got_request_headers() for that path, otherwise a 405 will be returned */
+ /* REST API for server status query handling */
soup_server_add_handler (server, STP_REST_ABORT_STREAM,
(SoupServerCallback)handle_abort_stream_cb,
tables, NULL);
@@ -1246,15 +1234,17 @@ main (int argc,
tables, NULL);
}
- /* Since chunked streaming requests send all the data in a single request,
- * we need to handle those when we get the headers. Hence, all PUT stream
- * handling is done here. */
- g_signal_connect (server, "request-started",
- G_CALLBACK (request_started_cb), tables);
-
g_unix_signal_add (SIGINT, (GSourceFunc)exit_on_signal_cb, server);
- soup_server_run (server);
+ soup_server_listen_all (server, port, 0, &error);
+ if (error) {
+ g_printerr ("Error starting soup server: %s\n", error->message);
+ return 1;
+ }
+
+ g_debug ("SoupServer setup, running mainloop...");
+ loop = g_main_loop_new (NULL, FALSE);
+ g_main_loop_run (loop);
g_hash_table_unref (tables->tokens);
g_hash_table_unref (tables->ctxs);