diff options
author | Christian Grothoff <christian@grothoff.org> | 2016-07-25 21:34:47 +0000 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2016-07-25 21:34:47 +0000 |
commit | 6446293d028db5fe66c53f70ab8194f6c47f3fa1 (patch) | |
tree | a27ec7e92f6ac78ba90e582ea9d88dc702ab10c2 /src/util/resolver_api.c | |
parent | 59a1974b48463e363442bd4e8f81741ee86d4123 (diff) | |
download | gnunet-6446293d028db5fe66c53f70ab8194f6c47f3fa1.tar.gz gnunet-6446293d028db5fe66c53f70ab8194f6c47f3fa1.zip |
-ensure clean DNS shutdown, fix DNS-STUN termination issues
Diffstat (limited to 'src/util/resolver_api.c')
-rw-r--r-- | src/util/resolver_api.c | 83 |
1 files changed, 66 insertions, 17 deletions
diff --git a/src/util/resolver_api.c b/src/util/resolver_api.c index 299fdfef9..c4ce1ccc2 100644 --- a/src/util/resolver_api.c +++ b/src/util/resolver_api.c | |||
@@ -249,8 +249,16 @@ GNUNET_RESOLVER_connect (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
249 | void | 249 | void |
250 | GNUNET_RESOLVER_disconnect () | 250 | GNUNET_RESOLVER_disconnect () |
251 | { | 251 | { |
252 | GNUNET_assert (NULL == req_head); | 252 | struct GNUNET_RESOLVER_RequestHandle *rh; |
253 | GNUNET_assert (NULL == req_tail); | 253 | |
254 | while (NULL != (rh = req_head)) | ||
255 | { | ||
256 | GNUNET_assert (GNUNET_SYSERR == rh->was_transmitted); | ||
257 | GNUNET_CONTAINER_DLL_remove (req_head, | ||
258 | req_tail, | ||
259 | rh); | ||
260 | GNUNET_free (rh); | ||
261 | } | ||
254 | if (NULL != mq) | 262 | if (NULL != mq) |
255 | { | 263 | { |
256 | LOG (GNUNET_ERROR_TYPE_DEBUG, | 264 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
@@ -272,6 +280,42 @@ GNUNET_RESOLVER_disconnect () | |||
272 | 280 | ||
273 | 281 | ||
274 | /** | 282 | /** |
283 | * Task executed on system shutdown. | ||
284 | */ | ||
285 | static void | ||
286 | shutdown_task (void *cls) | ||
287 | { | ||
288 | s_task = NULL; | ||
289 | GNUNET_RESOLVER_disconnect (); | ||
290 | backoff = GNUNET_TIME_UNIT_MILLISECONDS; | ||
291 | } | ||
292 | |||
293 | |||
294 | /** | ||
295 | * Consider disconnecting if we have no further requests pending. | ||
296 | */ | ||
297 | static void | ||
298 | check_disconnect () | ||
299 | { | ||
300 | struct GNUNET_RESOLVER_RequestHandle *rh; | ||
301 | |||
302 | for (rh = req_head; NULL != rh; rh = rh->next) | ||
303 | if (GNUNET_SYSERR != rh->was_transmitted) | ||
304 | return; | ||
305 | if (NULL != r_task) | ||
306 | { | ||
307 | GNUNET_SCHEDULER_cancel (r_task); | ||
308 | r_task = NULL; | ||
309 | } | ||
310 | if (NULL != s_task) | ||
311 | return; | ||
312 | s_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_MILLISECONDS, | ||
313 | &shutdown_task, | ||
314 | NULL); | ||
315 | } | ||
316 | |||
317 | |||
318 | /** | ||
275 | * Convert IP address to string without DNS resolution. | 319 | * Convert IP address to string without DNS resolution. |
276 | * | 320 | * |
277 | * @param af address family | 321 | * @param af address family |
@@ -339,23 +383,13 @@ mq_error_handler (void *cls, | |||
339 | { | 383 | { |
340 | GNUNET_MQ_destroy (mq); | 384 | GNUNET_MQ_destroy (mq); |
341 | mq = NULL; | 385 | mq = NULL; |
386 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
387 | "MQ error, reconnecting\n"); | ||
342 | reconnect (); | 388 | reconnect (); |
343 | } | 389 | } |
344 | 390 | ||
345 | 391 | ||
346 | /** | 392 | /** |
347 | * Task executed on system shutdown. | ||
348 | */ | ||
349 | static void | ||
350 | shutdown_task (void *cls) | ||
351 | { | ||
352 | s_task = NULL; | ||
353 | GNUNET_RESOLVER_disconnect (); | ||
354 | backoff = GNUNET_TIME_UNIT_MILLISECONDS; | ||
355 | } | ||
356 | |||
357 | |||
358 | /** | ||
359 | * Process pending requests to the resolver. | 393 | * Process pending requests to the resolver. |
360 | */ | 394 | */ |
361 | static void | 395 | static void |
@@ -599,7 +633,9 @@ numeric_resolution (void *cls) | |||
599 | } | 633 | } |
600 | if ( ( (rh->af == AF_UNSPEC) || | 634 | if ( ( (rh->af == AF_UNSPEC) || |
601 | (rh->af == AF_INET6) ) && | 635 | (rh->af == AF_INET6) ) && |
602 | (1 == inet_pton (AF_INET6, hostname, &v6.sin6_addr) ) ) | 636 | (1 == inet_pton (AF_INET6, |
637 | hostname, | ||
638 | &v6.sin6_addr) ) ) | ||
603 | { | 639 | { |
604 | rh->addr_callback (rh->cls, | 640 | rh->addr_callback (rh->cls, |
605 | (const struct sockaddr *) &v6, | 641 | (const struct sockaddr *) &v6, |
@@ -671,6 +707,9 @@ loopback_resolution (void *cls) | |||
671 | rh->addr_callback (rh->cls, | 707 | rh->addr_callback (rh->cls, |
672 | NULL, | 708 | NULL, |
673 | 0); | 709 | 0); |
710 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
711 | "Finished resolving hostname `%s'.\n", | ||
712 | (const char *) &rh[1]); | ||
674 | GNUNET_free (rh); | 713 | GNUNET_free (rh); |
675 | } | 714 | } |
676 | 715 | ||
@@ -740,6 +779,7 @@ reconnect () | |||
740 | req_tail, | 779 | req_tail, |
741 | rh); | 780 | rh); |
742 | GNUNET_free (rh); | 781 | GNUNET_free (rh); |
782 | check_disconnect (); | ||
743 | break; | 783 | break; |
744 | default: | 784 | default: |
745 | GNUNET_assert (0); | 785 | GNUNET_assert (0); |
@@ -841,13 +881,16 @@ GNUNET_RESOLVER_ip_get (const char *hostname, | |||
841 | GNUNET_break (0); | 881 | GNUNET_break (0); |
842 | return NULL; | 882 | return NULL; |
843 | } | 883 | } |
884 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
885 | "Trying to resolve hostname `%s'.\n", | ||
886 | hostname); | ||
844 | rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + slen); | 887 | rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + slen); |
845 | rh->af = af; | 888 | rh->af = af; |
846 | rh->addr_callback = callback; | 889 | rh->addr_callback = callback; |
847 | rh->cls = callback_cls; | 890 | rh->cls = callback_cls; |
848 | GNUNET_memcpy (&rh[1], | 891 | GNUNET_memcpy (&rh[1], |
849 | hostname, | 892 | hostname, |
850 | slen); | 893 | slen); |
851 | rh->data_len = slen; | 894 | rh->data_len = slen; |
852 | rh->timeout = GNUNET_TIME_relative_to_absolute (timeout); | 895 | rh->timeout = GNUNET_TIME_relative_to_absolute (timeout); |
853 | rh->direction = GNUNET_NO; | 896 | rh->direction = GNUNET_NO; |
@@ -1133,6 +1176,10 @@ GNUNET_RESOLVER_hostname_resolve (int af, | |||
1133 | void | 1176 | void |
1134 | GNUNET_RESOLVER_request_cancel (struct GNUNET_RESOLVER_RequestHandle *rh) | 1177 | GNUNET_RESOLVER_request_cancel (struct GNUNET_RESOLVER_RequestHandle *rh) |
1135 | { | 1178 | { |
1179 | if (GNUNET_NO == rh->direction) | ||
1180 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
1181 | "Asked to cancel request to resolve hostname `%s'.\n", | ||
1182 | (const char *) &rh[1]); | ||
1136 | if (NULL != rh->task) | 1183 | if (NULL != rh->task) |
1137 | { | 1184 | { |
1138 | GNUNET_SCHEDULER_cancel (rh->task); | 1185 | GNUNET_SCHEDULER_cancel (rh->task); |
@@ -1145,10 +1192,12 @@ GNUNET_RESOLVER_request_cancel (struct GNUNET_RESOLVER_RequestHandle *rh) | |||
1145 | req_tail, | 1192 | req_tail, |
1146 | rh); | 1193 | rh); |
1147 | GNUNET_free (rh); | 1194 | GNUNET_free (rh); |
1195 | check_disconnect (); | ||
1148 | return; | 1196 | return; |
1149 | } | 1197 | } |
1150 | GNUNET_assert (GNUNET_YES == rh->was_transmitted); | 1198 | GNUNET_assert (GNUNET_YES == rh->was_transmitted); |
1151 | rh->was_transmitted = GNUNET_SYSERR; /* mark as cancelled */ | 1199 | rh->was_transmitted = GNUNET_SYSERR; /* mark as cancelled */ |
1200 | check_disconnect (); | ||
1152 | } | 1201 | } |
1153 | 1202 | ||
1154 | 1203 | ||