2
0

test_gnunet_service_arm.c 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265
  1. /*
  2. This file is part of GNUnet.
  3. Copyright (C) 2009, 2014 GNUnet e.V.
  4. GNUnet is free software: you can redistribute it and/or modify it
  5. under the terms of the GNU Affero General Public License as published
  6. by the Free Software Foundation, either version 3 of the License,
  7. or (at your option) any later version.
  8. GNUnet is distributed in the hope that it will be useful, but
  9. WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. Affero General Public License for more details.
  12. You should have received a copy of the GNU Affero General Public License
  13. along with this program. If not, see <http://www.gnu.org/licenses/>.
  14. SPDX-License-Identifier: AGPL3.0-or-later
  15. */
  16. /**
  17. * @file arm/test_gnunet_service_arm.c
  18. * @brief testcase for gnunet-service-arm.c; tests ARM by making it start the resolver
  19. * @author Safey
  20. * @author Christian Grothoff
  21. */
  22. #include "platform.h"
  23. #include "gnunet_arm_service.h"
  24. #include "gnunet_resolver_service.h"
  25. #include "gnunet_os_lib.h"
  26. #include "gnunet_program_lib.h"
  27. /**
  28. * Timeout for starting services, very short because of the strange way start works
  29. * (by checking if running before starting, so really this time is always waited on
  30. * startup (annoying)).
  31. */
  32. #define START_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, 50)
  33. #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10)
  34. static int ret = 1;
  35. static int resolved_ok;
  36. static int asked_for_a_list;
  37. static struct GNUNET_ARM_Handle *arm;
  38. static const char hostname[] = "www.gnu.org"; /* any domain should do */
  39. static void
  40. trigger_disconnect (void *cls)
  41. {
  42. GNUNET_ARM_disconnect (arm);
  43. arm = NULL;
  44. }
  45. static void
  46. arm_stop_cb (void *cls,
  47. enum GNUNET_ARM_RequestStatus status,
  48. enum GNUNET_ARM_Result result)
  49. {
  50. GNUNET_break (status == GNUNET_ARM_REQUEST_SENT_OK);
  51. GNUNET_break (result == GNUNET_ARM_RESULT_STOPPED);
  52. if (result != GNUNET_ARM_RESULT_STOPPED)
  53. {
  54. GNUNET_break (0);
  55. ret = 4;
  56. }
  57. GNUNET_SCHEDULER_add_now (&trigger_disconnect, NULL);
  58. }
  59. static void
  60. service_list (void *cls,
  61. enum GNUNET_ARM_RequestStatus rs,
  62. unsigned int count,
  63. const char *const*list)
  64. {
  65. unsigned int i;
  66. GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
  67. "%u services are are currently running\n",
  68. count);
  69. if (GNUNET_ARM_REQUEST_SENT_OK != rs)
  70. goto stop_arm;
  71. for (i=0;i<count;i++)
  72. {
  73. if (0 == strcasecmp (list[i],
  74. "resolver (gnunet-service-resolver)"))
  75. {
  76. GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
  77. "Got service list, now stopping arm\n");
  78. ret = 0;
  79. }
  80. }
  81. stop_arm:
  82. GNUNET_ARM_request_service_stop (arm,
  83. "arm",
  84. &arm_stop_cb,
  85. NULL);
  86. }
  87. static void
  88. hostname_resolve_cb (void *cls,
  89. const struct sockaddr *addr,
  90. socklen_t addrlen)
  91. {
  92. if ((0 == ret) || (4 == ret) || (1 == resolved_ok))
  93. return;
  94. if (NULL == addr)
  95. {
  96. GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
  97. "Failed to resolve hostname!\n");
  98. GNUNET_break (0);
  99. ret = 3;
  100. GNUNET_ARM_request_service_stop (arm,
  101. "arm",
  102. &arm_stop_cb,
  103. NULL);
  104. return;
  105. }
  106. if (0 == asked_for_a_list)
  107. {
  108. GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
  109. "Resolved hostname, now checking the service list\n");
  110. GNUNET_ARM_request_service_list (arm,
  111. &service_list,
  112. NULL);
  113. asked_for_a_list = 1;
  114. resolved_ok = 1;
  115. }
  116. }
  117. static void
  118. arm_start_cb (void *cls,
  119. enum GNUNET_ARM_RequestStatus status,
  120. enum GNUNET_ARM_Result result)
  121. {
  122. GNUNET_break (status == GNUNET_ARM_REQUEST_SENT_OK);
  123. GNUNET_break (result == GNUNET_ARM_RESULT_STARTING);
  124. GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
  125. "Trying to resolve a hostname via the resolver service!\n");
  126. /* connect to the resolver service */
  127. if (NULL ==
  128. GNUNET_RESOLVER_ip_get (hostname,
  129. AF_UNSPEC,
  130. TIMEOUT,
  131. &hostname_resolve_cb,
  132. NULL))
  133. {
  134. GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
  135. "Unable initiate connection to resolver service\n");
  136. GNUNET_break (0);
  137. ret = 2;
  138. GNUNET_ARM_request_service_stop (arm,
  139. "arm",
  140. &arm_stop_cb,
  141. NULL);
  142. }
  143. }
  144. static void
  145. run (void *cls,
  146. char *const *args,
  147. const char *cfgfile,
  148. const struct GNUNET_CONFIGURATION_Handle *c)
  149. {
  150. arm = GNUNET_ARM_connect (c,
  151. NULL,
  152. NULL);
  153. GNUNET_ARM_request_service_start (arm,
  154. "arm",
  155. GNUNET_OS_INHERIT_STD_OUT_AND_ERR,
  156. &arm_start_cb,
  157. NULL);
  158. }
  159. int
  160. main (int argc, char *av[])
  161. {
  162. static char *const argv[] = {
  163. "test-gnunet-service-arm",
  164. "-c",
  165. "test_arm_api_data.conf",
  166. NULL
  167. };
  168. static struct GNUNET_GETOPT_CommandLineOption options[] = {
  169. GNUNET_GETOPT_OPTION_END
  170. };
  171. /* trigger DNS lookup */
  172. #if HAVE_GETADDRINFO
  173. {
  174. struct addrinfo *ai;
  175. int ret;
  176. if (0 != (ret = getaddrinfo (hostname, NULL, NULL, &ai)))
  177. {
  178. FPRINTF (stderr,
  179. "Failed to resolve `%s', testcase not run.\n",
  180. hostname);
  181. return 77;
  182. }
  183. freeaddrinfo (ai);
  184. }
  185. #elif HAVE_GETHOSTBYNAME2
  186. {
  187. struct hostent *host;
  188. host = gethostbyname2 (hostname, AF_INET);
  189. if (NULL == host)
  190. host = gethostbyname2 (hostname, AF_INET6);
  191. if (NULL == host)
  192. {
  193. FPRINTF (stderr,
  194. "Failed to resolve `%s', testcase not run.\n",
  195. hostname);
  196. return 77;
  197. }
  198. }
  199. #elif HAVE_GETHOSTBYNAME
  200. {
  201. struct hostent *host;
  202. host = gethostbyname (hostname);
  203. if (NULL == host)
  204. {
  205. FPRINTF (stderr,
  206. "Failed to resolve `%s', testcase not run.\n",
  207. hostname);
  208. return 77;
  209. }
  210. }
  211. #else
  212. FPRINTF (stderr,
  213. "libc fails to have resolver function, testcase not run.\n");
  214. return 77;
  215. #endif
  216. GNUNET_log_setup ("test-gnunet-service-arm",
  217. "WARNING",
  218. NULL);
  219. GNUNET_break (GNUNET_OK ==
  220. GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1,
  221. argv, "test-gnunet-service-arm",
  222. "nohelp", options,
  223. &run, NULL));
  224. if (0 != ret)
  225. {
  226. fprintf (stderr,
  227. "Test failed with error code %d\n",
  228. ret);
  229. }
  230. return ret;
  231. }
  232. /* end of test_gnunet_service_arm.c */