4 * Network implementation
5 * All network related functions are grouped here
7 * a Net::DNS like library for C
9 * (c) NLnet Labs, 2004-2006
11 * See the file LICENSE for the license
14 #include <ldns/config.h>
16 #include <ldns/ldns.h>
18 #ifdef HAVE_NETINET_IN_H
19 #include <netinet/in.h>
21 #ifdef HAVE_SYS_SOCKET_H
22 #include <sys/socket.h>
27 #ifdef HAVE_ARPA_INET_H
28 #include <arpa/inet.h>
38 ldns_send(ldns_pkt
**result_packet
, ldns_resolver
*r
, const ldns_pkt
*query_pkt
)
42 ldns_rdf
*tsig_mac
= NULL
;
44 qb
= ldns_buffer_new(LDNS_MIN_BUFLEN
);
46 if (query_pkt
&& ldns_pkt_tsig(query_pkt
)) {
47 tsig_mac
= ldns_rr_rdf(ldns_pkt_tsig(query_pkt
), 3);
51 ldns_pkt2buffer_wire(qb
, query_pkt
) != LDNS_STATUS_OK
) {
52 result
= LDNS_STATUS_ERR
;
54 result
= ldns_send_buffer(result_packet
, r
, qb
, tsig_mac
);
62 /* code from rdata.c */
63 static struct sockaddr_storage
*
64 ldns_rdf2native_sockaddr_storage_port(
65 const ldns_rdf
*rd
, uint16_t port
, size_t *size
)
67 struct sockaddr_storage
*data
;
68 struct sockaddr_in
*data_in
;
69 struct sockaddr_in6
*data_in6
;
71 data
= LDNS_MALLOC(struct sockaddr_storage
);
75 /* zero the structure for portability */
76 memset(data
, 0, sizeof(struct sockaddr_storage
));
78 switch(ldns_rdf_get_type(rd
)) {
81 data
->ss_family
= AF_INET
;
83 data_in
= (struct sockaddr_in
*) data
;
84 data_in
->sin_port
= (in_port_t
)htons(port
);
85 memcpy(&(data_in
->sin_addr
), ldns_rdf_data(rd
), ldns_rdf_size(rd
));
86 *size
= sizeof(struct sockaddr_in
);
88 case LDNS_RDF_TYPE_AAAA
:
90 data
->ss_family
= AF_INET6
;
92 data_in6
= (struct sockaddr_in6
*) data
;
93 data_in6
->sin6_port
= (in_port_t
)htons(port
);
94 memcpy(&data_in6
->sin6_addr
, ldns_rdf_data(rd
), ldns_rdf_size(rd
));
95 *size
= sizeof(struct sockaddr_in6
);
103 struct sockaddr_storage
*
104 ldns_rdf2native_sockaddr_storage(
105 const ldns_rdf
*rd
, uint16_t port
, size_t *size
)
107 return ldns_rdf2native_sockaddr_storage_port(
108 rd
, (port
== 0 ? (uint16_t)LDNS_PORT
: port
), size
);
111 /** best effort to set nonblocking */
113 ldns_sock_nonblock(int sockfd
)
117 if((flag
= fcntl(sockfd
, F_GETFL
)) != -1) {
119 if(fcntl(sockfd
, F_SETFL
, flag
) == -1) {
120 /* ignore error, continue blockingly */
123 #elif defined(HAVE_IOCTLSOCKET)
124 unsigned long on
= 1;
125 if(ioctlsocket(sockfd
, FIONBIO
, &on
) != 0) {
126 /* ignore error, continue blockingly */
131 /** best effort to set blocking */
133 ldns_sock_block(int sockfd
)
137 if((flag
= fcntl(sockfd
, F_GETFL
)) != -1) {
139 if(fcntl(sockfd
, F_SETFL
, flag
) == -1) {
140 /* ignore error, continue */
143 #elif defined(HAVE_IOCTLSOCKET)
144 unsigned long off
= 0;
145 if(ioctlsocket(sockfd
, FIONBIO
, &off
) != 0) {
146 /* ignore error, continue */
151 /** wait for a socket to become ready */
153 ldns_sock_wait(int sockfd
, struct timeval timeout
, int write
)
160 FD_SET(FD_SET_T sockfd
, &fds
);
162 ret
= select(sockfd
+1, NULL
, &fds
, NULL
, &timeout
);
164 ret
= select(sockfd
+1, &fds
, NULL
, NULL
, &timeout
);
167 struct pollfd pfds
[2];
169 memset(&pfds
[0], 0, sizeof(pfds
[0]) * 2);
172 pfds
[0].events
= POLLIN
|POLLERR
;
175 pfds
[0].events
|= POLLOUT
;
178 ret
= poll(pfds
, 1, (int)(timeout
.tv_sec
* 1000
179 + timeout
.tv_usec
/ 1000));
182 /* timeout expired */
192 ldns_tcp_connect_from(const struct sockaddr_storage
*to
, socklen_t tolen
,
193 const struct sockaddr_storage
*from
, socklen_t fromlen
,
194 struct timeval timeout
)
199 if ((sockfd
= socket((int)((struct sockaddr
*)to
)->sa_family
, SOCK_STREAM
,
200 IPPROTO_TCP
)) == SOCK_INVALID
) {
204 if (from
&& bind(sockfd
, (const struct sockaddr
*)from
, fromlen
) == SOCK_INVALID
){
205 close_socket(sockfd
);
209 /* perform nonblocking connect, to be able to wait with select() */
210 ldns_sock_nonblock(sockfd
);
211 if (connect(sockfd
, (struct sockaddr
*)to
, tolen
) == SOCK_INVALID
) {
214 if(errno
!= EINPROGRESS
) {
218 close_socket(sockfd
);
221 #else /* USE_WINSOCK */
222 if(WSAGetLastError() != WSAEINPROGRESS
&&
223 WSAGetLastError() != WSAEWOULDBLOCK
) {
224 close_socket(sockfd
);
228 /* error was only telling us that it would block */
231 /* wait(write) until connected or error */
234 socklen_t len
= (socklen_t
)sizeof(error
);
236 if(!ldns_sock_wait(sockfd
, timeout
, 1)) {
237 close_socket(sockfd
);
241 /* check if there is a pending error for nonblocking connect */
242 if(getsockopt(sockfd
, SOL_SOCKET
, SO_ERROR
, (void*)&error
,
245 error
= errno
; /* on solaris errno is error */
247 error
= WSAGetLastError();
251 #if defined(EINPROGRESS) && defined(EWOULDBLOCK)
252 if(error
== EINPROGRESS
|| error
== EWOULDBLOCK
)
253 continue; /* try again */
255 else if(error
!= 0) {
256 close_socket(sockfd
);
257 /* error in errno for our user */
261 #else /* USE_WINSOCK */
262 if(error
== WSAEINPROGRESS
)
264 else if(error
== WSAEWOULDBLOCK
)
266 else if(error
!= 0) {
267 close_socket(sockfd
);
271 #endif /* USE_WINSOCK */
276 /* set the socket blocking again */
277 ldns_sock_block(sockfd
);
283 ldns_tcp_connect(const struct sockaddr_storage
*to
, socklen_t tolen
,
284 struct timeval timeout
)
286 int s
= ldns_tcp_connect_from(to
, tolen
, NULL
, 0, timeout
);
287 return s
> 0 ? s
: 0;
291 ldns_tcp_connect2(const struct sockaddr_storage
*to
, socklen_t tolen
,
292 struct timeval timeout
)
294 return ldns_tcp_connect_from(to
, tolen
, NULL
, 0, timeout
);
298 ldns_tcp_bgsend_from(ldns_buffer
*qbin
,
299 const struct sockaddr_storage
*to
, socklen_t tolen
,
300 const struct sockaddr_storage
*from
, socklen_t fromlen
,
301 struct timeval timeout
)
305 sockfd
= ldns_tcp_connect_from(to
, tolen
, from
, fromlen
, timeout
);
307 if (sockfd
>= 0 && ldns_tcp_send_query(qbin
, sockfd
, to
, tolen
) == 0) {
308 close_socket(sockfd
);
316 ldns_tcp_bgsend(ldns_buffer
*qbin
,
317 const struct sockaddr_storage
*to
, socklen_t tolen
,
318 struct timeval timeout
)
320 int s
= ldns_tcp_bgsend_from(qbin
, to
, tolen
, NULL
, 0, timeout
);
321 return s
> 0 ? s
: 0;
325 ldns_tcp_bgsend2(ldns_buffer
*qbin
,
326 const struct sockaddr_storage
*to
, socklen_t tolen
,
327 struct timeval timeout
)
329 return ldns_tcp_bgsend_from(qbin
, to
, tolen
, NULL
, 0, timeout
);
332 /* keep in mind that in DNS tcp messages the first 2 bytes signal the
333 * amount data to expect
336 ldns_tcp_send_from(uint8_t **result
, ldns_buffer
*qbin
,
337 const struct sockaddr_storage
*to
, socklen_t tolen
,
338 const struct sockaddr_storage
*from
, socklen_t fromlen
,
339 struct timeval timeout
, size_t *answer_size
)
344 sockfd
= ldns_tcp_bgsend_from(qbin
, to
, tolen
, from
, fromlen
, timeout
);
347 return LDNS_STATUS_ERR
;
350 answer
= ldns_tcp_read_wire_timeout(sockfd
, answer_size
, timeout
);
351 close_socket(sockfd
);
355 return LDNS_STATUS_NETWORK_ERR
;
359 return LDNS_STATUS_OK
;
363 ldns_tcp_send(uint8_t **result
, ldns_buffer
*qbin
,
364 const struct sockaddr_storage
*to
, socklen_t tolen
,
365 struct timeval timeout
, size_t *answer_size
)
367 return ldns_tcp_send_from(result
, qbin
,
368 to
, tolen
, NULL
, 0, timeout
, answer_size
);
372 ldns_udp_connect(const struct sockaddr_storage
*to
, struct timeval
ATTR_UNUSED(timeout
))
377 if ((sockfd
= socket((int)((struct sockaddr
*)to
)->sa_family
, SOCK_DGRAM
,
387 ldns_udp_connect2(const struct sockaddr_storage
*to
, struct timeval
ATTR_UNUSED(timeout
))
392 if ((sockfd
= socket((int)((struct sockaddr
*)to
)->sa_family
, SOCK_DGRAM
,
402 ldns_udp_bgsend_from(ldns_buffer
*qbin
,
403 const struct sockaddr_storage
*to
, socklen_t tolen
,
404 const struct sockaddr_storage
*from
, socklen_t fromlen
,
405 struct timeval timeout
)
409 sockfd
= ldns_udp_connect2(to
, timeout
);
415 if (from
&& bind(sockfd
, (const struct sockaddr
*)from
, fromlen
) == -1){
416 close_socket(sockfd
);
420 if (ldns_udp_send_query(qbin
, sockfd
, to
, tolen
) == 0) {
421 close_socket(sockfd
);
428 ldns_udp_bgsend(ldns_buffer
*qbin
,
429 const struct sockaddr_storage
*to
, socklen_t tolen
,
430 struct timeval timeout
)
432 int s
= ldns_udp_bgsend_from(qbin
, to
, tolen
, NULL
, 0, timeout
);
433 return s
> 0 ? s
: 0;
437 ldns_udp_bgsend2(ldns_buffer
*qbin
,
438 const struct sockaddr_storage
*to
, socklen_t tolen
,
439 struct timeval timeout
)
441 return ldns_udp_bgsend_from(qbin
, to
, tolen
, NULL
, 0, timeout
);
445 ldns_udp_send_from(uint8_t **result
, ldns_buffer
*qbin
,
446 const struct sockaddr_storage
*to
, socklen_t tolen
,
447 const struct sockaddr_storage
*from
, socklen_t fromlen
,
448 struct timeval timeout
, size_t *answer_size
)
453 sockfd
= ldns_udp_bgsend_from(qbin
, to
, tolen
, from
, fromlen
, timeout
);
456 return LDNS_STATUS_SOCKET_ERROR
;
459 /* wait for an response*/
460 if(!ldns_sock_wait(sockfd
, timeout
, 0)) {
461 close_socket(sockfd
);
462 return LDNS_STATUS_NETWORK_ERR
;
465 /* set to nonblocking, so if the checksum is bad, it becomes
466 * an EAGAIN error and the ldns_udp_send function does not block,
467 * but returns a 'NETWORK_ERROR' much like a timeout. */
468 ldns_sock_nonblock(sockfd
);
470 answer
= ldns_udp_read_wire(sockfd
, answer_size
, NULL
, NULL
);
471 close_socket(sockfd
);
475 return LDNS_STATUS_NETWORK_ERR
;
479 return LDNS_STATUS_OK
;
483 ldns_udp_send(uint8_t **result
, ldns_buffer
*qbin
,
484 const struct sockaddr_storage
*to
, socklen_t tolen
,
485 struct timeval timeout
, size_t *answer_size
)
487 return ldns_udp_send_from(result
, qbin
, to
, tolen
, NULL
, 0,
488 timeout
, answer_size
);
492 ldns_send_buffer(ldns_pkt
**result
, ldns_resolver
*r
, ldns_buffer
*qb
, ldns_rdf
*tsig_mac
)
496 struct sockaddr_storage
*src
= NULL
;
498 struct sockaddr_storage
*ns
;
506 bool all_servers_rtt_inf
;
509 uint8_t *reply_bytes
= NULL
;
510 size_t reply_size
= 0;
511 ldns_status status
, send_status
;
515 status
= LDNS_STATUS_OK
;
516 rtt
= ldns_resolver_rtt(r
);
517 ns_array
= ldns_resolver_nameservers(r
);
521 all_servers_rtt_inf
= true;
523 if (ldns_resolver_random(r
)) {
524 ldns_resolver_nameservers_randomize(r
);
527 if(ldns_resolver_source(r
)) {
528 src
= ldns_rdf2native_sockaddr_storage_port(
529 ldns_resolver_source(r
), 0, &src_len
);
532 /* loop through all defined nameservers */
533 for (i
= 0; i
< ldns_resolver_nameserver_count(r
); i
++) {
534 if (rtt
[i
] == LDNS_RESOLV_RTT_INF
) {
535 /* not reachable nameserver! */
539 /* maybe verbosity setting?
540 printf("Sending to ");
541 ldns_rdf_print(stdout, ns_array[i]);
544 ns
= ldns_rdf2native_sockaddr_storage(ns_array
[i
],
545 ldns_resolver_port(r
), &ns_len
);
549 if ((ns
->ss_family
== AF_INET
) &&
550 (ldns_resolver_ip6(r
) == LDNS_RESOLV_INET6
)) {
556 if ((ns
->ss_family
== AF_INET6
) &&
557 (ldns_resolver_ip6(r
) == LDNS_RESOLV_INET
)) {
564 all_servers_rtt_inf
= false;
566 gettimeofday(&tv_s
, NULL
);
568 send_status
= LDNS_STATUS_ERR
;
570 /* reply_bytes implicitly handles our error */
571 if (ldns_resolver_usevc(r
)) {
572 for (retries
= ldns_resolver_retry(r
); retries
> 0; retries
--) {
574 ldns_tcp_send_from(&reply_bytes
, qb
,
575 ns
, (socklen_t
)ns_len
,
576 src
, (socklen_t
)src_len
,
577 ldns_resolver_timeout(r
),
579 if (send_status
== LDNS_STATUS_OK
) {
584 for (retries
= ldns_resolver_retry(r
); retries
> 0; retries
--) {
585 /* ldns_rdf_print(stdout, ns_array[i]); */
587 ldns_udp_send_from(&reply_bytes
, qb
,
588 ns
, (socklen_t
)ns_len
,
589 src
, (socklen_t
)src_len
,
590 ldns_resolver_timeout(r
),
592 if (send_status
== LDNS_STATUS_OK
) {
598 if (send_status
!= LDNS_STATUS_OK
) {
599 ldns_resolver_set_nameserver_rtt(r
, i
, LDNS_RESOLV_RTT_INF
);
600 status
= send_status
;
603 /* obey the fail directive */
605 /* the current nameserver seems to have a problem, blacklist it */
606 if (ldns_resolver_fail(r
)) {
611 return LDNS_STATUS_ERR
;
618 status
= ldns_wire2pkt(&reply
, reply_bytes
, reply_size
);
619 if (status
!= LDNS_STATUS_OK
) {
620 if(src
) LDNS_FREE(src
);
621 LDNS_FREE(reply_bytes
);
628 gettimeofday(&tv_e
, NULL
);
631 ldns_pkt_set_querytime(reply
, (uint32_t)
632 ((tv_e
.tv_sec
- tv_s
.tv_sec
) * 1000) +
633 (tv_e
.tv_usec
- tv_s
.tv_usec
) / 1000);
634 ldns_pkt_set_answerfrom(reply
,
635 ldns_rdf_clone(ns_array
[i
]));
636 ldns_pkt_set_timestamp(reply
, tv_s
);
637 ldns_pkt_set_size(reply
, reply_size
);
640 if (ldns_resolver_fail(r
)) {
641 /* if fail is set bail out, after the first
647 /* wait retrans seconds... */
648 sleep((unsigned int) ldns_resolver_retrans(r
));
654 if (all_servers_rtt_inf
) {
655 LDNS_FREE(reply_bytes
);
656 return LDNS_STATUS_RES_NO_NS
;
659 if (tsig_mac
&& reply
&& reply_bytes
) {
660 if (!ldns_pkt_tsig_verify(reply
,
663 ldns_resolver_tsig_keyname(r
),
664 ldns_resolver_tsig_keydata(r
), tsig_mac
)) {
665 status
= LDNS_STATUS_CRYPTO_TSIG_BOGUS
;
670 #endif /* HAVE_SSL */
672 LDNS_FREE(reply_bytes
);
681 ldns_tcp_send_query(ldns_buffer
*qbin
, int sockfd
,
682 const struct sockaddr_storage
*to
, socklen_t tolen
)
687 /* add length of packet */
688 sendbuf
= LDNS_XMALLOC(uint8_t, ldns_buffer_position(qbin
) + 2);
689 if(!sendbuf
) return 0;
690 ldns_write_uint16(sendbuf
, ldns_buffer_position(qbin
));
691 memcpy(sendbuf
+ 2, ldns_buffer_begin(qbin
), ldns_buffer_position(qbin
));
693 bytes
= sendto(sockfd
, (void*)sendbuf
,
694 ldns_buffer_position(qbin
) + 2, 0, (struct sockaddr
*)to
, tolen
);
698 if (bytes
== -1 || (size_t) bytes
!= ldns_buffer_position(qbin
) + 2 ) {
704 /* don't wait for an answer */
706 ldns_udp_send_query(ldns_buffer
*qbin
, int sockfd
, const struct sockaddr_storage
*to
,
711 bytes
= sendto(sockfd
, (void*)ldns_buffer_begin(qbin
),
712 ldns_buffer_position(qbin
), 0, (struct sockaddr
*)to
, tolen
);
714 if (bytes
== -1 || (size_t)bytes
!= ldns_buffer_position(qbin
)) {
721 ldns_udp_read_wire(int sockfd
, size_t *size
, struct sockaddr_storage
*from
,
724 uint8_t *wire
, *wireout
;
727 wire
= LDNS_XMALLOC(uint8_t, LDNS_MAX_PACKETLEN
);
733 wire_size
= recvfrom(sockfd
, (void*)wire
, LDNS_MAX_PACKETLEN
, 0,
734 (struct sockaddr
*)from
, fromlen
);
736 /* recvfrom can also return 0 */
737 if (wire_size
== -1 || wire_size
== 0) {
743 *size
= (size_t)wire_size
;
744 wireout
= LDNS_XREALLOC(wire
, uint8_t, (size_t)wire_size
);
745 if(!wireout
) LDNS_FREE(wire
);
751 ldns_tcp_read_wire_timeout(int sockfd
, size_t *size
, struct timeval timeout
)
755 ssize_t bytes
= 0, rc
= 0;
757 wire
= LDNS_XMALLOC(uint8_t, 2);
764 if(!ldns_sock_wait(sockfd
, timeout
, 0)) {
769 rc
= recv(sockfd
, (void*) (wire
+ bytes
),
770 (size_t) (2 - bytes
), 0);
771 if (rc
== -1 || rc
== 0) {
779 wire_size
= ldns_read_uint16(wire
);
782 wire
= LDNS_XMALLOC(uint8_t, wire_size
);
789 while (bytes
< (ssize_t
) wire_size
) {
790 if(!ldns_sock_wait(sockfd
, timeout
, 0)) {
795 rc
= recv(sockfd
, (void*) (wire
+ bytes
),
796 (size_t) (wire_size
- bytes
), 0);
797 if (rc
== -1 || rc
== 0) {
805 *size
= (size_t) bytes
;
810 ldns_tcp_read_wire(int sockfd
, size_t *size
)
814 ssize_t bytes
= 0, rc
= 0;
816 wire
= LDNS_XMALLOC(uint8_t, 2);
823 rc
= recv(sockfd
, (void*) (wire
+ bytes
),
824 (size_t) (2 - bytes
), 0);
825 if (rc
== -1 || rc
== 0) {
833 wire_size
= ldns_read_uint16(wire
);
836 wire
= LDNS_XMALLOC(uint8_t, wire_size
);
843 while (bytes
< (ssize_t
) wire_size
) {
844 rc
= recv(sockfd
, (void*) (wire
+ bytes
),
845 (size_t) (wire_size
- bytes
), 0);
846 if (rc
== -1 || rc
== 0) {
854 *size
= (size_t) bytes
;
860 ldns_sockaddr_storage2rdf(const struct sockaddr_storage
*sock
, uint16_t *port
)
863 struct sockaddr_in
*data_in
;
864 struct sockaddr_in6
*data_in6
;
866 switch(sock
->ss_family
) {
868 data_in
= (struct sockaddr_in
*)sock
;
870 *port
= ntohs((uint16_t)data_in
->sin_port
);
872 addr
= ldns_rdf_new_frm_data(LDNS_RDF_TYPE_A
,
873 LDNS_IP4ADDRLEN
, &data_in
->sin_addr
);
876 data_in6
= (struct sockaddr_in6
*)sock
;
878 *port
= ntohs((uint16_t)data_in6
->sin6_port
);
880 addr
= ldns_rdf_new_frm_data(LDNS_RDF_TYPE_AAAA
,
881 LDNS_IP6ADDRLEN
, &data_in6
->sin6_addr
);
893 /* code from resolver.c */
895 ldns_axfr_start(ldns_resolver
*resolver
, const ldns_rdf
*domain
, ldns_rr_class
class)
898 ldns_buffer
*query_wire
;
900 struct sockaddr_storage
*src
= NULL
;
902 struct sockaddr_storage
*ns
= NULL
;
907 if (!resolver
|| ldns_resolver_nameserver_count(resolver
) < 1) {
908 return LDNS_STATUS_ERR
;
911 query
= ldns_pkt_query_new(ldns_rdf_clone(domain
), LDNS_RR_TYPE_AXFR
, class, 0);
914 return LDNS_STATUS_ADDRESS_ERR
;
916 if(ldns_resolver_source(resolver
)) {
917 src
= ldns_rdf2native_sockaddr_storage_port(
918 ldns_resolver_source(resolver
), 0, &src_len
);
920 /* For AXFR, we have to make the connection ourselves */
921 /* try all nameservers (which usually would mean v4 fallback if
922 * @hostname is used */
924 ns_i
< ldns_resolver_nameserver_count(resolver
) &&
925 resolver
->_socket
== SOCK_INVALID
;
930 ns
= ldns_rdf2native_sockaddr_storage(
931 resolver
->_nameservers
[ns_i
],
932 ldns_resolver_port(resolver
), &ns_len
);
934 if ((ns
->ss_family
== AF_INET
) &&
935 (ldns_resolver_ip6(resolver
) == LDNS_RESOLV_INET6
)) {
942 if ((ns
->ss_family
== AF_INET6
) &&
943 (ldns_resolver_ip6(resolver
) == LDNS_RESOLV_INET
)) {
951 resolver
->_socket
= ldns_tcp_connect_from(
952 ns
, (socklen_t
)ns_len
,
953 src
, (socklen_t
)src_len
,
954 ldns_resolver_timeout(resolver
));
960 if (resolver
->_socket
== SOCK_INVALID
) {
961 ldns_pkt_free(query
);
963 return LDNS_STATUS_NETWORK_ERR
;
967 if (ldns_resolver_tsig_keyname(resolver
) && ldns_resolver_tsig_keydata(resolver
)) {
968 status
= ldns_pkt_tsig_sign(query
,
969 ldns_resolver_tsig_keyname(resolver
),
970 ldns_resolver_tsig_keydata(resolver
),
971 300, ldns_resolver_tsig_algorithm(resolver
), NULL
);
972 if (status
!= LDNS_STATUS_OK
) {
973 /* to prevent problems on subsequent calls to
974 * ldns_axfr_start we have to close the socket here! */
975 close_socket(resolver
->_socket
);
976 resolver
->_socket
= 0;
978 ldns_pkt_free(query
);
981 return LDNS_STATUS_CRYPTO_TSIG_ERR
;
984 #endif /* HAVE_SSL */
986 /* Convert the query to a buffer
989 query_wire
= ldns_buffer_new(LDNS_MAX_PACKETLEN
);
991 ldns_pkt_free(query
);
994 close_socket(resolver
->_socket
);
996 return LDNS_STATUS_MEM_ERR
;
998 status
= ldns_pkt2buffer_wire(query_wire
, query
);
999 if (status
!= LDNS_STATUS_OK
) {
1000 ldns_pkt_free(query
);
1001 ldns_buffer_free(query_wire
);
1004 /* to prevent problems on subsequent calls to ldns_axfr_start
1005 * we have to close the socket here! */
1006 close_socket(resolver
->_socket
);
1007 resolver
->_socket
= 0;
1011 /* Send the query */
1012 if (ldns_tcp_send_query(query_wire
, resolver
->_socket
, ns
,
1013 (socklen_t
)ns_len
) == 0) {
1014 ldns_pkt_free(query
);
1015 ldns_buffer_free(query_wire
);
1018 /* to prevent problems on subsequent calls to ldns_axfr_start
1019 * we have to close the socket here! */
1022 close_socket(resolver
->_socket
);
1024 return LDNS_STATUS_NETWORK_ERR
;
1027 ldns_pkt_free(query
);
1028 ldns_buffer_free(query_wire
);
1032 * The AXFR is done once the second SOA record is sent
1034 resolver
->_axfr_soa_count
= 0;
1035 return LDNS_STATUS_OK
;