diff options
Diffstat (limited to 'src/util/test_service.c')
-rw-r--r-- | src/util/test_service.c | 287 |
1 files changed, 287 insertions, 0 deletions
diff --git a/src/util/test_service.c b/src/util/test_service.c new file mode 100644 index 0000000..049282d --- /dev/null +++ b/src/util/test_service.c @@ -0,0 +1,287 @@ +/* + This file is part of GNUnet. + (C) 2009 Christian Grothoff (and other contributing authors) + + GNUnet is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published + by the Free Software Foundation; either version 3, or (at your + option) any later version. + + GNUnet is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with GNUnet; see the file COPYING. If not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +/** + * @file util/test_service.c + * @brief tests for service.c + */ +#include "platform.h" +#include "gnunet_common.h" +#include "gnunet_client_lib.h" +#include "gnunet_getopt_lib.h" +#include "gnunet_program_lib.h" +#include "gnunet_service_lib.h" +#include "gnunet_scheduler_lib.h" +#include "gnunet_time_lib.h" + + +#define VERBOSE GNUNET_NO + +#define PORT 12435 + +#define MY_TYPE 256 + +static struct GNUNET_SERVICE_Context *sctx; + +static int ok = 1; + + +static size_t +build_msg (void *cls, size_t size, void *buf) +{ + struct GNUNET_CLIENT_Connection *client = cls; + struct GNUNET_MessageHeader *msg = buf; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client connected, transmitting\n"); + GNUNET_assert (size >= sizeof (struct GNUNET_MessageHeader)); + msg->type = htons (MY_TYPE); + msg->size = htons (sizeof (struct GNUNET_MessageHeader)); + GNUNET_CLIENT_disconnect (client, GNUNET_NO); + return sizeof (struct GNUNET_MessageHeader); +} + + +static void +ready (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + const struct GNUNET_CONFIGURATION_Handle *cfg = cls; + struct GNUNET_CLIENT_Connection *client; + + GNUNET_assert (0 != (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Service confirmed running\n"); + client = GNUNET_CLIENT_connect ("test_service", cfg); + GNUNET_assert (client != NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, + "Client connecting, waiting to transmit\n"); + GNUNET_CLIENT_notify_transmit_ready (client, + sizeof (struct GNUNET_MessageHeader), + GNUNET_TIME_UNIT_SECONDS, GNUNET_NO, + &build_msg, client); +} + + +static void +do_stop (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + GNUNET_SERVICE_stop (sctx); +} + + +static void +recv_cb (void *cls, struct GNUNET_SERVER_Client *client, + const struct GNUNET_MessageHeader *message) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Receiving client message...\n"); + GNUNET_SERVER_receive_done (client, GNUNET_OK); + if (sctx != NULL) + GNUNET_SCHEDULER_add_now (&do_stop, NULL); + else + GNUNET_SCHEDULER_shutdown (); + ok = 0; +} + + +static struct GNUNET_SERVER_MessageHandler myhandlers[] = { + {&recv_cb, NULL, MY_TYPE, sizeof (struct GNUNET_MessageHeader)}, + {NULL, NULL, 0, 0} +}; + + +static void +runner (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Service initializing\n"); + GNUNET_SERVER_add_handlers (server, myhandlers); + GNUNET_CLIENT_service_test ("test_service", cfg, GNUNET_TIME_UNIT_SECONDS, + &ready, (void *) cfg); +} + + +/** + * Main method, starts scheduler with task1, + * checks that "ok" is correct at the end. + */ +static int +check () +{ + ok = 1; + char *const argv[] = { + "test_service", + "-c", + "test_service_data.conf", + "-L", +#if VERBOSE + "DEBUG", +#else + "WARNING", +#endif + NULL + }; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting service\n"); + GNUNET_assert (GNUNET_OK == + GNUNET_SERVICE_run (5, argv, "test_service", + GNUNET_SERVICE_OPTION_NONE, &runner, &ok)); + GNUNET_assert (0 == ok); + return ok; +} + +static void +ready6 (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) +{ + const struct GNUNET_CONFIGURATION_Handle *cfg = cls; + struct GNUNET_CLIENT_Connection *client; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "V6 ready\n"); + GNUNET_assert (0 != (tc->reason & GNUNET_SCHEDULER_REASON_PREREQ_DONE)); + client = GNUNET_CLIENT_connect ("test_service6", cfg); + GNUNET_assert (client != NULL); + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "V6 client connected\n"); + GNUNET_CLIENT_notify_transmit_ready (client, + sizeof (struct GNUNET_MessageHeader), + GNUNET_TIME_UNIT_SECONDS, GNUNET_NO, + &build_msg, client); +} + +static void +runner6 (void *cls, struct GNUNET_SERVER_Handle *server, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Initializing v6 service\n"); + GNUNET_SERVER_add_handlers (server, myhandlers); + GNUNET_CLIENT_service_test ("test_service6", cfg, GNUNET_TIME_UNIT_SECONDS, + &ready6, (void *) cfg); +} + +/** + * Main method, starts scheduler with task1, + * checks that "ok" is correct at the end. + */ +static int +check6 () +{ + char *const argv[] = { + "test_service6", + "-c", + "test_service_data.conf", + "-L", +#if VERBOSE + "DEBUG", +#else + "WARNING", +#endif + NULL + }; + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting v6 service\n"); + GNUNET_assert (GNUNET_OK == + GNUNET_SERVICE_run (5, argv, "test_service6", + GNUNET_SERVICE_OPTION_NONE, &runner6, + &ok)); + GNUNET_assert (0 == ok); + return ok; +} + + + +static void +start_stop_main (void *cls, char *const *args, const char *cfgfile, + const struct GNUNET_CONFIGURATION_Handle *cfg) +{ + int *ret = cls; + + GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting service using start method\n"); + sctx = GNUNET_SERVICE_start ("test_service", cfg); + GNUNET_assert (NULL != sctx); + runner (cls, GNUNET_SERVICE_get_server (sctx), cfg); + *ret = 0; +} + + +static int +check_start_stop () +{ + char *const argv[] = { + "test-service-program", + "-c", + "test_service_data.conf", + "-L", +#if VERBOSE + "DEBUG", +#else + "WARNING", +#endif + NULL + }; + const struct GNUNET_GETOPT_CommandLineOption options[] = { + GNUNET_GETOPT_OPTION_END + }; + int ret = 1; + + GNUNET_assert (GNUNET_OK == + GNUNET_PROGRAM_run (5, argv, "test-service-program", "no help", + options, &start_stop_main, &ret)); + + GNUNET_break (0 == ret); + return ret; +} + + +int +main (int argc, char *argv[]) +{ + int ret = 0; + struct GNUNET_NETWORK_Handle *s = NULL; + + GNUNET_log_setup ("test-service", +#if VERBOSE + "DEBUG", +#else + "WARNING", +#endif + NULL); + ret += check (); + ret += check (); + + // FIXME +#ifndef MINGW + s = GNUNET_NETWORK_socket_create (PF_INET6, SOCK_STREAM, 0); +#endif + if (NULL == s) + { + if ((errno == ENOBUFS) || (errno == ENOMEM) || (errno == ENFILE) || + (errno == EACCES)) + { + GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, "socket"); + return 1; + } + FPRINTF (stderr, + "IPv6 support seems to not be available (%s), not testing it!\n", + strerror (errno)); + } + else + { + GNUNET_break (GNUNET_OK == GNUNET_NETWORK_socket_close (s)); + ret += check6 (); + } + ret += check_start_stop (); + + return ret; +} + +/* end of test_service.c */ |