diff options
author | harsha <harsha@140774ce-b5e7-0310-ab8b-a85725594a96> | 2012-07-17 22:25:44 +0000 |
---|---|---|
committer | harsha <harsha@140774ce-b5e7-0310-ab8b-a85725594a96> | 2012-07-17 22:25:44 +0000 |
commit | 0dc94925e4b801ae27eda0cc80d1a7d7c34e2f77 (patch) | |
tree | b7c567693f7a4c2e47782d3b05538d8586942dd4 | |
parent | 8239765fed34196e29c6695dcde5f9a0bacf3bcf (diff) |
helper reply with modified config
git-svn-id: https://gnunet.org/svn/gnunet@22736 140774ce-b5e7-0310-ab8b-a85725594a96
-rw-r--r-- | src/include/gnunet_protocols.h | 5 | ||||
-rw-r--r-- | src/include/gnunet_testbed_service.h | 34 | ||||
-rw-r--r-- | src/testbed/Makefile.am | 3 | ||||
-rw-r--r-- | src/testbed/gnunet-service-testbed.c | 71 | ||||
-rw-r--r-- | src/testbed/gnunet-testbed-helper.c | 114 | ||||
-rw-r--r-- | src/testbed/test_testbed_api_hosts.c | 23 | ||||
-rw-r--r-- | src/testbed/testbed_api.c | 169 | ||||
-rw-r--r-- | src/testbed/testbed_api_hosts.c | 127 | ||||
-rw-r--r-- | src/testbed/testbed_api_hosts.h | 111 | ||||
-rw-r--r-- | src/testbed/testbed_helper.h | 21 |
10 files changed, 373 insertions, 305 deletions
diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h index 10869eba2b..9039d0f1b1 100644 --- a/src/include/gnunet_protocols.h +++ b/src/include/gnunet_protocols.h @@ -1511,6 +1511,11 @@ extern "C" */ #define GNUNET_MESSAGE_TYPE_TESTBED_HELPER_INIT 495 +/** + * The reply message from gnunet-testbed-helper + */ +#define GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY 496 + /** * Next available: 500 diff --git a/src/include/gnunet_testbed_service.h b/src/include/gnunet_testbed_service.h index a190b67a72..8888d781eb 100644 --- a/src/include/gnunet_testbed_service.h +++ b/src/include/gnunet_testbed_service.h @@ -403,14 +403,17 @@ struct GNUNET_TESTBED_ControllerProc; /** - * Function called on errors with the controller. + * Callback to signal successfull startup of the controller process * - * @param cls closure - * @param emsg error message if available; can be NULL, which does NOT mean - * that there was no error + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case */ -typedef void (*GNUNET_TESTBED_ControllerErrorCallback)(void *cls, - const char *emsg); +typedef void (*GNUNET_TESTBED_ControllerStatusCallback) (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + int status); /** @@ -419,25 +422,26 @@ typedef void (*GNUNET_TESTBED_ControllerErrorCallback)(void *cls, * * @param controller_ip the ip address of the controller. Will be set as TRUSTED * host when starting testbed controller at host - * @param host the host where the controller has to be started; NULL for localhost + * @param host the host where the controller has to be started; NULL for + * localhost * @param cfg template configuration to use for the remote controller; the * remote controller will be started with a slightly modified * configuration (port numbers, unix domain sockets and service home * values are changed as per TESTING library on the remote host) - * @param cec function called if the contoller dies unexpectedly; will not be - * invoked after GNUNET_TESTBED_controller_stop, if 'cec' was called, - * GNUNET_TESTBED_controller_stop must no longer be called; will - * never be called in the same task as 'GNUNET_TESTBED_controller_start' - * (synchronous errors will be signalled by returning NULL) - * @param cec_cls closure for 'cec' + * @param cb function called when the controller is successfully started or + * dies unexpectedly; GNUNET_TESTBED_controller_stop shouldn't be + * called if cb is called with GNUNET_SYSERR as status. Will never be + * called in the same task as 'GNUNET_TESTBED_controller_start' + * (synchronous errors will be signalled by returning NULL) + * @param cls closure for above callbacks * @return the controller process handle, NULL on errors */ struct GNUNET_TESTBED_ControllerProc * GNUNET_TESTBED_controller_start (const char *controller_ip, struct GNUNET_TESTBED_Host *host, const struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_TESTBED_ControllerErrorCallback cec, - void *cec_cls); + GNUNET_TESTBED_ControllerStatusCallback cb, + void *cls); /** diff --git a/src/testbed/Makefile.am b/src/testbed/Makefile.am index 80e6b9e3dc..f5fbbe21d3 100644 --- a/src/testbed/Makefile.am +++ b/src/testbed/Makefile.am @@ -33,6 +33,7 @@ gnunet_testbed_helper_SOURCES = \ gnunet_testbed_helper_LDADD = $(XLIB) \ $(top_builddir)/src/util/libgnunetutil.la \ $(top_builddir)/src/testing/libgnunettesting.la \ + libgnunettestbed.la \ $(LTLIBINTL) -lz gnunet_testbed_helper_DEPENDENCIES = \ gnunet-service-testbed.$(OBJEXT) @@ -70,7 +71,7 @@ check_PROGRAMS = \ if ENABLE_TEST_RUN TESTS = \ test_testbed_api_hosts \ - test_gnunet_testbed_helper + #test_gnunet_testbed_helper endif test_testbed_api_hosts_SOURCES = \ diff --git a/src/testbed/gnunet-service-testbed.c b/src/testbed/gnunet-service-testbed.c index 3908af14a0..6aafd1b607 100644 --- a/src/testbed/gnunet-service-testbed.c +++ b/src/testbed/gnunet-service-testbed.c @@ -167,6 +167,23 @@ struct Slave /** + * Slave startup context + */ +struct SlaveContext +{ + /** + * The slave corresponding to this context + */ + struct Slave *slave; + + /** + * The configuration used as a template while startup + */ + struct GNUNET_CONFIGURATION_Handle *cfg; +}; + + +/** * States of LCFContext */ enum LCFContextState @@ -703,24 +720,35 @@ slave_event_callback(void *cls, /** - * Callback for unexpected slave shutdowns + * Callback to signal successfull startup of the controller process * - * @param cls closure - * @param emsg error message if available; can be NULL, which does NOT mean - * that there was no error + * @param cls the closure from GNUNET_TESTBED_controller_start() + * @param cfg the configuration with which the controller has been started; + * NULL if status is not GNUNET_OK + * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not, + * GNUNET_TESTBED_controller_stop() shouldn't be called in this case */ static void -slave_shutdown_handler (void *cls, const char *emsg) +slave_status_callback (void *cls, + const struct GNUNET_CONFIGURATION_Handle *cfg, + int status) { - struct Slave *slave; + struct SlaveContext *sc = cls; - slave = (struct Slave *) cls; - slave->controller_proc = NULL; - LOG (GNUNET_ERROR_TYPE_WARNING, - "Unexpected slave shutdown\n"); - if (NULL != emsg) - LOG (GNUNET_ERROR_TYPE_WARNING, "Error: %s\n", emsg); - GNUNET_SCHEDULER_shutdown (); /* We too shutdown */ + if (GNUNET_SYSERR == status) + { + sc->slave->controller_proc = NULL; + LOG (GNUNET_ERROR_TYPE_WARNING, + "Unexpected slave shutdown\n"); + GNUNET_SCHEDULER_shutdown (); /* We too shutdown */ + return; + } + GNUNET_CONFIGURATION_destroy (sc->cfg); + sc->slave->controller = + GNUNET_TESTBED_controller_connect (cfg, host_list[sc->slave->host_id], + master_context->event_mask, + &slave_event_callback, sc->slave); + GNUNET_free (sc); } @@ -950,6 +978,7 @@ handle_link_controllers (void *cls, { const struct GNUNET_TESTBED_ControllerLinkMessage *msg; struct GNUNET_CONFIGURATION_Handle *cfg; + struct SlaveContext *sc; struct LCFContextQueue *lcfq; struct Route *route; struct Route *new_route; @@ -1053,19 +1082,17 @@ handle_link_controllers (void *cls, slave = GNUNET_malloc (sizeof (struct Slave)); slave->host_id = delegated_host_id; slave_list_add (slave); + sc = GNUNET_malloc (sizeof (struct SlaveContext)); + sc->slave = slave; + sc->cfg = cfg; if (1 == msg->is_subordinate) { slave->controller_proc = GNUNET_TESTBED_controller_start (master_context->master_ip, - host_list[delegated_host_id], - cfg, &slave_shutdown_handler, - slave); - } - slave->controller = - GNUNET_TESTBED_controller_connect (cfg, host_list[delegated_host_id], - master_context->event_mask, - &slave_event_callback, slave); - GNUNET_CONFIGURATION_destroy (cfg); + host_list[slave->host_id], + cfg, &slave_status_callback, + sc); + } new_route = GNUNET_malloc (sizeof (struct Route)); new_route->dest = delegated_host_id; new_route->thru = master_context->host_id; diff --git a/src/testbed/gnunet-testbed-helper.c b/src/testbed/gnunet-testbed-helper.c index 4c202193bb..23dfeddc25 100644 --- a/src/testbed/gnunet-testbed-helper.c +++ b/src/testbed/gnunet-testbed-helper.c @@ -33,7 +33,9 @@ #include "platform.h" #include "gnunet_util_lib.h" #include "gnunet_testing_lib-new.h" +#include "gnunet_testbed_service.h" #include "testbed_helper.h" +#include "testbed_api.h" #include <zlib.h> /** @@ -48,6 +50,29 @@ #define LOG_DEBUG(...) \ LOG (GNUNET_ERROR_TYPE_DEBUG, __VA_ARGS__) + +/** + * Context for a single write on a chunk of memory + */ +struct WriteContext +{ + /** + * The data to write + */ + void *data; + + /** + * The length of the data + */ + size_t length; + + /** + * The current position from where the write operation should begin + */ + size_t pos; +}; + + /** * Handle to the testing system */ @@ -64,6 +89,11 @@ struct GNUNET_SERVER_MessageStreamTokenizer *tokenizer; static struct GNUNET_DISK_FileHandle *stdin_fd; /** + * Disk handle for stdout + */ +static struct GNUNET_DISK_FileHandle *stdout_fd; + +/** * The process handle to the testbed service */ static struct GNUNET_OS_Process *testbed; @@ -84,6 +114,11 @@ static struct GNUNET_DISK_PipeHandle *pipe_out; static GNUNET_SCHEDULER_TaskIdentifier read_task_id; /** + * Task identifier for the write task + */ +static GNUNET_SCHEDULER_TaskIdentifier write_task_id; + +/** * Are we done reading messages from stdin? */ static int done_reading; @@ -109,7 +144,15 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) GNUNET_SCHEDULER_cancel (read_task_id); read_task_id = GNUNET_SCHEDULER_NO_TASK; } - (void) GNUNET_DISK_file_close (stdin_fd); + if (GNUNET_SCHEDULER_NO_TASK != write_task_id) + { + GNUNET_SCHEDULER_cancel (write_task_id); + write_task_id = GNUNET_SCHEDULER_NO_TASK; + } + if (NULL != stdin_fd) + (void) GNUNET_DISK_file_close (stdin_fd); + if (NULL != stdout_fd) + (void) GNUNET_DISK_file_close (stdin_fd); GNUNET_SERVER_mst_destroy (tokenizer); tokenizer = NULL; if (NULL != testbed) @@ -138,6 +181,41 @@ shutdown_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) /** + * Task to write to the standard out + * + * @param + * @return + */ +static void +write_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + struct WriteContext *wc = cls; + ssize_t bytes_wrote; + + GNUNET_assert (NULL != wc); + write_task_id = GNUNET_SCHEDULER_NO_TASK; + if (0 != (GNUNET_SCHEDULER_REASON_SHUTDOWN & tc->reason)) + { + GNUNET_free (wc->data); + GNUNET_free (wc); + return; + } + bytes_wrote = GNUNET_DISK_file_write (stdout_fd, wc->data + wc->pos, + wc->length - wc->pos); + GNUNET_assert (GNUNET_SYSERR != bytes_wrote); + wc->pos += bytes_wrote; + if (wc->pos == wc->length) + { + GNUNET_free (wc->data); + GNUNET_free (wc); + return; + } + write_task_id = GNUNET_SCHEDULER_add_write_file + (GNUNET_TIME_UNIT_FOREVER_REL, stdout_fd, &write_task, wc); +} + + +/** * Functions with this signature are called whenever a * complete message is received by the tokenizer. * @@ -154,11 +232,15 @@ tokenizer_cb (void *cls, void *client, const struct GNUNET_MessageHeader *message) { const struct GNUNET_TESTBED_HelperInit *msg; + struct GNUNET_TESTBED_HelperReply *reply; struct GNUNET_CONFIGURATION_Handle *cfg; + struct WriteContext *wc; char *controller; char *config; - uLongf config_size; - uint16_t xconfig_size; + char *xconfig; + size_t config_size; + uLongf ul_config_size; + size_t xconfig_size; uint16_t cname_size; if ((sizeof (struct GNUNET_TESTBED_HelperInit) >= ntohs (message->size)) || @@ -177,10 +259,11 @@ tokenizer_cb (void *cls, void *client, "Controller name cannot be empty -- exiting\n"); goto error; } - config_size = (uLongf) ntohs (msg->config_size); - config = GNUNET_malloc (config_size); - xconfig_size = ntohs (message->size) - (cname_size + 1); - if (Z_OK != uncompress ((Bytef *) config, &config_size, + ul_config_size = (uLongf) ntohs (msg->config_size); + config = GNUNET_malloc (ul_config_size); + xconfig_size = ntohs (message->size) - + (cname_size + 1 + sizeof (struct GNUNET_TESTBED_HelperInit)); + if (Z_OK != uncompress ((Bytef *) config, &ul_config_size, (const Bytef *) (controller + cname_size + 1), (uLongf) xconfig_size)) { @@ -190,8 +273,8 @@ tokenizer_cb (void *cls, void *client, goto error; } cfg = GNUNET_CONFIGURATION_create (); - if (GNUNET_OK != GNUNET_CONFIGURATION_deserialize (cfg, config, config_size, - GNUNET_NO)) + if (GNUNET_OK != GNUNET_CONFIGURATION_deserialize (cfg, config, + ul_config_size, GNUNET_NO)) { LOG (GNUNET_ERROR_TYPE_WARNING, "Unable to deserialize config -- exiting\n"); @@ -234,6 +317,18 @@ tokenizer_cb (void *cls, void *client, GNUNET_DISK_pipe_close_end (pipe_out, GNUNET_DISK_PIPE_END_WRITE); GNUNET_DISK_pipe_close_end (pipe_in, GNUNET_DISK_PIPE_END_READ); done_reading = GNUNET_YES; + config = GNUNET_CONFIGURATION_serialize (cfg, &config_size); + xconfig_size = GNUNET_TESTBED_compress_config (config, config_size, &xconfig); + wc = GNUNET_malloc (sizeof (struct WriteContext)); + wc->length = xconfig_size + sizeof (struct GNUNET_TESTBED_HelperReply); + reply = GNUNET_realloc (xconfig, wc->length); + memmove (&reply[1], reply, xconfig_size); + reply->header.type = htons (GNUNET_MESSAGE_TYPE_TESTBED_HELPER_REPLY); + reply->header.size = htons ((uint16_t) wc->length); + reply->config_size = htons ((uint16_t) config_size); + wc->data = reply; + write_task_id = GNUNET_SCHEDULER_add_write_file + (GNUNET_TIME_UNIT_FOREVER_REL, stdout_fd, &write_task, wc); return GNUNET_OK; error: @@ -302,6 +397,7 @@ run (void *cls, char *const *args, const char *cfgfile, LOG_DEBUG ("Starting testbed helper...\n"); tokenizer = GNUNET_SERVER_mst_create (&tokenizer_cb, NULL); stdin_fd = GNUNET_DISK_get_handle_from_native (stdin); + stdout_fd = GNUNET_DISK_get_handle_from_native (stdout); read_task_id = GNUNET_SCHEDULER_add_read_file (GNUNET_TIME_UNIT_FOREVER_REL, stdin_fd, &read_task, NULL); diff --git a/src/testbed/test_testbed_api_hosts.c b/src/testbed/test_testbed_api_hosts.c index 54e2461c7e..ae71abc547 100644 --- a/src/testbed/test_testbed_api_hosts.c +++ b/src/testbed/test_testbed_api_hosts.c @@ -39,11 +39,6 @@ static struct GNUNET_TESTBED_Host *host; /** - * The host helper handle - */ -static struct GNUNET_TESTBED_HelperHandle *helper_handle; - -/** * Global test status */ static int status; @@ -62,27 +57,11 @@ GNUNET_SCHEDULER_TaskIdentifier shutdown_id; static void do_shutdown (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) { - GNUNET_TESTBED_host_stop_ (helper_handle); GNUNET_TESTBED_host_destroy (host); } /** - * Callback that will be called when the helper process dies. This is not called - * when the helper process is stoped using GNUNET_HELPER_stop() - * - * @param cls the closure from GNUNET_HELPER_start() - */ -static void -exp_cb (void *cls) -{ - status = GNUNET_SYSERR; - GNUNET_SCHEDULER_cancel (shutdown_id); - GNUNET_SCHEDULER_add_now (&do_shutdown, NULL); -} - - -/** * Main run function. * * @param cls NULL @@ -102,8 +81,6 @@ run (void *cls, char *const *args, const char *cfgfile, GNUNET_assert (NULL != host); GNUNET_assert (0 == GNUNET_TESTBED_host_get_id_ (host)); GNUNET_assert (host == GNUNET_TESTBED_host_lookup_by_id_ (0)); - helper_handle = GNUNET_TESTBED_host_run_ ("127.0.0.1", host, cfg, &exp_cb, NULL); - GNUNET_assert (NULL != helper_handle); shutdown_id = GNUNET_SCHEDULER_add_delayed (TIME_REL_SECS (2), &do_shutdown, NULL); } diff --git a/src/testbed/testbed_api.c b/src/testbed/testbed_api.c index aa410e0109..3a42e87a8a 100644 --- a/src/testbed/testbed_api.c +++ b/src/testbed/testbed_api.c @@ -426,76 +426,179 @@ GNUNET_TESTBED_queue_message (struct GNUNET_TESTBED_Controller *controller, struct GNUNET_TESTBED_ControllerProc { /** - * The helper handle + * The process handle */ - struct GNUNET_TESTBED_HelperHandle *helper; + struct GNUNET_HELPER_Handle *helper; /** * The controller error callback */ - GNUNET_TESTBED_ControllerErrorCallback cec; + GNUNET_TESTBED_ControllerStatusCallback cb; /** * The closure for the above callback */ - void *cec_cls; + void *cls; + + /** + * The send handle for the helper + */ + struct GNUNET_HELPER_SendHandle *shandle; + + /** + * The port number for ssh; used for helpers starting ssh + */ + char *port; + + /** + * The ssh destination string; used for helpers starting ssh + */ + char *dst; + }; /** + * Functions with this signature are called whenever a + * complete message is received by the tokenizer. + * + * Do not call GNUNET_SERVER_mst_destroy in callback + * + * @param cls closure + * @param client identification of the client + * @param message the actual message + * + * @return GNUNET_OK on success, GNUNET_SYSERR to stop further processing + */ +static int helper_mst (void *cls, void *client, + const struct GNUNET_MessageHeader *message) +{ + GNUNET_break (0); + return GNUNET_OK; +} + + +/** + * Continuation function from GNUNET_HELPER_send() + * + * @param cls closure + * @param result GNUNET_OK on success, + * GNUNET_NO if helper process died + * GNUNET_SYSERR during GNUNET_HELPER_stop + */ +static void +clear_msg (void *cls, int result) +{ + GNUNET_free (cls); +} + + +/** * Callback that will be called when the helper process dies. This is not called * when the helper process is stoped using GNUNET_HELPER_stop() * * @param cls the closure from GNUNET_HELPER_start() */ static void -controller_exp_cb (void *cls) +helper_exp_cb (void *cls) { - struct GNUNET_TESTBED_ControllerProc *cproc = cls; - - if (NULL != cproc->cec) - cproc->cec (cproc->cec_cls, NULL); /* FIXME: How to get the error message? */ + struct GNUNET_TESTBED_ControllerProc *cp = cls; + GNUNET_TESTBED_ControllerStatusCallback cb; + void *cb_cls; + + cb = cp->cb; + cb_cls = cp->cls; + GNUNET_TESTBED_controller_stop (cp); + if (NULL != cb) + cb (cb_cls, NULL, GNUNET_SYSERR); } /** - * Starts a controller process at the host + * Starts a controller process at the host. FIXME: add controller start callback + * with the configuration with which the controller is started * * @param controller_ip the ip address of the controller. Will be set as TRUSTED * host when starting testbed controller at host - * @param host the host where the controller has to be started; NULL for localhost + * @param host the host where the controller has to be started; NULL for + * localhost * @param cfg template configuration to use for the remote controller; the * remote controller will be started with a slightly modified * configuration (port numbers, unix domain sockets and service home * values are changed as per TESTING library on the remote host) - * @param cec function called if the contoller dies unexpectedly; will not be - * invoked after GNUNET_TESTBED_controller_stop, if 'cec' was called, - * GNUNET_TESTBED_controller_stop must no longer be called; will - * never be called in the same task as 'GNUNET_TESTBED_controller_start' - * (synchronous errors will be signalled by returning NULL) - * @param cec_cls closure for 'cec' + * @param cb function called when the controller is successfully started or + * dies unexpectedly; GNUNET_TESTBED_controller_stop shouldn't be + * called if cb is called with GNUNET_SYSERR as status. Will never be + * called in the same task as 'GNUNET_TESTBED_controller_start' + * (synchronous errors will be signalled by returning NULL) + * @param cls closure for above callbacks * @return the controller process handle, NULL on errors */ struct GNUNET_TESTBED_ControllerProc * GNUNET_TESTBED_controller_start (const char *controller_ip, struct GNUNET_TESTBED_Host *host, const struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_TESTBED_ControllerErrorCallback cec, - void *cec_cls) + GNUNET_TESTBED_ControllerStatusCallback cb, + void *cls) { - struct GNUNET_TESTBED_ControllerProc *cproc; + struct GNUNET_TESTBED_ControllerProc *cp; + struct GNUNET_TESTBED_HelperInit *msg; - cproc = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_ControllerProc)); - cproc->helper = GNUNET_TESTBED_host_run_ (controller_ip, host, cfg, - &controller_exp_cb, cproc); - if (NULL == cproc->helper) + cp = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_ControllerProc)); + if ((NULL == host) || (0 == GNUNET_TESTBED_host_get_id_ (host))) + { + char * const binary_argv[] = { + "gnunet-testbed-helper", NULL + }; + + cp->helper = GNUNET_HELPER_start ("gnunet-testbed-helper", binary_argv, + &helper_mst, &helper_exp_cb, cp); + } + else + { + char *remote_args[6 + 1]; + unsigned int argp; + const char *username; + const char *hostname; + + username = GNUNET_TESTBED_host_get_username_ (host); + hostname = GNUNET_TESTBED_host_get_hostname_ (host); + GNUNET_asprintf (&cp->port, "%u", GNUNET_TESTBED_host_get_ssh_port_ (host)); + if (NULL == username) + GNUNET_asprintf (&cp->dst, "%s", hostname); + else + GNUNET_asprintf (&cp->dst, "%s@%s", hostname, username); + argp = 0; + remote_args[argp++] = "ssh"; + remote_args[argp++] = "-p"; + remote_args[argp++] = cp->port; + remote_args[argp++] = "-q"; + remote_args[argp++] = cp->dst; + remote_args[argp++] = "gnunet-testbed-helper"; + remote_args[argp++] = NULL; + GNUNET_assert (argp == 6 + 1); + cp->helper = GNUNET_HELPER_start ("ssh", remote_args, + &helper_mst, &helper_exp_cb, cp); + } + if (NULL == cp->helper) + { + GNUNET_free_non_null (cp->port); + GNUNET_free_non_null (cp->dst); + GNUNET_free (cp); + return NULL; + } + cp->cb = cb; + cp->cls = cls; + msg = GNUNET_TESTBED_create_helper_init_msg_ (controller_ip, cfg); + cp->shandle = GNUNET_HELPER_send (cp->helper, &msg->header, GNUNET_NO, + &clear_msg, msg); + if (NULL == cp->shandle) { - GNUNET_free (cproc); + GNUNET_free (msg); + GNUNET_TESTBED_controller_stop (cp); return NULL; } - cproc->cec = cec; - cproc->cec_cls = cec_cls; - return cproc; + return cp; } @@ -507,10 +610,14 @@ GNUNET_TESTBED_controller_start (const char *controller_ip, * @param cproc the controller process handle */ void -GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cproc) +GNUNET_TESTBED_controller_stop (struct GNUNET_TESTBED_ControllerProc *cp) { - GNUNET_TESTBED_host_stop_ (cproc->helper); - GNUNET_free (cproc); + if (NULL != cp->shandle) + GNUNET_HELPER_send_cancel (cp->shandle); + GNUNET_HELPER_stop (cp->helper); + GNUNET_free_non_null (cp->port); + GNUNET_free_non_null (cp->dst); + GNUNET_free (cp); } diff --git a/src/testbed/testbed_api_hosts.c b/src/testbed/testbed_api_hosts.c index f88da52b87..dd08d3a506 100644 --- a/src/testbed/testbed_api_hosts.c +++ b/src/testbed/testbed_api_hosts.c @@ -338,133 +338,6 @@ GNUNET_TESTBED_host_destroy (struct GNUNET_TESTBED_Host *host) /** - * Continuation function from GNUNET_HELPER_send() - * - * @param cls closure - * @param result GNUNET_OK on success, - * GNUNET_NO if helper process died - * GNUNET_SYSERR during GNUNET_HELPER_stop - */ -static void -clear_msg (void *cls, int result) -{ - GNUNET_free (cls); -} - - -/** - * Callback that will be called when the helper process dies. This is not called - * when the helper process is stoped using GNUNET_HELPER_stop() - * - * @param cls the closure from GNUNET_HELPER_start() - */ -static void -helper_exp_cb (void *cls) -{ - struct GNUNET_TESTBED_HelperHandle *handle = cls; - - handle->is_stopped = GNUNET_YES; - GNUNET_TESTBED_host_stop_ (handle); - handle->exp_cb (handle->exp_cb_cls); -} - - -/** - * Run a given helper process at the given host. Communication - * with the helper will be via GNUnet messages on stdin/stdout. - * Runs the process via 'ssh' at the specified host, or locally. - * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. - * - * @param controller_ip the ip address of the controller. Will be set as TRUSTED - * host when starting testbed controller at host - * @param host host to use, use "NULL" for localhost - * @param binary_argv binary name and command-line arguments to give to the - * binary - * @param cfg template configuration to use for the remote controller; the - * remote controller will be started with a slightly modified - * configuration (port numbers, unix domain sockets and service home - * values are changed as per TESTING library on the remote host) - * @param cb the callback to run when helper process dies; cannot be NULL - * @param cb_cls the closure for the above callback - * @return handle to terminate the command, NULL on error - */ -struct GNUNET_TESTBED_HelperHandle * -GNUNET_TESTBED_host_run_ (const char *controller_ip, - const struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_HELPER_ExceptionCallback cb, - void *cb_cls) -{ - struct GNUNET_TESTBED_HelperHandle *h; - struct GNUNET_TESTBED_HelperInit *msg; - - GNUNET_assert (NULL != cb); - h = GNUNET_malloc (sizeof (struct GNUNET_TESTBED_HelperHandle)); - h->exp_cb = cb; - h->exp_cb_cls = cb_cls; - h->is_stopped = GNUNET_NO; - if ((NULL == host) || (0 == host->id)) - { - char * const binary_argv[] = { - "gnunet-testbed-helper", NULL - }; - - h->helper = - GNUNET_HELPER_start ("gnunet-testbed-helper", binary_argv, NULL, &helper_exp_cb, h); - } - else - { - char *remote_args[6 + 1]; - unsigned int argp; - - GNUNET_asprintf (&h->port, "%d", host->port); - if (NULL == host->username) - GNUNET_asprintf (&h->dst, "%s", host->hostname); - else - GNUNET_asprintf (&h->dst, "%s@%s", host->hostname, host->username); - argp = 0; - remote_args[argp++] = "ssh"; - remote_args[argp++] = "-p"; - remote_args[argp++] = h->port; - remote_args[argp++] = "-q"; - remote_args[argp++] = h->dst; - remote_args[argp++] = "gnunet-testbed-helper"; - remote_args[argp++] = NULL; - GNUNET_assert (argp == 6 + 1); - h->helper = GNUNET_HELPER_start ("ssh", remote_args, NULL, &helper_exp_cb, h); - } - msg = GNUNET_TESTBED_create_helper_init_msg_ (controller_ip, cfg); - if ((NULL == h->helper) || - (NULL == (h->helper_shandle = GNUNET_HELPER_send (h->helper, &msg->header, GNUNET_NO, - &clear_msg, msg)))) - { - GNUNET_free (msg); - GNUNET_free_non_null (h->port); - GNUNET_free_non_null (h->dst); - GNUNET_free (h); - return NULL; - } - return h; -} - - -/** - * Stops a helper in the HelperHandle using GNUNET_HELPER_stop - * - * @param handle the handle returned from GNUNET_TESTBED_host_start_ - */ -void -GNUNET_TESTBED_host_stop_ (struct GNUNET_TESTBED_HelperHandle *handle) -{ - if (GNUNET_YES != handle->is_stopped) - GNUNET_HELPER_stop (handle->helper); - GNUNET_free_non_null (handle->port); - GNUNET_free_non_null (handle->dst); - GNUNET_free (handle); -} - - -/** * Marks a host as registered with a controller * * @param host the host to mark diff --git a/src/testbed/testbed_api_hosts.h b/src/testbed/testbed_api_hosts.h index 21e9520e20..2c89e29ace 100644 --- a/src/testbed/testbed_api_hosts.h +++ b/src/testbed/testbed_api_hosts.h @@ -32,48 +32,6 @@ /** - * Wrapper around - */ -struct GNUNET_TESTBED_HelperHandle -{ - /** - * The process handle - */ - struct GNUNET_HELPER_Handle *helper; - - /** - * The send handle for the helper - */ - struct GNUNET_HELPER_SendHandle *helper_shandle; - - /** - * The port number for ssh; used for helpers starting ssh - */ - char *port; - - /** - * The ssh destination string; used for helpers starting ssh - */ - char *dst; - - /** - * The helper exception callback - */ - GNUNET_HELPER_ExceptionCallback exp_cb; - - /** - * The closure for exp_cb - */ - void *exp_cb_cls; - - /** - * Is the helper stopped? - */ - int is_stopped; -}; - - -/** * Lookup a host by ID. * * @param id global host ID assigned to the host; 0 is @@ -144,40 +102,41 @@ GNUNET_TESTBED_host_get_ssh_port_ (const struct GNUNET_TESTBED_Host *host); struct GNUNET_TESTBED_HelperHandle; -/** - * Run a given helper process at the given host. Communication - * with the helper will be via GNUnet messages on stdin/stdout. - * Runs the process via 'ssh' at the specified host, or locally. - * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. - * - * @param controller_ip the ip address of the controller. Will be set as TRUSTED - * host when starting testbed controller at host - * @param host host to use, use "NULL" for localhost - * @param binary_argv binary name and command-line arguments to give to the - * binary - * @param cfg template configuration to use for the remote controller; the - * remote controller will be started with a slightly modified - * configuration (port numbers, unix domain sockets and service home - * values are changed as per TESTING library on the remote host) - * @param cb the callback to run when helper process dies; cannot be NULL - * @param cb_cls the closure for the above callback - * @return handle to terminate the command, NULL on error - */ -struct GNUNET_TESTBED_HelperHandle * -GNUNET_TESTBED_host_run_ (const char *controller_ip, - const struct GNUNET_TESTBED_Host *host, - const struct GNUNET_CONFIGURATION_Handle *cfg, - GNUNET_HELPER_ExceptionCallback cb, - void *cb_cls); - - -/** - * Stops a helper in the HelperHandle using GNUNET_HELPER_stop - * - * @param handle the handle returned from GNUNET_TESTBED_host_start_ - */ -void -GNUNET_TESTBED_host_stop_ (struct GNUNET_TESTBED_HelperHandle *handle); +/* /\** */ +/* * Run a given helper process at the given host. Communication */ +/* * with the helper will be via GNUnet messages on stdin/stdout. */ +/* * Runs the process via 'ssh' at the specified host, or locally. */ +/* * Essentially an SSH-wrapper around the 'gnunet_helper_lib.h' API. */ +/* * */ +/* * @param controller_ip the ip address of the controller. Will be set as TRUSTED */ +/* * host when starting testbed controller at host */ +/* * @param host host to use, use "NULL" for localhost */ +/* * @param binary_argv binary name and command-line arguments to give to the */ +/* * binary */ +/* * @param cfg template configuration to use for the remote controller; the */ +/* * remote controller will be started with a slightly modified */ +/* * configuration (port numbers, unix domain sockets and service home */ +/* * values are changed as per TESTING library on the remote host) */ +/* * @param cb the callback to run when helper process dies; cannot be NULL */ +/* * @param cb_cls the closure for the above callback */ +/* * @return handle to terminate the command, NULL on error */ +/* *\/ */ +/* struct GNUNET_TESTBED_HelperHandle * */ +/* GNUNET_TESTBED_host_run_ (const char *controller_ip, */ +/* const struct GNUNET_TESTBED_Host *host, */ +/* const struct GNUNET_CONFIGURATION_Handle *cfg, */ +/* GNUNET_HELPER_ExceptionCallback cb, */ +/* void *cb_cls); */ + + + +/* /\** */ +/* * Stops a helper in the HelperHandle using GNUNET_HELPER_stop */ +/* * */ +/* * @param handle the handle returned from GNUNET_TESTBED_host_start_ */ +/* *\/ */ +/* void */ +/* GNUNET_TESTBED_host_stop_ (struct GNUNET_TESTBED_HelperHandle *handle); */ /** diff --git a/src/testbed/testbed_helper.h b/src/testbed/testbed_helper.h index 8780d7e98c..8b3c84ddee 100644 --- a/src/testbed/testbed_helper.h +++ b/src/testbed/testbed_helper.h @@ -52,7 +52,26 @@ struct GNUNET_TESTBED_HelperInit /* Followed by NULL terminated controller hostname */ |