aboutsummaryrefslogtreecommitdiff
path: root/src/rest
diff options
context:
space:
mode:
authorMartin Schanzenbach <mschanzenbach@posteo.de>2020-08-04 19:40:23 +0200
committerMartin Schanzenbach <mschanzenbach@posteo.de>2020-08-04 19:40:23 +0200
commit815ded19f106990a37bbacec83546b1b897491f6 (patch)
tree9f9b013616809dad4cec996f96d0ca5e59331410 /src/rest
parent080519e980d8f8a3b138c733f837417bdb1b6757 (diff)
downloadgnunet-815ded19f106990a37bbacec83546b1b897491f6.tar.gz
gnunet-815ded19f106990a37bbacec83546b1b897491f6.zip
rest: fix #6462
Diffstat (limited to 'src/rest')
-rw-r--r--src/rest/gnunet-rest-server.c120
-rw-r--r--src/rest/plugin_rest_config.c7
-rw-r--r--src/rest/plugin_rest_copying.c32
3 files changed, 80 insertions, 79 deletions
diff --git a/src/rest/gnunet-rest-server.c b/src/rest/gnunet-rest-server.c
index 519a27515..44d4f345e 100644
--- a/src/rest/gnunet-rest-server.c
+++ b/src/rest/gnunet-rest-server.c
@@ -115,11 +115,6 @@ static struct MHD_Response *failure_response;
115static const struct GNUNET_CONFIGURATION_Handle *cfg; 115static const struct GNUNET_CONFIGURATION_Handle *cfg;
116 116
117/** 117/**
118 * Map of loaded plugins.
119 */
120static struct GNUNET_CONTAINER_MultiHashMap *plugin_map;
121
122/**
123 * Echo request Origin in CORS 118 * Echo request Origin in CORS
124 */ 119 */
125static int echo_origin; 120static int echo_origin;
@@ -140,6 +135,38 @@ static char *allow_headers;
140static char *allow_credentials; 135static char *allow_credentials;
141 136
142/** 137/**
138 * Plugin list head
139 */
140static struct PluginListEntry *plugins_head;
141
142/**
143 * Plugin list tail
144 */
145static struct PluginListEntry *plugins_tail;
146
147/**
148 * A plugin list entry
149 */
150struct PluginListEntry
151{
152 /* DLL */
153 struct PluginListEntry *next;
154
155 /* DLL */
156 struct PluginListEntry *prev;
157
158 /**
159 * libname (to cleanup)
160 */
161 char *libname;
162
163 /**
164 * The plugin
165 */
166 struct GNUNET_REST_Plugin *plugin;
167};
168
169/**
143 * MHD Connection handle 170 * MHD Connection handle
144 */ 171 */
145struct MhdConnectionHandle 172struct MhdConnectionHandle
@@ -148,8 +175,6 @@ struct MhdConnectionHandle
148 175
149 struct MHD_Response *response; 176 struct MHD_Response *response;
150 177
151 struct GNUNET_REST_Plugin *plugin;
152
153 struct GNUNET_REST_RequestHandle *data_handle; 178 struct GNUNET_REST_RequestHandle *data_handle;
154 179
155 struct MHD_PostProcessor *pp; 180 struct MHD_PostProcessor *pp;
@@ -322,15 +347,15 @@ post_data_iter (void *cls,
322 347
323 GNUNET_CRYPTO_hash (key, strlen (key), &hkey); 348 GNUNET_CRYPTO_hash (key, strlen (key), &hkey);
324 val = GNUNET_CONTAINER_multihashmap_get (handle->url_param_map, 349 val = GNUNET_CONTAINER_multihashmap_get (handle->url_param_map,
325 &hkey); 350 &hkey);
326 if (NULL == val) 351 if (NULL == val)
327 { 352 {
328 val = GNUNET_malloc (65536); 353 val = GNUNET_malloc (65536);
329 if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put ( 354 if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put (
330 handle->url_param_map, 355 handle->url_param_map,
331 &hkey, 356 &hkey,
332 val, 357 val,
333 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) 358 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY))
334 { 359 {
335 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 360 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
336 "Could not add url param '%s'\n", 361 "Could not add url param '%s'\n",
@@ -378,39 +403,21 @@ create_response (void *cls,
378 size_t *upload_data_size, 403 size_t *upload_data_size,
379 void **con_cls) 404 void **con_cls)
380{ 405{
381 char *plugin_name;
382 char *origin; 406 char *origin;
383 struct GNUNET_HashCode key; 407 struct GNUNET_HashCode key;
384 struct MhdConnectionHandle *con_handle; 408 struct MhdConnectionHandle *con_handle;
385 struct GNUNET_REST_RequestHandle *rest_conndata_handle; 409 struct GNUNET_REST_RequestHandle *rest_conndata_handle;
410 struct PluginListEntry *ple;
386 411
387 con_handle = *con_cls; 412 con_handle = *con_cls;
388 413
389 if (NULL == *con_cls) 414 if (NULL == *con_cls)
390 { 415 {
391 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "New connection %s\n", url); 416 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "New connection %s\n", url);
392 char tmp_url[strlen (url) + 1];
393 strcpy (tmp_url, url);
394 con_handle = GNUNET_new (struct MhdConnectionHandle); 417 con_handle = GNUNET_new (struct MhdConnectionHandle);
395 con_handle->con = con; 418 con_handle->con = con;
396 con_handle->state = GN_REST_STATE_INIT; 419 con_handle->state = GN_REST_STATE_INIT;
397 *con_cls = con_handle; 420 *con_cls = con_handle;
398
399 plugin_name = strtok (tmp_url, "/");
400
401 if (NULL != plugin_name)
402 {
403 GNUNET_CRYPTO_hash (plugin_name, strlen (plugin_name), &key);
404
405 con_handle->plugin = GNUNET_CONTAINER_multihashmap_get (plugin_map, &key);
406 }
407 if (NULL == con_handle->plugin)
408 {
409 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Queueing response with MHD\n");
410 GNUNET_free (con_handle);
411 return MHD_queue_response (con, MHD_HTTP_NOT_FOUND, failure_response);
412 }
413
414 return MHD_YES; 421 return MHD_YES;
415 } 422 }
416 if (GN_REST_STATE_INIT == con_handle->state) 423 if (GN_REST_STATE_INIT == con_handle->state)
@@ -445,9 +452,18 @@ create_response (void *cls,
445 MHD_destroy_post_processor (con_handle->pp); 452 MHD_destroy_post_processor (con_handle->pp);
446 453
447 con_handle->state = GN_REST_STATE_PROCESSING; 454 con_handle->state = GN_REST_STATE_PROCESSING;
448 con_handle->plugin->process_request (rest_conndata_handle, 455 for (ple = plugins_head; NULL != ple; ple = ple->next)
449 &plugin_callback, 456 {
450 con_handle); 457 if (GNUNET_YES == ple->plugin->process_request (rest_conndata_handle,
458 &plugin_callback,
459 con_handle))
460 break; /* Request handled */
461 }
462 if (NULL == ple)
463 {
464 /** Request not handled **/
465 MHD_queue_response (con, MHD_HTTP_NOT_FOUND, failure_response);
466 }
451 *upload_data_size = 0; 467 *upload_data_size = 0;
452 run_mhd_now (); 468 run_mhd_now ();
453 return MHD_YES; 469 return MHD_YES;
@@ -732,6 +748,18 @@ do_accept (void *cls)
732static void 748static void
733do_shutdown (void *cls) 749do_shutdown (void *cls)
734{ 750{
751 struct PluginListEntry *ple;
752
753 while (NULL != plugins_head)
754 {
755 ple = plugins_head;
756 GNUNET_CONTAINER_DLL_remove (plugins_head,
757 plugins_tail,
758 ple);
759 GNUNET_PLUGIN_unload (ple->libname, NULL);
760 GNUNET_free (ple->libname);
761 GNUNET_free (ple);
762 }
735 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down...\n"); 763 GNUNET_log (GNUNET_ERROR_TYPE_INFO, "Shutting down...\n");
736 kill_httpd (); 764 kill_httpd ();
737 GNUNET_free (allow_credentials); 765 GNUNET_free (allow_credentials);
@@ -820,7 +848,7 @@ static void
820load_plugin (void *cls, const char *libname, void *lib_ret) 848load_plugin (void *cls, const char *libname, void *lib_ret)
821{ 849{
822 struct GNUNET_REST_Plugin *plugin = lib_ret; 850 struct GNUNET_REST_Plugin *plugin = lib_ret;
823 struct GNUNET_HashCode key; 851 struct PluginListEntry *ple;
824 852
825 if (NULL == lib_ret) 853 if (NULL == lib_ret)
826 { 854 {
@@ -831,18 +859,12 @@ load_plugin (void *cls, const char *libname, void *lib_ret)
831 } 859 }
832 GNUNET_assert (1 < strlen (plugin->name)); 860 GNUNET_assert (1 < strlen (plugin->name));
833 GNUNET_assert ('/' == *plugin->name); 861 GNUNET_assert ('/' == *plugin->name);
834 GNUNET_CRYPTO_hash (plugin->name + 1, strlen (plugin->name + 1), &key); 862 ple = GNUNET_new (struct PluginListEntry);
835 if (GNUNET_OK != GNUNET_CONTAINER_multihashmap_put ( 863 ple->libname = GNUNET_strdup (libname);
836 plugin_map, 864 ple->plugin = plugin;
837 &key, 865 GNUNET_CONTAINER_DLL_insert (plugins_head,
838 plugin, 866 plugins_tail,
839 GNUNET_CONTAINER_MULTIHASHMAPOPTION_UNIQUE_ONLY)) 867 ple);
840 {
841 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
842 "Could not load add plugin `%s'\n",
843 libname);
844 return;
845 }
846 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loaded plugin `%s'\n", libname); 868 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Loaded plugin `%s'\n", libname);
847} 869}
848 870
@@ -864,8 +886,8 @@ run (void *cls,
864 char *addr_str; 886 char *addr_str;
865 887
866 cfg = c; 888 cfg = c;
867 plugin_map = GNUNET_CONTAINER_multihashmap_create (10, GNUNET_NO); 889 plugins_head = NULL;
868 890 plugins_tail = NULL;
869 /* Get port to bind to */ 891 /* Get port to bind to */
870 if (GNUNET_OK != 892 if (GNUNET_OK !=
871 GNUNET_CONFIGURATION_get_value_number (cfg, "rest", "HTTP_PORT", &port)) 893 GNUNET_CONFIGURATION_get_value_number (cfg, "rest", "HTTP_PORT", &port))
diff --git a/src/rest/plugin_rest_config.c b/src/rest/plugin_rest_config.c
index 43dea1b9f..d9ae57acd 100644
--- a/src/rest/plugin_rest_config.c
+++ b/src/rest/plugin_rest_config.c
@@ -347,7 +347,7 @@ options_cont (struct GNUNET_REST_RequestHandle *con_handle,
347 * @param proc_cls closure for @a proc 347 * @param proc_cls closure for @a proc
348 * @return #GNUNET_OK if request accepted 348 * @return #GNUNET_OK if request accepted
349 */ 349 */
350static void 350static enum GNUNET_GenericReturnValue
351rest_config_process_request (struct GNUNET_REST_RequestHandle *conndata_handle, 351rest_config_process_request (struct GNUNET_REST_RequestHandle *conndata_handle,
352 GNUNET_REST_ResultProcessor proc, 352 GNUNET_REST_ResultProcessor proc,
353 void *proc_cls) 353 void *proc_cls)
@@ -371,9 +371,10 @@ rest_config_process_request (struct GNUNET_REST_RequestHandle *conndata_handle,
371 if (GNUNET_NO == 371 if (GNUNET_NO ==
372 GNUNET_REST_handle_request (conndata_handle, handlers, &err, handle)) 372 GNUNET_REST_handle_request (conndata_handle, handlers, &err, handle))
373 { 373 {
374 handle->response_code = err.error_code; 374 cleanup_handle (handle);
375 GNUNET_SCHEDULER_add_now (&do_error, handle); 375 return GNUNET_NO;
376 } 376 }
377 return GNUNET_YES;
377} 378}
378 379
379 380
diff --git a/src/rest/plugin_rest_copying.c b/src/rest/plugin_rest_copying.c
index e601e505e..1649da3bb 100644
--- a/src/rest/plugin_rest_copying.c
+++ b/src/rest/plugin_rest_copying.c
@@ -82,24 +82,6 @@ cleanup_handle (struct RequestHandle *handle)
82 82
83 83
84/** 84/**
85 * Task run on shutdown. Cleans up everything.
86 *
87 * @param cls unused
88 * @param tc scheduler context
89 */
90static void
91do_error (void *cls)
92{
93 struct RequestHandle *handle = cls;
94 struct MHD_Response *resp;
95
96 resp = GNUNET_REST_create_response (NULL);
97 handle->proc (handle->proc_cls, resp, handle->response_code);
98 cleanup_handle (handle);
99}
100
101
102/**
103 * Handle rest request 85 * Handle rest request
104 * 86 *
105 * @param handle the lookup handle 87 * @param handle the lookup handle
@@ -155,7 +137,7 @@ options_cont (struct GNUNET_REST_RequestHandle *con_handle,
155 * @param proc_cls closure for @a proc 137 * @param proc_cls closure for @a proc
156 * @return #GNUNET_OK if request accepted 138 * @return #GNUNET_OK if request accepted
157 */ 139 */
158static void 140static enum GNUNET_GenericReturnValue
159rest_copying_process_request (struct GNUNET_REST_RequestHandle *conndata_handle, 141rest_copying_process_request (struct GNUNET_REST_RequestHandle *conndata_handle,
160 GNUNET_REST_ResultProcessor proc, 142 GNUNET_REST_ResultProcessor proc,
161 void *proc_cls) 143 void *proc_cls)
@@ -172,14 +154,10 @@ rest_copying_process_request (struct GNUNET_REST_RequestHandle *conndata_handle,
172 handle->proc = proc; 154 handle->proc = proc;
173 handle->rest_handle = conndata_handle; 155 handle->rest_handle = conndata_handle;
174 156
175 if (GNUNET_NO == GNUNET_REST_handle_request (conndata_handle, 157 return GNUNET_REST_handle_request (conndata_handle,
176 handlers, 158 handlers,
177 &err, 159 &err,
178 handle)) 160 handle);
179 {
180 handle->response_code = err.error_code;
181 GNUNET_SCHEDULER_add_now (&do_error, handle);
182 }
183} 161}
184 162
185 163