diff options
-rw-r--r-- | src/dns/gnunet-service-dns.c | 2 | ||||
-rw-r--r-- | src/exit/gnunet-daemon-exit.c | 2 | ||||
-rw-r--r-- | src/fs/fs_dirmetascan.c | 4 | ||||
-rw-r--r-- | src/include/gnunet_helper_lib.h | 42 | ||||
-rw-r--r-- | src/testbed/gnunet-service-testbed.c | 3 | ||||
-rw-r--r-- | src/testbed/gnunet-service-testbed_links.c | 57 | ||||
-rw-r--r-- | src/testbed/test_gnunet_helper_testbed.c | 2 | ||||
-rw-r--r-- | src/testbed/testbed_api_hosts.c | 43 | ||||
-rw-r--r-- | src/testbed/testbed_api_hosts.h | 20 | ||||
-rw-r--r-- | src/transport/plugin_transport_wlan.c | 2 | ||||
-rw-r--r-- | src/transport/test_plugin_transport.c | 4 | ||||
-rw-r--r-- | src/util/helper.c | 140 | ||||
-rw-r--r-- | src/vpn/gnunet-service-vpn.c | 4 |
13 files changed, 222 insertions, 103 deletions
diff --git a/src/dns/gnunet-service-dns.c b/src/dns/gnunet-service-dns.c index 5e9de5f4d..4a94283ab 100644 --- a/src/dns/gnunet-service-dns.c +++ b/src/dns/gnunet-service-dns.c | |||
@@ -281,7 +281,7 @@ cleanup_task (void *cls GNUNET_UNUSED, | |||
281 | { | 281 | { |
282 | unsigned int i; | 282 | unsigned int i; |
283 | 283 | ||
284 | GNUNET_HELPER_stop (hijacker); | 284 | GNUNET_HELPER_stop (hijacker, GNUNET_NO); |
285 | hijacker = NULL; | 285 | hijacker = NULL; |
286 | for (i=0;i<7;i++) | 286 | for (i=0;i<7;i++) |
287 | GNUNET_free_non_null (helper_argv[i]); | 287 | GNUNET_free_non_null (helper_argv[i]); |
diff --git a/src/exit/gnunet-daemon-exit.c b/src/exit/gnunet-daemon-exit.c index 72522e121..fbf173086 100644 --- a/src/exit/gnunet-daemon-exit.c +++ b/src/exit/gnunet-daemon-exit.c | |||
@@ -3074,7 +3074,7 @@ cleanup (void *cls GNUNET_UNUSED, | |||
3074 | 3074 | ||
3075 | if (helper_handle != NULL) | 3075 | if (helper_handle != NULL) |
3076 | { | 3076 | { |
3077 | GNUNET_HELPER_stop (helper_handle); | 3077 | GNUNET_HELPER_stop (helper_handle, GNUNET_NO); |
3078 | helper_handle = NULL; | 3078 | helper_handle = NULL; |
3079 | } | 3079 | } |
3080 | if (mesh_handle != NULL) | 3080 | if (mesh_handle != NULL) |
diff --git a/src/fs/fs_dirmetascan.c b/src/fs/fs_dirmetascan.c index e5a575a51..7139ea45a 100644 --- a/src/fs/fs_dirmetascan.c +++ b/src/fs/fs_dirmetascan.c | |||
@@ -102,7 +102,7 @@ GNUNET_FS_directory_scan_abort (struct GNUNET_FS_DirScanner *ds) | |||
102 | { | 102 | { |
103 | /* terminate helper */ | 103 | /* terminate helper */ |
104 | if (NULL != ds->helper) | 104 | if (NULL != ds->helper) |
105 | GNUNET_HELPER_stop (ds->helper); | 105 | GNUNET_HELPER_stop (ds->helper, GNUNET_NO); |
106 | 106 | ||
107 | /* free resources */ | 107 | /* free resources */ |
108 | if (NULL != ds->toplevel) | 108 | if (NULL != ds->toplevel) |
@@ -234,7 +234,7 @@ finish_scan (void *cls, | |||
234 | ds->stop_task = GNUNET_SCHEDULER_NO_TASK; | 234 | ds->stop_task = GNUNET_SCHEDULER_NO_TASK; |
235 | if (NULL != ds->helper) | 235 | if (NULL != ds->helper) |
236 | { | 236 | { |
237 | GNUNET_HELPER_stop (ds->helper); | 237 | GNUNET_HELPER_stop (ds->helper, GNUNET_NO); |
238 | ds->helper = NULL; | 238 | ds->helper = NULL; |
239 | } | 239 | } |
240 | ds->progress_callback (ds->progress_callback_cls, | 240 | ds->progress_callback (ds->progress_callback_cls, |
diff --git a/src/include/gnunet_helper_lib.h b/src/include/gnunet_helper_lib.h index 191d97b80..06d65b360 100644 --- a/src/include/gnunet_helper_lib.h +++ b/src/include/gnunet_helper_lib.h | |||
@@ -20,7 +20,8 @@ | |||
20 | 20 | ||
21 | /** | 21 | /** |
22 | * @file include/gnunet_helper_lib.h | 22 | * @file include/gnunet_helper_lib.h |
23 | * @brief API for dealing with (SUID) helper processes that communicate via GNUNET_MessageHeaders on stdin/stdout | 23 | * @brief API for dealing with (SUID) helper processes that communicate via |
24 | * GNUNET_MessageHeaders on stdin/stdout | ||
24 | * @author Philipp Toelke | 25 | * @author Philipp Toelke |
25 | * @author Christian Grothoff | 26 | * @author Christian Grothoff |
26 | */ | 27 | */ |
@@ -72,22 +73,49 @@ GNUNET_HELPER_start (int with_control_pipe, | |||
72 | 73 | ||
73 | 74 | ||
74 | /** | 75 | /** |
75 | * Kills the helper, closes the pipe and frees the handle | 76 | * Sends termination signal to the helper process. The helper process is not |
77 | * reaped; call GNUNET_HELPER_wait() for reaping the dead helper process. | ||
76 | * | 78 | * |
77 | * @param h handle to helper to stop | 79 | * @param h the helper handle |
80 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | ||
81 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | ||
82 | * @return GNUNET_OK on success; GNUNET_SYSERR on error | ||
83 | */ | ||
84 | int | ||
85 | GNUNET_HELPER_kill (struct GNUNET_HELPER_Handle *h, int soft_kill); | ||
86 | |||
87 | |||
88 | /** | ||
89 | * Reap the helper process. This call is blocking(!). The helper process | ||
90 | * should either be sent a termination signal before or should be dead before | ||
91 | * calling this function | ||
92 | * | ||
93 | * @param h the helper handle | ||
94 | * @return GNUNET_OK on success; GNUNET_SYSERR on error | ||
95 | */ | ||
96 | int | ||
97 | GNUNET_HELPER_wait (struct GNUNET_HELPER_Handle *h); | ||
98 | |||
99 | |||
100 | /** | ||
101 | * Free's the resources occupied by the helper handle | ||
102 | * | ||
103 | * @param h the helper handle to free | ||
78 | */ | 104 | */ |
79 | void | 105 | void |
80 | GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h); | 106 | GNUNET_HELPER_destroy (struct GNUNET_HELPER_Handle *h); |
81 | 107 | ||
82 | 108 | ||
83 | /** | 109 | /** |
84 | * Kills the helper by closing its stdin (the helper is expected to catch the | 110 | * Kills the helper, closes the pipe, frees the handle and calls wait() on the |
85 | * resulting SIGPIPE and shutdown), closes the pipe and frees the handle | 111 | * helper process |
86 | * | 112 | * |
87 | * @param h handle to helper to stop | 113 | * @param h handle to helper to stop |
114 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | ||
115 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | ||
88 | */ | 116 | */ |
89 | void | 117 | void |
90 | GNUNET_HELPER_soft_stop (struct GNUNET_HELPER_Handle *h); | 118 | GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h, int soft_kill); |
91 | 119 | ||
92 | 120 | ||
93 | /** | 121 | /** |
diff --git a/src/testbed/gnunet-service-testbed.c b/src/testbed/gnunet-service-testbed.c index bb791988e..1b74ad1df 100644 --- a/src/testbed/gnunet-service-testbed.c +++ b/src/testbed/gnunet-service-testbed.c | |||
@@ -785,7 +785,7 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
785 | uint32_t id; | 785 | uint32_t id; |
786 | 786 | ||
787 | shutdown_task_id = GNUNET_SCHEDULER_NO_TASK; | 787 | shutdown_task_id = GNUNET_SCHEDULER_NO_TASK; |
788 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Shutting down testbed service\n"); | 788 | LOG_DEBUG ("Shutting down testbed service\n"); |
789 | /* cleanup any remaining forwarded operations */ | 789 | /* cleanup any remaining forwarded operations */ |
790 | GST_clear_fopcq (); | 790 | GST_clear_fopcq (); |
791 | GST_free_lcfq (); | 791 | GST_free_lcfq (); |
@@ -904,6 +904,7 @@ testbed_run (void *cls, struct GNUNET_SERVER_Handle *server, | |||
904 | char *logfile; | 904 | char *logfile; |
905 | unsigned long long num; | 905 | unsigned long long num; |
906 | 906 | ||
907 | LOG_DEBUG ("Starting testbed\n"); | ||
907 | if (GNUNET_OK == | 908 | if (GNUNET_OK == |
908 | GNUNET_CONFIGURATION_get_value_filename (cfg, "TESTBED", "LOG_FILE", | 909 | GNUNET_CONFIGURATION_get_value_filename (cfg, "TESTBED", "LOG_FILE", |
909 | &logfile)) | 910 | &logfile)) |
diff --git a/src/testbed/gnunet-service-testbed_links.c b/src/testbed/gnunet-service-testbed_links.c index bcf8d91c8..7b0006d1f 100644 --- a/src/testbed/gnunet-service-testbed_links.c +++ b/src/testbed/gnunet-service-testbed_links.c | |||
@@ -425,32 +425,47 @@ reghost_free_iterator (void *cls, const struct GNUNET_HashCode *key, | |||
425 | void | 425 | void |
426 | GST_slave_list_clear () | 426 | GST_slave_list_clear () |
427 | { | 427 | { |
428 | unsigned int id; | ||
429 | struct HostRegistration *hr_entry; | 428 | struct HostRegistration *hr_entry; |
429 | struct GNUNET_TESTBED_ControllerProc *cproc; | ||
430 | unsigned int id; | ||
430 | 431 | ||
431 | for (id = 0; id < GST_slave_list_size; id++) | 432 | for (id = 0; id < GST_slave_list_size; id++) |
432 | if (NULL != GST_slave_list[id]) | 433 | { |
434 | if (NULL == GST_slave_list[id]) | ||
435 | continue; | ||
436 | while (NULL != (hr_entry = GST_slave_list[id]->hr_dll_head)) | ||
433 | { | 437 | { |
434 | while (NULL != (hr_entry = GST_slave_list[id]->hr_dll_head)) | 438 | GNUNET_CONTAINER_DLL_remove (GST_slave_list[id]->hr_dll_head, |
435 | { | 439 | GST_slave_list[id]->hr_dll_tail, hr_entry); |
436 | GNUNET_CONTAINER_DLL_remove (GST_slave_list[id]->hr_dll_head, | 440 | GNUNET_free (hr_entry); |
437 | GST_slave_list[id]->hr_dll_tail, hr_entry); | 441 | } |
438 | GNUNET_free (hr_entry); | 442 | if (NULL != GST_slave_list[id]->rhandle) |
439 | } | 443 | GNUNET_TESTBED_cancel_registration (GST_slave_list[id]->rhandle); |
440 | if (NULL != GST_slave_list[id]->rhandle) | 444 | (void) |
441 | GNUNET_TESTBED_cancel_registration (GST_slave_list[id]->rhandle); | 445 | GNUNET_CONTAINER_multihashmap_iterate (GST_slave_list |
442 | (void) | 446 | [id]->reghost_map, |
443 | GNUNET_CONTAINER_multihashmap_iterate (GST_slave_list | 447 | reghost_free_iterator, |
444 | [id]->reghost_map, | 448 | GST_slave_list[id]); |
445 | reghost_free_iterator, | 449 | GNUNET_CONTAINER_multihashmap_destroy (GST_slave_list[id]->reghost_map); |
446 | GST_slave_list[id]); | 450 | if (NULL != GST_slave_list[id]->controller) |
447 | GNUNET_CONTAINER_multihashmap_destroy (GST_slave_list[id]->reghost_map); | 451 | GNUNET_TESTBED_controller_disconnect (GST_slave_list[id]->controller); |
448 | if (NULL != GST_slave_list[id]->controller) | 452 | if (NULL != (cproc = GST_slave_list[id]->controller_proc)) |
449 | GNUNET_TESTBED_controller_disconnect (GST_slave_list[id]->controller); | 453 | { |
450 | if (NULL != GST_slave_list[id]->controller_proc) | 454 | LOG_DEBUG ("Stopping a slave\n"); |
451 | GNUNET_TESTBED_controller_stop (GST_slave_list[id]->controller_proc); | 455 | GNUNET_TESTBED_controller_kill_ (cproc); |
452 | GNUNET_free (GST_slave_list[id]); | ||
453 | } | 456 | } |
457 | } | ||
458 | for (id = 0; id < GST_slave_list_size; id++) | ||
459 | { | ||
460 | if (NULL == GST_slave_list[id]) | ||
461 | continue; | ||
462 | if (NULL != (cproc = GST_slave_list[id]->controller_proc)) | ||
463 | { | ||
464 | GNUNET_TESTBED_controller_destroy_ (cproc); | ||
465 | LOG_DEBUG ("Slave stopped\n"); | ||
466 | } | ||
467 | GNUNET_free (GST_slave_list[id]); | ||
468 | } | ||
454 | GNUNET_free_non_null (GST_slave_list); | 469 | GNUNET_free_non_null (GST_slave_list); |
455 | GST_slave_list = NULL; | 470 | GST_slave_list = NULL; |
456 | } | 471 | } |
diff --git a/src/testbed/test_gnunet_helper_testbed.c b/src/testbed/test_gnunet_helper_testbed.c index 0c7c5f27e..cf4559c26 100644 --- a/src/testbed/test_gnunet_helper_testbed.c +++ b/src/testbed/test_gnunet_helper_testbed.c | |||
@@ -88,7 +88,7 @@ do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
88 | if (GNUNET_SCHEDULER_NO_TASK != abort_task) | 88 | if (GNUNET_SCHEDULER_NO_TASK != abort_task) |
89 | GNUNET_SCHEDULER_cancel (abort_task); | 89 | GNUNET_SCHEDULER_cancel (abort_task); |
90 | if (NULL != helper) | 90 | if (NULL != helper) |
91 | GNUNET_HELPER_stop (helper); | 91 | GNUNET_HELPER_stop (helper, GNUNET_NO); |
92 | GNUNET_free_non_null (msg); | 92 | GNUNET_free_non_null (msg); |
93 | if (NULL != cfg) | 93 | if (NULL != cfg) |
94 | GNUNET_CONFIGURATION_destroy (cfg); | 94 | GNUNET_CONFIGURATION_destroy (cfg); |
diff --git a/src/testbed/testbed_api_hosts.c b/src/testbed/testbed_api_hosts.c index f61129b85..c386d18a0 100644 --- a/src/testbed/testbed_api_hosts.c +++ b/src/testbed/testbed_api_hosts.c | |||
@@ -1261,20 +1261,33 @@ GNUNET_TESTBED_controller_start (const char *trusted_ip, | |||
1261 | 1261 | ||
1262 | 1262 | ||
1263 | /** | 1263 | /** |
1264 | * Stop the controller process (also will terminate all peers and controllers | 1264 | * Sends termination signal to the controller's helper process |
1265 | * dependent on this controller). This function blocks until the testbed has | ||
1266 | * been fully terminated (!). The controller status cb from | ||
1267 | * GNUNET_TESTBED_controller_start() will not be called. | ||
1268 | * | 1265 | * |
1269 | * @param cproc the controller process handle | 1266 | * @param cproc the handle to the controller's helper process |
1270 | */ | 1267 | */ |
1271 | void | 1268 | void |
1272 | GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc) | 1269 | GNUNET_TESTBED_controller_kill_ (struct GNUNET_TESTBED_ControllerProc *cproc) |
1273 | { | 1270 | { |
1274 | if (NULL != cproc->shandle) | 1271 | if (NULL != cproc->shandle) |
1275 | GNUNET_HELPER_send_cancel (cproc->shandle); | 1272 | GNUNET_HELPER_send_cancel (cproc->shandle); |
1276 | if (NULL != cproc->helper) | 1273 | if (NULL != cproc->helper) |
1277 | GNUNET_HELPER_soft_stop (cproc->helper); | 1274 | GNUNET_HELPER_kill (cproc->helper, GNUNET_YES); |
1275 | } | ||
1276 | |||
1277 | |||
1278 | /** | ||
1279 | * Cleans-up the controller's helper process handle | ||
1280 | * | ||
1281 | * @param cproc the handle to the controller's helper process | ||
1282 | */ | ||
1283 | void | ||
1284 | GNUNET_TESTBED_controller_destroy_ (struct GNUNET_TESTBED_ControllerProc *cproc) | ||
1285 | { | ||
1286 | if (NULL != cproc->helper) | ||
1287 | { | ||
1288 | GNUNET_break (GNUNET_OK == GNUNET_HELPER_wait (cproc->helper)); | ||
1289 | GNUNET_HELPER_destroy (cproc->helper); | ||
1290 | } | ||
1278 | if (NULL != cproc->helper_argv) | 1291 | if (NULL != cproc->helper_argv) |
1279 | free_argv (cproc->helper_argv); | 1292 | free_argv (cproc->helper_argv); |
1280 | cproc->host->controller_started = GNUNET_NO; | 1293 | cproc->host->controller_started = GNUNET_NO; |
@@ -1284,6 +1297,22 @@ GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc) | |||
1284 | 1297 | ||
1285 | 1298 | ||
1286 | /** | 1299 | /** |
1300 | * Stop the controller process (also will terminate all peers and controllers | ||
1301 | * dependent on this controller). This function blocks until the testbed has | ||
1302 | * been fully terminated (!). The controller status cb from | ||
1303 | * GNUNET_TESTBED_controller_start() will not be called. | ||
1304 | * | ||
1305 | * @param cproc the controller process handle | ||
1306 | */ | ||
1307 | void | ||
1308 | GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc) | ||
1309 | { | ||
1310 | GNUNET_TESTBED_controller_kill_ (cproc); | ||
1311 | GNUNET_TESTBED_controller_destroy_ (cproc); | ||
1312 | } | ||
1313 | |||
1314 | |||
1315 | /** | ||
1287 | * The handle for whether a host is habitable or not | 1316 | * The handle for whether a host is habitable or not |
1288 | */ | 1317 | */ |
1289 | struct GNUNET_TESTBED_HostHabitableCheckHandle | 1318 | struct GNUNET_TESTBED_HostHabitableCheckHandle |
diff --git a/src/testbed/testbed_api_hosts.h b/src/testbed/testbed_api_hosts.h index 56cca624b..3cef4412a 100644 --- a/src/testbed/testbed_api_hosts.h +++ b/src/testbed/testbed_api_hosts.h | |||
@@ -233,5 +233,25 @@ GNUNET_TESTBED_host_handle_addhostconfirm_ (struct GNUNET_TESTBED_Controller *c, | |||
233 | GNUNET_TESTBED_HostConfirmedMessage | 233 | GNUNET_TESTBED_HostConfirmedMessage |
234 | *msg); | 234 | *msg); |
235 | 235 | ||
236 | |||
237 | /** | ||
238 | * Sends termination signal to the controller's helper process | ||
239 | * | ||
240 | * @param cproc the handle to the controller's helper process | ||
241 | */ | ||
242 | void | ||
243 | GNUNET_TESTBED_controller_kill_ (struct GNUNET_TESTBED_ControllerProc *cproc); | ||
244 | |||
245 | |||
246 | /** | ||
247 | * Cleans-up the controller's helper process handle | ||
248 | * | ||
249 | * @param cproc the handle to the controller's helper process | ||
250 | */ | ||
251 | void | ||
252 | GNUNET_TESTBED_controller_destroy_ (struct GNUNET_TESTBED_ControllerProc | ||
253 | *cproc); | ||
254 | |||
255 | |||
236 | #endif | 256 | #endif |
237 | /* end of testbed_api_hosts.h */ | 257 | /* end of testbed_api_hosts.h */ |
diff --git a/src/transport/plugin_transport_wlan.c b/src/transport/plugin_transport_wlan.c index 223791e18..5b4e702e5 100644 --- a/src/transport/plugin_transport_wlan.c +++ b/src/transport/plugin_transport_wlan.c | |||
@@ -1613,7 +1613,7 @@ libgnunet_plugin_transport_wlan_done (void *cls) | |||
1613 | } | 1613 | } |
1614 | if (NULL != plugin->suid_helper) | 1614 | if (NULL != plugin->suid_helper) |
1615 | { | 1615 | { |
1616 | GNUNET_HELPER_stop (plugin->suid_helper); | 1616 | GNUNET_HELPER_stop (plugin->suid_helper, GNUNET_NO); |
1617 | plugin->suid_helper = NULL; | 1617 | plugin->suid_helper = NULL; |
1618 | } | 1618 | } |
1619 | endpoint_next = plugin->mac_head; | 1619 | endpoint_next = plugin->mac_head; |
diff --git a/src/transport/test_plugin_transport.c b/src/transport/test_plugin_transport.c index 58fd07c78..9b1760919 100644 --- a/src/transport/test_plugin_transport.c +++ b/src/transport/test_plugin_transport.c | |||
@@ -186,7 +186,7 @@ end () | |||
186 | 186 | ||
187 | if (NULL != suid_helper) | 187 | if (NULL != suid_helper) |
188 | { | 188 | { |
189 | GNUNET_HELPER_stop (suid_helper); | 189 | GNUNET_HELPER_stop (suid_helper, GNUNET_NO); |
190 | suid_helper = NULL; | 190 | suid_helper = NULL; |
191 | } | 191 | } |
192 | } | 192 | } |
@@ -252,7 +252,7 @@ end_badly (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) | |||
252 | 252 | ||
253 | if (NULL != suid_helper) | 253 | if (NULL != suid_helper) |
254 | { | 254 | { |
255 | GNUNET_HELPER_stop (suid_helper); | 255 | GNUNET_HELPER_stop (suid_helper, GNUNET_NO); |
256 | suid_helper = NULL; | 256 | suid_helper = NULL; |
257 | } | 257 | } |
258 | 258 | ||
diff --git a/src/util/helper.c b/src/util/helper.c index d7a3cb271..57e5798d8 100644 --- a/src/util/helper.c +++ b/src/util/helper.c | |||
@@ -20,7 +20,8 @@ | |||
20 | 20 | ||
21 | /** | 21 | /** |
22 | * @file util/helper.c | 22 | * @file util/helper.c |
23 | * @brief API for dealing with (SUID) helper processes that communicate via GNUNET_MessageHeaders on stdin/stdout | 23 | * @brief API for dealing with (SUID) helper processes that communicate via |
24 | * GNUNET_MessageHeaders on stdin/stdout | ||
24 | * @author Philipp Toelke | 25 | * @author Philipp Toelke |
25 | * @author Christian Grothoff | 26 | * @author Christian Grothoff |
26 | */ | 27 | */ |
@@ -162,38 +163,71 @@ struct GNUNET_HELPER_Handle | |||
162 | 163 | ||
163 | 164 | ||
164 | /** | 165 | /** |
165 | * Stop the helper process, we're closing down or had an error. | 166 | * Sends termination signal to the helper process. The helper process is not |
167 | * reaped; call GNUNET_HELPER_wait() for reaping the dead helper process. | ||
166 | * | 168 | * |
167 | * @param h handle to the helper process | 169 | * @param h the helper handle |
168 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | 170 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's |
169 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | 171 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper |
172 | * @return GNUNET_OK on success; GNUNET_SYSERR on error | ||
170 | */ | 173 | */ |
171 | static void | 174 | int |
172 | stop_helper (struct GNUNET_HELPER_Handle *h, int soft_kill) | 175 | GNUNET_HELPER_kill (struct GNUNET_HELPER_Handle *h, int soft_kill) |
173 | { | 176 | { |
174 | struct GNUNET_HELPER_SendHandle *sh; | 177 | struct GNUNET_HELPER_SendHandle *sh; |
178 | int ret; | ||
175 | 179 | ||
176 | if (NULL != h->helper_proc) | 180 | while (NULL != (sh = h->sh_head)) |
177 | { | 181 | { |
178 | if (GNUNET_YES == soft_kill) | 182 | GNUNET_CONTAINER_DLL_remove (h->sh_head, |
179 | { | 183 | h->sh_tail, |
180 | /* soft-kill only possible with pipes */ | 184 | sh); |
181 | GNUNET_assert (NULL != h->helper_in); | 185 | if (NULL != sh->cont) |
182 | GNUNET_DISK_pipe_close (h->helper_in); | 186 | sh->cont (sh->cont_cls, GNUNET_NO); |
183 | h->helper_in = NULL; | 187 | GNUNET_free (sh); |
184 | h->fh_to_helper = NULL; | ||
185 | } | ||
186 | else | ||
187 | GNUNET_break (0 == GNUNET_OS_process_kill (h->helper_proc, SIGTERM)); | ||
188 | GNUNET_break (GNUNET_OK == GNUNET_OS_process_wait (h->helper_proc)); | ||
189 | GNUNET_OS_process_destroy (h->helper_proc); | ||
190 | h->helper_proc = NULL; | ||
191 | } | 188 | } |
192 | if (GNUNET_SCHEDULER_NO_TASK != h->restart_task) | 189 | if (GNUNET_SCHEDULER_NO_TASK != h->restart_task) |
193 | { | 190 | { |
194 | GNUNET_SCHEDULER_cancel (h->restart_task); | 191 | GNUNET_SCHEDULER_cancel (h->restart_task); |
195 | h->restart_task = GNUNET_SCHEDULER_NO_TASK; | 192 | h->restart_task = GNUNET_SCHEDULER_NO_TASK; |
196 | } | 193 | } |
194 | if (NULL == h->helper_proc) | ||
195 | return GNUNET_SYSERR; | ||
196 | if (GNUNET_YES == soft_kill) | ||
197 | { | ||
198 | /* soft-kill only possible with pipes */ | ||
199 | GNUNET_assert (NULL != h->helper_in); | ||
200 | ret = GNUNET_DISK_pipe_close (h->helper_in); | ||
201 | h->helper_in = NULL; | ||
202 | h->fh_to_helper = NULL; | ||
203 | return ret; | ||
204 | } | ||
205 | if (0 != GNUNET_OS_process_kill (h->helper_proc, SIGTERM)) | ||
206 | return GNUNET_SYSERR; | ||
207 | return GNUNET_OK; | ||
208 | } | ||
209 | |||
210 | |||
211 | /** | ||
212 | * Reap the helper process. This call is blocking(!). The helper process | ||
213 | * should either be sent a termination signal before or should be dead before | ||
214 | * calling this function | ||
215 | * | ||
216 | * @param h the helper handle | ||
217 | * @return GNUNET_OK on success; GNUNET_SYSERR on error | ||
218 | */ | ||
219 | int | ||
220 | GNUNET_HELPER_wait (struct GNUNET_HELPER_Handle *h) | ||
221 | { | ||
222 | struct GNUNET_HELPER_SendHandle *sh; | ||
223 | int ret; | ||
224 | |||
225 | if (NULL != h->helper_proc) | ||
226 | { | ||
227 | ret = GNUNET_OS_process_wait (h->helper_proc); | ||
228 | GNUNET_OS_process_destroy (h->helper_proc); | ||
229 | h->helper_proc = NULL; | ||
230 | } | ||
197 | if (GNUNET_SCHEDULER_NO_TASK != h->read_task) | 231 | if (GNUNET_SCHEDULER_NO_TASK != h->read_task) |
198 | { | 232 | { |
199 | GNUNET_SCHEDULER_cancel (h->read_task); | 233 | GNUNET_SCHEDULER_cancel (h->read_task); |
@@ -227,6 +261,22 @@ stop_helper (struct GNUNET_HELPER_Handle *h, int soft_kill) | |||
227 | } | 261 | } |
228 | /* purge MST buffer */ | 262 | /* purge MST buffer */ |
229 | (void) GNUNET_SERVER_mst_receive (h->mst, NULL, NULL, 0, GNUNET_YES, GNUNET_NO); | 263 | (void) GNUNET_SERVER_mst_receive (h->mst, NULL, NULL, 0, GNUNET_YES, GNUNET_NO); |
264 | return ret; | ||
265 | } | ||
266 | |||
267 | |||
268 | /** | ||
269 | * Stop the helper process, we're closing down or had an error. | ||
270 | * | ||
271 | * @param h handle to the helper process | ||
272 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | ||
273 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | ||
274 | */ | ||
275 | static void | ||
276 | stop_helper (struct GNUNET_HELPER_Handle *h, int soft_kill) | ||
277 | { | ||
278 | GNUNET_break (GNUNET_OK == GNUNET_HELPER_kill (h, soft_kill)); | ||
279 | GNUNET_break (GNUNET_OK == GNUNET_HELPER_wait (h)); | ||
230 | } | 280 | } |
231 | 281 | ||
232 | 282 | ||
@@ -274,7 +324,7 @@ helper_read (void *cls, | |||
274 | if (NULL != h->exp_cb) | 324 | if (NULL != h->exp_cb) |
275 | { | 325 | { |
276 | h->exp_cb (h->cb_cls); | 326 | h->exp_cb (h->cb_cls); |
277 | GNUNET_HELPER_stop (h); | 327 | GNUNET_HELPER_stop (h, GNUNET_NO); |
278 | return; | 328 | return; |
279 | } | 329 | } |
280 | stop_helper (h, GNUNET_NO); | 330 | stop_helper (h, GNUNET_NO); |
@@ -293,7 +343,7 @@ helper_read (void *cls, | |||
293 | if (NULL != h->exp_cb) | 343 | if (NULL != h->exp_cb) |
294 | { | 344 | { |
295 | h->exp_cb (h->cb_cls); | 345 | h->exp_cb (h->cb_cls); |
296 | GNUNET_HELPER_stop (h); | 346 | GNUNET_HELPER_stop (h, GNUNET_NO); |
297 | return; | 347 | return; |
298 | } | 348 | } |
299 | stop_helper (h, GNUNET_NO); | 349 | stop_helper (h, GNUNET_NO); |
@@ -318,7 +368,7 @@ helper_read (void *cls, | |||
318 | if (NULL != h->exp_cb) | 368 | if (NULL != h->exp_cb) |
319 | { | 369 | { |
320 | h->exp_cb (h->cb_cls); | 370 | h->exp_cb (h->cb_cls); |
321 | GNUNET_HELPER_stop (h); | 371 | GNUNET_HELPER_stop (h, GNUNET_NO); |
322 | return; | 372 | return; |
323 | } | 373 | } |
324 | stop_helper (h, GNUNET_NO); | 374 | stop_helper (h, GNUNET_NO); |
@@ -445,30 +495,15 @@ GNUNET_HELPER_start (int with_control_pipe, | |||
445 | 495 | ||
446 | 496 | ||
447 | /** | 497 | /** |
448 | * @brief Kills the helper, closes the pipe and frees the h | 498 | * Free's the resources occupied by the helper handle |
449 | * | 499 | * |
450 | * @param h h to helper to stop | 500 | * @param h the helper handle to free |
451 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | ||
452 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | ||
453 | */ | 501 | */ |
454 | static void | 502 | void |
455 | kill_helper (struct GNUNET_HELPER_Handle *h, int soft_kill) | 503 | GNUNET_HELPER_destroy (struct GNUNET_HELPER_Handle *h) |
456 | { | 504 | { |
457 | struct GNUNET_HELPER_SendHandle *sh; | ||
458 | unsigned int c; | 505 | unsigned int c; |
459 | 506 | ||
460 | h->exp_cb = NULL; | ||
461 | /* signal pending writes that we were stopped */ | ||
462 | while (NULL != (sh = h->sh_head)) | ||
463 | { | ||
464 | GNUNET_CONTAINER_DLL_remove (h->sh_head, | ||
465 | h->sh_tail, | ||
466 | sh); | ||
467 | if (NULL != sh->cont) | ||
468 | sh->cont (sh->cont_cls, GNUNET_SYSERR); | ||
469 | GNUNET_free (sh); | ||
470 | } | ||
471 | stop_helper (h, soft_kill); | ||
472 | GNUNET_SERVER_mst_destroy (h->mst); | 507 | GNUNET_SERVER_mst_destroy (h->mst); |
473 | GNUNET_free (h->binary_name); | 508 | GNUNET_free (h->binary_name); |
474 | for (c = 0; h->binary_argv[c] != NULL; c++) | 509 | for (c = 0; h->binary_argv[c] != NULL; c++) |
@@ -482,24 +517,15 @@ kill_helper (struct GNUNET_HELPER_Handle *h, int soft_kill) | |||
482 | * Kills the helper, closes the pipe and frees the handle | 517 | * Kills the helper, closes the pipe and frees the handle |
483 | * | 518 | * |
484 | * @param h handle to helper to stop | 519 | * @param h handle to helper to stop |
520 | * @param soft_kill if GNUNET_YES, signals termination by closing the helper's | ||
521 | * stdin; GNUNET_NO to signal termination by sending SIGTERM to helper | ||
485 | */ | 522 | */ |
486 | void | 523 | void |
487 | GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h) | 524 | GNUNET_HELPER_stop (struct GNUNET_HELPER_Handle *h, int soft_kill) |
488 | { | ||
489 | kill_helper (h, GNUNET_NO); | ||
490 | } | ||
491 | |||
492 | |||
493 | /** | ||
494 | * Kills the helper by closing its stdin (the helper is expected to catch the | ||
495 | * resulting SIGPIPE and shutdown), closes the pipe and frees the handle | ||
496 | * | ||
497 | * @param h handle to helper to stop | ||
498 | */ | ||
499 | void | ||
500 | GNUNET_HELPER_soft_stop (struct GNUNET_HELPER_Handle *h) | ||
501 | { | 525 | { |
502 | kill_helper (h, GNUNET_YES); | 526 | h->exp_cb = NULL; |
527 | stop_helper (h, soft_kill); | ||
528 | GNUNET_HELPER_destroy (h); | ||
503 | } | 529 | } |
504 | 530 | ||
505 | 531 | ||
@@ -540,7 +566,7 @@ helper_write (void *cls, | |||
540 | if (NULL != h->exp_cb) | 566 | if (NULL != h->exp_cb) |
541 | { | 567 | { |
542 | h->exp_cb (h->cb_cls); | 568 | h->exp_cb (h->cb_cls); |
543 | GNUNET_HELPER_stop (h); | 569 | GNUNET_HELPER_stop (h, GNUNET_NO); |
544 | return; | 570 | return; |
545 | } | 571 | } |
546 | stop_helper (h, GNUNET_NO); | 572 | stop_helper (h, GNUNET_NO); |
diff --git a/src/vpn/gnunet-service-vpn.c b/src/vpn/gnunet-service-vpn.c index 61bd977bc..a56aff52a 100644 --- a/src/vpn/gnunet-service-vpn.c +++ b/src/vpn/gnunet-service-vpn.c | |||
@@ -2928,8 +2928,8 @@ cleanup (void *cls GNUNET_UNUSED, | |||
2928 | mesh_handle = NULL; | 2928 | mesh_handle = NULL; |
2929 | } | 2929 | } |
2930 | if (NULL != helper_handle) | 2930 | if (NULL != helper_handle) |
2931 | { | 2931 | { |
2932 | GNUNET_HELPER_stop (helper_handle); | 2932 | GNUNET_HELPER_stop (helper_handle, GNUNET_NO); |
2933 | helper_handle = NULL; | 2933 | helper_handle = NULL; |
2934 | } | 2934 | } |
2935 | if (NULL != nc) | 2935 | if (NULL != nc) |