aboutsummaryrefslogtreecommitdiff
path: root/src/util/resolver_api.c
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2012-01-27 12:46:51 +0000
committerChristian Grothoff <christian@grothoff.org>2012-01-27 12:46:51 +0000
commitfae775b8e3ebc6e19b97156d3a3008ee91c3b64b (patch)
tree12c7d0f18bc3f1f00f356df0f493c71ee006dda3 /src/util/resolver_api.c
parentf4c1249ba12461abe0616963959b9470a41e1de5 (diff)
downloadgnunet-fae775b8e3ebc6e19b97156d3a3008ee91c3b64b.tar.gz
gnunet-fae775b8e3ebc6e19b97156d3a3008ee91c3b64b.zip
-fixing #2116
Diffstat (limited to 'src/util/resolver_api.c')
-rw-r--r--src/util/resolver_api.c102
1 files changed, 71 insertions, 31 deletions
diff --git a/src/util/resolver_api.c b/src/util/resolver_api.c
index 03dc2ce89..371b2165a 100644
--- a/src/util/resolver_api.c
+++ b/src/util/resolver_api.c
@@ -139,7 +139,7 @@ struct GNUNET_RESOLVER_RequestHandle
139 /** 139 /**
140 * Desired address family. 140 * Desired address family.
141 */ 141 */
142 int domain; 142 int af;
143 143
144 /** 144 /**
145 * Has this request been transmitted to the service? 145 * Has this request been transmitted to the service?
@@ -344,19 +344,18 @@ handle_response (void *cls, const struct GNUNET_MessageHeader *msg)
344{ 344{
345 struct GNUNET_RESOLVER_RequestHandle *rh = cls; 345 struct GNUNET_RESOLVER_RequestHandle *rh = cls;
346 uint16_t size; 346 uint16_t size;
347 const char *hostname;
348 const struct sockaddr *sa;
349 socklen_t salen;
350 347
351#if DEBUG_RESOLVER 348#if DEBUG_RESOLVER
352 LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving response from DNS service\n"); 349 LOG (GNUNET_ERROR_TYPE_DEBUG, "Receiving response from DNS service\n");
353#endif 350#endif
354 if (msg == NULL) 351 if (msg == NULL)
355 { 352 {
353 char buf[INET6_ADDRSTRLEN];
354
356 if (NULL != rh->name_callback) 355 if (NULL != rh->name_callback)
357 LOG (GNUNET_ERROR_TYPE_INFO, 356 LOG (GNUNET_ERROR_TYPE_INFO,
358 _("Timeout trying to resolve IP address `%s'.\n"), 357 _("Timeout trying to resolve IP address `%s'.\n"),
359 GNUNET_a2s ((const void *) &rh[1], rh->data_len)); 358 inet_ntop (rh->af, (const void *) &rh[1], buf, sizeof(buf)));
360 else 359 else
361 LOG (GNUNET_ERROR_TYPE_INFO, 360 LOG (GNUNET_ERROR_TYPE_INFO,
362 _("Timeout trying to resolve hostname `%s'.\n"), 361 _("Timeout trying to resolve hostname `%s'.\n"),
@@ -413,6 +412,8 @@ handle_response (void *cls, const struct GNUNET_MessageHeader *msg)
413 /* return reverse lookup results to caller */ 412 /* return reverse lookup results to caller */
414 if (NULL != rh->name_callback) 413 if (NULL != rh->name_callback)
415 { 414 {
415 const char *hostname;
416
416 hostname = (const char *) &msg[1]; 417 hostname = (const char *) &msg[1];
417 if (hostname[size - sizeof (struct GNUNET_MessageHeader) - 1] != '\0') 418 if (hostname[size - sizeof (struct GNUNET_MessageHeader) - 1] != '\0')
418 { 419 {
@@ -439,9 +440,38 @@ handle_response (void *cls, const struct GNUNET_MessageHeader *msg)
439 /* return lookup results to caller */ 440 /* return lookup results to caller */
440 if (NULL != rh->addr_callback) 441 if (NULL != rh->addr_callback)
441 { 442 {
442 sa = (const struct sockaddr *) &msg[1]; 443 struct sockaddr_in v4;
443 salen = size - sizeof (struct GNUNET_MessageHeader); 444 struct sockaddr_in6 v6;
444 if (salen < sizeof (struct sockaddr)) 445 const struct sockaddr *sa;
446 socklen_t salen;
447 const void *ip;
448 size_t ip_len;
449
450 ip = &msg[1];
451 ip_len = size - sizeof (struct GNUNET_MessageHeader);
452 if (ip_len == sizeof (struct in_addr))
453 {
454 memset (&v4, 0, sizeof (v4));
455 v4.sin_family = AF_INET;
456 v4.sin_addr = *(struct in_addr*) ip;
457#if HAVE_SOCKADDR_IN_SIN_LEN
458 v4.sin_len = sizeof (v4);
459#endif
460 salen = sizeof (v4);
461 sa = (const struct sockaddr *) &v4;
462 }
463 else if (ip_len == sizeof (struct in6_addr))
464 {
465 memset (&v6, 0, sizeof (v6));
466 v6.sin6_family = AF_INET6;
467 v6.sin6_addr = *(struct in6_addr*) ip;
468#if HAVE_SOCKADDR_IN_SIN_LEN
469 v6.sin6_len = sizeof (v6);
470#endif
471 salen = sizeof (v6);
472 sa = (const struct sockaddr *) &v6;
473 }
474 else
445 { 475 {
446 GNUNET_break (0); 476 GNUNET_break (0);
447 if (rh->was_transmitted != GNUNET_SYSERR) 477 if (rh->was_transmitted != GNUNET_SYSERR)
@@ -496,11 +526,11 @@ numeric_resolution (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
496 v6.sin6_len = sizeof (v6); 526 v6.sin6_len = sizeof (v6);
497#endif 527#endif
498 hostname = (const char *) &rh[1]; 528 hostname = (const char *) &rh[1];
499 if (((rh->domain == AF_UNSPEC) || (rh->domain == AF_INET)) && 529 if (((rh->af == AF_UNSPEC) || (rh->af == AF_INET)) &&
500 (1 == inet_pton (AF_INET, hostname, &v4.sin_addr))) 530 (1 == inet_pton (AF_INET, hostname, &v4.sin_addr)))
501 { 531 {
502 rh->addr_callback (rh->cls, (const struct sockaddr *) &v4, sizeof (v4)); 532 rh->addr_callback (rh->cls, (const struct sockaddr *) &v4, sizeof (v4));
503 if ((rh->domain == AF_UNSPEC) && 533 if ((rh->af == AF_UNSPEC) &&
504 (1 == inet_pton (AF_INET6, hostname, &v6.sin6_addr))) 534 (1 == inet_pton (AF_INET6, hostname, &v6.sin6_addr)))
505 { 535 {
506 /* this can happen on some systems IF "hostname" is "localhost" */ 536 /* this can happen on some systems IF "hostname" is "localhost" */
@@ -510,7 +540,7 @@ numeric_resolution (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
510 GNUNET_free (rh); 540 GNUNET_free (rh);
511 return; 541 return;
512 } 542 }
513 if (((rh->domain == AF_UNSPEC) || (rh->domain == AF_INET6)) && 543 if (((rh->af == AF_UNSPEC) || (rh->af == AF_INET6)) &&
514 (1 == inet_pton (AF_INET6, hostname, &v6.sin6_addr))) 544 (1 == inet_pton (AF_INET6, hostname, &v6.sin6_addr)))
515 { 545 {
516 rh->addr_callback (rh->cls, (const struct sockaddr *) &v6, sizeof (v6)); 546 rh->addr_callback (rh->cls, (const struct sockaddr *) &v6, sizeof (v6));
@@ -551,7 +581,7 @@ loopback_resolution (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
551 v6.sin6_len = sizeof (v6); 581 v6.sin6_len = sizeof (v6);
552#endif 582#endif
553 v6.sin6_addr = in6addr_loopback; 583 v6.sin6_addr = in6addr_loopback;
554 switch (rh->domain) 584 switch (rh->af)
555 { 585 {
556 case AF_INET: 586 case AF_INET:
557 rh->addr_callback (rh->cls, (const struct sockaddr *) &v4, sizeof (v4)); 587 rh->addr_callback (rh->cls, (const struct sockaddr *) &v4, sizeof (v4));
@@ -615,7 +645,7 @@ process_requests ()
615 htons (sizeof (struct GNUNET_RESOLVER_GetMessage) + rh->data_len); 645 htons (sizeof (struct GNUNET_RESOLVER_GetMessage) + rh->data_len);
616 msg->header.type = htons (GNUNET_MESSAGE_TYPE_RESOLVER_REQUEST); 646 msg->header.type = htons (GNUNET_MESSAGE_TYPE_RESOLVER_REQUEST);
617 msg->direction = htonl (rh->direction); 647 msg->direction = htonl (rh->direction);
618 msg->domain = htonl (rh->domain); 648 msg->af = htonl (rh->af);
619 memcpy (&msg[1], &rh[1], rh->data_len); 649 memcpy (&msg[1], &rh[1], rh->data_len);
620#if DEBUG_RESOLVER 650#if DEBUG_RESOLVER
621 LOG (GNUNET_ERROR_TYPE_DEBUG, 651 LOG (GNUNET_ERROR_TYPE_DEBUG,
@@ -711,14 +741,14 @@ reconnect ()
711 * Convert a string to one or more IP addresses. 741 * Convert a string to one or more IP addresses.
712 * 742 *
713 * @param hostname the hostname to resolve 743 * @param hostname the hostname to resolve
714 * @param domain AF_INET or AF_INET6; use AF_UNSPEC for "any" 744 * @param af AF_INET or AF_INET6; use AF_UNSPEC for "any"
715 * @param callback function to call with addresses 745 * @param callback function to call with addresses
716 * @param callback_cls closure for callback 746 * @param callback_cls closure for callback
717 * @param timeout how long to try resolving 747 * @param timeout how long to try resolving
718 * @return handle that can be used to cancel the request, NULL on error 748 * @return handle that can be used to cancel the request, NULL on error
719 */ 749 */
720struct GNUNET_RESOLVER_RequestHandle * 750struct GNUNET_RESOLVER_RequestHandle *
721GNUNET_RESOLVER_ip_get (const char *hostname, int domain, 751GNUNET_RESOLVER_ip_get (const char *hostname, int af,
722 struct GNUNET_TIME_Relative timeout, 752 struct GNUNET_TIME_Relative timeout,
723 GNUNET_RESOLVER_AddressCallback callback, 753 GNUNET_RESOLVER_AddressCallback callback,
724 void *callback_cls) 754 void *callback_cls)
@@ -737,7 +767,7 @@ GNUNET_RESOLVER_ip_get (const char *hostname, int domain,
737 return NULL; 767 return NULL;
738 } 768 }
739 rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + slen); 769 rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + slen);
740 rh->domain = domain; 770 rh->af = af;
741 rh->addr_callback = callback; 771 rh->addr_callback = callback;
742 rh->cls = callback_cls; 772 rh->cls = callback_cls;
743 memcpy (&rh[1], hostname, slen); 773 memcpy (&rh[1], hostname, slen);
@@ -746,9 +776,9 @@ GNUNET_RESOLVER_ip_get (const char *hostname, int domain,
746 rh->direction = GNUNET_NO; 776 rh->direction = GNUNET_NO;
747 /* first, check if this is a numeric address */ 777 /* first, check if this is a numeric address */
748 if (((1 == inet_pton (AF_INET, hostname, &v4)) && 778 if (((1 == inet_pton (AF_INET, hostname, &v4)) &&
749 ((domain == AF_INET) || (domain == AF_UNSPEC))) || 779 ((af == AF_INET) || (af == AF_UNSPEC))) ||
750 ((1 == inet_pton (AF_INET6, hostname, &v6)) && 780 ((1 == inet_pton (AF_INET6, hostname, &v6)) &&
751 ((domain == AF_INET6) || (domain == AF_UNSPEC)))) 781 ((af == AF_INET6) || (af == AF_UNSPEC))))
752 { 782 {
753 rh->task = GNUNET_SCHEDULER_add_now (&numeric_resolution, rh); 783 rh->task = GNUNET_SCHEDULER_add_now (&numeric_resolution, rh);
754 return rh; 784 return rh;
@@ -820,14 +850,31 @@ GNUNET_RESOLVER_hostname_get (const struct sockaddr *sa, socklen_t salen,
820 void *cls) 850 void *cls)
821{ 851{
822 struct GNUNET_RESOLVER_RequestHandle *rh; 852 struct GNUNET_RESOLVER_RequestHandle *rh;
853 size_t ip_len;
854 const void *ip;
823 855
824 check_config (); 856 check_config ();
857 switch (sa->sa_family)
858 {
859 case AF_INET:
860 ip_len = sizeof (struct in_addr);
861 ip = &((const struct sockaddr_in*)sa)->sin_addr;
862 break;
863 case AF_INET6:
864 ip_len = sizeof (struct in6_addr);
865 ip = &((const struct sockaddr_in6*)sa)->sin6_addr;
866 break;
867 default:
868 GNUNET_break (0);
869 return NULL;
870 }
825 rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + salen); 871 rh = GNUNET_malloc (sizeof (struct GNUNET_RESOLVER_RequestHandle) + salen);
826 rh->name_callback = callback; 872 rh->name_callback = callback;
827 rh->cls = cls; 873 rh->cls = cls;
874 rh->af = sa->sa_family;
828 rh->timeout = GNUNET_TIME_relative_to_absolute (timeout); 875 rh->timeout = GNUNET_TIME_relative_to_absolute (timeout);
829 memcpy (&rh[1], sa, salen); 876 memcpy (&rh[1], ip, ip_len);
830 rh->data_len = salen; 877 rh->data_len = ip_len;
831 rh->direction = GNUNET_YES; 878 rh->direction = GNUNET_YES;
832 rh->received_response = GNUNET_NO; 879 rh->received_response = GNUNET_NO;
833 if (GNUNET_NO == do_resolve) 880 if (GNUNET_NO == do_resolve)
@@ -835,13 +882,6 @@ GNUNET_RESOLVER_hostname_get (const struct sockaddr *sa, socklen_t salen,
835 rh->task = GNUNET_SCHEDULER_add_now (&numeric_reverse, rh); 882 rh->task = GNUNET_SCHEDULER_add_now (&numeric_reverse, rh);
836 return rh; 883 return rh;
837 } 884 }
838 if (salen + sizeof (struct GNUNET_RESOLVER_GetMessage) >=
839 GNUNET_SERVER_MAX_MESSAGE_SIZE)
840 {
841 GNUNET_break (0);
842 GNUNET_free (rh);
843 return NULL;
844 }
845 GNUNET_CONTAINER_DLL_insert_tail (req_head, req_tail, rh); 885 GNUNET_CONTAINER_DLL_insert_tail (req_head, req_tail, rh);
846 rh->was_queued = GNUNET_YES; 886 rh->was_queued = GNUNET_YES;
847 if (s_task != GNUNET_SCHEDULER_NO_TASK) 887 if (s_task != GNUNET_SCHEDULER_NO_TASK)
@@ -855,7 +895,7 @@ GNUNET_RESOLVER_hostname_get (const struct sockaddr *sa, socklen_t salen,
855 895
856 896
857/** 897/**
858 * Get local fully qualified domain name 898 * Get local fully qualified af name
859 * 899 *
860 * @return fqdn 900 * @return fqdn
861 */ 901 */
@@ -888,14 +928,14 @@ GNUNET_RESOLVER_local_fqdn_get ()
888/** 928/**
889 * Looking our own hostname. 929 * Looking our own hostname.
890 * 930 *
891 * @param domain AF_INET or AF_INET6; use AF_UNSPEC for "any" 931 * @param af AF_INET or AF_INET6; use AF_UNSPEC for "any"
892 * @param callback function to call with addresses 932 * @param callback function to call with addresses
893 * @param cls closure for callback 933 * @param cls closure for callback
894 * @param timeout how long to try resolving 934 * @param timeout how long to try resolving
895 * @return handle that can be used to cancel the request, NULL on error 935 * @return handle that can be used to cancel the request, NULL on error
896 */ 936 */
897struct GNUNET_RESOLVER_RequestHandle * 937struct GNUNET_RESOLVER_RequestHandle *
898GNUNET_RESOLVER_hostname_resolve (int domain, 938GNUNET_RESOLVER_hostname_resolve (int af,
899 struct GNUNET_TIME_Relative timeout, 939 struct GNUNET_TIME_Relative timeout,
900 GNUNET_RESOLVER_AddressCallback callback, 940 GNUNET_RESOLVER_AddressCallback callback,
901 void *cls) 941 void *cls)
@@ -911,7 +951,7 @@ GNUNET_RESOLVER_hostname_resolve (int domain,
911#if DEBUG_RESOLVER 951#if DEBUG_RESOLVER
912 LOG (GNUNET_ERROR_TYPE_DEBUG, _("Resolving our hostname `%s'\n"), hostname); 952 LOG (GNUNET_ERROR_TYPE_DEBUG, _("Resolving our hostname `%s'\n"), hostname);
913#endif 953#endif
914 return GNUNET_RESOLVER_ip_get (hostname, domain, timeout, callback, cls); 954 return GNUNET_RESOLVER_ip_get (hostname, af, timeout, callback, cls);
915} 955}
916 956
917 957