#ifndef NO_IPV6
hints.ai_flags = AI_NUMERICHOST;
hints.ai_family = address_family;
- hints.ai_socktype = 0;
+ hints.ai_socktype = SOCK_STREAM;
hints.ai_protocol = 0;
hints.ai_addrlen = 0;
hints.ai_addr = NULL;
hints.ai_next = NULL;
sprintf(portstr, "%d", port);
retcode = getaddrinfo(srcaddr, portstr, &hints, &ai);
- addr = ai->ai_addr;
- addrlen = ai->ai_addrlen;
+ if (retcode == 0) {
+ addr = ai->ai_addr;
+ addrlen = ai->ai_addrlen;
+ }
#else
memset(&a,'\0',sizeof(struct sockaddr_in));
a.sin_family = AF_INET;
return s->sending_oob;
}
+static int sockaddr_is_loopback(struct sockaddr *sa)
+{
+ struct sockaddr_in *sin;
+#ifndef NO_IPV6
+ struct sockaddr_in6 *sin6;
+#endif
+
+ switch (sa->sa_family) {
+ case AF_INET:
+ sin = (struct sockaddr_in *)sa;
+ return ipv4_is_loopback(sin->sin_addr);
+#ifndef NO_IPV6
+ case AF_INET6:
+ sin6 = (struct sockaddr_in6 *)sa;
+ return IN6_IS_ADDR_LOOPBACK(&sin6->sin6_addr);
+#endif
+ case AF_LOCAL:
+ return TRUE;
+ default:
+ return FALSE;
+ }
+}
+
static int net_select_result(int fd, int event)
{
int ret;
- int err;
char buf[20480]; /* nice big buffer for plenty of speed */
Actual_Socket s;
u_long atmark;
* On a listening socket, the readability event means a
* connection is ready to be accepted.
*/
- struct sockaddr_in isa;
- int addrlen = sizeof(struct sockaddr_in);
+#ifdef NO_IPV6
+ struct sockaddr_in ss;
+#else
+ struct sockaddr_storage ss;
+#endif
+ socklen_t addrlen = sizeof(ss);
int t; /* socket of connection */
- memset(&isa, 0, sizeof(struct sockaddr_in));
- err = 0;
- t = accept(s->s,(struct sockaddr *)&isa,(socklen_t *) &addrlen);
+ memset(&ss, 0, addrlen);
+ t = accept(s->s, (struct sockaddr *)&ss, &addrlen);
if (t < 0) {
break;
}
- if (s->localhost_only && !ipv4_is_loopback(isa.sin_addr)) {
+ if (s->localhost_only &&
+ !sockaddr_is_loopback((struct sockaddr *)&ss)) {
close(t); /* someone let nonlocal through?! */
} else if (plug_accepting(s->plug, t)) {
close(t); /* denied or error */