aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Stenberg <daniel@haxx.se>2005-12-22 15:27:41 +0000
committerDaniel Stenberg <daniel@haxx.se>2005-12-22 15:27:41 +0000
commite5247ae65d9884c7c454b1cb641b66e2beb047ef (patch)
tree80004250818062cc8072fc38ea25d49b8a2a7a9a
parenta718cb05ff4405dd5a3e09b718413b5066fc5e09 (diff)
Added ares_getsock() to extract sockets to wait for action on, without being
limited to select().
-rw-r--r--ares/Makefile.inc16
-rw-r--r--ares/ares.h43
-rw-r--r--ares/ares_getsock.356
-rw-r--r--ares/ares_getsock.c71
4 files changed, 160 insertions, 26 deletions
diff --git a/ares/Makefile.inc b/ares/Makefile.inc
index f8d9058b1..c90aae4b7 100644
--- a/ares/Makefile.inc
+++ b/ares/Makefile.inc
@@ -1,11 +1,11 @@
-CSOURCES = ares_fds.c ares_process.c ares_free_hostent.c ares_query.c \
-ares__close_sockets.c ares_free_string.c ares_search.c ares__get_hostent.c \
-ares_gethostbyaddr.c ares_send.c ares__read_line.c ares_gethostbyname.c \
-ares_strerror.c ares_cancel.c ares_init.c ares_timeout.c ares_destroy.c \
-ares_mkquery.c ares_version.c ares_expand_name.c ares_parse_a_reply.c \
-windows_port.c ares_expand_string.c ares_parse_ptr_reply.c \
-ares_parse_aaaa_reply.c ares_getnameinfo.c inet_net_pton.c bitncmp.c \
-inet_ntop.c
+CSOURCES = ares_fds.c ares_getsock.c ares_process.c ares_free_hostent.c \
+ares_query.c ares__close_sockets.c ares_free_string.c ares_search.c \
+ares__get_hostent.c ares_gethostbyaddr.c ares_send.c ares__read_line.c \
+ares_gethostbyname.c ares_strerror.c ares_cancel.c ares_init.c \
+ares_timeout.c ares_destroy.c ares_mkquery.c ares_version.c \
+ares_expand_name.c ares_parse_a_reply.c windows_port.c \
+ares_expand_string.c ares_parse_ptr_reply.c ares_parse_aaaa_reply.c \
+ares_getnameinfo.c inet_net_pton.c bitncmp.c inet_ntop.c
HHEADERS = ares.h ares_private.h setup.h ares_dns.h ares_version.h \
nameser.h inet_net_pton.h inet_ntop.h ares_ipv6.h bitncmp.h
diff --git a/ares/ares.h b/ares/ares.h
index 7f76112f7..8e8da2847 100644
--- a/ares/ares.h
+++ b/ares/ares.h
@@ -70,8 +70,8 @@ extern "C" {
#define ARES_EBADFLAGS 18
/* ares_getaddrinfo error codes */
-#define ARES_ENONAME 19
-#define ARES_EBADHINTS 20
+#define ARES_ENONAME 19
+#define ARES_EBADHINTS 20
/* Flag values */
#define ARES_FLAG_USEVC (1 << 0)
@@ -108,27 +108,32 @@ extern "C" {
#define ARES_NI_LOOKUPHOST (1 << 8)
#define ARES_NI_LOOKUPSERVICE (1 << 9)
/* Reserved for future use */
-#define ARES_NI_IDN (1 << 10)
-#define ARES_NI_IDN_ALLOW_UNASSIGNED (1 << 11)
+#define ARES_NI_IDN (1 << 10)
+#define ARES_NI_IDN_ALLOW_UNASSIGNED (1 << 11)
#define ARES_NI_IDN_USE_STD3_ASCII_RULES (1 << 12)
/* Addrinfo flag values */
-#define ARES_AI_CANONNAME (1 << 0)
-#define ARES_AI_NUMERICHOST (1 << 1)
-#define ARES_AI_PASSIVE (1 << 2)
-#define ARES_AI_NUMERICSERV (1 << 3)
-#define ARES_AI_V4MAPPED (1 << 4)
-#define ARES_AI_ALL (1 << 5)
-#define ARES_AI_ADDRCONFIG (1 << 6)
+#define ARES_AI_CANONNAME (1 << 0)
+#define ARES_AI_NUMERICHOST (1 << 1)
+#define ARES_AI_PASSIVE (1 << 2)
+#define ARES_AI_NUMERICSERV (1 << 3)
+#define ARES_AI_V4MAPPED (1 << 4)
+#define ARES_AI_ALL (1 << 5)
+#define ARES_AI_ADDRCONFIG (1 << 6)
/* Reserved for future use */
-#define ARES_AI_IDN (1 << 10)
-#define ARES_AI_IDN_ALLOW_UNASSIGNED (1 << 11)
+#define ARES_AI_IDN (1 << 10)
+#define ARES_AI_IDN_ALLOW_UNASSIGNED (1 << 11)
#define ARES_AI_IDN_USE_STD3_ASCII_RULES (1 << 12)
-#define ARES_AI_CANONIDN (1 << 13)
+#define ARES_AI_CANONIDN (1 << 13)
-#define ARES_AI_MASK (ARES_AI_CANONNAME|ARES_AI_NUMERICHOST|ARES_AI_PASSIVE| \
- ARES_AI_NUMERICSERV|ARES_AI_V4MAPPED|ARES_AI_ALL| \
- ARES_AI_ADDRCONFIG)
+#define ARES_AI_MASK (ARES_AI_CANONNAME|ARES_AI_NUMERICHOST|ARES_AI_PASSIVE| \
+ ARES_AI_NUMERICSERV|ARES_AI_V4MAPPED|ARES_AI_ALL| \
+ ARES_AI_ADDRCONFIG)
+#define ARES_GETSOCK_MAXNUM 16 /* ares_getsock() can return info about this
+ many sockets */
+#define ARES_GETSOCK_READABLE(bits,num) (bits & (1<< (num)))
+#define ARES_GETSOCK_WRITABLE(bits,num) (bits & (1 << ((num) + \
+ ARES_GETSOCK_MAXNUM)))
struct ares_options {
int flags;
@@ -172,9 +177,11 @@ void ares_gethostbyname(ares_channel channel, const char *name, int family,
void ares_gethostbyaddr(ares_channel channel, const void *addr, int addrlen,
int family, ares_host_callback callback, void *arg);
void ares_getnameinfo(ares_channel channel, const struct sockaddr *sa,
- socklen_t salen, int flags, ares_nameinfo_callback callback,
+ socklen_t salen, int flags,
+ ares_nameinfo_callback callback,
void *arg);
int ares_fds(ares_channel channel, fd_set *read_fds, fd_set *write_fds);
+int ares_getsock(ares_channel channel, int *socks, int numsocks);
struct timeval *ares_timeout(ares_channel channel, struct timeval *maxtv,
struct timeval *tv);
void ares_process(ares_channel channel, fd_set *read_fds, fd_set *write_fds);
diff --git a/ares/ares_getsock.3 b/ares/ares_getsock.3
new file mode 100644
index 000000000..301d8c244
--- /dev/null
+++ b/ares/ares_getsock.3
@@ -0,0 +1,56 @@
+.\" $Id$
+.\"
+.\" Copyright 1998 by Daniel Stenberg
+.\"
+.\" Permission to use, copy, modify, and distribute this
+.\" software and its documentation for any purpose and without
+.\" fee is hereby granted, provided that the above copyright
+.\" notice appear in all copies and that both that copyright
+.\" notice and this permission notice appear in supporting
+.\" documentation, and that the name of M.I.T. not be used in
+.\" advertising or publicity pertaining to distribution of the
+.\" software without specific, written prior permission.
+.\" M.I.T. makes no representations about the suitability of
+.\" this software for any purpose. It is provided "as is"
+.\" without express or implied warranty.
+.\"
+.TH ARES_GETSOCK 3 "22 December 2005"
+.SH NAME
+ares_getsock \- get file descriptors to wait on
+.SH SYNOPSIS
+.nf
+.B #include <ares.h>
+.PP
+.B int ares_getsock(ares_channel \fIchannel\fP, int *\fIsocks\fP,
+.B int \fInumsocks\fP);
+.fi
+.SH DESCRIPTION
+The
+.B ares_getsock
+function retrieves the set of file descriptors which the calling
+application should wait on for reading and/or writing for the
+processing of name service queries pending on the name service channel
+identified by
+.IR channel .
+File descriptors will be set in the integer array pointed to by
+\fIsocks\fP.
+\fInumsocks\fP is the size of the given array in number of ints.
+
+This function can only return information about up to 16 sockets. If more are
+in use (however unlikely that is), they are simply not reported back.
+.SH RETURN VALUES
+\fBares_getsock\fP returns a bitmask for what actions to wait for on the
+different sockets. The ares.h header file provides these convenience macros to
+extract the information appropriately:
+
+.nf
+#define ARES_GETSOCK_MAXNUM 16 /* ares_getsock() can return info about
+ this many sockets */
+#define ARES_GETSOCK_READABLE(bits,num) (bits & (1<< (num)))
+#define ARES_GETSOCK_WRITABLE(bits,num) (bits & (1 << ((num) + \
+ ARES_GETSOCK_MAXNUM)))
+.fi
+.SH SEE ALSO
+.BR ares_timeout (3),
+.BR ares_fds (3),
+.BR ares_process (3)
diff --git a/ares/ares_getsock.c b/ares/ares_getsock.c
new file mode 100644
index 000000000..3c52a8367
--- /dev/null
+++ b/ares/ares_getsock.c
@@ -0,0 +1,71 @@
+/* $Id$ */
+
+/* Copyright 2005 by Daniel Stenberg.
+ *
+ * Permission to use, copy, modify, and distribute this software and its
+ * documentation for any purpose and without fee is hereby granted, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the name of M.I.T. not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. M.I.T. makes no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ */
+
+#include "setup.h"
+#include <sys/types.h>
+
+#ifdef HAVE_SYS_TIME_H
+#include <sys/time.h>
+#endif
+
+#include "ares.h"
+#include "ares_private.h"
+
+int ares_getsock(ares_channel channel,
+ int *s,
+ int numsocks) /* size of the 'socks' array */
+{
+ struct server_state *server;
+ ares_socket_t nfds;
+ int i;
+ int sockindex=0;
+ int bitmap = 0;
+ unsigned int setbits = 0xffffffff;
+
+ ares_socket_t *socks = (ares_socket_t *)s;
+
+ /* No queries, no file descriptors. */
+ if (!channel->queries)
+ return 0;
+
+ nfds = 0;
+ for (i = 0; i < channel->nservers; i++)
+ {
+ server = &channel->servers[i];
+ if (server->udp_socket != ARES_SOCKET_BAD)
+ {
+ if(sockindex >= numsocks)
+ break;
+ socks[sockindex] = server->udp_socket;
+ bitmap |= ARES_GETSOCK_READABLE(setbits, sockindex);
+ sockindex++;
+ }
+ if (server->tcp_socket != ARES_SOCKET_BAD)
+ {
+ if(sockindex >= numsocks)
+ break;
+ socks[sockindex] = server->tcp_socket;
+ bitmap |= ARES_GETSOCK_READABLE(setbits, sockindex);
+ sockindex++;
+
+ if (server->qhead) {
+ /* then the tcp socket is also writable! */
+ bitmap |= ARES_GETSOCK_WRITABLE(setbits, sockindex-1);
+ }
+
+ }
+ }
+ return (int)nfds;
+}