]> git.pld-linux.org Git - packages/apache1.git/blame - apache1-ipv6-PLD.patch
- update to 1.3.39
[packages/apache1.git] / apache1-ipv6-PLD.patch
CommitLineData
a3b982d0
JB
1--- apache_1.3.28.orig/README.v6 Thu Jan 1 01:00:00 1970
2+++ apache_1.3.28/README.v6 Fri Jul 25 11:01:55 2003
831e4313 3@@ -0,0 +1,166 @@
4+IPv6-ready apache 1.3.x
5+KAME Project
6+$Id$
7+
8+This patchkit enables apache 1.3.x to perform HTTP connection over IPv6.
9+Most of optional modules are left unchanged, i.e. it won't support IPv6,
10+and it may not compile.
11+
12+Basically you can write IPv6 address where IPv4 address fits.
13+
14+extra command-line argument:
15+ -4 Assume IPv4 address on ambiguous directives
16+ -6 Assume IPv6 address on ambiguous directives (default)
17+
18+ The above two can be used, for example, to disambiguate
19+ "BindAddress *".
20+
21+base commands:
22+ Listen
23+ Listen is expanded to take one or two arguments.
24+ Listen port
25+ Listen address:port
26+ Listen address port
27+ This is to let you specify "Listen :: 80", since "Listen :::80"
28+ won't work.
29+
30+mod_access:
31+ deny from
32+ allow from
33+ "deny from" and "allow from" supports IPv6 addresses, under the
34+ following forms:
35+ {deny,allow} from v6addr
36+ {deny,allow} from v6addr/v6mask
37+ {deny,allow} from v6addr/prefixlen
38+ Also, wildcard ("*") and string hostname matches IPv6 hosts as well.
39+
40+mod_proxy:
41+ ProxyRequests on
42+ http/ftp proxying for both IPv4 and IPv6 is possible.
43+ Access control functions (NoProxy) are not updated yet.
44+
45+ NOTE: for security reasons, we recommend you to filter out
46+ outsider's access to your proxy, by directives like below:
47+ <Directory proxy:*>
48+ order deny,allow
49+ deny from all
50+ allow from 10.0.0.0/8
51+ allow from 3ffe:9999:8888:7777::/64
52+ </Directory>
53+
54+virtual host:
55+ If you would like to this feature, you must describe 'Listen'
56+ part on configuration file explicitly. like below:
57+ Listen :: 80
58+ Listen 0.0.0.0 80
59+
60+ NameVirtualHost
61+ NameVirtualHost is expanded to take one more two arguments.
62+ NameVirtualHost address
63+ NameVirtualHost address:port
64+ NameVirtualHost address port
65+ This is to let you specify IPv6 address into address part.
66+
67+ Note that, if colon is found in the specified address string,
68+ the code will to resolve the address in the following way:
69+ 1. try to resolve as address:port (most of IPv6 address fails)
70+ 2. if (1) is failed, try to resolve as address only
71+ If there's ambiguity, i.e. 3ffe:0501::1:2, the address may not be
72+ parsed as you expect (3ffe:0501::1 with port 2, or 3ffe:0501::1:2
73+ with default port). To get the right effect you are encouraged
74+ to specify it without ambiguity. In IPv6 case "address port"
75+ (specify address and port separated by a space) is the safest way.
76+
77+ <VirtualHost host:port [host:port ...]>
78+ If you would like to specify IPv6 numeric address in host part,
79+ use bracketed format like below:
80+ <VirtualHost [::1]:80>
81+ Note: Now we DO NOT handle old non-bracketed format,
82+ <VirtualHost 0:0:0:0:0:0:0:1:80>
83+ so configuration file must be updated.
84+ Note: The following is bad example to specify host ::1 port 80.
85+ This will treated as host ::1:80.
86+ <VirtualHost ::1:80>
87+
88+logresolve (src/support)
89+ error statistics in nameserver cache code is omitted.
90+
91+mod_unique_id
92+ Originally mod_unique_id used IPv4 address as a seed for UNIQUE_ID,
93+ and took IPv4 address registered onto DNS for the hostname (UNIX
94+ hostname taken by gethostname(3)). Therefore, this does not work
95+ for IPv6-only hosts as they do not have IPv4 address for them.
96+
97+ Now, UNIQUE_ID can be generated using IPv6 address. IPv6 address can
98+ be used as the seed for UNIQUE_ID.
99+ Because of this, UNIQUE_ID will be longer than normal apache. This
100+ may cause problem with some of the CGI scripts.
101+ The preference of the addresses is based on the order returned
102+ by getaddrinfo(). If your getaddrinfo() returns IPv4 address, IPv4
103+ adderss will be used as a seed.
104+ Note that some of IPv6 addresses are "scoped"; If you happened to use
105+ link-local or site-local address as a seed, the UNIQUE_ID may not be
106+ worldwide unique.
107+
108+ If longer UNIQUE_ID causes a problem, define SHORT_UNIQUE_ID in
109+ mod_unique_id.c. In this case, length of UNIQUE_ID will be kept the
110+ same. However, for IPv6 addresses mod_unique_id.c will use the last
111+ 32bit (not the whole 128bit) as the seed. Therefore, there can be
112+ collision in UNIQUE_ID.
113+
114+ The behavior should be improved in the near future; we welcome your
115+ inputs.
116+
117+Modules known to be incompatible with IPv6
118+ (please report us)
119+
120+configure
121+ Configure has extra option, --enable-rule=INET6. if the option
122+ is specified, IPv6 code will be enabled.
123+
124+configuration file
125+ We do not support IPv4 mapped address (IPv6 address format like
126+ ::ffff:10.1.1.1) in configuration file.
127+
128+This kit assumes that you have working(*) getaddrinfo() and getnameinfo()
129+library functions. Even if you don't have one, don't panic. We have
130+included last-resort version (which support IPv4 only) into the kit.
131+For more complete implementation you might want to check BIND 8.2.
132+(*) NOTE: we have noticed that some of IPv6 stack is shipped with broken
133+getaddrinfo(). In such cases, you should get and install BIND 8.2.
134+
135+When compiling this kit onto IPv6, you may need to specify some additional
136+library paths or cpp defs (like -linet6 or -DINET6).
137+Now you don't have to specify --enable-rule=INET6. The "configure" script
138+will give you some warnings if the IPv6 stack is not known to the
139+"configure" script. Currently, the following IPv6 stacks are supported:
140+- KAME IPv6 stack, http://www.kame.net/
141+ use configure.v6 for convenience,
142+- Linux IPv6 stack, http://www.linux.org/
143+ use configure.v6 for convenience.
144+- Solaris 8 IPv6 stack, http://www.sun.com/
145+ use configure.v6 for convenience.
146+To disable IPv6 support, specify --disable-rule=INET6 to the "configure"
147+script.
148+
149+CAVEAT: This patchkit may change some of apache module API, to avoid
150+IPv4-dependent structure member variable. Please let us know if there's
151+any troubles as we know very little about the apache module API.
152+
153+Acknowledgements
154+ Thanks to all people submitted patches/fixes for this patch kit,
155+ including:
156+ "Chris P. Ross" <cross@eng.us.uu.net>
157+
158+Author contacts
159+ Jun-ichiro itojun Hagino, KAME project
160+ http://www.kame.net/
161+ mailto:core@kame.net
162+Linux Port
163+ Arkadiusz Miskiewicz, Polish Linux Distribution project (IPv6)
164+ http://www.pld.org.pl/
a6148d70 165+ mailto:feedback@pld.org.pl
831e4313 166+ Satoshi SHIDA, Linux IPv6 Users Group JP
167+ http://www.v6.linux.or.jp/
168+ YOSHIFUJI Hideaki, USAGI Project
169+ http://www.linux-ipv6.org/
a3b982d0
JB
170--- apache_1.3.28.orig/conf/httpd.conf-dist Wed Jul 16 21:36:41 2003
171+++ apache_1.3.28/conf/httpd.conf-dist Fri Jul 25 11:01:55 2003
831e4313 172@@ -174,6 +174,11 @@
173 #Listen 3000
174 #Listen 12.34.56.78:80
175
176+# Listen can take two arguments.
177+# (this is an extension for supporting IPv6 addresses)
178+#Listen :: 80
179+#Listen 0.0.0.0 80
180+
181 #
182 # BindAddress: You can support virtual hosts with this option. This directive
183 # is used to tell the server which IP address to listen to. It can either
a3b982d0
JB
184--- apache_1.3.28.orig/configure.v6 Thu Jan 1 01:00:00 1970
185+++ apache_1.3.28/configure.v6 Fri Jul 25 11:01:55 2003
831e4313 186@@ -0,0 +1,3 @@
187+#! /bin/sh
188+
189+./configure --enable-rule=INET6 --enable-module=proxy $*
a3b982d0
JB
190--- apache_1.3.28.orig/src/Configuration.tmpl Fri Jul 25 11:00:49 2003
191+++ apache_1.3.28/src/Configuration.tmpl Fri Jul 25 11:01:55 2003
67983ac1 192@@ -191,6 +191,9 @@
193 # Rule EXPAT=default : If Expat can be found at the system or
194 # in lib/expat-lite, use it; otherwise
195 # skip it
831e4313 196+# INET6:
197+# IPv6 support.
198+#
a6148d70 199 #
200 # CYGWIN_WINSOCK:
201 # Use Win32 API system calls for socket communication instead
202@@ -205,6 +208,7 @@
831e4313 203 Rule IRIXN32=yes
204 Rule PARANOID=no
205 Rule EXPAT=default
206+Rule INET6=no
a6148d70 207 Rule CYGWIN_WINSOCK=no
831e4313 208
209 # DEV_RANDOM:
a3b982d0
JB
210--- apache_1.3.28.orig/src/Configure Fri Jul 25 11:00:49 2003
211+++ apache_1.3.28/src/Configure Fri Jul 25 11:01:55 2003
a6148d70 212@@ -238,6 +238,7 @@
213 RULE_CYGWIN_WINSOCK=`./helpers/CutRule CYGWIN_WINSOCK $file`
831e4313 214 RULE_SHARED_CORE=`./helpers/CutRule SHARED_CORE $file`
215 RULE_SHARED_CHAIN=`./helpers/CutRule SHARED_CHAIN $file`
216+RULE_INET6=`./helpers/CutRule INET6 $file`
217
218 ####################################################################
219 ## Rule SHARED_CORE implies required DSO support
a3b982d0 220@@ -1724,6 +1725,124 @@
831e4313 221 esac
222 fi
223
224+# INET6 support.
225+if [ "$RULE_INET6" = "yes" ]; then
226+ echo " + enabling INET6 support"
227+ CFLAGS="$CFLAGS -DINET6"
228+ CFLAGS="$CFLAGS -Dss_family=__ss_family -Dss_len=__ss_len"
229+ IPV6_STACKTYPE="UNKNOWN"
230+ for i in KAME Linux Solaris; do
231+ case "$i" in
232+ KAME)
233+ if [ -f /usr/include/netinet6/in6.h -a "x`egrep '__KAME__' /usr/include/netinet6/in6.h 2>/dev/null`" != "x" ]; then
234+ IPV6_STACKTYPE=$i
235+ fi
236+ ;;
237+ Linux)
238+ if [ /usr/include/netinet/ip6.h -a -d /usr/include/linux ]; then
239+ IPV6_STACKTYPE=$i
240+ fi
241+ ;;
242+ Solaris)
243+ SOL_VERSION=`(uname -v) 2>/dev/null` || SOL_VERSION="unknown"
244+ case "${PLAT}-${SOL_VERSION}" in
245+ *-solaris2.27*-*IPv6*)
246+ if [ -f /etc/hostname -o -f /etc/hostname.[a-z]*[0-9] ]; then
247+ IPV6_STACKTYPE="Solaris 7 (${SOL_VERSION})"
248+ fi
249+ ;;
250+ esac
251+ ;;
252+ esac
253+ if [ "$IPV6_STACKTYPE" != "UNKNOWN" ]; then
254+ break
255+ fi
256+ done
257+ if [ "$IPV6_STACKTYPE" != "UNKNOWN" ]; then
258+ echo " + You seem to be using $IPV6_STACKTYPE stack"
259+ if ./helpers/TestCompile func getaddrinfo; then
260+ echo " - Assuming you have working getaddrinfo in libc"
261+ else
262+ if [ -f /usr/local/v6/lib/libinet6.a -a "x`egrep '^EXTRA_L' Makefile.config | grep linet6`" = "x" ]; then
263+ LIBS="$LIBS -L/usr/local/v6/lib -linet6"
264+ echo " - using getaddrinfo in libinet6"
265+ elif [ -f /usr/local/lib/libinet6.a -a "x`egrep '^EXTRA_L' Makefile.config | grep linet6`" = "x" ]; then
266+ LIBS="$LIBS -L/usr/local/lib -linet6"
267+ echo " - using getaddrinfo in libinet6"
268+ elif [ -f /usr/inet6/lib/libinet6.a -a "x`egrep '^EXTRA_L' Makefile.config | grep linet6`" = "x" ]; then
269+ echo " - using getaddrinfo in libinet6"
270+ else
271+ echo "** WARNING: No getaddrinfo found, linkage may fail"
272+ fi
273+ fi
274+ else
275+ echo ""
276+ echo "** WARNING: We have no explicit knowledge about the IPv6"
277+ echo "** implementation on this host. You may need to specify"
278+ echo "** EXTRA_LIBS so that we can find getaddrinfo() and"
279+ echo "** getnameinfo() library functions."
280+ echo ""
281+ fi
282+ case $PLAT in
283+ *-solaris2* )
284+ LIBS="$LIBS -lresolv"
285+ ;;
286+ esac
287+else
288+ CFLAGS="$CFLAGS -DNEED_GETADDRINFO -DNEED_GETNAMEINFO"
289+ if [ -f /usr/include/netdb.h -a "x`egrep 'addrinfo' /usr/include/netdb.h`" = "x" ]; then
290+ CFLAGS="$CFLAGS -DNEED_ADDRINFO"
291+ fi
292+fi
293+
294+echo '#include <sys/types.h>' >testfunc.c
295+echo '#include <sys/socket.h>' >>testfunc.c
296+echo 'int testfunc(){ struct sockaddr sa; int i = sa.sa_len; };' >>testfunc.c
297+rm -f testfunc.o
298+eval "${MAKE-make} -f Makefile.config testfunc.o >/dev/null 2>/dev/null"
299+if [ -f testfunc.o ]; then
300+ echo " + you have sa_len in struct sockaddr."
301+ CFLAGS="$CFLAGS -DHAVE_SOCKADDR_LEN"
302+else
303+ echo " + you don't have sa_len in struct sockaddr."
304+fi
305+rm -f testfunc.c testfunc.o
306+
307+echo '#include <sys/types.h>' >testfunc.c
308+echo '#include <sys/socket.h>' >>testfunc.c
309+echo 'struct sockaddr_storage sockaddr_storage;' >>testfunc.c
310+rm -f testfunc.o
311+eval "${MAKE-make} -f Makefile.config testfunc.o >/dev/null 2>/dev/null"
312+if [ -f testfunc.o ]; then
313+ echo " + assuming you have struct sockaddr_storage"
314+else
315+ CFLAGS="$CFLAGS -DNEED_SOCKADDR_STORAGE"
316+ echo " + you need struct sockaddr_storage"
317+fi
318+rm -f testfunc.c testfunc.o
319+
320+echo '#include <sys/types.h>' >testfunc.c
321+echo '#include <sys/socket.h>' >>testfunc.c
322+echo 'int testfunc(){ socklen_t t; }' >>testfunc.c
323+rm -f testfunc.o
324+eval "${MAKE-make} -f Makefile.config testfunc.o >/dev/null 2>/dev/null"
325+if [ ! -f testfunc.o ]; then
326+ CFLAGS="$CFLAGS -Dsocklen_t=int"
327+fi
328+rm -f testfunc.c testfunc.o
329+
330+echo '#include <sys/types.h>' >testfunc.c
331+echo '#include <sys/socket.h>' >>testfunc.c
332+echo 'struct sockaddr_in sin;' >>testfunc.c
333+echo 'int main(){ int i = sin.sin_len; }' >>testfunc.c
334+rm -f testfunc.o
335+eval "${MAKE-make} -f Makefile.config testfunc.o >/dev/null 2>/dev/null"
336+if [ -f testfunc.o ]; then
337+ CFLAGS="$CFLAGS -DSIN_LEN"
338+fi
339+rm -f testfunc.c testfunc.o
340+
341+
342 ####################################################################
343 ## Find out what modules we want and try and configure things for them
344 ## Module lines can look like this:
a3b982d0 345@@ -2320,6 +2439,38 @@
831e4313 346 echo "#define AP_LONGEST_LONG $AP_LONGEST_LONG" >>$AP_CONFIG_AUTO_H
347 echo "#endif" >>$AP_CONFIG_AUTO_H
98e8ae3d 348
831e4313 349+if [ x`./helpers/TestCompile -r sizeof 'uint32_t'` != x"" ]; then
350+ echo "" >>$AP_CONFIG_AUTO_H
351+ echo "/* determine: use uint32_t as 32bit unsigned int */" >>$AP_CONFIG_AUTO_H
352+ echo "#ifndef ap_uint32_t" >>$AP_CONFIG_AUTO_H
353+ echo "#define ap_uint32_t uint32_t" >>$AP_CONFIG_AUTO_H
354+ echo "#endif" >>$AP_CONFIG_AUTO_H
355+ echo " - use uint32_t as 32bit unsigned int"
356+elif [ x`./helpers/TestCompile -r sizeof 'u_int32_t'` != x"" ]; then
357+ echo "" >>$AP_CONFIG_AUTO_H
358+ echo "/* determine: use u_int32_t as 32bit unsigned int */" >>$AP_CONFIG_AUTO_H
359+ echo "#ifndef ap_uint32_t" >>$AP_CONFIG_AUTO_H
360+ echo "#define ap_uint32_t u_int32_t" >>$AP_CONFIG_AUTO_H
361+ echo "#endif" >>$AP_CONFIG_AUTO_H
362+ echo " - use u_int32_t as 32bit unsigned int"
363+elif [ x`./helpers/TestCompile -r sizeof 'unsigned int'` = x"4" ]; then
364+ echo "" >>$AP_CONFIG_AUTO_H
365+ echo "/* determine: use unsigned int as 32bit unsigned int */" >>$AP_CONFIG_AUTO_H
366+ echo "#ifndef ap_uint32_t" >>$AP_CONFIG_AUTO_H
367+ echo "#define ap_uint32_t unsigned int" >>$AP_CONFIG_AUTO_H
368+ echo "#endif" >>$AP_CONFIG_AUTO_H
369+ echo " - use unsigned int as 32bit unsigned int"
370+elif [ x`./helpers/TestCompile -r sizeof 'unsigned long int'` = x"4" ]; then
371+ echo "" >>$AP_CONFIG_AUTO_H
372+ echo "/* determine: use unsigned long int as 32bit unsigned int */" >>$AP_CONFIG_AUTO_H
373+ echo "#ifndef uint32_t" >>$AP_CONFIG_AUTO_H
374+ echo "#define uint32_t unsigned long int" >>$AP_CONFIG_AUTO_H
375+ echo "#endif" >>$AP_CONFIG_AUTO_H
376+ echo " - use unsigned long int as 32bit unsigned int"
377+else
378+ echo " - Warning: cannot determine what type should we use as 32bit unsigned int"
379+fi
98e8ae3d 380+
831e4313 381 ####################################################################
382 ## More building ap_config_auto.h
98e8ae3d 383 ##
a3b982d0
JB
384--- apache_1.3.28.orig/src/ap/ap_snprintf.c Mon Feb 3 18:13:17 2003
385+++ apache_1.3.28/src/ap/ap_snprintf.c Fri Jul 25 11:01:55 2003
831e4313 386@@ -73,6 +73,7 @@
387 #include <string.h>
388 #include <stdlib.h>
389 #include <math.h>
390+#include "sa_len.h"
391 #ifdef WIN32
392 #include <float.h>
393 #endif
a3b982d0 394@@ -510,6 +511,42 @@
831e4313 395
396
397
398+#ifdef INET6
399+static char *conv_sockaddr(struct sockaddr *sa, char *buf_end, int *len)
400+{
401+ char *p = buf_end;
402+ char hostnamebuf[MAXHOSTNAMELEN];
403+ char portnamebuf[MAXHOSTNAMELEN];
404+ char *q;
405+ int salen;
406+
407+#ifndef SIN6_LEN
408+ salen = SA_LEN(sa);
409+#else
410+ salen = sa->sa_len;
411+#endif
412+ if (getnameinfo(sa, salen, hostnamebuf, sizeof(hostnamebuf),
413+ portnamebuf, sizeof(portnamebuf), NI_NUMERICHOST | NI_NUMERICSERV)) {
414+ strcpy(hostnamebuf, "???");
415+ strcpy(portnamebuf, "???");
416+ }
417+ if (strcmp(portnamebuf,"0") == 0)
418+ strcpy(portnamebuf, "*");
419+ q = portnamebuf + strlen(portnamebuf);
420+ while (portnamebuf < q)
421+ *--p = *--q;
422+ *--p = ':';
423+ q = hostnamebuf + strlen(hostnamebuf);
424+ while (hostnamebuf < q)
425+ *--p = *--q;
426+
427+ *len = buf_end - p;
428+ return (p);
429+}
430+#endif /*INET6*/
431+
432+
a6148d70 433+
434 /*
435 * Convert a floating point number to a string formats 'f', 'e' or 'E'.
436 * The result is placed in buf, and len denotes the length of the string
a3b982d0 437@@ -1057,6 +1094,7 @@
a6148d70 438 /* print a struct sockaddr_in as a.b.c.d:port */
439 case 'I':
440 {
441+#ifndef INET6
442 struct sockaddr_in *si;
443
444 si = va_arg(ap, struct sockaddr_in *);
a3b982d0 445@@ -1065,6 +1103,16 @@
a6148d70 446 if (adjust_precision && precision < s_len)
447 s_len = precision;
448 }
831e4313 449+#else
450+ struct sockaddr *sa;
451+
452+ sa = va_arg(ap, struct sockaddr *);
453+ if (sa != NULL) {
454+ s = conv_sockaddr(sa, &num_buf[NUM_BUF_SIZE], &s_len);
455+ if (adjust_precision && precision < s_len)
456+ s_len = precision;
457+ }
458+#endif
a6148d70 459 else {
460 s = S_NULL;
461 s_len = S_NULL_LEN;
a3b982d0
JB
462--- apache_1.3.28.orig/src/include/ap.h Mon Feb 3 18:13:17 2003
463+++ apache_1.3.28/src/include/ap.h Fri Jul 25 11:01:55 2003
23d312ca 464@@ -95,7 +95,8 @@
831e4313 465 * with some extensions. The extensions are:
466 *
467 * %pA takes a struct in_addr *, and prints it as a.b.c.d
468- * %pI takes a struct sockaddr_in * and prints it as a.b.c.d:port
469+ * %pI takes a struct sockaddr * and prints it as a.b.c.d:port, or
470+ * ipv6-numeric-addr:port
471 * %pp takes a void * and outputs it in hex
472 *
473 * The %p hacks are to force gcc's printf warning code to skip
a3b982d0
JB
474--- apache_1.3.28.orig/src/include/ap_config.h Mon May 5 13:45:49 2003
475+++ apache_1.3.28/src/include/ap_config.h Fri Jul 25 11:01:55 2003
476@@ -411,6 +411,10 @@
831e4313 477 #endif
478 #ifndef S_IWOTH
479 #define S_IWOTH 000002
480+#ifndef rlim_t
481+typedef int rlim_t;
482+#endif
483+typedef u_long n_long;
484 #endif
485
486 #define STDIN_FILENO 0
a3b982d0 487@@ -1523,6 +1527,70 @@
831e4313 488 #define ap_wait_t int
98e8ae3d
JB
489 #endif
490
831e4313 491+#ifndef INET6
492+#define sockaddr_storage sockaddr
493+#define ss_family sa_family
494+#define ss_len sa_len
495+#else
496+#include "sockaddr_storage.h" /* sshida@st.rim.or.jp */
497+#endif
498+
499+#ifndef INET6_ADDRSTRLEN
500+#define INET6_ADDRSTRLEN 46
501+#endif
502+#ifndef INET_ADDRSTRLEN
503+#define INET_ADDRSTRLEN 16
504+#endif
505+#ifndef NI_MAXHOST
506+#define NI_MAXHOST 1025
507+#endif
508+#ifndef NI_MAXSERV
509+#define NI_MAXSERV 32
510+#endif
511+
512+#if defined(NEED_GETADDRINFO) || defined(NEED_GETNAMEINFO)
513+/*
514+ * minimal definitions for fake getaddrinfo()/getnameinfo().
515+ */
516+#ifndef EAI_NODATA
517+#define EAI_NODATA 1
518+#define EAI_MEMORY 2
519+#endif
520+
521+#ifndef AI_PASSIVE
522+#define AI_PASSIVE 1
523+#define AI_CANONNAME 2
524+#define AI_NUMERICHOST 4
525+#define NI_NUMERICHOST 8
526+#define NI_NAMEREQD 16
527+#define NI_NUMERICSERV 32
528+#endif
529+#endif
530+
531+#ifdef NEED_GETADDRINFO
532+#ifdef NEED_ADDRINFO
533+struct addrinfo {
534+ int ai_flags; /* AI_PASSIVE, AI_CANONNAME */
535+ int ai_family; /* PF_xxx */
536+ int ai_socktype; /* SOCK_xxx */
537+ int ai_protocol; /* 0 or IPPROTO_xxx for IPv4 and IPv6 */
538+ size_t ai_addrlen; /* length of ai_addr */
539+ char *ai_canonname; /* canonical name for hostname */
540+ struct sockaddr *ai_addr; /* binary address */
541+ struct addrinfo *ai_next; /* next structure in linked list */
542+};
543+#endif
544+extern char *gai_strerror(int ecode);
545+extern void freeaddrinfo(struct addrinfo *ai);
546+extern int getaddrinfo(const char *hostname, const char *servname,
547+ const struct addrinfo *hints, struct addrinfo **res);
548+#endif
549+#ifdef NEED_GETNAMEINFO
550+extern int getnameinfo(const struct sockaddr *sa, size_t salen,
551+ char *host, size_t hostlen, char *serv, size_t servlen,
552+ int flag);
98e8ae3d
JB
553+#endif
554+
831e4313 555 #ifdef __cplusplus
98e8ae3d
JB
556 }
557 #endif
a3b982d0
JB
558--- apache_1.3.28.orig/src/include/http_conf_globals.h Fri Jul 25 11:00:49 2003
559+++ apache_1.3.28/src/include/http_conf_globals.h Fri Jul 25 11:01:55 2003
831e4313 560@@ -82,7 +82,8 @@
561 extern API_VAR_EXPORT int ap_max_requests_per_child;
562 extern API_VAR_EXPORT int ap_threads_per_child;
563 extern API_VAR_EXPORT int ap_excess_requests_per_child;
a6148d70 564-extern API_VAR_EXPORT struct in_addr ap_bind_address;
565+extern API_VAR_EXPORT struct sockaddr_storage ap_bind_address;
831e4313 566+extern API_VAR_EXPORT int ap_default_family;
567 extern listen_rec *ap_listeners;
568 extern API_VAR_EXPORT int ap_daemons_to_start;
569 extern API_VAR_EXPORT int ap_daemons_min_free;
a3b982d0
JB
570--- apache_1.3.28.orig/src/include/http_vhost.h Mon Feb 3 18:13:19 2003
571+++ apache_1.3.28/src/include/http_vhost.h Fri Jul 25 11:01:55 2003
831e4313 572@@ -73,7 +73,7 @@
a6148d70 573 API_EXPORT(const char *) ap_parse_vhost_addrs(pool *p, const char *hostname, server_rec *s);
831e4313 574
575 /* handle NameVirtualHost directive */
a6148d70 576-API_EXPORT_NONSTD(const char *) ap_set_name_virtual_host (cmd_parms *cmd, void *dummy, char *arg);
577+API_EXPORT_NONSTD(const char *) ap_set_name_virtual_host (cmd_parms *cmd, void *dummy, char *h, char *p);
831e4313 578
579 /* given an ip address only, give our best guess as to what vhost it is */
a6148d70 580 API_EXPORT(void) ap_update_vhost_given_ip(conn_rec *conn);
a3b982d0
JB
581--- apache_1.3.28.orig/src/include/httpd.h Fri Jul 25 11:00:49 2003
582+++ apache_1.3.28/src/include/httpd.h Fri Jul 25 11:01:55 2003
583@@ -904,8 +904,8 @@
831e4313 584
585 /* Who is the client? */
586
587- struct sockaddr_in local_addr; /* local address */
588- struct sockaddr_in remote_addr; /* remote address */
589+ struct sockaddr_storage local_addr; /* local address */
590+ struct sockaddr_storage remote_addr; /* remote address */
591 char *remote_ip; /* Client's IP address */
592 char *remote_host; /* Client's DNS name, if known.
593 * NULL if DNS hasn't been checked,
a3b982d0 594@@ -947,8 +947,8 @@
831e4313 595 typedef struct server_addr_rec server_addr_rec;
596 struct server_addr_rec {
597 server_addr_rec *next;
598- struct in_addr host_addr; /* The bound address, for this server */
599- unsigned short host_port; /* The bound port, for this server */
600+ struct sockaddr_storage host_addr; /* The bound address, for this server */
601+ unsigned short host_port; /* The bound port, for this server XXX */
602 char *virthost; /* The name given in <VirtualHost> */
603 };
604
a3b982d0 605@@ -1016,7 +1016,7 @@
831e4313 606 /* These are more like real hosts than virtual hosts */
607 struct listen_rec {
608 listen_rec *next;
609- struct sockaddr_in local_addr; /* local IP address and port */
610+ struct sockaddr_storage local_addr; /* local IP address and port */
611 int fd;
612 int used; /* Only used during restart */
613 /* more stuff here, like which protocol is bound to the port */
a3b982d0 614@@ -1184,7 +1184,7 @@
831e4313 615 #endif /*#ifdef CHARSET_EBCDIC*/
616
a6148d70 617 API_EXPORT(char *) ap_get_local_host(pool *);
618-API_EXPORT(unsigned long) ap_get_virthost_addr(char *hostname, unsigned short *port);
619+API_EXPORT(struct sockaddr *) ap_get_virthost_addr(char *hostname, unsigned short *port);
831e4313 620
621 extern API_VAR_EXPORT time_t ap_restart_time;
622
a3b982d0
JB
623--- apache_1.3.28.orig/src/include/sa_len.h Thu Jan 1 01:00:00 1970
624+++ apache_1.3.28/src/include/sa_len.h Fri Jul 25 11:01:55 2003
831e4313 625@@ -0,0 +1,41 @@
626+/* sa_len.h : tiny version of SA_LEN (written by <yoshfuji@ecei.tohoku.ac.jp>) */
627+
628+#include <sys/types.h>
629+#include <sys/socket.h>
630+#include <netinet/in.h>
631+#include <sys/un.h>
632+
633+#ifndef HAVE_SOCKADDR_LEN
634+#ifndef SA_LEN
635+#define SA_LEN(s_) ap_sa_len((s_)->sa_family)
636+
637+static NET_SIZE_T ap_sa_len (sa_family_t af)
638+{
639+ switch (af){
640+#if defined(AF_INET)
641+ case AF_INET:
642+ return (sizeof(struct sockaddr_in));
643+#endif /* AF_INET */
644+#if defined(AF_INET6)
645+ case AF_INET6:
646+ return (sizeof(struct sockaddr_in6));
647+#endif
648+#ifdef AF_LOCAL
649+ case AF_LOCAL:
650+#endif /* AF_LOCAL */
651+#if defined(AF_UNIX) && (AF_UNIX != AF_LOCAL)
652+ case AF_UNIX:
653+#endif /* AF_UNIX */
654+#if defined(AF_FILE) && (AF_FILE != AF_LOCAL || AF_FILE != AF_UNIX)
655+ case AF_FILE:
656+#endif /* AF_FILE */
657+#if defined(AF_LOCAL) || defined(AF_UNIX) || defined(AF_FILE)
658+ return (sizeof(struct sockaddr_un));
659+#endif /* defined(AF_LOCAL) || defined(AF_UNIX) || defined(AF_FILE) */
660+ default:
661+ return 0;
662+ }
663+ return 0;
664+}
665+#endif /* SA_LEN */
666+#endif /* HAVE_SOCKADDR_LEN */
a3b982d0
JB
667--- apache_1.3.28.orig/src/include/sockaddr_storage.h Thu Jan 1 01:00:00 1970
668+++ apache_1.3.28/src/include/sockaddr_storage.h Fri Jul 25 11:01:55 2003
831e4313 669@@ -0,0 +1,53 @@
670+/*
671+struct sockaddr_storage
672+
673+ RFC2553 proposes struct sockaddr_storage.
674+ This is a placeholder for all sockaddr-variant structures. This is
675+ implemented like follows:
676+
677+ You should use this structure to hold any of sockaddr-variant
678+ structures.
679+*/
680+#ifdef NEED_SOCKADDR_STORAGE
681+
682+struct sockaddr_storage {
683+#ifdef HAVE_SOCKADDR_LEN
684+ u_char ss_len;
685+ u_char ss_family;
686+#else
687+ u_short ss_family;
688+#endif
689+ u_char __padding[128 - 2];
690+};
691+
692+/*
693+union sockunion
694+
695+ Alternatively, you may want to implement sockunion.h, with the
696+ following content:
697+
698+ NOTE: For better portability, struct sockaddr_storage should be used.
699+ union sockunion is okay, but is not really portable enough.
700+*/
701+union sockunion {
702+ struct sockinet {
703+#ifdef HAVE_SOCKADDR_LEN
704+ u_char si_len;
705+ u_char si_family;
706+#else
707+ u_short si_family;
708+#endif
709+ u_short si_port;
710+ } su_si;
711+ struct sockaddr_in su_sin;
712+#ifdef INET6
713+ struct sockaddr_in6 su_sin6;
714+#endif
715+};
716+#ifdef HAVE_SOCKADDR_LEN
717+#define su_len su_si.si_len
718+#endif
719+#define su_family su_si.si_family
720+#define su_port su_si.si_port
721+
722+#endif /* NEED_SOCKADDR_STORAGE */
a3b982d0
JB
723--- apache_1.3.28.orig/src/main/getaddrinfo.c Thu Jan 1 01:00:00 1970
724+++ apache_1.3.28/src/main/getaddrinfo.c Fri Jul 25 11:01:55 2003
831e4313 725@@ -0,0 +1,162 @@
726+/*
727+ * Copyright (C) 1995, 1996, 1997, 1998, and 1999 WIDE Project.
728+ * All rights reserved.
729+ *
730+ * Redistribution and use in source and binary forms, with or without
731+ * modification, are permitted provided that the following conditions
732+ * are met:
733+ * 1. Redistributions of source code must retain the above copyright
734+ * notice, this list of conditions and the following disclaimer.
735+ * 2. Redistributions in binary form must reproduce the above copyright
736+ * notice, this list of conditions and the following disclaimer in the
737+ * documentation and/or other materials provided with the distribution.
738+ * 3. Neither the name of the project nor the names of its contributors
739+ * may be used to endorse or promote products derived from this software
740+ * without specific prior written permission.
741+ *
742+ * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
743+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
744+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
745+ * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
746+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
747+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
748+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
749+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
750+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
751+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
752+ * SUCH DAMAGE.
753+ */
754+/*
755+ * fake library for ssh v6 enabler patch
756+ *
757+ * This file includes getaddrinfo(), freeaddrinfo() and gai_strerror().
758+ * These funtions are defined in rfc2133.
759+ *
760+ * But these functions are not implemented correctly. The minimum subset
761+ * is implemented for ssh use only. For exapmle, this routine assumes
762+ * that ai_family is AF_INET. Don't use it for another purpose.
763+ *
764+ * In the case not using 'configure --enable-ipv6', this getaddrinfo.c
765+ * will be used if you have broken getaddrinfo or no getaddrinfo.
766+ */
767+
768+#if 0
769+#include <stdlib.h>
770+#include <sys/types.h>
771+#include <sys/socket.h>
772+#include <netinet/in.h>
773+#include <arpa/inet.h>
774+#include <netdb.h>
775+#include "gai.h"
776+#endif
777+
778+static struct addrinfo *
779+malloc_ai(port, addr, socktype, protocol)
780+int port;
781+u_long addr;
782+int socktype;
783+int protocol;
784+{
785+ struct addrinfo *ai;
786+
787+ if (ai = (struct addrinfo *)malloc(sizeof(struct addrinfo) +
788+ sizeof(struct sockaddr_in))) {
789+ memset(ai, 0, sizeof(struct addrinfo) + sizeof(struct sockaddr_in));
790+ ai->ai_addr = (struct sockaddr *)(ai + 1);
791+#if defined(HAVE_SOCKADDR_LEN)
792+ ai->ai_addr->sa_len =
793+#endif
794+ ai->ai_addrlen = sizeof(struct sockaddr_in);
795+ ai->ai_addr->sa_family = ai->ai_family = AF_INET;
796+ ai->ai_socktype = socktype;
797+ ai->ai_protocol = protocol;
798+ ((struct sockaddr_in *)(ai)->ai_addr)->sin_port = port;
799+ ((struct sockaddr_in *)(ai)->ai_addr)->sin_addr.s_addr = addr;
800+ return ai;
801+ } else {
802+ return NULL;
803+ }
804+}
805+
806+char *
807+gai_strerror(ecode)
808+int ecode;
809+{
810+ switch (ecode) {
811+ case EAI_NODATA:
812+ return "no address associated with hostname.";
813+ case EAI_MEMORY:
814+ return "memory allocation failure.";
815+ default:
816+ return "unknown error.";
817+ }
818+}
819+
820+void
821+freeaddrinfo(ai)
822+struct addrinfo *ai;
823+{
824+ struct addrinfo *next;
825+
826+ do {
827+ next = ai->ai_next;
828+ free(ai);
829+ } while (ai = next);
830+}
831+
832+int
833+getaddrinfo(hostname, servname, hints, res)
834+const char *hostname, *servname;
835+const struct addrinfo *hints;
836+struct addrinfo **res;
837+{
838+ struct addrinfo *cur, *prev = NULL;
839+ struct hostent *hp;
840+ int i, port;
841+
842+ if (servname)
843+ port = htons(atoi(servname));
844+ else
845+ port = 0;
846+ if (hints && hints->ai_flags & AI_PASSIVE)
847+ if (*res = malloc_ai(port, htonl(0x00000000),
848+ (*res)->ai_socktype ? (*res)->ai_socktype : SOCK_STREAM,
849+ (*res)->ai_protocol))
850+ return 0;
851+ else
852+ return EAI_MEMORY;
853+ if (!hostname)
854+ if (*res = malloc_ai(port, htonl(0x7f000001),
855+ (*res)->ai_socktype ? (*res)->ai_socktype : SOCK_STREAM,
856+ (*res)->ai_protocol))
857+ return 0;
858+ else
859+ return EAI_MEMORY;
860+ if (inet_addr(hostname) != -1)
861+ if (*res = malloc_ai(port, inet_addr(hostname),
862+ (*res)->ai_socktype ? (*res)->ai_socktype : SOCK_STREAM,
863+ (*res)->ai_protocol))
864+ return 0;
865+ else
866+ return EAI_MEMORY;
867+ if ((hp = gethostbyname(hostname)) &&
868+ hp->h_name && hp->h_name[0] && hp->h_addr_list[0]) {
869+ for (i = 0; hp->h_addr_list[i]; i++)
870+ if (cur = malloc_ai(port,
871+ ((struct in_addr *)hp->h_addr_list[i])->s_addr,
872+ (*res)->ai_socktype ? (*res)->ai_socktype : SOCK_STREAM,
873+ (*res)->ai_protocol)) {
874+ if (prev)
875+ prev->ai_next = cur;
876+ else
877+ *res = cur;
878+ prev = cur;
879+ } else {
880+ if (*res)
881+ freeaddrinfo(*res);
882+ return EAI_MEMORY;
883+ }
884+ return 0;
885+ }
886+ return EAI_NODATA;
887+}
a3b982d0
JB
888--- apache_1.3.28.orig/src/main/getnameinfo.c Thu Jan 1 01:00:00 1970
889+++ apache_1.3.28/src/main/getnameinfo.c Fri Jul 25 11:01:55 2003
831e4313 890@@ -0,0 +1,95 @@
891+/*
892+ * Copyright (C) 1995, 1996, 1997, 1998, and 1999 WIDE Project.
893+ * All rights reserved.
894+ *
895+ * Redistribution and use in source and binary forms, with or without
896+ * modification, are permitted provided that the following conditions
897+ * are met:
898+ * 1. Redistributions of source code must retain the above copyright
899+ * notice, this list of conditions and the following disclaimer.
900+ * 2. Redistributions in binary form must reproduce the above copyright
901+ * notice, this list of conditions and the following disclaimer in the
902+ * documentation and/or other materials provided with the distribution.
903+ * 3. Neither the name of the project nor the names of its contributors
904+ * may be used to endorse or promote products derived from this software
905+ * without specific prior written permission.
906+ *
907+ * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
908+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
909+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
910+ * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
911+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
912+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
913+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
914+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
915+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
916+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
917+ * SUCH DAMAGE.
918+ */
919+/*
920+ * fake library for ssh v6 enabler patch
921+ *
922+ * This file includes getnameinfo().
923+ * These funtions are defined in rfc2133.
924+ *
925+ * But these functions are not implemented correctly. The minimum subset
926+ * is implemented for ssh use only. For exapmle, this routine assumes
927+ * that ai_family is AF_INET. Don't use it for another purpose.
928+ *
929+ * In the case not using 'configure --enable-ipv6', this getnameinfo.c
930+ * will be used if you have broken getnameinfo or no getnameinfo.
931+ */
932+
933+#if 0
934+#include <stdlib.h>
935+#include <sys/types.h>
936+#include <sys/socket.h>
937+#include <netinet/in.h>
938+#include <arpa/inet.h>
939+#include <netdb.h>
940+#include <string.h>
941+#include "gai.h"
942+#endif
943+
944+int
945+getnameinfo(sa, salen, host, hostlen, serv, servlen, flags)
946+const struct sockaddr *sa;
947+size_t salen;
948+char *host;
949+size_t hostlen;
950+char *serv;
951+size_t servlen;
952+int flags;
953+{
954+ struct sockaddr_in *sin = (struct sockaddr_in *)sa;
955+ struct hostent *hp;
956+ char tmpserv[16];
957+
958+ if (serv) {
959+ sprintf(tmpserv, "%d", ntohs(sin->sin_port));
960+ if (strlen(tmpserv) > servlen)
961+ return EAI_MEMORY;
962+ else
963+ strcpy(serv, tmpserv);
964+ }
965+ if (host)
966+ if (flags & NI_NUMERICHOST)
967+ if (strlen(inet_ntoa(sin->sin_addr)) > hostlen)
968+ return EAI_MEMORY;
969+ else {
970+ strcpy(host, inet_ntoa(sin->sin_addr));
971+ return 0;
972+ }
973+ else
974+ if (hp = gethostbyaddr((char *)&sin->sin_addr, sizeof(struct in_addr),
975+ AF_INET))
976+ if (strlen(hp->h_name) > hostlen)
977+ return EAI_MEMORY;
978+ else {
979+ strcpy(host, hp->h_name);
980+ return 0;
981+ }
982+ else
983+ return EAI_NODATA;
984+ return 0;
985+}
a3b982d0
JB
986--- apache_1.3.28.orig/src/main/http_config.c Fri Jul 25 11:00:49 2003
987+++ apache_1.3.28/src/main/http_config.c Fri Jul 25 11:01:55 2003
988@@ -1591,7 +1591,6 @@
831e4313 989 ap_scoreboard_fname = DEFAULT_SCOREBOARD;
990 ap_lock_fname = DEFAULT_LOCKFILE;
991 ap_max_requests_per_child = DEFAULT_MAX_REQUESTS_PER_CHILD;
992- ap_bind_address.s_addr = htonl(INADDR_ANY);
993 ap_listeners = NULL;
994 ap_listenbacklog = DEFAULT_LISTENBACKLOG;
995 ap_extended_status = 0;
a3b982d0 996@@ -1624,7 +1623,13 @@
831e4313 997 s->next = NULL;
998 s->addrs = ap_pcalloc(p, sizeof(server_addr_rec));
999 /* NOT virtual host; don't match any real network interface */
1000- s->addrs->host_addr.s_addr = htonl(INADDR_ANY);
1001+ memset(&s->addrs->host_addr, 0, sizeof(s->addrs->host_addr));
1002+#if 0
1003+ s->addrs->host_addr.ss_family = ap_default_family; /* XXX: needed?, XXX: PF_xxx can be different from AF_xxx */
1004+#endif
1005+#ifdef HAVE_SOCKADDR_LEN
1006+ s->addrs->host_addr.ss_len = sizeof(s->addrs->host_addr); /* XXX: needed ? */
1007+#endif
1008 s->addrs->host_port = 0; /* matches any port */
1009 s->addrs->virthost = ""; /* must be non-NULL */
1010 s->names = s->wild_names = NULL;
a3b982d0 1011@@ -1643,21 +1648,33 @@
831e4313 1012 static void default_listeners(pool *p, server_rec *s)
1013 {
1014 listen_rec *new;
1015+ struct addrinfo hints, *res0, *res;
1016+ int gai;
1017+ char servbuf[NI_MAXSERV];
1018
1019 if (ap_listeners != NULL) {
1020 return;
1021 }
1022+ ap_snprintf(servbuf, sizeof(servbuf), "%d", s->port ? s->port : DEFAULT_HTTP_PORT);
1023+ memset (&hints, 0, sizeof(hints));
1024+ hints.ai_family = ap_default_family;
1025+ hints.ai_socktype = SOCK_STREAM;
1026+ hints.ai_flags = AI_PASSIVE;
1027+ gai = getaddrinfo(NULL, servbuf, &hints, &res0);
1028+ if (gai){
1029+ fprintf(stderr, "default_listeners(): getaddrinfo(PASSIVE) for family %u: %s\n",
1030+ gai_strerror(gai), ap_default_family);
1031+ exit (1);
1032+ }
1033 /* allocate a default listener */
1034 new = ap_pcalloc(p, sizeof(listen_rec));
1035- new->local_addr.sin_family = AF_INET;
1036- new->local_addr.sin_addr = ap_bind_address;
a6148d70 1037- /* Buck ugly cast to get around terniary op bug in some (MS) compilers */
1038- new->local_addr.sin_port = htons((unsigned short)(s->port ? s->port
1039- : DEFAULT_HTTP_PORT));
831e4313 1040+ memcpy(&new->local_addr, res0->ai_addr, res0->ai_addrlen);
1041 new->fd = -1;
1042 new->used = 0;
1043 new->next = NULL;
1044 ap_listeners = new;
1045+
1046+ freeaddrinfo(res0);
1047 }
1048
1049
6685e6e0
JB
1050--- apache_1.3.34/src/main/http_core.c.orig 2005-06-28 20:03:25.000000000 +0200
1051+++ apache_1.3.34/src/main/http_core.c 2005-10-18 10:14:09.000000000 +0200
2af413f1 1052@@ -28,6 +28,7 @@
a3b982d0
JB
1053 #include "util_md5.h"
1054 #include "scoreboard.h"
1055 #include "fnmatch.h"
831e4313 1056+#include "sa_len.h"
1057
a3b982d0
JB
1058 #ifdef USE_MMAP_FILES
1059 #include <sys/mman.h>
6685e6e0 1060@@ -570,7 +571,7 @@
2af413f1
JB
1061 * file if you care. So the adhoc value should do.
1062 */
6685e6e0 1063 return ap_psprintf(r->pool,"%pA%pp%pp%pp%pp",
78bd3122
JB
1064- &r->connection->local_addr.sin_addr,
1065+ &((struct sockaddr_in *)&(r->connection->local_addr))->sin_addr,
2af413f1
JB
1066 (void *)ap_user_name,
1067 (void *)ap_listeners,
1068 (void *)ap_server_argv0,
6685e6e0 1069@@ -666,7 +667,9 @@
23d312ca 1070 */
a3b982d0 1071 static ap_inline void do_double_reverse (conn_rec *conn)
831e4313 1072 {
a3b982d0 1073- struct hostent *hptr;
831e4313 1074+ struct addrinfo hints, *res, *res0;
a3b982d0
JB
1075+ char hostbuf1[128], hostbuf2[128]; /* INET6_ADDRSTRLEN(=46) is enough */
1076+ int ok = 0;
412ecbb0 1077
a3b982d0
JB
1078 if (conn->double_reverse) {
1079 /* already done */
6685e6e0 1080@@ -678,30 +681,54 @@
a3b982d0
JB
1081 conn->remote_host = ""; /* prevent another lookup */
1082 return;
831e4313 1083 }
a3b982d0
JB
1084- hptr = gethostbyname(conn->remote_host);
1085- if (hptr) {
1086- char **haddr;
1087-
1088- for (haddr = hptr->h_addr_list; *haddr; haddr++) {
1089- if (((struct in_addr *)(*haddr))->s_addr
1090- == conn->remote_addr.sin_addr.s_addr) {
1091- conn->double_reverse = 1;
1092- return;
1093- }
831e4313 1094+ memset(&hints, 0, sizeof(hints));
a3b982d0 1095+ hints.ai_family = PF_UNSPEC;
831e4313 1096+ hints.ai_socktype = SOCK_STREAM;
a3b982d0
JB
1097+ if (getaddrinfo(conn->remote_host, NULL, &hints, &res0)) {
1098+ conn->double_reverse = -1;
1099+ return;
831e4313 1100+ }
a3b982d0
JB
1101+ for (res = res0; res; res = res->ai_next) {
1102+ if (res->ai_addr->sa_family != conn->remote_addr.ss_family ||
1103+ !(res->ai_family == AF_INET
831e4313 1104+#ifdef INET6
a3b982d0 1105+ || res->ai_family == AF_INET6
831e4313 1106+#endif
a3b982d0
JB
1107+ )
1108+ )
1109+ continue;
1110+#ifndef HAVE_SOCKADDR_LEN
1111+ if (res->ai_addrlen != SA_LEN((struct sockaddr *)&conn->remote_addr))
1112+#else
1113+ if (res->ai_addr->sa_len != conn->remote_addr.ss_len)
831e4313 1114+#endif
412ecbb0 1115+ continue;
a3b982d0
JB
1116+ if (getnameinfo(res->ai_addr, res->ai_addrlen,
1117+ hostbuf1, sizeof(hostbuf1), NULL, 0,
1118+ NI_NUMERICHOST))
1119+ continue;
1120+ if (getnameinfo(((struct sockaddr *)&conn->remote_addr), res->ai_addrlen,
1121+ hostbuf2, sizeof(hostbuf2), NULL, 0,
1122+ NI_NUMERICHOST))
1123+ continue;
1124+ if (strcmp(hostbuf1, hostbuf2) == 0){
1125+ ok = 1;
1126+ break;
1127 }
831e4313 1128 }
a3b982d0
JB
1129- conn->double_reverse = -1;
1130+ conn->double_reverse = ok ? 1 : -1;
831e4313 1131+ freeaddrinfo(res0);
a3b982d0 1132 /* invalidate possible reverse-resolved hostname if forward lookup fails */
6d6006fd
JB
1133- conn->remote_host = "";
1134+ if(!ok)
1135+ conn->remote_host = "";
412ecbb0 1136 }
6d6006fd 1137
a3b982d0
JB
1138 API_EXPORT(const char *) ap_get_remote_host(conn_rec *conn, void *dir_config,
1139 int type)
412ecbb0 1140 {
a3b982d0
JB
1141- struct in_addr *iaddr;
1142- struct hostent *hptr;
1143 int hostname_lookups;
1144 int old_stat = SERVER_DEAD; /* we shouldn't ever be in this state */
1145+ char hostnamebuf[MAXHOSTNAMELEN];
831e4313 1146
a3b982d0
JB
1147 /* If we haven't checked the host name, and we want to */
1148 if (dir_config) {
6685e6e0 1149@@ -723,10 +750,14 @@
a3b982d0
JB
1150 || hostname_lookups != HOSTNAME_LOOKUP_OFF)) {
1151 old_stat = ap_update_child_status(conn->child_num, SERVER_BUSY_DNS,
1152 (request_rec*)NULL);
1153- iaddr = &(conn->remote_addr.sin_addr);
1154- hptr = gethostbyaddr((char *)iaddr, sizeof(struct in_addr), AF_INET);
1155- if (hptr != NULL) {
1156- conn->remote_host = ap_pstrdup(conn->pool, (void *)hptr->h_name);
1157+ if (!getnameinfo((struct sockaddr *)&conn->remote_addr,
1158+#ifndef SIN6_LEN
1159+ SA_LEN((struct sockaddr *)&conn->remote_addr),
1160+#else
1161+ conn->remote_addr.ss_len,
1162+#endif
1163+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, 0)) {
1164+ conn->remote_host = ap_pstrdup(conn->pool, (void *)hostnamebuf);
1165 ap_str_tolower(conn->remote_host);
1166
1167 if (hostname_lookups == HOSTNAME_LOOKUP_DOUBLE) {
6685e6e0 1168@@ -804,6 +835,7 @@
a3b982d0
JB
1169 {
1170 conn_rec *conn = r->connection;
1171 core_dir_config *d;
1172+ char hbuf[MAXHOSTNAMELEN];
831e4313 1173
a3b982d0
JB
1174 d = (core_dir_config *)ap_get_module_config(r->per_dir_config,
1175 &core_module);
6685e6e0 1176@@ -813,23 +845,22 @@
a3b982d0
JB
1177 }
1178 if (d->use_canonical_name == USE_CANONICAL_NAME_DNS) {
1179 if (conn->local_host == NULL) {
1180- struct in_addr *iaddr;
1181- struct hostent *hptr;
1182 int old_stat;
1183 old_stat = ap_update_child_status(conn->child_num,
1184 SERVER_BUSY_DNS, r);
1185- iaddr = &(conn->local_addr.sin_addr);
1186- hptr = gethostbyaddr((char *)iaddr, sizeof(struct in_addr),
1187- AF_INET);
1188- if (hptr != NULL) {
1189- conn->local_host = ap_pstrdup(conn->pool,
1190- (void *)hptr->h_name);
1191- ap_str_tolower(conn->local_host);
1192- }
1193- else {
1194- conn->local_host = ap_pstrdup(conn->pool,
1195- r->server->server_hostname);
1196+ if (getnameinfo((struct sockaddr *)&conn->local_addr,
1197+#ifndef SIN6_LEN
1198+ SA_LEN((struct sockaddr *)&conn->local_addr),
1199+#else
1200+ conn->local_addr.ss_len,
1201+#endif
1202+ hbuf, sizeof(hbuf), NULL, 0, 0) == 0) {
1203+ conn->local_host = ap_pstrdup(conn->pool, hbuf);
1204+ } else {
1205+ conn->local_host = ap_pstrdup(conn->pool,
1206+ r->server->server_hostname);
1207 }
1208+ ap_str_tolower(conn->local_host);
1209 (void) ap_update_child_status(conn->child_num, old_stat, r);
1210 }
1211 return conn->local_host;
6685e6e0 1212@@ -841,7 +872,7 @@
2af413f1
JB
1213 API_EXPORT(unsigned) ap_get_server_port(const request_rec *r)
1214 {
1215 unsigned port;
1216- unsigned cport = ntohs(r->connection->local_addr.sin_port);
1217+ unsigned cport = ntohs(((struct sockaddr_in *)&r->connection->local_addr)->sin_port);
1218 core_dir_config *d =
1219 (core_dir_config *)ap_get_module_config(r->per_dir_config, &core_module);
1220
6685e6e0 1221@@ -2647,12 +2678,25 @@
831e4313 1222
a3b982d0
JB
1223 static const char *set_bind_address(cmd_parms *cmd, void *dummy, char *arg)
1224 {
1225+ struct addrinfo hints, *res;
1226+ struct sockaddr *sa;
1227+ size_t sa_len;
1228+ int error;
1229 const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
1230 if (err != NULL) {
1231 return err;
831e4313 1232 }
a3b982d0
JB
1233
1234- ap_bind_address.s_addr = ap_get_virthost_addr(arg, NULL);
1235+ if (strcmp(arg, "*") == 0)
1236+ arg = NULL;
831e4313 1237+
a3b982d0
JB
1238+ sa = ap_get_virthost_addr(arg, NULL);
1239+#ifdef HAVE_SOCKADDR_LEN
1240+ sa_len = sa->sa_len;
1241+#else
1242+ sa_len = SA_LEN(sa);
412ecbb0 1243+#endif
a3b982d0 1244+ memcpy(&ap_bind_address, &sa, sa_len);
412ecbb0 1245 return NULL;
1246 }
831e4313 1247
6685e6e0 1248@@ -2684,48 +2728,71 @@
a3b982d0
JB
1249 return NULL;
1250 }
831e4313 1251
a3b982d0
JB
1252-static const char *set_listener(cmd_parms *cmd, void *dummy, char *ips)
1253+static const char *set_listener(cmd_parms *cmd, void *dummy, char *h, char *p)
1254 {
1255 listen_rec *new;
1256- char *ports, *endptr;
1257- long port;
1258+ char *host, *port;
1259+ struct addrinfo hints, *res;
1260+ int error;
1261
1262 const char *err = ap_check_cmd_context(cmd, GLOBAL_ONLY);
1263 if (err != NULL) {
1264 return err;
1265 }
1266
1267- ports = strchr(ips, ':');
1268- if (ports != NULL) {
1269- if (ports == ips) {
1270- return "Missing IP address";
1271- }
1272- else if (ports[1] == '\0') {
1273- return "Address must end in :<port-number>";
1274+ host = port = NULL;
1275+ if (!p) {
1276+ port = strrchr(h, ':');
1277+ if (port != NULL) {
1278+ if (port == h) {
1279+ return "Missing IP address";
1280+ }
1281+ else if (port[1] == '\0') {
1282+ return "Address must end in :<port-number>";
1283+ }
1284+ *(port++) = '\0';
1285+ if (*h)
1286+ host = h;
1287+ }
1288+ else {
1289+ host = NULL;
1290+ port = h;
1291 }
1292- *(ports++) = '\0';
412ecbb0 1293- }
1294- else {
a3b982d0
JB
1295- ports = ips;
1296+ } else {
1297+ host = h;
1298+ port = p;
1299 }
1300
1301- new=ap_pcalloc(cmd->pool, sizeof(listen_rec));
1302- new->local_addr.sin_family = AF_INET;
1303- if (ports == ips) { /* no address */
1304- new->local_addr.sin_addr.s_addr = htonl(INADDR_ANY);
412ecbb0 1305- }
a3b982d0
JB
1306- else {
1307- new->local_addr.sin_addr.s_addr = ap_get_virthost_addr(ips, NULL);
412ecbb0 1308- }
a3b982d0
JB
1309- errno = 0; /* clear errno before calling strtol */
1310- port = ap_strtol(ports, &endptr, 10);
1311- if (errno /* some sort of error */
1312- || (endptr && *endptr) /* make sure no trailing characters */
1313- || port < 1 || port > 65535) /* underflow/overflow */
1314- {
1315- return "Missing, invalid, or non-numeric port";
1316+ if (host && strcmp(host, "*") == 0)
1317+ host = NULL;
1318+
1319+ new = ap_pcalloc(cmd->pool, sizeof(listen_rec));
412ecbb0 1320+
a3b982d0
JB
1321+ memset(&hints, 0, sizeof(hints));
1322+ hints.ai_family = host ? PF_UNSPEC : ap_default_family;
1323+ hints.ai_flags = AI_PASSIVE;
1324+ hints.ai_socktype = SOCK_STREAM;
1325+ error = getaddrinfo(host, port, &hints, &res);
1326+ if (error || !res) {
1327+ fprintf(stderr, "could not resolve ");
1328+ if (host)
1329+ fprintf(stderr, "host \"%s\" ", host);
1330+ if (port)
1331+ fprintf(stderr, "port \"%s\" ", port);
1332+ fprintf(stderr, "--- %s\n", gai_strerror(error));
1333+ exit(1);
1334+ }
1335+ if (res->ai_next) {
1336+ if (host)
1337+ fprintf(stderr, "host \"%s\" ", host);
1338+ if (port)
1339+ fprintf(stderr, "port \"%s\" ", port);
1340+ fprintf(stderr, "resolved to multiple addresses, ambiguous.\n");
1341+ exit(1);
1342 }
1343- new->local_addr.sin_port = htons((unsigned short)port);
1344+
1345+ memcpy(&new->local_addr, res->ai_addr, res->ai_addrlen);
1346+
1347 new->fd = -1;
1348 new->used = 0;
1349 new->next = ap_listeners;
6685e6e0 1350@@ -3650,7 +3717,7 @@
a3b982d0
JB
1351 { "ThreadStackSize", set_threadstacksize, NULL, RSRC_CONF, TAKE1,
1352 "Stack size each created thread will use."},
1353 #endif
1354-{ "Listen", set_listener, NULL, RSRC_CONF, TAKE1,
1355+{ "Listen", set_listener, NULL, RSRC_CONF, TAKE12,
1356 "A port number or a numeric IP address and a port number"},
1357 { "SendBufferSize", set_send_buffer_size, NULL, RSRC_CONF, TAKE1,
1358 "Send buffer size in bytes"},
6685e6e0 1359@@ -3684,7 +3751,7 @@
a3b982d0
JB
1360 "Name of the config file to be included" },
1361 { "LogLevel", set_loglevel, NULL, RSRC_CONF, TAKE1,
1362 "Level of verbosity in error logging" },
1363-{ "NameVirtualHost", ap_set_name_virtual_host, NULL, RSRC_CONF, TAKE1,
1364+{ "NameVirtualHost", ap_set_name_virtual_host, NULL, RSRC_CONF, TAKE12,
1365 "A numeric IP address:port, or the name of a host" },
1366 #ifdef _OSD_POSIX
1367 { "BS2000Account", set_bs2000_account, NULL, RSRC_CONF, TAKE1,
a3b982d0
JB
1368--- apache_1.3.28.orig/src/main/http_main.c Fri Jul 25 11:00:49 2003
1369+++ apache_1.3.28/src/main/http_main.c Fri Jul 25 12:13:12 2003
1370@@ -124,6 +124,8 @@
1371 #include <bstring.h> /* for IRIX, FD_SET calls bzero() */
1372 #endif
412ecbb0 1373
a3b982d0 1374+#include "sa_len.h"
412ecbb0 1375+
a3b982d0
JB
1376 #ifdef MULTITHREAD
1377 /* special debug stuff -- PCS */
1378
1379@@ -249,7 +251,12 @@
1380 API_VAR_EXPORT char *ap_scoreboard_fname=NULL;
1381 API_VAR_EXPORT char *ap_lock_fname=NULL;
1382 API_VAR_EXPORT char *ap_server_argv0=NULL;
1383-API_VAR_EXPORT struct in_addr ap_bind_address={0};
831e4313 1384+#ifdef INET6
a3b982d0
JB
1385+API_VAR_EXPORT int ap_default_family = PF_INET6;
1386+#else
1387+API_VAR_EXPORT int ap_default_family = PF_INET;
831e4313 1388+#endif
a3b982d0
JB
1389+API_VAR_EXPORT struct sockaddr_storage ap_bind_address={0};
1390 API_VAR_EXPORT int ap_daemons_to_start=0;
1391 API_VAR_EXPORT int ap_daemons_min_free=0;
1392 API_VAR_EXPORT int ap_daemons_max_free=0;
1393@@ -1448,7 +1455,11 @@
1394 fprintf(stderr, "Usage: %s [-D name] [-d directory] [-f file]\n", bin);
1395 #endif
1396 fprintf(stderr, " %s [-C \"directive\"] [-c \"directive\"]\n", pad);
1397- fprintf(stderr, " %s [-v] [-V] [-h] [-l] [-L] [-S] [-t] [-T] [-F]\n", pad);
1398+ fprintf(stderr, " %s [-v] [-V] [-h] [-l] [-L] [-S] [-t] [-T] [-F]"
1399+#ifdef INET6
1400+ " [-46]"
1401+#endif
1402+ "\n", pad);
1403 fprintf(stderr, "Options:\n");
1404 #ifdef SHARED_CORE
1405 fprintf(stderr, " -R directory : specify an alternate location for shared object files\n");
1406@@ -1474,6 +1485,10 @@
1407 #ifndef WIN32
1408 fprintf(stderr, " -F : run main process in foreground, for process supervisors\n");
1409 #endif
1410+#ifdef INET6
1411+ fprintf(stderr, " -4 : assume IPv4 on parsing configuration file\n");
1412+ fprintf(stderr, " -6 : assume IPv6 on parsing configuration file\n");
1413+#endif
1414 #ifdef WIN32
1415 fprintf(stderr, " -n name : name the Apache service for -k options below;\n");
1416 fprintf(stderr, " -k stop|shutdown : tell running Apache to shutdown\n");
1417@@ -3630,11 +3645,13 @@
831e4313 1418
1419
a3b982d0
JB
1420 static conn_rec *new_connection(pool *p, server_rec *server, BUFF *inout,
1421- const struct sockaddr_in *remaddr,
1422- const struct sockaddr_in *saddr,
1423+ const struct sockaddr *remaddr,
1424+ const struct sockaddr *saddr,
1425 int child_num)
1426 {
1427 conn_rec *conn = (conn_rec *) ap_pcalloc(p, sizeof(conn_rec));
1428+ char hostnamebuf[MAXHOSTNAMELEN];
1429+ size_t addr_len;
831e4313 1430
a3b982d0
JB
1431 /* Got a connection structure, so initialize what fields we can
1432 * (the rest are zeroed out by pcalloc).
1433@@ -3643,17 +3660,29 @@
1434 conn->child_num = child_num;
831e4313 1435
a3b982d0
JB
1436 conn->pool = p;
1437- conn->local_addr = *saddr;
1438- conn->local_ip = ap_pstrdup(conn->pool,
1439- inet_ntoa(conn->local_addr.sin_addr));
412ecbb0 1440+#ifndef SIN6_LEN
a3b982d0
JB
1441+ addr_len = SA_LEN(saddr);
1442+#else
1443+ addr_len = saddr->sa_len;
831e4313 1444+#endif
a3b982d0
JB
1445+ memcpy(&conn->local_addr, saddr, addr_len);
1446+ getnameinfo((struct sockaddr *)&conn->local_addr, addr_len,
1447+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, NI_NUMERICHOST);
1448+ conn->local_ip = ap_pstrdup(conn->pool, hostnamebuf);
1449 conn->server = server; /* just a guess for now */
1450 ap_update_vhost_given_ip(conn);
1451 conn->base_server = conn->server;
1452 conn->client = inout;
831e4313 1453
a3b982d0
JB
1454- conn->remote_addr = *remaddr;
1455- conn->remote_ip = ap_pstrdup(conn->pool,
1456- inet_ntoa(conn->remote_addr.sin_addr));
1457+#ifndef SIN6_LEN
1458+ addr_len = SA_LEN(remaddr);
1459+#else
1460+ addr_len = remaddr->sa_len;
1461+#endif
1462+ memcpy(&conn->remote_addr, remaddr, addr_len);
1463+ getnameinfo((struct sockaddr *)&conn->remote_addr, addr_len,
1464+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, NI_NUMERICHOST);
1465+ conn->remote_ip = ap_pstrdup(conn->pool, hostnamebuf);
1466 #ifdef EAPI
1467 conn->ctx = ap_ctx_new(conn->pool);
1468 #endif /* EAPI */
1469@@ -3711,21 +3740,47 @@
1470 #define sock_disable_nagle(s, c) /* NOOP */
1471 #endif
831e4313 1472
a3b982d0
JB
1473-static int make_sock(pool *p, const struct sockaddr_in *server)
1474+static int make_sock(pool *p, const struct sockaddr *server)
1475 {
1476 int s;
1477 int one = 1;
1478- char addr[512];
1479+ char addr[INET6_ADDRSTRLEN + 128];
1480+ char a0[INET6_ADDRSTRLEN];
1481+ char p0[NI_MAXSERV];
1482+#ifdef MPE
1483+ int privport = 0;
412ecbb0 1484+#endif
831e4313 1485
a3b982d0
JB
1486- if (server->sin_addr.s_addr != htonl(INADDR_ANY))
1487- ap_snprintf(addr, sizeof(addr), "address %s port %d",
1488- inet_ntoa(server->sin_addr), ntohs(server->sin_port));
1489- else
1490- ap_snprintf(addr, sizeof(addr), "port %d", ntohs(server->sin_port));
1491+ switch(server->sa_family){
412ecbb0 1492+ case AF_INET:
412ecbb0 1493+#ifdef INET6
1494+ case AF_INET6:
412ecbb0 1495+#endif
a3b982d0 1496+ break;
412ecbb0 1497+ default:
a3b982d0
JB
1498+ ap_log_error(APLOG_MARK, APLOG_CRIT, server_conf,
1499+ "make_sock: unsupported address family %u",
1500+ server->sa_family);
1501+ ap_unblock_alarms();
1502+ exit(1);
412ecbb0 1503+ }
a3b982d0
JB
1504+
1505+ getnameinfo(server,
1506+#ifndef SIN6_LEN
1507+ SA_LEN(server),
1508+#else
1509+ server->sa_len,
1510+#endif
1511+ a0, sizeof(a0), p0, sizeof(p0), NI_NUMERICHOST | NI_NUMERICSERV);
1512+ ap_snprintf(addr, sizeof(addr), "address %s port %s", a0, p0);
1513+#ifdef MPE
1514+ if (atoi(p0) < 1024)
1515+ privport++;
1516+#endif
831e4313 1517
a3b982d0
JB
1518 /* note that because we're about to slack we don't use psocket */
1519 ap_block_alarms();
1520- if ((s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) {
1521+ if ((s = socket(server->sa_family, SOCK_STREAM, IPPROTO_TCP)) == -1) {
1522 ap_log_error(APLOG_MARK, APLOG_CRIT, server_conf,
1523 "make_sock: failed to get a socket for %s", addr);
1524
1525@@ -3828,15 +3883,19 @@
1526
1527 #ifdef MPE
1528 /* MPE requires CAP=PM and GETPRIVMODE to bind to ports less than 1024 */
1529- if (ntohs(server->sin_port) < 1024)
1530+ if (privport)
1531 GETPRIVMODE();
1532 #endif
1533-
1534- if (bind(s, (struct sockaddr *) server, sizeof(struct sockaddr_in)) == -1) {
831e4313 1535+#ifndef SIN6_LEN
a3b982d0
JB
1536+ if (bind(s, server, SA_LEN(server)) == -1)
1537+#else
1538+ if (bind(s, server, server->sa_len) == -1)
831e4313 1539+#endif
a3b982d0
JB
1540+ {
1541 ap_log_error(APLOG_MARK, APLOG_CRIT, server_conf,
1542 "make_sock: could not bind to %s", addr);
1543 #ifdef MPE
1544- if (ntohs(server->sin_port) < 1024)
1545+ if (privport)
1546 GETUSERMODE();
1547 #endif
831e4313 1548
a3b982d0
JB
1549@@ -3849,7 +3908,7 @@
1550 exit(1);
831e4313 1551 }
a3b982d0
JB
1552 #ifdef MPE
1553- if (ntohs(server->sin_port) < 1024)
1554+ if (privport)
1555 GETUSERMODE();
1556 #endif
831e4313 1557
a3b982d0
JB
1558@@ -4002,15 +4061,17 @@
1559 for (;;) {
1560 fd = find_listener(lr);
1561 if (fd < 0) {
1562- fd = make_sock(p, &lr->local_addr);
1563+ fd = make_sock(p, (struct sockaddr *)&lr->local_addr);
1564 }
1565 else {
1566 ap_note_cleanups_for_socket_ex(p, fd, 1);
1567 }
1568 /* if we get here, (fd >= 0) && (fd < FD_SETSIZE) */
1569- FD_SET(fd, &listenfds);
1570- if (fd > listenmaxfd)
1571- listenmaxfd = fd;
1572+ if (fd > 0) {
1573+ FD_SET(fd, &listenfds);
1574+ if (fd > listenmaxfd)
1575+ listenmaxfd = fd;
1576+ }
1577 lr->fd = fd;
1578 if (lr->next == NULL)
1579 break;
1580@@ -4327,8 +4388,8 @@
1581 static void child_main(int child_num_arg)
831e4313 1582 {
a3b982d0
JB
1583 NET_SIZE_T clen;
1584- struct sockaddr sa_server;
1585- struct sockaddr sa_client;
1586+ struct sockaddr_storage sa_server;
1587+ struct sockaddr_storage sa_client;
1588 listen_rec *lr;
831e4313 1589
a3b982d0
JB
1590 /* All of initialization is a critical section, we don't care if we're
1591@@ -4505,7 +4566,7 @@
1592 usr1_just_die = 0;
1593 for (;;) {
1594 clen = sizeof(sa_client);
1595- csd = ap_accept(sd, &sa_client, &clen);
1596+ csd = ap_accept(sd, (struct sockaddr *)&sa_client, &clen);
1597 if (csd >= 0 || errno != EINTR)
1598 break;
1599 if (deferred_die) {
1600@@ -4671,7 +4732,7 @@
1601 */
831e4313 1602
a3b982d0
JB
1603 clen = sizeof(sa_server);
1604- if (getsockname(csd, &sa_server, &clen) < 0) {
1605+ if (getsockname(csd, (struct sockaddr *)&sa_server, &clen) < 0) {
1606 ap_log_error(APLOG_MARK, APLOG_DEBUG, server_conf,
1607 "getsockname, client %pA probably dropped the "
1608 "connection",
1609@@ -4719,8 +4780,8 @@
1610 ap_bpushfd(conn_io, csd, dupped_csd);
831e4313 1611
a3b982d0
JB
1612 current_conn = new_connection(ptrans, server_conf, conn_io,
1613- (struct sockaddr_in *) &sa_client,
1614- (struct sockaddr_in *) &sa_server,
1615+ (struct sockaddr *)&sa_client,
1616+ (struct sockaddr *)&sa_server,
1617 my_child_num);
831e4313 1618
a3b982d0
JB
1619 /*
1620@@ -4875,12 +4936,13 @@
831e4313 1621
a3b982d0
JB
1622 #ifdef _OSD_POSIX
1623 /* BS2000 requires a "special" version of fork() before a setuid() call */
1624- if ((pid = os_fork(ap_user_name)) == -1) {
1625+ if ((pid = os_fork(ap_user_name)) == -1)
1626 #elif defined(TPF)
1627- if ((pid = os_fork(s, slot)) == -1) {
1628+ if ((pid = os_fork(s, slot)) == -1)
1629 #else
1630- if ((pid = fork()) == -1) {
1631+ if ((pid = fork()) == -1)
1632 #endif
1633+ {
1634 ap_log_error(APLOG_MARK, APLOG_ERR, s, "fork: Unable to fork new process");
831e4313 1635
a3b982d0
JB
1636 /* fork didn't succeed. Fix the scoreboard or else
1637@@ -5497,7 +5559,10 @@
1638 ap_setup_prelinked_modules();
831e4313 1639
a3b982d0
JB
1640 while ((c = getopt(argc, argv,
1641- "D:C:c:xXd:Ff:vVlLR:StTh"
1642+ "D:C:c:xXd:Ff:vVlLR:StTh4"
1643+#ifdef INET6
1644+ "6"
1645+#endif
1646 #ifdef DEBUG_SIGSTOP
1647 "Z:"
1648 #endif
1649@@ -5575,8 +5640,14 @@
1650 ap_configtestonly = 1;
1651 ap_docrootcheck = 0;
1652 break;
1653- case 'h':
1654- usage(argv[0]);
1655+ case '4':
1656+ ap_default_family = PF_INET;
1657+ break;
1658+#ifdef INET6
1659+ case '6':
1660+ ap_default_family = PF_INET6;
1661+ break;
1662+#endif
1663 case '?':
1664 usage(argv[0]);
1665 }
1666@@ -5665,9 +5736,10 @@
1667 else {
1668 conn_rec *conn;
1669 request_rec *r;
1670- struct sockaddr sa_server, sa_client;
1671 BUFF *cio;
1672+ struct sockaddr_storage sa_server, sa_client;
1673 NET_SIZE_T l;
1674+ char servbuf[NI_MAXSERV];
23d312ca 1675
a3b982d0
JB
1676 ap_set_version();
1677 /* Yes this is called twice. */
1678@@ -5722,25 +5794,32 @@
23d312ca 1679 #endif
831e4313 1680
a3b982d0
JB
1681 l = sizeof(sa_client);
1682- if ((getpeername(sock_in, &sa_client, &l)) < 0) {
1683+ if ((getpeername(sock_in, (struct sockaddr *)&sa_client, &l)) < 0) {
1684 /* get peername will fail if the input isn't a socket */
1685 perror("getpeername");
1686 memset(&sa_client, '\0', sizeof(sa_client));
1687 }
831e4313 1688
a3b982d0
JB
1689 l = sizeof(sa_server);
1690- if (getsockname(sock_in, &sa_server, &l) < 0) {
1691+ if (getsockname(sock_in, (struct sockaddr *)&sa_server, &l) < 0) {
1692 perror("getsockname");
1693 fprintf(stderr, "Error getting local address\n");
1694 exit(1);
1695 }
1696- server_conf->port = ntohs(((struct sockaddr_in *) &sa_server)->sin_port);
1697+ if (getnameinfo(((struct sockaddr *)&sa_server), l,
1698+ NULL, 0, servbuf, sizeof(servbuf),
1699+ NI_NUMERICSERV)){
1700+ fprintf(stderr, "getnameinfo(): family=%d\n", sa_server.ss_family);
1701+ exit(1);
1702+ }
1703+ servbuf[sizeof(servbuf)-1] = '\0';
1704+ server_conf->port = atoi(servbuf);
1705 cio = ap_bcreate(ptrans, B_RDWR | B_SOCKET);
1706 cio->fd = sock_out;
1707 cio->fd_in = sock_in;
1708 conn = new_connection(ptrans, server_conf, cio,
1709- (struct sockaddr_in *) &sa_client,
1710- (struct sockaddr_in *) &sa_server, -1);
1711+ (struct sockaddr *)&sa_client,
1712+ (struct sockaddr *)&sa_server, -1);
831e4313 1713
a3b982d0 1714 while ((r = ap_read_request(conn)) != NULL) {
831e4313 1715
a3b982d0 1716@@ -7447,7 +7526,11 @@
412ecbb0 1717
a3b982d0
JB
1718 while ((c = getopt(argc, argv, "D:C:c:Xd:f:vVlLz:Z:wiuStThk:n:W:")) != -1) {
1719 #else /* !WIN32 */
1720- while ((c = getopt(argc, argv, "D:C:c:Xd:Ff:vVlLesStTh")) != -1) {
1721+ while ((c = getopt(argc, argv, "D:C:c:Xd:Ff:vVlLesStTh4"
1722+#ifdef INET6
1723+ "6"
1724+#endif
1725+ )) != -1) {
1726 #endif
1727 char **new;
1728 switch (c) {
1729@@ -7993,6 +8076,10 @@
1730 case 't':
1731 case 'T':
1732 case 'h':
1733+ case '4':
1734+#ifdef INET6
1735+ case '6':
1736+#endif
1737 case '?':
1738 break;
1739 case 'R':
2af413f1
JB
1740--- apache_1.3.31/src/main/http_vhost.c.orig Mon Mar 29 23:03:25 2004
1741+++ apache_1.3.31/src/main/http_vhost.c Wed May 12 13:49:13 2004
1742@@ -25,6 +25,7 @@
412ecbb0 1743 #include "http_log.h"
a3b982d0
JB
1744 #include "http_vhost.h"
1745 #include "http_protocol.h"
412ecbb0 1746+#include "sa_len.h"
831e4313 1747
a3b982d0
JB
1748 /*
1749 * After all the definitions there's an explanation of how it's all put
2af413f1 1750@@ -122,78 +123,114 @@
a3b982d0
JB
1751 * *paddr is the variable used to keep track of **paddr between calls
1752 * port is the default port to assume
1753 */
1754-static const char *get_addresses(pool *p, char *w, server_addr_rec ***paddr,
1755- unsigned port)
1756+static const char *get_addresses(pool *p, char *w, char *pstr,
1757+ server_addr_rec ***paddr, unsigned port)
1758 {
1759- struct hostent *hep;
1760- unsigned long my_addr;
1761+ struct addrinfo hints, *res, *res0;
1762 server_addr_rec *sar;
1763- char *t;
1764- int i, is_an_ip_addr;
412ecbb0 1765+ char *t = NULL, *u = NULL, *v = NULL;
a3b982d0
JB
1766+ char *hoststr = NULL, *portstr = NULL;
1767+ char portpool[10];
1768+ int error;
1769+ char servbuf[NI_MAXSERV];
831e4313 1770
a3b982d0
JB
1771- if (*w == 0)
1772+ if (w == 0 || *w == 0)
1773 return NULL;
1774
1775- t = strchr(w, ':');
1776- if (t) {
1777- if (strcmp(t + 1, "*") == 0) {
1778- port = 0;
1779+ portstr = portpool;
1780+ ap_snprintf(portpool, sizeof(portpool), "%u", port);
1781+ if (!pstr) {
1782+ v = w;
1783+ u = NULL;
1784+ if (*w == '['){
1785+ u = strrchr(w, ']');
1786+ if (u) { /* [host]:port or [host] */
1787+ w++;
1788+ *u = '\0';
1789+ v = u + 1;
1790+ }
1791 }
1792- else if ((i = atoi(t + 1))) {
1793- port = i;
1794+ /* w uv , w=v , w=v */
1795+ /* u!=0: [host]:port , u==0: [host:port , host */
1796+ t = strchr(v, ':');
1797+ if (t != NULL && strchr(t+1, ':') == NULL) {
1798+ /* [host]:port-w/o-colons, host-without-colons:port-w/o-colons */
1799+ *t = '\0';
1800+ portstr = t + 1;
1801 }
1802 else {
1803- return ":port must be numeric";
1804+ portstr = "0";
1805 }
1806- *t = 0;
1807+ } else {
1808+ portstr = pstr;
412ecbb0 1809 }
1810
a3b982d0
JB
1811- is_an_ip_addr = 0;
1812- if (strcmp(w, "*") == 0) {
1813- my_addr = htonl(INADDR_ANY);
1814- is_an_ip_addr = 1;
1815- }
1816- else if (strcasecmp(w, "_default_") == 0
1817- || strcmp(w, "255.255.255.255") == 0) {
1818- my_addr = DEFAULT_VHOST_ADDR;
1819- is_an_ip_addr = 1;
1820- }
1821- else if ((my_addr = ap_inet_addr(w)) != INADDR_NONE) {
1822- is_an_ip_addr = 1;
1823+ memset(&hints, 0, sizeof(hints));
1824+ hints.ai_socktype = SOCK_STREAM;
1825+ if (strcmp(w, "*") == 0 || strlen(w) == 0) {
1826+ hoststr = NULL;
1827+ hints.ai_family = PF_UNSPEC;
1828+ hints.ai_flags = AI_PASSIVE;
412ecbb0 1829+ }
a3b982d0
JB
1830+ else if (strcasecmp(w, "_default4_") == 0 ||
1831+ ((ap_default_family == PF_INET
1832+#ifndef INET6
1833+ || ap_default_family == PF_UNSPEC
1834+#endif
1835+ ) && strcasecmp(w, "_default_") == 0)){
1836+ hoststr = "255.255.255.255";
1837+ hints.ai_family = PF_INET;
412ecbb0 1838+ }
a3b982d0
JB
1839+#ifdef INET6
1840+ else if (strcasecmp(w, "_default6_") == 0 ||
1841+ ((ap_default_family == PF_INET6
1842+ || ap_default_family == PF_UNSPEC
1843+ ) && strcasecmp(w, "_default_") == 0)){
1844+ hoststr = "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff";
1845+ hints.ai_family = PF_INET6;
1846 }
1847- if (is_an_ip_addr) {
1848- sar = ap_pcalloc(p, sizeof(server_addr_rec));
1849- **paddr = sar;
1850- *paddr = &sar->next;
1851- sar->host_addr.s_addr = my_addr;
1852- sar->host_port = port;
1853- sar->virthost = ap_pstrdup(p, w);
1854- if (t != NULL)
1855- *t = ':';
1856- return NULL;
1857+#endif
1858+ else{
1859+ hoststr = w;
412ecbb0 1860+ hints.ai_family = PF_UNSPEC;
412ecbb0 1861 }
a3b982d0
JB
1862
1863- hep = gethostbyname(w);
1864-
1865- if ((!hep) || (hep->h_addrtype != AF_INET || !hep->h_addr_list[0])) {
1866+ error = getaddrinfo(hoststr, portstr, &hints, &res0);
1867+ if (error || !res0) {
1868 ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, NULL,
1869- "Cannot resolve host name %s --- ignoring!", w);
1870- if (t != NULL)
1871- *t = ':';
1872+ "Cannot resolve host %s port %s --- ignoring!", hoststr, portstr);
1873+ if (t != NULL) *t = ':';
1874+ if (u != NULL) *u = ']';
1875 return NULL;
1876 }
1877-
1878- for (i = 0; hep->h_addr_list[i]; ++i) {
1879+ for (res=res0; res; res=res->ai_next) {
1880+ switch (res->ai_addr->sa_family) {
1881+ case AF_INET:
1882+#ifdef INET6
1883+ case AF_INET6:
831e4313 1884+#endif
a3b982d0
JB
1885+ break;
1886+ default:
1887+ ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, NULL,
1888+ "Unsupported address family %u, for host %s port %s --- ignoring!",
1889+ res->ai_addr->sa_family, hoststr, portstr);
1890+ continue;
1891+ }
1892 sar = ap_pcalloc(p, sizeof(server_addr_rec));
1893 **paddr = sar;
1894 *paddr = &sar->next;
1895- sar->host_addr = *(struct in_addr *) hep->h_addr_list[i];
1896- sar->host_port = port;
1897+ memcpy(&sar->host_addr, res->ai_addr, res->ai_addrlen);
1898+ if (getnameinfo(res->ai_addr, res->ai_addrlen, NULL, 0, servbuf,
1899+ sizeof(servbuf), NI_NUMERICSERV) == 0)
1900+ sar->host_port = atoi(servbuf);
1901+ else
1902+ sar->host_port = 0;
1903 sar->virthost = ap_pstrdup(p, w);
1904 }
831e4313 1905
a3b982d0
JB
1906- if (t != NULL)
1907- *t = ':';
1908+ freeaddrinfo(res0);
1909+ if (t != NULL) *t = ':';
1910+ if (u != NULL) *u = ']';
1911 return NULL;
412ecbb0 1912 }
831e4313 1913
2af413f1 1914@@ -207,7 +244,8 @@
a3b982d0
JB
1915 /* start the list of addreses */
1916 addrs = &s->addrs;
1917 while (hostname[0]) {
1918- err = get_addresses(p, ap_getword_conf(p, &hostname), &addrs, s->port);
1919+ err = get_addresses(p, ap_getword_conf(p, &hostname), NULL,
1920+ &addrs, s->port);
1921 if (err) {
1922 *addrs = NULL;
1923 return err;
2af413f1 1924@@ -225,10 +263,11 @@
a3b982d0
JB
1925 }
1926
1927
1928-API_EXPORT_NONSTD(const char *) ap_set_name_virtual_host (cmd_parms *cmd, void *dummy, char *arg)
1929+API_EXPORT_NONSTD(const char *) ap_set_name_virtual_host (cmd_parms *cmd, void *dummy, char *h,
1930+ char *p)
412ecbb0 1931 {
a3b982d0
JB
1932 /* use whatever port the main server has at this point */
1933- return get_addresses(cmd->pool, arg, &name_vhost_list_tail,
1934+ return get_addresses(cmd->pool, h, p, &name_vhost_list_tail,
1935 cmd->server->port);
1936 }
831e4313 1937
2af413f1 1938@@ -302,6 +341,19 @@
a3b982d0
JB
1939 return ((key >> 8) ^ key) % IPHASH_TABLE_SIZE;
1940 }
1941
1942+static unsigned hash_addr(struct sockaddr *sa)
1943+{
1944+ switch (sa->sa_family) {
1945+ case AF_INET:
1946+ return hash_inaddr(((struct sockaddr_in *)sa)->sin_addr.s_addr);
1947+#ifdef INET6
412ecbb0 1948+ case AF_INET6:
a3b982d0
JB
1949+ return hash_inaddr(((struct sockaddr_in6 *)sa)->sin6_addr.s6_addr[12]);
1950+#endif
412ecbb0 1951+ default:
a3b982d0 1952+ return hash_inaddr(sa->sa_family);
412ecbb0 1953+ }
a3b982d0 1954+}
412ecbb0 1955
831e4313 1956
a3b982d0 1957 static ipaddr_chain *new_ipaddr_chain(pool *p,
2af413f1 1958@@ -329,25 +381,77 @@
a3b982d0
JB
1959 return new;
1960 }
831e4313 1961
a3b982d0
JB
1962-
1963-static ap_inline ipaddr_chain *find_ipaddr(struct in_addr *server_ip,
1964- unsigned port)
1965+static ap_inline ipaddr_chain *find_ipaddr(struct sockaddr *sa)
1966 {
1967 unsigned bucket;
1968 ipaddr_chain *trav;
1969- unsigned addr;
1970+ char a[NI_MAXHOST], b[NI_MAXHOST];
831e4313 1971
a3b982d0
JB
1972 /* scan the hash table for an exact match first */
1973- addr = server_ip->s_addr;
1974- bucket = hash_inaddr(addr);
1975+ bucket = hash_addr(sa);
1976 for (trav = iphash_table[bucket]; trav; trav = trav->next) {
1977 server_addr_rec *sar = trav->sar;
1978- if ((sar->host_addr.s_addr == addr)
1979- && (sar->host_port == 0 || sar->host_port == port
1980- || port == 0)) {
1981- return trav;
1982+ if (sar->host_addr.ss_family != sa->sa_family)
1983+ continue;
1984+ switch (sa->sa_family) {
1985+ case AF_INET:
1986+ {
1987+ struct sockaddr_in *sin1, *sin2;
1988+ sin1 = (struct sockaddr_in *)&sar->host_addr;
1989+ sin2 = (struct sockaddr_in *)sa;
1990+ if (sin1->sin_port == 0 || sin2->sin_port == 0
1991+ || sin1->sin_port == sin2->sin_port) {
1992+ if (memcmp(&sin1->sin_addr, &sin2->sin_addr,
1993+ sizeof(sin1->sin_addr)) == 0) {
1994+ return trav;
1995+ }
1996+ }
1997+ break;
1998+ }
1999+#ifdef INET6
2000+ case AF_INET6:
2001+ {
2002+ struct sockaddr_in6 *sin1, *sin2;
2003+ sin1 = (struct sockaddr_in6 *)&sar->host_addr;
2004+ sin2 = (struct sockaddr_in6 *)sa;
2005+ if (sin1->sin6_port == 0 || sin2->sin6_port == 0
2006+ || sin1->sin6_port == sin2->sin6_port) {
2007+ if (memcmp(&sin1->sin6_addr, &sin2->sin6_addr,
2008+ sizeof(sin1->sin6_addr)) == 0) {
2009+ return trav;
2010+ }
2011+ }
2012+ break;
2013+ }
831e4313 2014+#endif
a3b982d0
JB
2015+ default: /*unsupported*/
2016+ break;
412ecbb0 2017 }
a3b982d0
JB
2018 }
2019+
2020+#ifdef INET6
2021+ if (sa->sa_family == AF_INET6 &&
2022+ IN6_IS_ADDR_V4MAPPED(&((struct sockaddr_in6 *)sa)->sin6_addr)) {
2023+ /*
2024+ * This is just horrible. I just hate IPv4 mapped address. It
2025+ * complicates access control too much.
2026+ * Due to hashed lookup, we need to visit it again.
2027+ */
2028+ struct sockaddr_in sin;
2029+
2030+ memset(&sin, 0, sizeof(sin));
2031+ sin.sin_family = AF_INET;
2032+#ifdef SIN6_LEN
2033+ sin.sin_len = sizeof(sin);
2034+#endif
2035+ sin.sin_port = ((struct sockaddr_in6 *)sa)->sin6_port;
2036+ memcpy(&sin.sin_addr,
2037+ &((struct sockaddr_in6 *)sa)->sin6_addr.s6_addr[12],
2038+ sizeof(sin.sin_addr));
2039+ return find_ipaddr((struct sockaddr *)&sin);
2040+ }
2041+#endif
2042+
2043 return NULL;
2044 }
831e4313 2045
2af413f1 2046@@ -373,21 +477,7 @@
a3b982d0
JB
2047 int len;
2048 char buf[MAX_STRING_LEN];
2049
2050- if (ic->sar->host_addr.s_addr == DEFAULT_VHOST_ADDR) {
2051- len = ap_snprintf(buf, sizeof(buf), "_default_:%u",
2052- ic->sar->host_port);
2053- }
2054- else if (ic->sar->host_addr.s_addr == INADDR_ANY) {
2055- len = ap_snprintf(buf, sizeof(buf), "*:%u",
2056- ic->sar->host_port);
2057- }
2058- else {
2059- len = ap_snprintf(buf, sizeof(buf), "%pA:%u",
2060- &ic->sar->host_addr, ic->sar->host_port);
2061- }
2062- if (ic->sar->host_port == 0) {
2063- buf[len-1] = '*';
2064- }
2065+ len = ap_snprintf(buf, sizeof(buf), "%pI", &ic->sar->host_addr);
2066 if (ic->names == NULL) {
2067 if (ic->server == NULL)
2068 fprintf(f, "%-22s WARNING: No <VirtualHost> defined for this NameVirtualHost!\n", buf);
2af413f1 2069@@ -515,10 +605,37 @@
a3b982d0
JB
2070 * occured in the config file, we'll copy it in that order.
2071 */
2072 for (sar = name_vhost_list; sar; sar = sar->next) {
2073- unsigned bucket = hash_inaddr(sar->host_addr.s_addr);
2074+ unsigned bucket = hash_addr((struct sockaddr *)&sar->host_addr);
2075 ipaddr_chain *ic = new_ipaddr_chain(p, NULL, sar);
2076+ int wildcard;
2af413f1
JB
2077
2078- if (sar->host_addr.s_addr != INADDR_ANY) {
a3b982d0
JB
2079+ wildcard = 0;
2080+ switch (sar->host_addr.ss_family) {
412ecbb0 2081+ case AF_INET:
a3b982d0
JB
2082+ {
2083+ struct sockaddr_in *sin;
2084+ sin = (struct sockaddr_in *)&sar->host_addr;
2085+ if (sin->sin_addr.s_addr == INADDR_ANY)
2086+ wildcard++;
412ecbb0 2087+ break;
a3b982d0 2088+ }
831e4313 2089+#ifdef INET6
412ecbb0 2090+ case AF_INET6:
a3b982d0
JB
2091+ {
2092+ struct sockaddr_in6 *sin6;
2093+ sin6 = (struct sockaddr_in6 *)&sar->host_addr;
2094+ if (*(ap_uint32_t *)&sin6->sin6_addr.s6_addr[0] == 0
2095+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[4] == 0
2096+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[8] == 0
2097+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[12] == 0) {
2098+ wildcard++;
2099+ }
412ecbb0 2100+ break;
a3b982d0 2101+ }
831e4313 2102+#endif
a3b982d0 2103+ }
2af413f1 2104+
a3b982d0
JB
2105+ if (!wildcard) {
2106 *iphash_table_tail[bucket] = ic;
2107 iphash_table_tail[bucket] = &ic->next;
412ecbb0 2108 }
2af413f1 2109@@ -545,12 +662,45 @@
a3b982d0
JB
2110 has_default_vhost_addr = 0;
2111 for (sar = s->addrs; sar; sar = sar->next) {
2112 ipaddr_chain *ic;
2113+ int wildcard;
2af413f1
JB
2114
2115- if (sar->host_addr.s_addr == DEFAULT_VHOST_ADDR
2116- || sar->host_addr.s_addr == INADDR_ANY) {
2117- ic = find_default_server(sar->host_port);
2118- if (!ic || !add_name_vhost_config(p, main_s, s, sar, ic)) {
2119- if (ic && ic->sar->host_port != 0) {
a3b982d0
JB
2120+ wildcard = 0;
2121+ switch (sar->host_addr.ss_family) {
2122+ case AF_INET:
2123+ {
2124+ struct sockaddr_in *sin;
2125+ sin = (struct sockaddr_in *)&sar->host_addr;
2126+ if (sin->sin_addr.s_addr == DEFAULT_VHOST_ADDR)
2127+ wildcard++;
2128+ else if (sin->sin_addr.s_addr == INADDR_ANY)
2129+ wildcard++;
2130+ break;
2131+ }
2132+#ifdef INET6
2133+ case AF_INET6:
2134+ {
2135+ struct sockaddr_in6 *sin6;
2136+ sin6 = (struct sockaddr_in6 *)&sar->host_addr;
2137+ if (*(ap_uint32_t *)&sin6->sin6_addr.s6_addr[0] == ~0
2138+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[4] == ~0
2139+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[8] == ~0
2140+ && *(ap_uint32_t *)&sin6->sin6_addr.s6_addr[12] == ~0) {
2141+ wildcard++;
2142+ }
2143+ break;
2144+ }
831e4313 2145+#endif
a3b982d0 2146+ }
2af413f1 2147+
a3b982d0
JB
2148+ if (wildcard) {
2149+ /* add it to default bucket for each appropriate sar
2150+ * since we need to do a port test
2151+ */
2152+ ipaddr_chain *other;
2153+
2154+ other = find_default_server(sar->host_port);
2155+ if (!other || !add_name_vhost_config(p, main_s, s, sar, other)) {
2156+ if (other && other->sar->host_port != 0) {
2157 ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_WARNING,
2158 main_s, "_default_ VirtualHost overlap on port %u,"
2159 " the first has precedence", sar->host_port);
2af413f1 2160@@ -563,10 +713,11 @@
412ecbb0 2161 }
a3b982d0
JB
2162 else {
2163 /* see if it matches something we've already got */
2164- ic = find_ipaddr(&sar->host_addr, sar->host_port);
2165+ ic = find_ipaddr((struct sockaddr *)&sar->host_addr);
2166
2167 if (!ic) {
2168- unsigned bucket = hash_inaddr(sar->host_addr.s_addr);
2169+ unsigned bucket =
2170+ hash_addr((struct sockaddr *)&sar->host_addr);
2171
2172 ic = new_ipaddr_chain(p, s, sar);
2173 ic->next = *iphash_table_tail[bucket];
2af413f1 2174@@ -603,19 +754,33 @@
412ecbb0 2175 }
a3b982d0
JB
2176 else {
2177 struct hostent *h;
2178+ char hostnamebuf[MAXHOSTNAMELEN];
2179
2180- if ((h = gethostbyaddr((char *) &(s->addrs->host_addr),
2181- sizeof(struct in_addr), AF_INET))) {
2182- s->server_hostname = ap_pstrdup(p, (char *) h->h_name);
2183+ if (!getnameinfo((struct sockaddr *)&s->addrs->host_addr,
2184+#ifndef SIN6_LEN
2185+ SA_LEN((struct sockaddr *)&s->addrs->host_addr),
2186+#else
2187+ s->addrs->host_addr.ss_len,
412ecbb0 2188+#endif
a3b982d0
JB
2189+ hostnamebuf, sizeof(hostnamebuf),
2190+ NULL, 0, 0)) {
2191+ s->server_hostname = ap_pstrdup(p, hostnamebuf);
2192 }
2193 else {
2194 /* again, what can we do? They didn't specify a
2195 ServerName, and their DNS isn't working. -djg */
2196+ getnameinfo((struct sockaddr *)&s->addrs->host_addr,
2197+#ifndef SIN6_LEN
2198+ SA_LEN((struct sockaddr *)&s->addrs->host_addr),
2199+#else
2200+ s->addrs->host_addr.ss_len,
412ecbb0 2201+#endif
a3b982d0
JB
2202+ hostnamebuf, sizeof(hostnamebuf),
2203+ NULL, 0, NI_NUMERICHOST);
2204 ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, main_s,
2205 "Failed to resolve server name "
2206 "for %s (check DNS) -- or specify an explicit "
2207- "ServerName",
2208- inet_ntoa(s->addrs->host_addr));
2209+ "ServerName", hostnamebuf);
2210 s->server_hostname =
2211 ap_pstrdup(p, "bogus_host_without_reverse_dns");
2212 }
2af413f1 2213@@ -663,45 +828,80 @@
a3b982d0
JB
2214 const char *src;
2215 char *dst;
2af413f1
JB
2216 const char *port_str;
2217+ const char *u, *v = NULL;
a3b982d0
JB
2218
2219 /* check and copy the host part */
2220- src = r->hostname;
2221+ u = src = r->hostname;
2222
2223 dst = host;
2224- while (*src) {
2225- if (*src == '.') {
2226- *dst++ = *src++;
2227- if (*src == '.')
2228- goto bad;
2229- else
2230- continue;
2231- }
2232- if (*src == '/' || *src == '\\') {
2233- goto bad;
2234- }
2235- if (*src == ':') {
2af413f1 2236- port_str = src + 1;
a3b982d0
JB
2237- /* check the port part */
2238- while (*++src) {
2239- if (!ap_isdigit(*src)) {
2af413f1
JB
2240+ if (*u == '[') { /* IPv6 numeral address in brackets */
2241+ v = strchr(u, ']');
2242+ if (v == NULL) {
2243+ /* missing closing bracket */
2244+ goto bad;
2245+ }
2246+ if (v == (u + 1)) {
2247+ /* bad empty address */
2248+ goto bad;
2249+ }
2250+ for (src = u+1; src < v; src++) /* copy IPv6 adress */
2251+ *dst = *src;
2252+ v++;
2253+ if (*v == ':') {
2254+ port_str = v + 1;
2255+ v++;
2256+ while (*v) { /* check if portnum is correct */
2257+ if (!ap_isdigit(*v++))
2258 goto bad;
a3b982d0 2259- }
2af413f1 2260 }
a3b982d0 2261- if (src[-1] == ':')
2af413f1
JB
2262+ if (v[-1] == ':')
2263+ goto bad;
2264+ else {
2265+ /* a known "good" port value */
2266+ int iport;
2267+ iport = atoi(port_str);
2268+ if (iport < 1 || iport > 65535) {
2269+ goto bad;
2270+ }
2271+ r->parsed_uri.port_str = ap_pstrdup(r->pool, port_str);
2272+ r->parsed_uri.port = iport;
2273+ }
2274+ }
2275+ } else {
2276+ while (*src) {
2277+ if (*src == '.') {
2278+ *dst++ = *src++;
2279+ if (*src == '.')
2280+ goto bad;
2281+ else
2282+ continue;
2283+ }
2284+ if (*src == '/' || *src == '\\') {
2285 goto bad;
2286- else {
2287- /* a known "good" port value */
2288- int iport;
2289- iport = atoi(port_str);
2290- if (iport < 1 || iport > 65535) {
2291+ }
2292+ if (*src == ':') {
2293+ port_str = src + 1;
2294+ /* sheck the port part */
2295+ while (*++src) {
2296+ if (!ap_isdigit(*src)) {
2297+ goto bad;
2298+ }
2299+ }
2300+ if (src[-1] == ':')
2301 goto bad;
2302+ else {
2303+ /* a known "good" port value */
2304+ int iport;
2305+ iport = atoi(port_str);
2306+ if (iport < 1 || iport > 65535) {
2307+ goto bad;
2308+ }
2309+ r->parsed_uri.port_str = ap_pstrdup(r->pool, port_str);
2310+ r->parsed_uri.port = iport;
2311 }
2312- r->parsed_uri.port_str = ap_pstrdup(r->pool, port_str);
2313- r->parsed_uri.port = iport;
a3b982d0 2314- break;
2af413f1
JB
2315 }
2316+ *dst++ = *src++;
a3b982d0
JB
2317 }
2318- *dst++ = *src++;
831e4313 2319 }
a3b982d0
JB
2320 /* strip trailing gubbins */
2321 if (dst > host && dst[-1] == '.') {
2af413f1 2322@@ -716,7 +916,7 @@
a3b982d0
JB
2323 bad:
2324 r->status = HTTP_BAD_REQUEST;
2325 ap_log_rerror(APLOG_MARK, APLOG_NOERRNO|APLOG_ERR, r,
2326- "Client sent malformed Host header");
2327+ "Client sent malformed Host header <<%s>>",u);
2328 return;
2329 }
831e4313 2330
2af413f1 2331@@ -819,11 +1019,25 @@
a3b982d0
JB
2332 * names we'll match have ports associated with them
2333 */
2334 const char *host = r->hostname;
2335- unsigned port = ntohs(r->connection->local_addr.sin_port);
2336+ unsigned port;
2337 server_rec *s;
2338 server_rec *last_s;
2339 name_chain *src;
831e4313 2340
a3b982d0
JB
2341+ switch (r->connection->local_addr.ss_family) {
2342+ case AF_INET:
2343+ port = ntohs(((struct sockaddr_in *)
2344+ &r->connection->local_addr)->sin_port);
2345+ break;
412ecbb0 2346+#ifdef INET6
a3b982d0
JB
2347+ case AF_INET6:
2348+ port = ntohs(((struct sockaddr_in6 *)
2349+ &r->connection->local_addr)->sin6_port);
2350+ break;
412ecbb0 2351+#endif
a3b982d0
JB
2352+ default:
2353+ port = 0; /*XXX*/
2354+ }
2355 last_s = NULL;
2356
2357 /* Recall that the name_chain is a list of server_addr_recs, some of
2af413f1 2358@@ -878,7 +1092,22 @@
a3b982d0
JB
2359 server_rec *s;
2360 server_rec *last_s;
2361 name_chain *src;
2362- unsigned port = ntohs(r->connection->local_addr.sin_port);
2363+ unsigned port;
412ecbb0 2364+
a3b982d0
JB
2365+ switch (r->connection->local_addr.ss_family) {
2366+ case AF_INET:
2367+ port = ntohs(((struct sockaddr_in *)
2368+ &r->connection->local_addr)->sin_port);
2369+ break;
412ecbb0 2370+#ifdef INET6
a3b982d0
JB
2371+ case AF_INET6:
2372+ port = ntohs(((struct sockaddr_in6 *)
2373+ &r->connection->local_addr)->sin6_port);
2374+ break;
412ecbb0 2375+#endif
a3b982d0
JB
2376+ default:
2377+ port = 0; /*XXX*/
2378+ }
831e4313 2379
a3b982d0
JB
2380 /*
2381 * This is in conjunction with the ServerPath code in http_core, so we
2af413f1 2382@@ -938,10 +1167,22 @@
a3b982d0
JB
2383 API_EXPORT(void) ap_update_vhost_given_ip(conn_rec *conn)
2384 {
2385 ipaddr_chain *trav;
2386- unsigned port = ntohs(conn->local_addr.sin_port);
2387+ char portbuf[NI_MAXSERV];
2388+ unsigned port;
412ecbb0 2389+
a3b982d0
JB
2390+ if (getnameinfo((struct sockaddr *)&conn->local_addr,
2391+#ifndef SIN6_LEN
2392+ SA_LEN((struct sockaddr *)&conn->local_addr),
2393+#else
2394+ conn->local_addr.ss_len,
412ecbb0 2395+#endif
a3b982d0
JB
2396+ NULL, 0, portbuf, sizeof(portbuf), NI_NUMERICSERV) != 0) {
2397+ goto fail;
2398+ }
2399+ port = atoi(portbuf);
831e4313 2400
a3b982d0
JB
2401 /* scan the hash table for an exact match first */
2402- trav = find_ipaddr(&conn->local_addr.sin_addr, port);
2403+ trav = find_ipaddr((struct sockaddr *)&conn->local_addr);
2404 if (trav) {
2405 /* save the name_chain for later in case this is a name-vhost */
2406 conn->vhost_lookup_data = trav->names;
2af413f1 2407@@ -959,6 +1200,7 @@
a3b982d0
JB
2408 return;
2409 }
831e4313 2410
a3b982d0
JB
2411+fail:
2412 /* otherwise we're stuck with just the main server
2413 * and no name-based vhosts
2414 */
a3b982d0
JB
2415--- apache_1.3.28.orig/src/main/rfc1413.c Mon Feb 3 18:13:23 2003
2416+++ apache_1.3.28/src/main/rfc1413.c Fri Jul 25 12:15:05 2003
2417@@ -82,6 +82,7 @@
2418 #include "http_log.h" /* for aplog_error */
2419 #include "rfc1413.h"
2420 #include "http_main.h" /* set_callback_and_alarm */
2421+#include "sa_len.h"
831e4313 2422
a3b982d0
JB
2423 /* Local stuff. */
2424 /* Semi-well-known port */
2425@@ -109,12 +110,13 @@
2426
2427 /* bind_connect - bind both ends of a socket */
2428 /* Ambarish fix this. Very broken */
2429-static int get_rfc1413(int sock, const struct sockaddr_in *our_sin,
2430- const struct sockaddr_in *rmt_sin,
2431+static int get_rfc1413(int sock, const struct sockaddr *our_sin,
2432+ const struct sockaddr *rmt_sin,
2433 char user[RFC1413_USERLEN+1], server_rec *srv)
2434 {
2435- struct sockaddr_in rmt_query_sin, our_query_sin;
2436- unsigned int rmt_port, our_port;
2437+ struct sockaddr_storage rmt_query_sin, our_query_sin;
2438+ unsigned int o_rmt_port, o_our_port; /* original port pair */
2439+ unsigned int rmt_port, our_port; /* replied port pair */
2440 int i;
2441 char *cp;
2442 char buffer[RFC1413_MAXDATA + 1];
2443@@ -129,16 +131,47 @@
2444 * addresses from the query socket.
412ecbb0 2445 */
412ecbb0 2446
a3b982d0
JB
2447- our_query_sin = *our_sin;
2448- our_query_sin.sin_port = htons(ANY_PORT);
2449-#ifdef MPE
2450- our_query_sin.sin_addr.s_addr = INADDR_ANY;
2451+#ifndef SIN6_LEN
2452+ memcpy(&our_query_sin, our_sin, SA_LEN(our_sin));
2453+ memcpy(&rmt_query_sin, rmt_sin, SA_LEN(rmt_sin));
2454+#else
2455+ memcpy(&our_query_sin, our_sin, our_sin->sa_len);
2456+ memcpy(&rmt_query_sin, rmt_sin, rmt_sin->sa_len);
2457 #endif
2458- rmt_query_sin = *rmt_sin;
2459- rmt_query_sin.sin_port = htons(RFC1413_PORT);
2460+ switch (our_sin->sa_family) {
2461+ case AF_INET:
2462+#ifdef MPE
2463+ ((struct sockaddr_in *)&our_query_sin)->sin_addr.s_addr = INADDR_ANY; /* XXX: htonl(??) */
2464+#endif
2465+ ((struct sockaddr_in *)&our_query_sin)->sin_port = htons(ANY_PORT);
2466+ o_our_port = ntohs(((struct sockaddr_in *)our_sin)->sin_port);
2467+ ((struct sockaddr_in *)&rmt_query_sin)->sin_port = htons(RFC1413_PORT);
2468+ o_rmt_port = ntohs(((struct sockaddr_in *)rmt_sin)->sin_port);
2469+ break;
412ecbb0 2470+#ifdef INET6
a3b982d0
JB
2471+ case AF_INET6:
2472+#ifdef MPE
2473+ memcpy(&((struct sockaddr_in6 *)&our_query_sin)->sin6_addr,
2474+ &in6addr_any, sizeof(struct in6_addr));
831e4313 2475+#endif
a3b982d0
JB
2476+ ((struct sockaddr_in6 *)&our_query_sin)->sin6_port = htons(ANY_PORT);
2477+ o_our_port = ntohs(((struct sockaddr_in6 *)our_sin)->sin6_port);
2478+ ((struct sockaddr_in6 *)&rmt_query_sin)->sin6_port = htons(RFC1413_PORT);
2479+ o_rmt_port = ntohs(((struct sockaddr_in6 *)rmt_sin)->sin6_port);
2480+ break;
2481+#endif
2482+ default:
2483+ /* unsupported AF */
2484+ return -1;
412ecbb0 2485+ }
831e4313 2486
a3b982d0
JB
2487 if (bind(sock, (struct sockaddr *) &our_query_sin,
2488- sizeof(struct sockaddr_in)) < 0) {
412ecbb0 2489+#ifndef SIN6_LEN
a3b982d0 2490+ SA_LEN((struct sockaddr *) &our_query_sin)
412ecbb0 2491+#else
a3b982d0 2492+ our_query_sin.ss_len
412ecbb0 2493+#endif
a3b982d0
JB
2494+ ) < 0) {
2495 ap_log_error(APLOG_MARK, APLOG_CRIT, srv,
2496 "bind: rfc1413: Error binding to local port");
2497 return -1;
2498@@ -149,12 +182,18 @@
2499 * the service
2500 */
2501 if (connect(sock, (struct sockaddr *) &rmt_query_sin,
2502- sizeof(struct sockaddr_in)) < 0)
2503- return -1;
2504+#ifndef SIN6_LEN
2505+ SA_LEN((struct sockaddr *) &rmt_query_sin)
831e4313 2506+#else
a3b982d0 2507+ rmt_query_sin.ss_len
831e4313 2508+#endif
a3b982d0
JB
2509+ ) < 0) {
2510+ return -1;
831e4313 2511+ }
2512
a3b982d0
JB
2513 /* send the data */
2514- buflen = ap_snprintf(buffer, sizeof(buffer), "%u,%u\r\n", ntohs(rmt_sin->sin_port),
2515- ntohs(our_sin->sin_port));
2516+ buflen = ap_snprintf(buffer, sizeof(buffer), "%u,%u\r\n", o_rmt_port,
2517+ o_our_port);
831e4313 2518
a3b982d0
JB
2519 /* send query to server. Handle short write. */
2520 #ifdef CHARSET_EBCDIC
2521@@ -219,9 +258,9 @@
2522 ascii2ebcdic(buffer, buffer, (size_t)i);
2523 #endif
2524 if (sscanf(buffer, "%u , %u : USERID :%*[^:]:%512s", &rmt_port, &our_port,
2525- user) != 3 || ntohs(rmt_sin->sin_port) != rmt_port
2526- || ntohs(our_sin->sin_port) != our_port)
2527+ user) != 3 || o_rmt_port != rmt_port || o_our_port != our_port) {
2528 return -1;
2529+ }
831e4313 2530
a3b982d0
JB
2531 /*
2532 * Strip trailing carriage return. It is part of the
2533@@ -243,7 +282,7 @@
831e4313 2534
a3b982d0 2535 result = FROM_UNKNOWN;
831e4313 2536
a3b982d0
JB
2537- sock = ap_psocket_ex(conn->pool, AF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
2538+ sock = ap_psocket_ex(conn->pool, conn->remote_addr.ss_family, SOCK_STREAM, IPPROTO_TCP, 1);
2539 if (sock < 0) {
2540 ap_log_error(APLOG_MARK, APLOG_CRIT, srv,
2541 "socket: rfc1413: error creating socket");
2542@@ -256,8 +295,10 @@
2543 if (ap_setjmp(timebuf) == 0) {
2544 ap_set_callback_and_alarm(ident_timeout, ap_rfc1413_timeout);
831e4313 2545
a3b982d0
JB
2546- if (get_rfc1413(sock, &conn->local_addr, &conn->remote_addr, user, srv) >= 0)
2547+ if (get_rfc1413(sock, (struct sockaddr *)&conn->local_addr,
2548+ (struct sockaddr *)&conn->remote_addr, user, srv) >= 0) {
2549 result = user;
2550+ }
2551 }
2552 ap_set_callback_and_alarm(NULL, 0);
2553 ap_pclosesocket(conn->pool, sock);
a3b982d0
JB
2554--- apache_1.3.28.orig/src/main/util.c Mon Feb 3 18:13:23 2003
2555+++ apache_1.3.28/src/main/util.c Fri Jul 25 11:01:55 2003
2556@@ -2017,52 +2017,87 @@
2557 * Parses a host of the form <address>[:port]
2558 * :port is permitted if 'port' is not NULL
2559 */
2560-API_EXPORT(unsigned long) ap_get_virthost_addr(char *w, unsigned short *ports)
2561+API_EXPORT(struct sockaddr *) ap_get_virthost_addr(char *w, unsigned short *ports)
2562 {
2563- struct hostent *hep;
2564- unsigned long my_addr;
2565- char *p;
2566-
2567- p = strchr(w, ':');
2568+ static struct sockaddr_storage ss;
2569+ struct addrinfo hints, *res;
2570+ char *p, *r;
2571+ char *host;
2572+ char *port = "0";
2573+ int error;
2574+ char servbuf[NI_MAXSERV];
2575+
2576+ if (w == NULL)
2577+ w = "*";
2578+ p = r = NULL;
2579+ if (*w == '['){
2580+ if (r = strrchr(w+1, ']')){
2581+ *r = '\0';
2582+ p = r + 1;
2583+ switch(*p){
2584+ case ':':
2585+ p++;
2586+ /* nobreak; */
2587+ case '\0':
2588+ w++;
2589+ break;
2590+ default:
2591+ p = NULL;
2592+ }
2593+ }
2594+ }
2595+ else{
2596+ p = strchr(w, ':');
2597+ if (p != NULL && strchr(p+1, ':') != NULL)
2598+ p = NULL;
2599+ }
2600 if (ports != NULL) {
2601- *ports = 0;
2602- if (p != NULL && strcmp(p + 1, "*") != 0)
2603- *ports = atoi(p + 1);
2604+ if (p != NULL && *p && strcmp(p + 1, "*") != 0)
2605+ port = p + 1;
2606 }
831e4313 2607
a3b982d0
JB
2608+ memset(&hints, 0, sizeof(hints));
2609+ hints.ai_socktype = SOCK_STREAM;
2610 if (p != NULL)
2611 *p = '\0';
2612 if (strcmp(w, "*") == 0) {
2613- if (p != NULL)
2614- *p = ':';
2615- return htonl(INADDR_ANY);
2616- }
2617-
2618- my_addr = ap_inet_addr((char *)w);
2619- if (my_addr != INADDR_NONE) {
2620- if (p != NULL)
2621- *p = ':';
2622- return my_addr;
2623+ host = NULL;
2624+ hints.ai_flags = AI_PASSIVE;
2625+ hints.ai_family = ap_default_family;
2626+ } else {
2627+ host = w;
2628+ hints.ai_family = PF_UNSPEC;
2629 }
831e4313 2630
a3b982d0
JB
2631- hep = gethostbyname(w);
2632+ error = getaddrinfo(host, port, &hints, &res);
831e4313 2633
a3b982d0
JB
2634- if ((!hep) || (hep->h_addrtype != AF_INET || !hep->h_addr_list[0])) {
2635- fprintf(stderr, "Cannot resolve host name %s --- exiting!\n", w);
2636+ if (error || !res) {
2637+ fprintf(stderr, "ap_get_vitrhost_addr(): getaddrinfo(%s):%s --- exiting!\n", w, gai_strerror(error));
2638 exit(1);
831e4313 2639 }
412ecbb0 2640
a3b982d0
JB
2641- if (hep->h_addr_list[1]) {
2642- fprintf(stderr, "Host %s has multiple addresses ---\n", w);
2643+ if (res->ai_next) {
2644+ fprintf(stderr, "ap_get_vitrhost_addr(): Host %s has multiple addresses ---\n", w);
2645 fprintf(stderr, "you must choose one explicitly for use as\n");
2646 fprintf(stderr, "a virtual host. Exiting!!!\n");
2647 exit(1);
831e4313 2648 }
2649
a3b982d0
JB
2650+ if (r != NULL)
2651+ *r = ']';
2652 if (p != NULL)
2653 *p = ':';
831e4313 2654
a3b982d0
JB
2655- return ((struct in_addr *) (hep->h_addr))->s_addr;
2656+ memcpy(&ss, res->ai_addr, res->ai_addrlen);
2657+ if (getnameinfo(res->ai_addr, res->ai_addrlen,
2658+ NULL, 0, servbuf, sizeof(servbuf),
2659+ NI_NUMERICSERV)){
2660+ fprintf(stderr, "ap_get_virthost_addr(): getnameinfo() failed --- Exiting!!!\n");
2661+ exit(1);
2662+ }
2663+ if (ports) *ports = atoi(servbuf);
2664+ freeaddrinfo(res);
2665+ return (struct sockaddr *)&ss;
412ecbb0 2666 }
831e4313 2667
831e4313 2668
a3b982d0
JB
2669@@ -2090,7 +2125,8 @@
2670 #endif
2671 char str[MAXHOSTNAMELEN];
2672 char *server_hostname = NULL;
2673- struct hostent *p;
2674+ struct addrinfo hints, *res;
2675+ int error;
831e4313 2676
a3b982d0
JB
2677 #ifdef BEOS /* BeOS returns zero as an error for gethostname */
2678 if (gethostname(str, sizeof(str) - 1) == 0) {
2679@@ -2103,29 +2139,38 @@
2680 }
2681 else
2682 {
2683- str[sizeof(str) - 1] = '\0';
2684- if ((!(p = gethostbyname(str)))
2685- || (!(server_hostname = find_fqdn(a, p)))) {
2686- /* Recovery - return the default servername by IP: */
2687- if (p && p->h_addr_list && p->h_addr_list[0]) {
2688- ap_snprintf(str, sizeof(str), "%pA", p->h_addr_list[0]);
2689- server_hostname = ap_pstrdup(a, str);
2690- /* We will drop through to report the IP-named server */
2691- }
2692- }
2693- else
2694- /* Since we found a fqdn, return it with no logged message. */
2695- return server_hostname;
2696- }
2697-
2698- /* If we don't have an fdqn or IP, fall back to the loopback addr */
2699- if (!server_hostname)
2700- server_hostname = ap_pstrdup(a, "127.0.0.1");
2701-
2702- ap_log_error(APLOG_MARK, APLOG_ALERT|APLOG_NOERRNO, NULL,
2703- "%s: Could not determine the server's fully qualified "
2704- "domain name, using %s for ServerName",
2705- ap_server_argv0, server_hostname);
2706+ str[sizeof(str) - 1] = '\0';
2707+ memset(&hints, 0, sizeof(hints));
2708+ hints.ai_family = PF_UNSPEC;
2709+ hints.ai_flags = AI_CANONNAME;
2710+ error = getaddrinfo(str, NULL, &hints, &res);
2711+ if (error)
2712+ {
2713+ /* Recovery - return the default servername by IP: */
831e4313 2714+
a3b982d0
JB
2715+ fprintf(stderr, "%s: cannot determine local host name.\n",
2716+ ap_server_argv0);
2717+ fprintf(stderr, "Use the ServerName directive to set it manually.\n");
2718+ exit(1);
2719+
2720+ server_hostname = ap_pstrdup(a, res->ai_canonname);
2721+ }
2722+ else if (1) /*fqdn found*/
2723+ {
2724+ /* XXX should check more conditions */
2725+ server_hostname = ap_pstrdup(a, res->ai_canonname);
2726+ }
2727+ else
2728+ {
2729+ ap_log_error(APLOG_MARK, APLOG_ALERT|APLOG_NOERRNO, NULL,
2730+ "%s: Could not determine the server's fully qualified "
2731+ "domain name, using %s for ServerName",
2732+ ap_server_argv0, server_hostname);
2733+ }
2734+
2735+ /* Since we found a fdqn, return it with no logged message. */
2736+ freeaddrinfo(res);
2737+ }
2738
2739 return server_hostname;
2740 }
2741@@ -2369,3 +2414,11 @@
2742 }
2743 *dest = 0;
2744 }
2745+
2746+#ifdef NEED_GETADDRINFO
2747+#include "getaddrinfo.c"
412ecbb0 2748+#endif
831e4313 2749+
a3b982d0
JB
2750+#ifdef NEED_GETNAMEINFO
2751+#include "getnameinfo.c"
412ecbb0 2752+#endif
a3b982d0
JB
2753--- apache_1.3.28.orig/src/main/util_script.c Mon Feb 3 18:13:23 2003
2754+++ apache_1.3.28/src/main/util_script.c Fri Jul 25 11:01:55 2003
2755@@ -67,6 +67,7 @@
2756 #include "http_request.h" /* for sub_req_lookup_uri() */
2757 #include "util_script.h"
2758 #include "util_date.h" /* For parseHTTPdate() */
2759+#include "sa_len.h"
831e4313 2760
a3b982d0
JB
2761 #ifdef OS2
2762 #define INCL_DOS
2763@@ -203,6 +204,7 @@
2764 array_header *hdrs_arr = ap_table_elts(r->headers_in);
2765 table_entry *hdrs = (table_entry *) hdrs_arr->elts;
2766 int i;
2767+ char servbuf[NI_MAXSERV];
831e4313 2768
a3b982d0
JB
2769 /* use a temporary table which we'll overlap onto
2770 * r->subprocess_env later
2771@@ -294,8 +296,16 @@
2772 ap_table_addn(e, "SERVER_ADMIN", s->server_admin); /* Apache */
2773 ap_table_addn(e, "SCRIPT_FILENAME", r->filename); /* Apache */
831e4313 2774
a3b982d0
JB
2775- ap_table_addn(e, "REMOTE_PORT",
2776- ap_psprintf(r->pool, "%d", ntohs(c->remote_addr.sin_port)));
2777+ servbuf[0] = '\0';
2778+ if (!getnameinfo((struct sockaddr *)&c->remote_addr,
2779+#ifndef HAVE_SOCKADDR_LEN
2780+ SA_LEN((struct sockaddr *)&c->remote_addr),
412ecbb0 2781+#else
a3b982d0 2782+ c->remote_addr.ss_len,
831e4313 2783+#endif
a3b982d0
JB
2784+ NULL, 0, servbuf, sizeof(servbuf), NI_NUMERICSERV)){
2785+ ap_table_addn(e, "REMOTE_PORT", ap_pstrdup(r->pool, servbuf));
2786+ }
831e4313 2787
a3b982d0
JB
2788 if (c->user) {
2789 ap_table_addn(e, "REMOTE_USER", c->user);
a3b982d0
JB
2790--- apache_1.3.28.orig/src/main/util_uri.c Mon Feb 3 18:13:24 2003
2791+++ apache_1.3.28/src/main/util_uri.c Fri Jul 25 11:01:55 2003
2792@@ -424,6 +424,12 @@
2793 * the hostname. If there's a port it is the first colon.
2794 */
2795 s = memchr(hostinfo, ':', uri - hostinfo);
2796+ if (*hostinfo == '[') {
2797+ s = memchr(hostinfo+1, ']', uri - hostinfo - 1);
2798+ if (s)
2799+ s = strchr(s, ':');
2800+ } else
2801+ s = memchr(hostinfo, ':', uri - hostinfo);
2802 if (s == NULL) {
2803 /* we expect the common case to have no port */
2804 uptr->hostname = ap_pstrndup(p, hostinfo, uri - hostinfo);
2805@@ -480,7 +486,12 @@
2806 /* We expect hostinfo to point to the first character of
2807 * the hostname. There must be a port, separated by a colon
2808 */
2809- s = strchr(hostinfo, ':');
2810+ if (*hostinfo == '[') {
2811+ s = strchr(hostinfo+1, ']');
2812+ if (s)
2813+ s = strchr(s, ':');
2814+ } else
2815+ s = strchr(hostinfo, ':');
2816 if (s == NULL) {
2817 return HTTP_BAD_REQUEST;
2818 }
a3b982d0
JB
2819--- apache_1.3.28.orig/src/modules/proxy/mod_proxy.c Fri Jul 25 11:00:49 2003
2820+++ apache_1.3.28/src/modules/proxy/mod_proxy.c Fri Jul 25 11:01:55 2003
2821@@ -574,11 +574,31 @@
2822 struct proxy_remote *new;
2823 char *p, *q;
2824 int port;
2825+ char *bl = NULL, *br = NULL;
2826
2827 p = strchr(r, ':');
2828 if (p == NULL || p[1] != '/' || p[2] != '/' || p[3] == '\0')
2829 return "ProxyRemote: Bad syntax for a remote proxy server";
2830- q = strchr(p + 3, ':');
2831+ bl = p + 3;
2832+ if (*bl == '['){
2833+ br = strrchr(bl+1, ']');
2834+ if (br){
2835+ bl++;
2836+ *br = '\0';
2837+ if (*(br+1) == ':'){ /* [host]:xx */
2838+ q = br+1;
a6148d70 2839+ }
a3b982d0
JB
2840+ else if (*(br+1) == '\0'){ /* [host] */
2841+ q = NULL;
2842+ }
2843+ else
2844+ q = strrchr(br, ':'); /* XXX */
2845+ }
2846+ else
2847+ q = strrchr(bl, ':'); /* XXX */
2848+ }
2849+ else
2850+ q = strrchr(bl, ':');
2851 if (q != NULL) {
2852 if (sscanf(q + 1, "%u", &port) != 1 || port > 65535)
2853 return "ProxyRemote: Bad syntax for a remote proxy server (bad port number)";
2854@@ -589,7 +609,7 @@
2855 *p = '\0';
2856 if (strchr(f, ':') == NULL)
2857 ap_str_tolower(f); /* lowercase scheme */
2858- ap_str_tolower(p + 3); /* lowercase hostname */
2859+ ap_str_tolower(bl); /* lowercase hostname */
2860
2861 if (port == -1) {
2862 int i;
2863@@ -602,7 +622,7 @@
2864 new = ap_push_array(conf->proxies);
2865 new->scheme = f;
2866 new->protocol = r;
2867- new->hostname = p + 3;
2868+ new->hostname = bl;
2869 new->port = port;
2870 return NULL;
2871 }
a3b982d0
JB
2872--- apache_1.3.28.orig/src/modules/proxy/mod_proxy.h Mon Feb 3 18:13:26 2003
2873+++ apache_1.3.28/src/modules/proxy/mod_proxy.h Fri Jul 25 11:01:55 2003
2874@@ -310,7 +310,7 @@
2875 int ap_proxy_is_domainname(struct dirconn_entry *This, pool *p);
2876 int ap_proxy_is_hostname(struct dirconn_entry *This, pool *p);
2877 int ap_proxy_is_word(struct dirconn_entry *This, pool *p);
2878-int ap_proxy_doconnect(int sock, struct sockaddr_in *addr, request_rec *r);
2879+int ap_proxy_doconnect(int sock, struct sockaddr *addr, request_rec *r);
2880 int ap_proxy_garbage_init(server_rec *, pool *);
2881 /* This function is called by ap_table_do() for all header lines */
2882 int ap_proxy_send_hdr_line(void *p, const char *key, const char *value);
a3b982d0
JB
2883--- apache_1.3.28.orig/src/modules/proxy/proxy_connect.c Mon Feb 3 18:13:26 2003
2884+++ apache_1.3.28/src/modules/proxy/proxy_connect.c Fri Jul 25 11:27:12 2003
2885@@ -113,14 +113,15 @@
2886 const char *proxyhost, int proxyport)
2887 {
2888 struct sockaddr_in server;
2889- struct in_addr destaddr;
2890- struct hostent server_hp;
2891- const char *host, *err;
2892+ struct addrinfo hints, *res, *res0;
2893+ const char *hoststr;
2894+ const char *portstr = NULL;
2895 char *p;
2896 int port, sock;
2897 char buffer[HUGE_STRING_LEN];
2898- int nbytes, i, j;
2899+ int nbytes, i;
2900 fd_set fds;
2901+ int error;
412ecbb0 2902
a3b982d0
JB
2903 void *sconf = r->server->module_config;
2904 proxy_server_conf *conf =
2905@@ -128,27 +129,59 @@
2906 struct noproxy_entry *npent = (struct noproxy_entry *) conf->noproxies->elts;
412ecbb0 2907
a3b982d0
JB
2908 memset(&server, '\0', sizeof(server));
2909+#ifdef HAVE_SOCKADDR_LEN
2910+ server.sin_len = sizeof(server);
831e4313 2911+#endif
a3b982d0 2912 server.sin_family = AF_INET;
a6148d70 2913
a3b982d0 2914 /* Break the URL into host:port pairs */
831e4313 2915
a3b982d0
JB
2916- host = url;
2917+ hoststr = url;
2918 p = strchr(url, ':');
2919- if (p == NULL)
2920- port = DEFAULT_HTTPS_PORT;
2921- else {
2922- port = atoi(p + 1);
2923+ if (p == NULL) {
2924+ char pbuf[32];
2925+ ap_snprintf(pbuf, sizeof(pbuf), "%d", DEFAULT_HTTPS_PORT);
2926+ portstr = pbuf;
2927+ } else {
2928+ portstr = p + 1;
2929 *p = '\0';
2930 }
2931+ port = atoi(portstr);
2932+
2933+ memset(&hints, 0, sizeof(hints));
2934+ hints.ai_family = PF_UNSPEC;
2935+ hints.ai_socktype = SOCK_STREAM;
2936+ hints.ai_protocol = IPPROTO_TCP;
2937+ error = getaddrinfo(hoststr, portstr, &hints, &res0);
2938+ if (error) {
2939+ return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
2940+ gai_strerror(error)); /* give up */
2941+ }
2942
2943 /* check if ProxyBlock directive on this host */
2944- destaddr.s_addr = ap_inet_addr(host);
2945- for (i = 0; i < conf->noproxies->nelts; i++) {
2946- if ((npent[i].name != NULL && strstr(host, npent[i].name) != NULL)
2947- || destaddr.s_addr == npent[i].addr.s_addr
2948- || npent[i].name[0] == '*')
2949+ for (res = res0; res; res = res = res->ai_next) {
2950+ struct sockaddr_in *sin;
2951+ int fail;
2952+
2953+ fail = 0;
2954+ for (i = 0; i < conf->noproxies->nelts; i++) {
2955+ if (npent[i].name != NULL && strstr(hoststr, npent[i].name))
2956+ fail++;
2957+ if (npent[i].name != NULL && strcmp(npent[i].name, "*") == 0)
2958+ fail++;
2959+ switch (res->ai_family) {
2960+ case AF_INET:
2961+ sin = (struct sockaddr_in *)res->ai_addr;
2962+ if (sin->sin_addr.s_addr == npent[i].addr.s_addr)
2963+ fail++;
2964+ break;
2965+ }
2966+ }
2967+ if (fail) {
2968+ freeaddrinfo(res0);
2969 return ap_proxyerror(r, HTTP_FORBIDDEN,
2970 "Connect to remote machine blocked");
2971+ }
2972 }
2973
2974 /* Check if it is an allowed port */
2975@@ -159,34 +192,42 @@
2976 case DEFAULT_SNEWS_PORT:
2977 break;
2978 default:
2979+ freeaddrinfo(res0);
2980 return HTTP_FORBIDDEN;
2981 }
2982 }
2983- else if (!allowed_port(conf, port))
2984+ else if (!allowed_port(conf, port)) {
2985+ freeaddrinfo(res0);
2986 return HTTP_FORBIDDEN;
2987+ }
2988
2989 if (proxyhost) {
2990+ char pbuf[10];
2991+
2992+ freeaddrinfo(res0);
2993+
2994+ ap_snprintf(pbuf, sizeof(pbuf), "%d", proxyport);
412ecbb0 2995+ memset(&hints, 0, sizeof(hints));
2996+ hints.ai_family = PF_UNSPEC;
a3b982d0
JB
2997+ hints.ai_socktype = SOCK_STREAM;
2998+ hints.ai_protocol = IPPROTO_TCP;
2999+ error = getaddrinfo(proxyhost, pbuf, &hints, &res0);
3000+ if (error)
3001+ return HTTP_INTERNAL_SERVER_ERROR; /* XXX */
3002+
3003 ap_log_error(APLOG_MARK, APLOG_DEBUG | APLOG_NOERRNO, r->server,
3004 "CONNECT to remote proxy %s on port %d", proxyhost, proxyport);
3005 }
3006 else {
3007 ap_log_error(APLOG_MARK, APLOG_DEBUG | APLOG_NOERRNO, r->server,
3008- "CONNECT to %s on port %d", host, port);
3009+ "CONNECT to %s on port %d", hoststr, port);
3010 }
412ecbb0 3011
a3b982d0
JB
3012- /* Nasty cast to work around broken terniary expressions on MSVC */
3013- server.sin_port = htons((unsigned short)(proxyport ? proxyport : port));
3014- err = ap_proxy_host2addr(proxyhost ? proxyhost : host, &server_hp);
3015-
3016- if (err != NULL)
3017- return ap_proxyerror(r,
3018- proxyhost ? HTTP_BAD_GATEWAY : HTTP_INTERNAL_SERVER_ERROR, err);
3019-
3020- sock = ap_psocket_ex(r->pool, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3021- if (sock == -1) {
3022- ap_log_rerror(APLOG_MARK, APLOG_ERR, r, "proxy: error creating socket");
3023- return HTTP_INTERNAL_SERVER_ERROR;
3024- }
3025+ sock = i = -1;
3026+ for (res = res0; res; res = res->ai_next) {
3027+ sock = ap_psocket_ex(r->pool, res->ai_family, res->ai_socktype, res->ai_protocol, 1);
3028+ if (sock == -1)
3029+ continue;
412ecbb0 3030
a3b982d0
JB
3031 #ifdef CHECK_FD_SETSIZE
3032 if (sock >= FD_SETSIZE) {
3033@@ -196,19 +237,15 @@
3034 "found, you probably need to rebuild Apache with a "
3035 "larger FD_SETSIZE", sock, FD_SETSIZE);
3036 ap_pclosesocket(r->pool, sock);
3037- return HTTP_INTERNAL_SERVER_ERROR;
3038+ continue;
831e4313 3039 }
a3b982d0 3040 #endif
831e4313 3041
a3b982d0
JB
3042- j = 0;
3043- while (server_hp.h_addr_list[j] != NULL) {
3044- memcpy(&server.sin_addr, server_hp.h_addr_list[j],
3045- sizeof(struct in_addr));
3046- i = ap_proxy_doconnect(sock, &server, r);
3047+ i = ap_proxy_doconnect(sock, res->ai_addr, r);
3048 if (i == 0)
3049 break;
3050- j++;
3051 }
3052+ freeaddrinfo(res0);
3053 if (i == -1) {
3054 ap_pclosesocket(r->pool, sock);
3055 return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR, ap_pstrcat(r->pool,
a3b982d0
JB
3056--- apache_1.3.28.orig/src/modules/proxy/proxy_ftp.c Mon Feb 3 18:13:26 2003
3057+++ apache_1.3.28/src/modules/proxy/proxy_ftp.c Fri Jul 25 11:18:38 2003
3058@@ -62,6 +62,7 @@
3059 #include "http_main.h"
3060 #include "http_log.h"
3061 #include "http_core.h"
3062+#include "sa_len.h"
412ecbb0 3063
a3b982d0
JB
3064 #define AUTODETECT_PWD
3065
3066@@ -555,8 +556,10 @@
3067 const char *err;
3068 int port, i, j, len, rc, nocache = 0;
3069 int csd = 0, sock = -1, dsock = -1;
3070- struct sockaddr_in server;
3071- struct hostent server_hp;
3072+ struct sockaddr_storage server;
3073+ struct addrinfo hints, *res, *res0;
3074+ char portbuf[10];
3075+ int error;
3076 struct in_addr destaddr;
3077 table *resp_hdrs;
3078 BUFF *ctrl = NULL;
3079@@ -577,11 +580,18 @@
3080 unsigned int presult, h0, h1, h2, h3, p0, p1;
3081 unsigned int paddr;
3082 unsigned short pport;
3083- struct sockaddr_in data_addr;
3084+ struct sockaddr_storage data_addr;
3085+ struct sockaddr_in *sin;
3086 int pasvmode = 0;
3087 char pasv[64];
3088 char *pstr;
3089
3090+/* stuff for LPSV/EPSV */
3091+ unsigned int paf, holen, ho[16], polen, po[2];
3092+ struct sockaddr_in6 *sin6;
3093+ int lpsvmode = 0;
3094+ char *cmd;
412ecbb0 3095+
a3b982d0
JB
3096 /* stuff for responses */
3097 char resp[MAX_STRING_LEN];
3098 char *size = NULL;
3099@@ -658,62 +668,50 @@
3100 if (parms != NULL)
3101 *(parms++) = '\0';
3102
3103- memset(&server, 0, sizeof(struct sockaddr_in));
3104- server.sin_family = AF_INET;
e69938be
JB
3105- server.sin_port = htons((unsigned short)destport);
3106- err = ap_proxy_host2addr(desthost, &server_hp);
a3b982d0
JB
3107- if (err != NULL)
3108- return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR, err);
3109-
3110- sock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3111- if (sock == -1) {
3112- ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3113- "proxy: error creating socket");
3114- return HTTP_INTERNAL_SERVER_ERROR;
e69938be 3115+ ap_snprintf(portbuf, sizeof(portbuf), "%d", destport);
a3b982d0
JB
3116+ memset(&hints, 0, sizeof(hints));
3117+ hints.ai_family = PF_UNSPEC;
3118+ hints.ai_socktype = SOCK_STREAM;
e69938be 3119+ error = getaddrinfo(desthost, portbuf, &hints, &res0);
a3b982d0
JB
3120+ if (error) {
3121+ return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR, gai_strerror(error));
3122 }
3123
3124+ i = -1;
3125+ for (res = res0; res; res = res->ai_next) {
3126+ sock = ap_psocket_ex(p, res->ai_family, res->ai_socktype,
3127+ res->ai_protocol, 1);
3128+ if (sock == -1)
3129+ continue;
23d312ca 3130+
a3b982d0
JB
3131 #if !defined(TPF) && !defined(BEOS)
3132- if (conf->recv_buffer_size > 0
3133- && setsockopt(sock, SOL_SOCKET, SO_RCVBUF,
3134- (const char *)&conf->recv_buffer_size, sizeof(int))
3135- == -1) {
3136- ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3137- "setsockopt(SO_RCVBUF): Failed to set ProxyReceiveBufferSize, using default");
3138- }
3139+ if (conf->recv_buffer_size > 0
3140+ && setsockopt(sock, SOL_SOCKET, SO_RCVBUF,
3141+ (const char *)&conf->recv_buffer_size, sizeof(int))
3142+ == -1) {
3143+ ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3144+ "setsockopt(SO_RCVBUF): Failed to set ProxyReceiveBufferSize, using default");
3145+ }
412ecbb0 3146 #endif
23d312ca 3147
a3b982d0
JB
3148- if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (void *)&one,
3149- sizeof(one)) == -1) {
3150+ if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (void *)&one,
3151+ sizeof(one)) == -1) {
3152 #ifndef _OSD_POSIX /* BS2000 has this option "always on" */
3153- ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3154- "proxy: error setting reuseaddr option: setsockopt(SO_REUSEADDR)");
3155- ap_pclosesocket(p, sock);
3156- return HTTP_INTERNAL_SERVER_ERROR;
3157+ ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3158+ "proxy: error setting reuseaddr option: setsockopt(SO_REUSEADDR)");
3159+ ap_pclosesocket(p, sock);
3160+ freeaddrinfo(res0);
3161+ return HTTP_INTERNAL_SERVER_ERROR;
3162 #endif /* _OSD_POSIX */
3163- }
3164-
3165-#ifdef SINIX_D_RESOLVER_BUG
3166- {
3167- struct in_addr *ip_addr = (struct in_addr *)*server_hp.h_addr_list;
3168-
3169- for (; ip_addr->s_addr != 0; ++ip_addr) {
3170- memcpy(&server.sin_addr, ip_addr, sizeof(struct in_addr));
3171- i = ap_proxy_doconnect(sock, &server, r);
3172- if (i == 0)
3173- break;
3174 }
3175- }
3176-#else
3177- j = 0;
3178- while (server_hp.h_addr_list[j] != NULL) {
3179- memcpy(&server.sin_addr, server_hp.h_addr_list[j],
3180- sizeof(struct in_addr));
3181- i = ap_proxy_doconnect(sock, &server, r);
3182- if (i == 0)
3183+ i = ap_proxy_doconnect(sock, res->ai_addr, r);
3184+ if (i == 0) {
3185+ memcpy(&server, res->ai_addr, res->ai_addrlen);
3186 break;
3187- j++;
3188+ }
3189+ ap_pclosesocket(p, sock);
3190 }
3191-#endif
3192+ freeaddrinfo(res0);
3193 if (i == -1) {
3194 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3195 ap_proxyerror(r, HTTP_BAD_GATEWAY, ap_pstrcat(r->pool,
3196@@ -944,7 +942,7 @@
3197 }
23d312ca 3198
a3b982d0
JB
3199 /* try to set up PASV data connection first */
3200- dsock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3201+ dsock = ap_psocket_ex(p, server.ss_family, SOCK_STREAM, IPPROTO_TCP, 1);
3202 if (dsock == -1) {
3203 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3204 ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3205@@ -961,11 +959,22 @@
3206 }
412ecbb0 3207 #endif
831e4313 3208
a3b982d0
JB
3209- ap_bputs("PASV" CRLF, ctrl);
3210+lpsvagain:
3211+ if (server.ss_family == AF_INET)
3212+ cmd = "PASV";
3213+ else if (lpsvmode)
3214+ cmd = "LPSV";
3215+ else
3216+ cmd = "EPSV";
3217+ ap_bputs(cmd, ctrl);
3218+ ap_bputs(CRLF, ctrl);
3219 ap_bflush(ctrl);
3220+ Explain0("FTP: passive command issued");
3221 ap_log_error(APLOG_MARK, APLOG_DEBUG | APLOG_NOERRNO, r->server, "FTP: PASV command issued");
3222-/* possible results: 227, 421, 500, 501, 502, 530 */
3223+/* possible results: 227, 228, 229, 421, 500, 501, 502, 530 */
3224 /* 227 Entering Passive Mode (h1,h2,h3,h4,p1,p2). */
3225+ /* 228 Entering Long Passive Mode (...). */
3226+ /* 229 Entering Extended Passive Mode (...). */
3227 /* 421 Service not available, closing control connection. */
3228 /* 500 Syntax error, command unrecognized. */
3229 /* 501 Syntax error in parameters or arguments. */
3230@@ -976,7 +985,7 @@
3231 if (i == -1 || i == 421) {
3232 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3233 ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3234- "proxy: PASV: control connection is toast"));
3235+ ap_psprintf(p, "proxy: %s: control connection is toast", cmd)));
3236 }
3237 else {
3238 pasv[i - 1] = '\0';
3239@@ -1004,10 +1013,14 @@
3240 pport = (p1 << 8) + p0;
3241 ap_log_error(APLOG_MARK, APLOG_DEBUG | APLOG_NOERRNO, r->server, "FTP: contacting host %d.%d.%d.%d:%d",
3242 h3, h2, h1, h0, pport);
3243- data_addr.sin_family = AF_INET;
3244- data_addr.sin_addr.s_addr = htonl(paddr);
3245- data_addr.sin_port = htons(pport);
3246- i = ap_proxy_doconnect(dsock, &data_addr, r);
3247+ sin = (struct sockaddr_in *)&data_addr;
3248+ sin->sin_family = AF_INET;
3249+#ifdef SIN6_LEN
3250+ sin->sin_len = sizeof(*sin);
3251+#endif
3252+ sin->sin_addr.s_addr = htonl(paddr);
3253+ sin->sin_port = htons(pport);
3254+ i = ap_proxy_doconnect(dsock, (struct sockaddr *)&data_addr, r);
831e4313 3255
a3b982d0
JB
3256 if (i == -1) {
3257 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3258@@ -1017,6 +1030,64 @@
3259 strerror(errno), NULL)));
3260 }
3261 pasvmode = 1;
3262+ } else if (presult == 228 && pstr != NULL
3263+ && sscanf(pstr,
3264+"%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u,%u",
3265+ &paf, &holen, &ho[0], &ho[1], &ho[2], &ho[3],
3266+ &ho[4], &ho[5], &ho[6], &ho[7], &ho[8], &ho[9], &ho[10], &ho[11],
3267+ &ho[12], &ho[13], &ho[14], &ho[15], &polen, &po[0], &po[1]) == 21
3268+ && paf == 6 && holen == 16 && polen == 2) {
3269+ int i;
3270+ sin6 = (struct sockaddr_in6 *)&data_addr;
3271+ sin6->sin6_family = AF_INET6;
3272+#ifdef SIN6_LEN
3273+ sin6->sin6_len = sizeof(*sin6);
3274+#endif
3275+ for (i = 0; i < 16; i++)
3276+ sin6->sin6_addr.s6_addr[i] = ho[i] & 0xff;
3277+ sin6->sin6_port = htons(((po[0] & 0xff) << 8) | (po[1] & 0xff));
3278+ i = ap_proxy_doconnect(dsock, (struct sockaddr *)&data_addr, r);
3279+
3280+ if (i == -1) {
3281+ return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3282+ ap_proxyerror(r, HTTP_BAD_GATEWAY,
3283+ ap_pstrcat(r->pool,
3284+ "Could not connect to remote machine: ",
3285+ strerror(errno), NULL)));
3286+ }
3287+ pasvmode = 1;
3288+ } else if (presult == 229 && pstr != NULL
3289+ && pstr[0] == pstr[1] && pstr[0] == pstr[2]
3290+ && pstr[0] == pstr[strlen(pstr) - 1]) {
3291+ /* expect "|||port|" */
412ecbb0 3292+#ifndef SIN6_LEN
a3b982d0
JB
3293+ memcpy(&data_addr, &server, SA_LEN((struct sockaddr *)&server));
3294+#else
3295+ memcpy(&data_addr, &server, server.ss_len);
831e4313 3296+#endif
a3b982d0
JB
3297+ switch (data_addr.ss_family) {
3298+ case AF_INET:
3299+ sin = (struct sockaddr_in *)&data_addr;
3300+ sin->sin_port = htons(atoi(pstr + 3));
3301+ break;
3302+ case AF_INET6:
3303+ sin6 = (struct sockaddr_in6 *)&data_addr;
3304+ sin6->sin6_port = htons(atoi(pstr + 3));
3305+ break;
3306+ }
3307+ i = ap_proxy_doconnect(dsock, (struct sockaddr *)&data_addr, r);
3308+
3309+ if (i == -1) {
3310+ return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3311+ ap_proxyerror(r, HTTP_BAD_GATEWAY,
3312+ ap_pstrcat(r->pool,
3313+ "Could not connect to remote machine: ",
3314+ strerror(errno), NULL)));
3315+ }
3316+ pasvmode = 1;
3317+ } else if (!lpsvmode && strcmp(cmd, "EPSV") == 0) {
3318+ lpsvmode = 1;
3319+ goto lpsvagain;
3320 }
3321 else {
3322 ap_pclosesocket(p, dsock); /* and try the regular way */
3323@@ -1025,14 +1096,14 @@
3324 }
831e4313 3325
a3b982d0
JB
3326 if (!pasvmode) { /* set up data connection */
3327- clen = sizeof(struct sockaddr_in);
3328+ clen = sizeof(server);
3329 if (getsockname(sock, (struct sockaddr *)&server, &clen) < 0) {
3330 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3331 ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3332 "proxy: error getting socket address"));
3333 }
831e4313 3334
a3b982d0
JB
3335- dsock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3336+ dsock = ap_psocket_ex(p, server.ss_family, SOCK_STREAM, IPPROTO_TCP, 1);
3337 if (dsock == -1) {
3338 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3339 ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3340@@ -1048,13 +1119,28 @@
3341 #endif /* _OSD_POSIX */
3342 }
831e4313 3343
a3b982d0
JB
3344- if (bind(dsock, (struct sockaddr *)&server,
3345- sizeof(struct sockaddr_in)) == -1) {
412ecbb0 3346+#ifndef SIN6_LEN
a3b982d0 3347+ if (bind(dsock, (struct sockaddr *)&server, SA_LEN((struct sockaddr *)&server)) == -1)
412ecbb0 3348+#else
a3b982d0 3349+ if (bind(dsock, (struct sockaddr *)&server, server.ss_len) == -1)
831e4313 3350+#endif
a3b982d0
JB
3351+ {
3352+ char hostnamebuf[MAXHOSTNAMELEN], portnamebuf[MAXHOSTNAMELEN];
3353+
3354+ getnameinfo((struct sockaddr *)&server,
412ecbb0 3355+#ifndef SIN6_LEN
a3b982d0 3356+ SA_LEN((struct sockaddr *)&server),
412ecbb0 3357+#else
a3b982d0 3358+ server.ss_len,
831e4313 3359+#endif
a3b982d0
JB
3360+ hostnamebuf, sizeof(hostnamebuf),
3361+ portnamebuf, sizeof(portnamebuf),
3362+ NI_NUMERICHOST | NI_NUMERICSERV);
831e4313 3363
a3b982d0
JB
3364 return ftp_cleanup_and_return(r, ctrl, data, sock, dsock,
3365 ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3366- ap_psprintf(p, "proxy: error binding to ftp data socket %s:%d",
3367- inet_ntoa(server.sin_addr), server.sin_port)));
3368+ ap_psprintf(p, "proxy: error binding to ftp data socket %s:%s",
3369+ hostnamebuf, portnamebuf)));
3370 }
3371 listen(dsock, 2); /* only need a short queue */
831e4313 3372 }
a3b982d0 3373@@ -1308,7 +1394,7 @@
831e4313 3374
a3b982d0
JB
3375 if (!pasvmode) { /* wait for connection */
3376 ap_hard_timeout("proxy ftp data connect", r);
3377- clen = sizeof(struct sockaddr_in);
3378+ clen = sizeof(server);
3379 do
3380 csd = accept(dsock, (struct sockaddr *)&server, &clen);
3381 while (csd == -1 && errno == EINTR);
6685e6e0
JB
3382--- apache_1.3.34/src/modules/proxy/proxy_http.c.orig 2005-10-18 09:56:15.000000000 +0200
3383+++ apache_1.3.34/src/modules/proxy/proxy_http.c 2005-10-18 10:15:06.000000000 +0200
2af413f1 3384@@ -113,9 +113,8 @@
a3b982d0
JB
3385 table *req_hdrs, *resp_hdrs;
3386 array_header *reqhdrs_arr;
3387 table_entry *reqhdrs_elts;
3388- struct sockaddr_in server;
3389- struct in_addr destaddr;
3390- struct hostent server_hp;
3391+ struct addrinfo hints, *res, *res0;
3392+ int error;
3393 BUFF *f;
3394 char buffer[HUGE_STRING_LEN];
3395 char portstr[32];
2af413f1 3396@@ -141,9 +140,6 @@
a3b982d0
JB
3397 if (conf->cache.root == NULL)
3398 nocache = 1;
412ecbb0 3399
a3b982d0
JB
3400- memset(&server, '\0', sizeof(server));
3401- server.sin_family = AF_INET;
6685e6e0 3402-
a3b982d0 3403 /* We break the URL into host, port, path-search */
412ecbb0 3404
a3b982d0 3405 urlptr = strstr(url, "://");
2af413f1 3406@@ -151,6 +147,8 @@
a3b982d0
JB
3407 return HTTP_BAD_REQUEST;
3408 urlptr += 3;
3409 destport = DEFAULT_HTTP_PORT;
3410+ ap_snprintf(portstr, sizeof(portstr), "%d", DEFAULT_HTTP_PORT);
3411+ destportstr = portstr;
3412 #ifdef EAPI
3413 ap_hook_use("ap::mod_proxy::http::handler::set_destport",
3414 AP_HOOK_SIG2(int,ptr),
2af413f1 3415@@ -169,7 +167,20 @@
a3b982d0
JB
3416 urlptr = strp;
3417 desthost = q;
3418 }
3419-
3420+ if (*desthost == '['){
3421+ char *u = strrchr(desthost+1, ']');
3422+ if (u){
3423+ desthost++;
3424+ *u = '\0';
3425+ if (*(u+1) == ':'){ /* [host]:xx */
3426+ strp2 = u+1;
3427+ } else if (*(u+1) == '\0'){ /* [host] */
3428+ strp2 = NULL;
3429+ } else
3430+ return HTTP_BAD_REQUEST;
3431+ } else
3432+ return HTTP_BAD_REQUEST;
3433+ } else
3434 strp2 = strchr(desthost, ':');
3435 if (strp2 != NULL) {
3436 *(strp2++) = '\0';
2af413f1 3437@@ -179,46 +190,71 @@
a3b982d0
JB
3438 }
3439 }
412ecbb0 3440
a3b982d0
JB
3441+ memset(&hints, 0, sizeof(hints));
3442+ hints.ai_family = PF_UNSPEC;
3443+ hints.ai_socktype = SOCK_STREAM;
3444+ hints.ai_protocol = IPPROTO_TCP;
3445+ error = getaddrinfo(desthost, destportstr, &hints, &res0);
3446+ if (error) {
3447+ return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR,
3448+ gai_strerror(error)); /* give up */
3449+ }
3450+
3451 /* check if ProxyBlock directive on this host */
3452- destaddr.s_addr = ap_inet_addr(desthost);
3453- for (i = 0; i < conf->noproxies->nelts; i++) {
3454- if (destaddr.s_addr == npent[i].addr.s_addr ||
3455- (npent[i].name != NULL &&
3456- (npent[i].name[0] == '*' || strstr(desthost, npent[i].name) != NULL)))
3457+ for (res = res0; res; res = res->ai_next) {
3458+ struct sockaddr_in *sin;
3459+#ifdef INET6
3460+ struct sockaddr_in6 *sin6;
3461+#endif
3462+ int fail;
3463+
3464+ fail = 0;
3465+ for (i = 0; i < conf->noproxies->nelts; i++) {
3466+ if (npent[i].name != NULL && strstr(desthost, npent[i].name))
3467+ fail++;
3468+ if (npent[i].name != NULL && strcmp(npent[i].name, "*") == 0)
3469+ fail++;
3470+ switch (res->ai_family) {
3471+ case AF_INET:
3472+ sin = (struct sockaddr_in *)res->ai_addr;
3473+ if (sin->sin_addr.s_addr == npent[i].addr.s_addr)
3474+ fail++;
3475+ break;
3476+ }
3477+ }
3478+ if (fail) {
3479+ freeaddrinfo(res0);
3480 return ap_proxyerror(r, HTTP_FORBIDDEN,
3481 "Connect to remote machine blocked");
3482+ }
3483 }
3484
3485 if (proxyhost != NULL) {
3486- server.sin_port = htons((unsigned short)proxyport);
3487- err = ap_proxy_host2addr(proxyhost, &server_hp);
3488- if (err != NULL)
3489+ char pbuf[10];
3490+
3491+ freeaddrinfo(res0);
3492+ ap_snprintf(pbuf, sizeof(pbuf), "%d", proxyport);
3493+ memset(&hints, 0, sizeof(hints));
3494+ hints.ai_family = PF_UNSPEC;
3495+ hints.ai_socktype = SOCK_STREAM;
3496+ hints.ai_protocol = IPPROTO_TCP;
3497+ error = getaddrinfo(proxyhost, pbuf, &hints, &res0);
3498+ if (error)
3499 return DECLINED; /* try another */
3500 #ifdef EAPI
3501 peer = ap_psprintf(p, "%s:%u", proxyhost, proxyport);
3502 #endif
3503 }
3504- else {
3505- server.sin_port = htons((unsigned short)destport);
3506- err = ap_proxy_host2addr(desthost, &server_hp);
3507- if (err != NULL)
3508- return ap_proxyerror(r, HTTP_INTERNAL_SERVER_ERROR, err);
3509-#ifdef EAPI
3510- peer = ap_psprintf(p, "%s:%u", desthost, destport);
3511-#endif
3512- }
3513-
412ecbb0 3514
a3b982d0
JB
3515 /*
3516 * we have worked out who exactly we are going to connect to, now make
3517 * that connection...
3518 */
3519- sock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3520- if (sock == -1) {
3521- ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3522- "proxy: error creating socket");
3523- return HTTP_INTERNAL_SERVER_ERROR;
3524- }
3525+ sock = i = -1;
3526+ for (res = res0; res; res = res->ai_next) {
3527+ sock = ap_psocket_ex(p, res->ai_family, res->ai_socktype, res->ai_protocol, 1);
3528+ if (sock < 0)
3529+ continue;
412ecbb0 3530
a3b982d0
JB
3531 #if !defined(TPF) && !defined(BEOS)
3532 if (conf->recv_buffer_size) {
2af413f1 3533@@ -231,38 +267,13 @@
a3b982d0 3534 }
412ecbb0 3535 #endif
412ecbb0 3536
a3b982d0
JB
3537-#ifdef SINIX_D_RESOLVER_BUG
3538- {
3539- struct in_addr *ip_addr = (struct in_addr *)*server_hp.h_addr_list;
3540-
3541- for (; ip_addr->s_addr != 0; ++ip_addr) {
3542- memcpy(&server.sin_addr, ip_addr, sizeof(struct in_addr));
3543- i = ap_proxy_doconnect(sock, &server, r);
3544- if (i == 0)
3545- break;
2af413f1
JB
3546- /*
3547- * Even if the connection was unsuccesful we should
3548- * reinit the socket
3549- */
3550- sock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
a3b982d0
JB
3551- }
3552- }
3553-#else
3554- j = 0;
3555- while (server_hp.h_addr_list[j] != NULL) {
3556- memcpy(&server.sin_addr, server_hp.h_addr_list[j],
3557- sizeof(struct in_addr));
3558- i = ap_proxy_doconnect(sock, &server, r);
2af413f1 3559+ i = ap_proxy_doconnect(sock, res->ai_addr, r);
a3b982d0
JB
3560 if (i == 0)
3561 break;
2af413f1
JB
3562- /*
3563- * Even if the connection was unsuccesful we should
3564- * reinit the socket
3565- */
3566- sock = ap_psocket_ex(p, PF_INET, SOCK_STREAM, IPPROTO_TCP, 1);
3567+ ap_pclosesocket(p, sock);
3568 j++;
a3b982d0
JB
3569 }
3570-#endif
3571+ freeaddrinfo(res0);
3572 if (i == -1) {
3573 if (proxyhost != NULL)
3574 return DECLINED; /* try again another way */
6685e6e0 3575@@ -591,17 +602,30 @@
a3b982d0 3576 ap_table_set(resp_hdrs, "Content-Location", proxy_location_reverse_map(r, urlstr));
412ecbb0 3577
a3b982d0
JB
3578 /* check if NoCache directive on this host */
3579+ {
3580+ struct sockaddr_in *sin;
412ecbb0 3581+#ifdef INET6
a3b982d0 3582+ struct sockaddr_in6 *sin6;
412ecbb0 3583+#endif
a3b982d0
JB
3584+
3585 if (nocache == 0) {
3586 for (i = 0; i < conf->nocaches->nelts; i++) {
3587- if (destaddr.s_addr == ncent[i].addr.s_addr ||
3588- (ncent[i].name != NULL &&
3589- (ncent[i].name[0] == '*' ||
3590- strstr(desthost, ncent[i].name) != NULL))) {
3591- nocache = 1;
3592- break;
3593+ if (ncent[i].name != NULL &&
3594+ (ncent[i].name[0] == '*' ||
3595+ strstr(desthost, ncent[i].name) != NULL)) {
3596+ nocache = 1;
3597+ break;
3598+ }
3599+ switch (res->ai_addr->sa_family) {
3600+ case AF_INET:
3601+ sin = (struct sockaddr_in *)res->ai_addr;
3602+ if (sin->sin_addr.s_addr == ncent[i].addr.s_addr) {
3603+ nocache = 1;
3604+ break;
3605+ }
3606 }
3607 }
3608-
3609+ }
3610 /*
3611 * update the cache file, possibly even fulfilling the request if it
3612 * turns out a conditional allowed us to serve the object from the
a3b982d0
JB
3613--- apache_1.3.28.orig/src/modules/proxy/proxy_util.c Mon Feb 3 18:13:26 2003
3614+++ apache_1.3.28/src/modules/proxy/proxy_util.c Fri Jul 25 11:01:55 2003
3615@@ -64,6 +64,7 @@
3616 #include "http_log.h"
3617 #include "util_uri.h"
3618 #include "util_date.h" /* get ap_checkmask() decl. */
3619+#include "sa_len.h"
3620
3621 static int proxy_match_ipaddr(struct dirconn_entry *This, request_rec *r);
3622 static int proxy_match_domainname(struct dirconn_entry *This, request_rec *r);
3623@@ -219,6 +220,7 @@
3624 int i;
3625 char *strp, *host, *url = *urlp;
3626 char *user = NULL, *password = NULL;
3627+ char *t = NULL, *u = NULL, *v = NULL;
3628
3629 if (url[0] != '/' || url[1] != '/')
3630 return "Malformed URL";
3631@@ -257,11 +259,22 @@
3632 *passwordp = password;
3633 }
3634
3635- strp = strrchr(host, ':');
3636- if (strp != NULL) {
3637- *(strp++) = '\0';
3638-
3639- for (i = 0; strp[i] != '\0'; i++)
3640+ v = host;
3641+ if (*host == '['){
3642+ u = strrchr(host, ']');
3643+ if (u){
3644+ host++;
3645+ *u = '\0';
3646+ v = u + 1;
3647+ }
3648+ }
3649+ t = strrchr(v, ':');
3650+ if (t){
3651+ *t = '\0';
3652+ strp = t + 1;
3653+ }
3654+ if (strp) {
3655+ for (i=0; strp[i] != '\0'; i++)
3656 if (!ap_isdigit(strp[i]))
3657 break;
3658
3659@@ -280,17 +293,29 @@
3660 return "Missing host in URL";
3661 /* check hostname syntax */
3662 for (i = 0; host[i] != '\0'; i++)
3663- if (!ap_isdigit(host[i]) && host[i] != '.')
3664+ if (!ap_isdigit(host[i]) && host[i] != '.' && host[i] != ':')
3665 break;
3666 /* must be an IP address */
3667 #if defined(WIN32) || defined(NETWARE) || defined(TPF) || defined(BEOS)
3668 if (host[i] == '\0' && (inet_addr(host) == -1))
3669+ return "Bad IP address in URL";
3670+#else
3671+ if (host[i] == '\0') {
3672+ struct addrinfo hints, *res0;
3673+ int gai;
3674+ memset(&hints, 0, sizeof(hints));
3675+ hints.ai_family = PF_UNSPEC;
3676+ hints.ai_flags = AI_NUMERICHOST;
3677+ if (gai = getaddrinfo(host, NULL, &hints, &res0)) {
3678+#if 0
3679+ return gai_strerror(gai);
3680 #else
3681- if (host[i] == '\0' && (ap_inet_addr(host) == -1 || inet_network(host) == -1))
3682+ return "Bad IP address in URL";
412ecbb0 3683 #endif
a3b982d0
JB
3684- {
3685- return "Bad IP address in URL";
3686+ }
3687+ freeaddrinfo(res0);
3688 }
831e4313 3689+#endif
412ecbb0 3690
a3b982d0
JB
3691 /* if (strchr(host,'.') == NULL && domain != NULL)
3692 host = pstrcat(p, host, domain, NULL);
3693@@ -1359,22 +1384,46 @@
3694 return host != NULL && strstr(host, This->name) != NULL;
3695 }
412ecbb0 3696
a3b982d0
JB
3697-int ap_proxy_doconnect(int sock, struct sockaddr_in *addr, request_rec *r)
3698+int ap_proxy_doconnect(int sock, struct sockaddr *addr, request_rec *r)
3699 {
3700 int i;
3701+ int salen;
3702+ char hbuf[NI_MAXHOST], pbuf[NI_MAXSERV];
3703+#ifdef NI_WITHSCOPEID
3704+ const int niflags = NI_NUMERICHOST | NI_NUMERICSERV | NI_WITHSCOPEID;
3705+#else
3706+ const int niflags = NI_NUMERICHOST | NI_NUMERICSERV;
3707+#endif
412ecbb0 3708
a3b982d0
JB
3709 ap_hard_timeout("proxy connect", r);
3710+#ifdef HAVE_SOCKADDR_LEN
3711+ salen = addr->sa_len;
3712+#else
3713+ switch (addr->sa_family) {
3714+ case AF_INET6:
3715+ salen = sizeof(struct sockaddr_in6);
3716+ break;
3717+ default:
3718+ salen = sizeof(struct sockaddr_in);
3719+ break;
3720+ }
3721+#endif
3722 do {
3723- i = connect(sock, (struct sockaddr *)addr, sizeof(struct sockaddr_in));
3724+ i = connect(sock, addr, salen);
3725 #if defined(WIN32) || defined(NETWARE)
3726 if (i == SOCKET_ERROR)
3727 errno = WSAGetLastError();
3728 #endif /* WIN32 */
3729 } while (i == -1 && errno == EINTR);
3730 if (i == -1) {
3731+ if (getnameinfo(addr, salen, hbuf, sizeof(hbuf), pbuf, sizeof(pbuf),
3732+ niflags) != 0) {
3733+ strcpy(hbuf, "?");
3734+ strcpy(pbuf, "?");
831e4313 3735+ }
a3b982d0
JB
3736 ap_log_rerror(APLOG_MARK, APLOG_ERR, r,
3737 "proxy connect to %s port %d failed",
3738- inet_ntoa(addr->sin_addr), ntohs(addr->sin_port));
3739+ hbuf, pbuf);
3740 }
3741 ap_kill_timeout(r);
412ecbb0 3742
2af413f1 3743--- apache_1.3.31/src/modules/standard/mod_access.c.orig Sun Mar 7 22:47:14 2004
6d6006fd 3744+++ apache_1.3.31/src/modules/standard/mod_access.c Sat May 15 00:05:40 2004
2af413f1 3745@@ -31,7 +31,10 @@
a3b982d0
JB
3746 T_ALL,
3747 T_IP,
3748 T_HOST,
3749- T_FAIL
3750+ T_FAIL,
831e4313 3751+#ifdef INET6
a3b982d0 3752+ T_IP6,
831e4313 3753+#endif
a3b982d0
JB
3754 };
3755
3756 typedef struct {
2af413f1
JB
3757@@ -42,6 +45,12 @@
3758 struct in_addr net;
3759 struct in_addr mask;
a3b982d0 3760 } ip;
831e4313 3761+#ifdef INET6
a3b982d0
JB
3762+ struct {
3763+ struct in6_addr net6;
3764+ struct in6_addr mask6;
3765+ } ip6;
412ecbb0 3766+#endif
a3b982d0
JB
3767 } x;
3768 enum allowdeny_type type;
3769 } allowdeny;
6d6006fd 3770@@ -124,94 +133,242 @@
412ecbb0 3771
412ecbb0 3772 }
a3b982d0 3773 else if ((s = strchr(where, '/'))) {
2af413f1 3774- struct in_addr mask;
a3b982d0
JB
3775+ struct addrinfo hints, *resnet, *resmask;
3776+ struct sockaddr_storage net, mask;
3777+ int error;
3778+ char *p;
3779+ int justdigits;
3780
3781- a->type = T_IP;
3782+ a->type = T_FAIL; /*just in case*/
3783 /* trample on where, we won't be using it any more */
3784 *s++ = '\0';
3785
3786- if (!is_ip(where)
2af413f1 3787- || (a->x.ip.net.s_addr = ap_inet_addr(where)) == INADDR_NONE) {
a3b982d0
JB
3788+ justdigits = 0;
3789+ for (p = s; *p; p++) {
3790+ if (!isdigit(*p))
3791+ break;
690e69bd 3792+ }
a3b982d0
JB
3793+ if (!*p)
3794+ justdigits++;
690e69bd 3795+
a3b982d0
JB
3796+ memset(&hints, 0, sizeof(hints));
3797+ hints.ai_family = PF_UNSPEC;
3798+ hints.ai_socktype = SOCK_STREAM; /*dummy*/
3799+#ifdef AI_NUMERICHOST
3800+ hints.ai_flags = AI_NUMERICHOST; /*don't resolve*/
831e4313 3801+#endif
a3b982d0
JB
3802+ resnet = NULL;
3803+ error = getaddrinfo(where, NULL, &hints, &resnet);
3804+ if (error || !resnet) {
3805+ if (resnet)
3806+ freeaddrinfo(resnet);
3807 a->type = T_FAIL;
690e69bd
JB
3808 return "syntax error in network portion of network/netmask";
3809 }
3810-
3811- /* is_ip just tests if it matches [\d.]+ */
3812- if (!is_ip(s)) {
3813+ if (resnet->ai_next) {
3814+ freeaddrinfo(resnet);
3815 a->type = T_FAIL;
2af413f1 3816- return "syntax error in mask portion of network/netmask";
690e69bd 3817+ return "network/netmask resolved to multiple addresses";
412ecbb0 3818 }
2af413f1
JB
3819- /* is it in /a.b.c.d form? */
3820- if (strchr(s, '.')) {
3821- mask.s_addr = ap_inet_addr(s);
3822- if (mask.s_addr == INADDR_NONE) {
3823- a->type = T_FAIL;
3824- return "syntax error in mask portion of network/netmask";
3825- }
690e69bd
JB
3826+ memcpy(&net, resnet->ai_addr, resnet->ai_addrlen);
3827+ freeaddrinfo(resnet);
3828+
a3b982d0
JB
3829+ switch (net.ss_family) {
3830+ case AF_INET:
3831+ a->type = T_IP;
3832+ a->x.ip.net.s_addr = ((struct sockaddr_in *)&net)->sin_addr.s_addr;
3833+ break;
3834+#ifdef INET6
3835+ case AF_INET6:
3836+ a->type = T_IP6;
3837+ memcpy(&a->x.ip6.net6, &((struct sockaddr_in6 *)&net)->sin6_addr,
3838+ sizeof(a->x.ip6.net6));
3839+ break;
412ecbb0 3840+#endif
a3b982d0 3841+ default:
2af413f1 3842+ a->type = T_FAIL;
a3b982d0
JB
3843+ return "unknown address family for network";
3844 }
2af413f1
JB
3845- else {
3846- int i;
3847
3848- /* assume it's in /nnn form */
3849- i = atoi(s);
3850- if (i > 32 || i <= 0) {
a3b982d0
JB
3851+ if (!justdigits) {
3852+ memset(&hints, 0, sizeof(hints));
3853+ hints.ai_family = PF_UNSPEC;
3854+ hints.ai_socktype = SOCK_STREAM; /*dummy*/
3855+#ifdef AI_NUMERICHOST
3856+ hints.ai_flags = AI_NUMERICHOST; /*don't resolve*/
3857+#endif
3858+ resmask = NULL;
3859+ error = getaddrinfo(s, NULL, &hints, &resmask);
3860+ if (error || !resmask) {
3861+ if (resmask)
3862+ freeaddrinfo(resmask);
3863 a->type = T_FAIL;
a3b982d0 3864- return "invalid mask in network/netmask";
690e69bd
JB
3865+ return "syntax error in mask portion of network/netmask";
3866 }
2af413f1
JB
3867- mask.s_addr = 0xFFFFFFFFUL << (32 - i);
3868- mask.s_addr = htonl(mask.s_addr);
a3b982d0
JB
3869- }
3870- a->x.ip.mask = mask;
2af413f1 3871- a->x.ip.net.s_addr = (a->x.ip.net.s_addr & mask.s_addr); /* pjr - This fixes PR 4770 */
a3b982d0
JB
3872- }
3873- else if (ap_isdigit(*where) && is_ip(where)) {
3874- /* legacy syntax for ip addrs: a.b.c. ==> a.b.c.0/24 for example */
3875- int shift;
3876- char *t;
3877- int octet;
3878-
3879- a->type = T_IP;
3880- /* parse components */
3881- s = where;
2af413f1
JB
3882- a->x.ip.net.s_addr = 0;
3883- a->x.ip.mask.s_addr = 0;
a3b982d0
JB
3884- shift = 24;
3885- while (*s) {
3886- t = s;
3887- if (!ap_isdigit(*t)) {
3888+ if (resmask->ai_next) {
3889+ freeaddrinfo(resmask);
3890 a->type = T_FAIL;
3891- return "invalid ip address";
6d6006fd 3892- }
a3b982d0
JB
3893- while (ap_isdigit(*t)) {
3894- ++t;
3895- }
3896- if (*t == '.') {
3897- *t++ = 0;
6d6006fd
JB
3898+ return "network/netmask resolved to multiple addresses";
3899 }
a3b982d0
JB
3900- else if (*t) {
3901+ memcpy(&mask, resmask->ai_addr, resmask->ai_addrlen);
3902+ freeaddrinfo(resmask);
3903+
3904+ if (net.ss_family != mask.ss_family) {
3905 a->type = T_FAIL;
3906- return "invalid ip address";
3907+ return "network/netmask resolved to different address family";
3908 }
3909- if (shift < 0) {
2af413f1 3910- a->type = T_FAIL;
a3b982d0
JB
3911- return "invalid ip address, only 4 octets allowed";
3912+
3913+ switch (a->type) {
3914+ case T_IP:
3915+ a->x.ip.mask.s_addr =
3916+ ((struct sockaddr_in *)&mask)->sin_addr.s_addr;
3917+ break;
3918+#ifdef INET6
3919+ case T_IP6:
3920+ memcpy(&a->x.ip6.mask6,
3921+ &((struct sockaddr_in6 *)&mask)->sin6_addr,
3922+ sizeof(a->x.ip6.mask6));
3923+ break;
831e4313 3924+#endif
412ecbb0 3925 }
a3b982d0
JB
3926- octet = atoi(s);
3927- if (octet < 0 || octet > 255) {
3928- a->type = T_FAIL;
3929- return "each octet must be between 0 and 255 inclusive";
3930+ } else {
3931+ int mask;
3932+ mask = atoi(s);
3933+ switch (a->type) {
3934+ case T_IP:
3935+ if (mask < 0 || 32 < mask) {
3936+ a->type = T_FAIL;
3937+ return "netmask out of range";
3938+ }
3939+ a->x.ip.mask.s_addr = htonl(0xFFFFFFFFUL << (32 - mask));
3940+ break;
3941+#ifdef INET6
3942+ case T_IP6:
3943+ {
3944+ int i;
3945+ if (mask < 0 || 128 < mask) {
3946+ a->type = T_FAIL;
3947+ return "netmask out of range";
3948+ }
3949+ for (i = 0; i < mask / 8; i++) {
3950+ a->x.ip6.mask6.s6_addr[i] = 0xff;
3951+ }
3952+ if (mask % 8)
3953+ a->x.ip6.mask6.s6_addr[i] = 0xff << (8 - (mask % 8));
3954+ break;
3955+ }
3956+#endif
3957 }
2af413f1
JB
3958- a->x.ip.net.s_addr |= (unsigned int)octet << shift;
3959- a->x.ip.mask.s_addr |= 0xFFUL << shift;
a3b982d0
JB
3960- s = t;
3961- shift -= 8;
412ecbb0 3962 }
2af413f1
JB
3963- a->x.ip.net.s_addr = ntohl(a->x.ip.net.s_addr);
3964- a->x.ip.mask.s_addr = ntohl(a->x.ip.mask.s_addr);
6d6006fd
JB
3965+ /* mask network address */
3966+ switch (a->type) {
3967+ case T_IP:
3968+ a->x.ip.net.s_addr &= a->x.ip.mask.s_addr;
3969+ break;
3970+ case T_IP6:
3971+ a->x.ip6.net6.s6_addr32[0] &= a->x.ip6.mask6.s6_addr32[0];
3972+ a->x.ip6.net6.s6_addr32[1] &= a->x.ip6.mask6.s6_addr32[1];
3973+ a->x.ip6.net6.s6_addr32[2] &= a->x.ip6.mask6.s6_addr32[2];
3974+ a->x.ip6.net6.s6_addr32[3] &= a->x.ip6.mask6.s6_addr32[3];
3975+ }
831e4313 3976 }
a3b982d0
JB
3977 else {
3978- a->type = T_HOST;
2af413f1 3979- }
a3b982d0
JB
3980+ struct addrinfo hints, *res;
3981+ struct sockaddr_storage ss;
3982+ int error;
412ecbb0 3983+
a3b982d0
JB
3984+ a->type = T_FAIL; /*just in case*/
3985+
3986+ /* First, try using the old apache code to match */
3987+ /* legacy syntax for ip addrs: a.b.c. ==> a.b.c.0/24 for example */
3988+ if (ap_isdigit(*where) && is_ip(where)) {
3989+ int shift;
3990+ char *t;
3991+ int octet;
3992+
3993+ a->type = T_IP;
3994+ /* parse components */
3995+ s = where;
3996+ a->x.ip.net.s_addr = 0;
3997+ a->x.ip.mask.s_addr = 0;
3998+ shift = 24;
3999+ while (*s) {
4000+ t = s;
4001+ if (!ap_isdigit(*t)) {
4002+ a->type = T_FAIL;
4003+ return "invalid ip address";
4004+ }
4005+ while (ap_isdigit(*t)) {
4006+ ++t;
4007+ }
4008+ if (*t == '.') {
4009+ *t++ = 0;
4010+ }
4011+ else if (*t) {
4012+ a->type = T_FAIL;
4013+ return "invalid ip address";
4014+ }
4015+ if (shift < 0) {
4016+ return "invalid ip address, only 4 octets allowed";
4017+ }
4018+ octet = atoi(s);
4019+ if (octet < 0 || octet > 255) {
4020+ a->type = T_FAIL;
4021+ return "each octet must be between 0 and 255 inclusive";
4022+ }
2af413f1 4023+ a->x.ip.net.s_addr |= (unsigned int)octet << shift;
a3b982d0
JB
4024+ a->x.ip.mask.s_addr |= 0xFFUL << shift;
4025+ s = t;
4026+ shift -= 8;
4027+ }
4028+ a->x.ip.net.s_addr = ntohl(a->x.ip.net.s_addr);
4029+ a->x.ip.mask.s_addr = ntohl(a->x.ip.mask.s_addr);
4030+
4031+ return NULL;
4032+ }
4033+
4034+ /* IPv4/v6 numeric address */
4035+ memset(&hints, 0, sizeof(hints));
4036+ hints.ai_family = PF_UNSPEC;
4037+ hints.ai_socktype = SOCK_STREAM; /*dummy*/
4038+#ifdef AI_NUMERICHOST
4039+ hints.ai_flags = AI_NUMERICHOST; /*don't resolve*/
4040+#endif
4041+ res = NULL;
4042+ error = getaddrinfo(where, NULL, &hints, &res);
4043+ if (error || !res) {
4044+ if (res)
4045+ freeaddrinfo(res);
4046+ a->type = T_HOST;
4047+ return NULL;
4048+ }
4049+ if (res->ai_next) {
4050+ freeaddrinfo(res);
4051+ a->type = T_FAIL;
4052+ return "network/netmask resolved to multiple addresses";
4053+ }
4054+ memcpy(&ss, res->ai_addr, res->ai_addrlen);
4055+ freeaddrinfo(res);
4056+
4057+ switch (ss.ss_family) {
4058+ case AF_INET:
4059+ a->type = T_IP;
4060+ a->x.ip.net.s_addr = ((struct sockaddr_in *)&ss)->sin_addr.s_addr;
4061+ memset(&a->x.ip.mask, 0xff, sizeof(a->x.ip.mask));
4062+ break;
4063+#ifdef INET6
4064+ case AF_INET6:
4065+ a->type = T_IP6;
4066+ memcpy(&a->x.ip6.net6, &((struct sockaddr_in6 *)&ss)->sin6_addr,
4067+ sizeof(a->x.ip6.net6));
4068+ memset(&a->x.ip6.mask6, 0xff, sizeof(a->x.ip6.mask6));
4069+ break;
412ecbb0 4070+#endif
a3b982d0
JB
4071+ default:
4072+ a->type = T_FAIL;
4073+ return "unknown address family for network";
4074+ }
2af413f1 4075+ }
412ecbb0 4076
412ecbb0 4077 return NULL;
2af413f1 4078 }
6d6006fd 4079@@ -275,13 +432,63 @@
a3b982d0 4080 return 1;
831e4313 4081
a3b982d0 4082 case T_IP:
2af413f1 4083- if (ap[i].x.ip.net.s_addr != INADDR_NONE
a3b982d0 4084- && (r->connection->remote_addr.sin_addr.s_addr
2af413f1 4085- & ap[i].x.ip.mask.s_addr) == ap[i].x.ip.net.s_addr) {
a3b982d0
JB
4086- return 1;
4087+ if (ap[i].x.ip.net.s_addr == INADDR_NONE)
4088+ break;
4089+ switch (r->connection->remote_addr.ss_family) {
4090+ case AF_INET:
4091+ if ((((struct sockaddr_in *)&r->connection->remote_addr)->sin_addr.s_addr
4092+ & ap[i].x.ip.mask.s_addr) == ap[i].x.ip.net.s_addr) {
4093+ return 1;
4094+ }
4095+ break;
4096+#ifdef INET6
4097+ case AF_INET6:
4098+ if (!IN6_IS_ADDR_V4MAPPED(&((struct sockaddr_in6 *)&r->connection->remote_addr)->sin6_addr)) /*XXX*/
4099+ break;
4100+ if ((*(ap_uint32_t *)&((struct sockaddr_in6 *)&r->connection->remote_addr)->sin6_addr.s6_addr[12]
4101+ & ap[i].x.ip.mask.s_addr) == ap[i].x.ip.net.s_addr) {
4102+ return 1;
4103+ }
4104+ break;
4105+#endif
2af413f1
JB
4106 }
4107 break;
4108
a3b982d0
JB
4109+#ifdef INET6
4110+ case T_IP6:
4111+ {
4112+ struct in6_addr masked;
4113+ int j;
4114+ if (IN6_IS_ADDR_UNSPECIFIED(&ap[i].x.ip6.net6))
4115+ break;
4116+ switch (r->connection->remote_addr.ss_family) {
4117+ case AF_INET:
4118+ if (!IN6_IS_ADDR_V4MAPPED(&ap[i].x.ip6.net6)) /*XXX*/
4119+ break;
4120+ memset(&masked, 0, sizeof(masked));
4121+ masked.s6_addr[10] = masked.s6_addr[11] = 0xff;
4122+ memcpy(&masked.s6_addr[12],
4123+ &((struct sockaddr_in *)&r->connection->remote_addr)->sin_addr.s_addr,
4124+ sizeof(struct sockaddr_in));
4125+ for (j = 0; j < sizeof(struct in6_addr); j++)
4126+ masked.s6_addr[j] &= ap[i].x.ip6.mask6.s6_addr[j];
4127+ if (memcmp(&masked, &ap[i].x.ip6.net6, sizeof(masked)) == 0)
4128+ return 1;
4129+ break;
4130+ case AF_INET6:
4131+ memset(&masked, 0, sizeof(masked));
4132+ memcpy(&masked,
4133+ &((struct sockaddr_in6 *)&r->connection->remote_addr)->sin6_addr,
4134+ sizeof(masked));
4135+ for (j = 0; j < sizeof(struct in6_addr); j++)
4136+ masked.s6_addr[j] &= ap[i].x.ip6.mask6.s6_addr[j];
4137+ if (memcmp(&masked, &ap[i].x.ip6.net6, sizeof(masked)) == 0)
4138+ return 1;
4139+ break;
2af413f1
JB
4140+ }
4141+ break;
a3b982d0
JB
4142+ }
4143+#endif
a3b982d0
JB
4144 case T_HOST:
4145 if (!gothost) {
2af413f1 4146 remotehost = ap_get_remote_host(r->connection, r->per_dir_config,
a3b982d0
JB
4147--- apache_1.3.28.orig/src/modules/standard/mod_unique_id.c Mon Feb 3 18:13:30 2003
4148+++ apache_1.3.28/src/modules/standard/mod_unique_id.c Fri Jul 25 11:01:55 2003
4149@@ -67,10 +67,22 @@
4150 #include "http_config.h"
4151 #include "http_log.h"
4152 #include "multithread.h"
412ecbb0 4153+#include "sa_len.h"
a3b982d0
JB
4154+
4155+/*#define SHORT_UNIQUE_ID*/
412ecbb0 4156
a3b982d0
JB
4157 typedef struct {
4158 unsigned int stamp;
4159- unsigned int in_addr;
4160+ union {
4161+ struct in_addr in;
4162+#ifdef INET6
4163+# ifdef SHORT_UNIQUE_ID
4164+ ap_uint32_t in6;
4165+# else
4166+ struct in6_addr in6;
4167+# endif
4168+#endif
4169+ } addr;
4170 unsigned int pid;
4171 #ifdef MULTITHREAD
4172 unsigned int tid;
4173@@ -142,7 +154,7 @@
4174 * this shouldn't be a problem till year 2106.
4175 */
412ecbb0 4176
a3b982d0
JB
4177-static unsigned global_in_addr;
4178+static struct sockaddr_storage global_addr;
831e4313 4179
a3b982d0
JB
4180 #ifdef WIN32
4181
4182@@ -221,7 +233,8 @@
4183 #define MAXHOSTNAMELEN 256
412ecbb0 4184 #endif
a3b982d0
JB
4185 char str[MAXHOSTNAMELEN + 1];
4186- struct hostent *hent;
4187+ struct addrinfo hints, *res, *res0;
4188+ int error;
4189 #ifndef NO_GETTIMEOFDAY
4190 struct timeval tv;
4191 #endif
4192@@ -232,8 +245,8 @@
4193 */
4194 unique_id_rec_offset[0] = XtOffsetOf(unique_id_rec, stamp);
4195 unique_id_rec_size[0] = sizeof(cur_unique_id->stamp);
4196- unique_id_rec_offset[1] = XtOffsetOf(unique_id_rec, in_addr);
4197- unique_id_rec_size[1] = sizeof(cur_unique_id->in_addr);
4198+ unique_id_rec_offset[1] = XtOffsetOf(unique_id_rec, addr);
4199+ unique_id_rec_size[1] = sizeof(cur_unique_id->addr);
4200 unique_id_rec_offset[2] = XtOffsetOf(unique_id_rec, pid);
4201 unique_id_rec_size[2] = sizeof(cur_unique_id->pid);
4202 #ifdef MULTITHREAD
4203@@ -269,17 +282,44 @@
4204 }
4205 str[sizeof(str) - 1] = '\0';
4206
4207- if ((hent = gethostbyname(str)) == NULL) {
4208+ memset(&hints, 0, sizeof(hints));
4209+ hints.ai_family = PF_UNSPEC;
4210+ error = getaddrinfo(str, NULL, &hints, &res0);
4211+ if (error) {
4212 ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ALERT, s,
4213- "mod_unique_id: unable to gethostbyname(\"%s\")", str);
4214+ "mod_unique_id: getaddrinfo failed for \"%s\" (%s)", str,
4215+ gai_strerror(error));
4216 exit(1);
4217 }
4218
4219- global_in_addr = ((struct in_addr *) hent->h_addr_list[0])->s_addr;
4220+ error = 1;
4221+ for (res = res0; res; res = res->ai_next) {
4222+ switch (res->ai_family) {
4223+ case AF_INET:
831e4313 4224+#ifdef INET6
a3b982d0 4225+ case AF_INET6:
412ecbb0 4226+#endif
a3b982d0
JB
4227+ memcpy(&global_addr, res->ai_addr, res->ai_addrlen);
4228+ error = 0;
4229+ break;
4230+ }
4231+ }
4232+ freeaddrinfo(res0);
4233+ if (error) {
4234+ ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_ALERT, s,
4235+ "mod_unique_id: no known AF found for \"%s\"", str);
4236+ exit(1);
412ecbb0 4237+ }
4238
a3b982d0 4239+ getnameinfo((struct sockaddr *)&global_addr,
412ecbb0 4240+#ifndef SIN6_LEN
a3b982d0 4241+ SA_LEN((struct sockaddr *)&global_addr),
412ecbb0 4242+#else
a3b982d0 4243+ global_addr.ss_len,
831e4313 4244+#endif
a3b982d0
JB
4245+ str, sizeof(str), NULL, 0, NI_NUMERICHOST);
4246 ap_log_error(APLOG_MARK, APLOG_NOERRNO|APLOG_INFO, s,
4247- "mod_unique_id: using ip addr %s",
4248- inet_ntoa(*(struct in_addr *) hent->h_addr_list[0]));
4249+ "mod_unique_id: using ip addr %s", str);
831e4313 4250
a3b982d0
JB
4251 /*
4252 * If the server is pummelled with restart requests we could possibly end
4253@@ -336,7 +376,23 @@
4254 "oh no! pids are greater than 32-bits! I'm broken!");
4255 }
831e4313 4256
a3b982d0
JB
4257- cur_unique_id->in_addr = global_in_addr;
4258+ memset(&cur_unique_id->addr, 0, sizeof(cur_unique_id->addr));
4259+ switch (global_addr.ss_family) {
4260+ case AF_INET:
4261+ cur_unique_id->addr.in = ((struct sockaddr_in *)&global_addr)->sin_addr;
4262+ break;
4263+#ifdef INET6
4264+ case AF_INET6:
4265+#ifdef SHORT_UNIQUE_ID
4266+ cur_unique_id->addr.in6 =
4267+ ((struct sockaddr_in6 *)&global_addr)->sin6_addr.s6_addr32[3];
4268+#else
4269+ cur_unique_id->addr.in6 =
4270+ ((struct sockaddr_in6 *)&global_addr)->sin6_addr;
4271+#endif
4272+ break;
4273+#endif
412ecbb0 4274+ }
831e4313 4275
412ecbb0 4276 /*
a3b982d0 4277 * If we use 0 as the initial counter we have a little less protection
a3b982d0
JB
4278--- apache_1.3.28.orig/src/support/ab.c Sun Jul 6 19:52:27 2003
4279+++ apache_1.3.28/src/support/ab.c Fri Jul 25 11:01:55 2003
4280@@ -158,6 +158,8 @@
4281 #include <sys/uio.h>
4282 #endif
831e4313 4283
a3b982d0
JB
4284+#include "sa_len.h"
4285+
4286 #endif /* NO_APACHE_INCLUDES */
831e4313 4287
a3b982d0
JB
4288 #ifdef USE_SSL
4289@@ -246,7 +248,7 @@
4290 char servername[1024]; /* name that server reports */
4291 char hostname[1024]; /* host name */
4292 char proxyhost[1024]; /* proxy host name */
4293-int proxyport = 0; /* proxy port */
4294+char *proxyport = NULL; /* proxy port */
4295 int isproxy = 0;
4296 char path[1024]; /* path name */
4297 char postfile[1024]; /* name of file containing post data */
4298@@ -262,7 +264,7 @@
4299 auth[1024], /* optional (basic/uuencoded)
4300 * authentification */
4301 hdrs[4096]; /* optional arbitrary headers */
4302-int port = 80; /* port number */
4303+char *port = "80"; /* port number */
831e4313 4304
a3b982d0
JB
4305 int use_html = 0; /* use html in the report */
4306 char *tablestring;
4307@@ -299,7 +301,7 @@
4308 struct data *stats; /* date for each request */
831e4313 4309
a3b982d0
JB
4310 fd_set readbits, writebits; /* bits for select */
4311-struct sockaddr_in server; /* server addr structure */
4312+struct sockaddr_storage server; /* server addr structure */
831e4313 4313
a3b982d0
JB
4314 #ifndef BEOS
4315 #define ab_close(s) close(s)
4316@@ -525,7 +527,7 @@
4317 printf("\r \r");
4318 printf("Server Software: %s\n", servername);
4319 printf("Server Hostname: %s\n", hostname);
4320- printf("Server Port: %d\n", port);
4321+ printf("Server Port: %s\n", port);
4322 printf("\n");
4323 printf("Document Path: %s\n", path);
4324 printf("Document Length: %d bytes\n", doclen);
4325@@ -878,7 +880,7 @@
4326 c->cbx = 0;
4327 c->gotheader = 0;
9c7dbe42 4328
a3b982d0
JB
4329- c->fd = socket(AF_INET, SOCK_STREAM, 0);
4330+ c->fd = socket(server.ss_family, SOCK_STREAM, 0);
4331 if (c->fd < 0) {
4332 what = "SOCKET";
4333 goto _bad;
4334@@ -895,7 +897,12 @@
412ecbb0 4335
a3b982d0
JB
4336 again:
4337 gettimeofday(&c->start, 0);
4338- if (connect(c->fd, (struct sockaddr *) & server, sizeof(server)) < 0) {
4339+#ifndef SIN6_LEN
4340+ if (connect(c->fd, (struct sockaddr *) & server, SA_LEN((struct sockaddr*)&server)) < 0)
4341+#else
4342+ if (connect(c->fd, (struct sockaddr *) & server, server.ss_len) < 0)
4343+#endif
4344+ {
4345 if (errno != EINPROGRESS) {
4346 what = "CONNECT";
4347 goto _bad;
4348@@ -1189,7 +1196,7 @@
4349 struct timeval timeout, now;
4350 fd_set sel_read, sel_except, sel_write;
4351 long i;
4352- int connectport;
4353+ char * connectport;
4354 char * connecthost;
4355 char * url_on_request;
412ecbb0 4356
a3b982d0
JB
4357@@ -1232,17 +1239,21 @@
4358 }
4359 {
4360 /* get server information */
4361- struct hostent *he;
4362- he = gethostbyname(connecthost);
4363- if (!he) {
4364- char theerror[1024];
4365- ap_snprintf(theerror, sizeof(theerror),
4366- "Bad hostname: %s\n", connecthost);
4367- err(theerror);
4368- }
4369- server.sin_family = he->h_addrtype;
4370- server.sin_port = htons(connectport);
4371- server.sin_addr.s_addr = ((unsigned long *) (he->h_addr_list[0]))[0];
4372+ struct addrinfo hints, *res;
4373+ int error;
831e4313 4374+
a3b982d0
JB
4375+ memset(&hints, 0, sizeof(hints));
4376+ hints.ai_family = PF_UNSPEC;
4377+ hints.ai_socktype = SOCK_STREAM;
4378+ error = getaddrinfo(connecthost, connectport, &hints, &res);
4379+ if (error) {
4380+ char *theerror=malloc(strlen(connecthost)+16);
4381+ sprintf(theerror, "Bad hostname: %s\n", connecthost);
4382+ err(theerror);
4383+ free(theerror);
98e8ae3d 4384+ }
a3b982d0
JB
4385+ memcpy(&server, res->ai_addr, res->ai_addrlen);
4386+ freeaddrinfo(res);
831e4313 4387 }
4388
a3b982d0
JB
4389 con = malloc(concurrency * sizeof(struct connection));
4390@@ -1430,7 +1441,7 @@
4391 if (strlen(purl) > 8 && strncmp(purl, "https://", 8) == 0) {
4392 purl += 8;
4393 ssl = 1;
4394- port = 443;
4395+ port = "443";
412ecbb0 4396 }
a3b982d0
JB
4397 #else
4398 if (strlen(purl) > 8 && strncmp(purl, "https://", 8) == 0) {
4399@@ -1451,15 +1462,15 @@
4400 *cp = '\0';
4401 strcpy(hostname, h);
4402 if (p != NULL)
4403- port = atoi(p);
4404+ port = strdup(p);
831e4313 4405
a3b982d0
JB
4406 if ((
4407 #ifdef USE_SSL
4408- (ssl != 0) && (port != 443)) || ((ssl == 0) &&
4409+ (ssl != 0) && (strcmp(port, "443"))) || ((ssl == 0) &&
412ecbb0 4410 #endif
a3b982d0
JB
4411- (port != 80)))
4412+ (strcmp(port, "80"))))
4413 {
4414- ap_snprintf(colonport,sizeof(colonport),":%d",port);
4415+ ap_snprintf(colonport,sizeof(colonport),":%s",port);
4416 } else {
4417 colonport[0] = '\0';
4418 }
4419@@ -1622,7 +1633,7 @@
4420 if ((p = strchr(optarg, ':'))) {
4421 *p = '\0';
4422 p++;
4423- proxyport = atoi(p);
4424+ proxyport = strdup(p);
4425 };
4426 strcpy(proxyhost, optarg);
4427 isproxy = 1;
4428@@ -1705,3 +1716,7 @@
831e4313 4429
a3b982d0
JB
4430 exit(0);
4431 }
4432+
4433+#ifdef NEED_GETADDRINFO
4434+#include "../main/getaddrinfo.c"
4435+#endif
a3b982d0
JB
4436--- apache_1.3.28.orig/src/support/logresolve.c Wed May 23 00:52:21 2001
4437+++ apache_1.3.28/src/support/logresolve.c Fri Jul 25 11:01:55 2003
4438@@ -54,7 +54,9 @@
4439 #endif /* BEOS */
4440 #endif /* !MPE && !WIN32*/
4441
4442-static void cgethost(struct in_addr ipnum, char *string, int check);
831e4313 4443+#include "sa_len.h"
a3b982d0
JB
4444+
4445+static void cgethost(struct sockaddr *sa, char *string, int check);
4446 static int getline(char *s, int n);
4447 static void stats(FILE *output);
831e4313 4448
a3b982d0
JB
4449@@ -91,7 +93,7 @@
4450 */
831e4313 4451
a3b982d0
JB
4452 struct nsrec {
4453- struct in_addr ipnum;
4454+ struct sockaddr_storage addr;
4455 char *hostname;
4456 int noname;
4457 struct nsrec *next;
4458@@ -122,17 +124,48 @@
4459 * IP numbers with their IP number as hostname, setting noname flag
4460 */
412ecbb0 4461
a3b982d0
JB
4462-static void cgethost (struct in_addr ipnum, char *string, int check)
4463+static void cgethost (struct sockaddr *sa, char *string, int check)
4464 {
4465+ ap_uint32_t hashval;
4466+ struct sockaddr_in *sin;
4467+#ifdef INET6
831e4313 4468+ struct sockaddr_in6 *sin6;
a3b982d0
JB
4469+#endif
4470 struct nsrec **current, *new;
4471- struct hostent *hostdata;
4472 char *name;
4473+ char hostnamebuf[MAXHOSTNAMELEN];
831e4313 4474+
a3b982d0
JB
4475+ switch (sa->sa_family) {
4476+ case AF_INET:
4477+ hashval = ((struct sockaddr_in *)sa)->sin_addr.s_addr;
4478+ break;
4479+#ifdef INET6
4480+ case AF_INET6:
4481+ hashval = *(ap_uint32_t *)&((struct sockaddr_in6 *)sa)->sin6_addr.s6_addr[12];
4482+ break;
4483+#endif
4484+ default:
4485+ hashval = 0;
4486+ break;
4487+ }
4488+
4489+ current = &nscache[((hashval + (hashval >> 8) +
4490+ (hashval >> 16) + (hashval >> 24)) % BUCKETS)];
831e4313 4491
a3b982d0
JB
4492- current = &nscache[((ipnum.s_addr + (ipnum.s_addr >> 8) +
4493- (ipnum.s_addr >> 16) + (ipnum.s_addr >> 24)) % BUCKETS)];
4494+ while (*current) {
4495+#ifndef SIN6_LEN
4496+ if (SA_LEN(sa) == SA_LEN((struct sockaddr *)&(*current)->addr)
4497+ && memcmp(sa, &(*current)->addr, SA_LEN(sa)) == 0)
4498+#else
4499+ if (sa->sa_len == (*current)->addr.ss_len
4500+ && memcmp(sa, &(*current)->addr, sa->sa_len) == 0)
4501+#endif
4502+ {
4503+ break;
4504+ }
831e4313 4505
a3b982d0
JB
4506- while (*current != NULL && ipnum.s_addr != (*current)->ipnum.s_addr)
4507 current = &(*current)->next;
4508+ }
831e4313 4509
a3b982d0
JB
4510 if (*current == NULL) {
4511 cachesize++;
4512@@ -145,45 +178,55 @@
4513 *current = new;
4514 new->next = NULL;
831e4313 4515
a3b982d0
JB
4516- new->ipnum = ipnum;
4517+#ifndef SIN6_LEN
4518+ memcpy(&new->addr, sa, SA_LEN(sa));
4519+#else
4520+ memcpy(&new->addr, sa, sa->sa_len);
831e4313 4521+#endif
4522
a3b982d0
JB
4523- hostdata = gethostbyaddr((const char *) &ipnum, sizeof(struct in_addr),
4524- AF_INET);
4525- if (hostdata == NULL) {
4526- if (h_errno > MAX_ERR)
4527- errors[UNKNOWN_ERR]++;
4528- else
4529- errors[h_errno]++;
4530- new->noname = h_errno;
4531- name = strdup(inet_ntoa(ipnum));
4532- }
4533- else {
4534- new->noname = 0;
4535- name = strdup(hostdata->h_name);
4536- if (check) {
4537- if (name == NULL) {
4538- perror("strdup");
4539- fprintf(stderr, "Insufficient memory\n");
4540- exit(1);
4541- }
4542- hostdata = gethostbyname(name);
4543- if (hostdata != NULL) {
4544- char **hptr;
4545-
4546- for (hptr = hostdata->h_addr_list; *hptr != NULL; hptr++)
4547- if (((struct in_addr *) (*hptr))->s_addr == ipnum.s_addr)
4548- break;
4549- if (*hptr == NULL)
4550- hostdata = NULL;
4551- }
4552- if (hostdata == NULL) {
4553- fprintf(stderr, "Bad host: %s != %s\n", name,
4554- inet_ntoa(ipnum));
4555- new->noname = NO_REVERSE;
4556- free(name);
4557- name = strdup(inet_ntoa(ipnum));
4558- errors[NO_REVERSE]++;
4559+ new->noname = getnameinfo(sa,
4560+#ifndef SIN6_LEN
4561+ SA_LEN(sa),
4562+#else
4563+ sa->sa_len,
831e4313 4564+#endif
a3b982d0
JB
4565+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, 0);
4566+ name = strdup(hostnamebuf);
4567+ if (check) {
4568+ struct addrinfo hints, *res;
4569+ int error;
4570+ memset(&hints, 0, sizeof(hints));
4571+ hints.ai_family = PF_UNSPEC;
4572+ error = getaddrinfo(hostnamebuf, NULL, &hints, &res);
4573+ if (!error) {
4574+ while (res) {
831e4313 4575+#ifndef SIN6_LEN
a3b982d0
JB
4576+ if (SA_LEN(sa) == res->ai_addrlen
4577+ && memcmp(sa, res->ai_addr, SA_LEN(sa)) == 0)
831e4313 4578+#else
a3b982d0
JB
4579+ if (sa->sa_len == res->ai_addrlen
4580+ && memcmp(sa, res->ai_addr, sa->sa_len) == 0)
831e4313 4581+#endif
a3b982d0
JB
4582+ {
4583+ break;
4584+ }
4585+ res = res->ai_next;
4586 }
4587+ if (!res)
4588+ error++;
412ecbb0 4589+ }
a3b982d0
JB
4590+ if (error) {
4591+ getnameinfo(sa,
831e4313 4592+#ifndef SIN6_LEN
a3b982d0 4593+ SA_LEN(sa),
831e4313 4594+#else
a3b982d0 4595+ sa->sa_len,
831e4313 4596+#endif
a3b982d0
JB
4597+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, NI_NUMERICHOST);
4598+ fprintf(stderr, "Bad host: %s != %s\n", name, hostnamebuf);
4599+ new->noname = NO_REVERSE;
4600+ free(name);
4601+ name = strdup(hostnamebuf);
4602 }
4603 }
4604 new->hostname = name;
4605@@ -211,6 +254,7 @@
4606 char *ipstring;
4607 struct nsrec *current;
4608 char *errstring[MAX_ERR + 3];
4609+ char hostnamebuf[MAXHOSTNAMELEN];
4610
4611 for (i = 0; i < MAX_ERR + 3; i++)
4612 errstring[i] = "Unknown error";
4613@@ -242,7 +286,14 @@
4614
4615 for (i = 0; i < BUCKETS; i++)
4616 for (current = nscache[i]; current != NULL; current = current->next) {
4617- ipstring = inet_ntoa(current->ipnum);
4618+ getnameinfo((struct sockaddr *)&current->addr,
412ecbb0 4619+#ifndef SIN6_LEN
a3b982d0 4620+ SA_LEN((struct sockaddr *)&current->addr),
412ecbb0 4621+#else
a3b982d0 4622+ current->addr.ss_len,
412ecbb0 4623+#endif
a3b982d0
JB
4624+ hostnamebuf, sizeof(hostnamebuf), NULL, 0, NI_NUMERICHOST);
4625+ ipstring = hostnamebuf;
4626 if (current->noname == 0)
4627 fprintf(output, " %3d %15s - %s\n", i, ipstring,
4628 current->hostname);
4629@@ -276,9 +327,10 @@
412ecbb0 4630
a3b982d0
JB
4631 int main (int argc, char *argv[])
4632 {
4633- struct in_addr ipnum;
4634 char *bar, hoststring[MAXDNAME + 1], line[MAXLINE], *statfile;
4635 int i, check;
4636+ struct addrinfo hints, *res;
831e4313 4637+ int error;
831e4313 4638
a3b982d0
JB
4639 #ifdef WIN32
4640 WSADATA wsaData;
4641@@ -322,8 +374,10 @@
4642 bar = strchr(line, ' ');
4643 if (bar != NULL)
4644 *bar = '\0';
4645- ipnum.s_addr = inet_addr(line);
4646- if (ipnum.s_addr == 0xffffffffu) {
4647+ memset(&hints, 0, sizeof(hints));
4648+ hints.ai_family = PF_UNSPEC;
4649+ error = getaddrinfo(line, NULL, &hints, &res);
4650+ if (error) {
4651 if (bar != NULL)
4652 *bar = ' ';
4653 puts(line);
4654@@ -333,11 +387,12 @@
831e4313 4655
a3b982d0 4656 resolves++;
831e4313 4657
a3b982d0
JB
4658- cgethost(ipnum, hoststring, check);
4659+ cgethost(res->ai_addr, hoststring, check);
4660 if (bar != NULL)
4661 printf("%s %s\n", hoststring, bar + 1);
4662 else
4663 puts(hoststring);
4664+ freeaddrinfo(res);
412ecbb0 4665 }
831e4313 4666
a3b982d0
JB
4667 #ifdef WIN32
4668@@ -358,3 +413,11 @@
412ecbb0 4669
a3b982d0
JB
4670 return (0);
4671 }
831e4313 4672+
a3b982d0
JB
4673+#ifdef NEED_GETADDRINFO
4674+#include "../main/getaddrinfo.c"
831e4313 4675+#endif
4676+
a3b982d0
JB
4677+#ifdef NEED_GETNAMEINFO
4678+#include "../main/getnameinfo.c"
4679+#endif
4680--- apache_1.3.28/src/modules/standard/mod_usertrack.c.orig Mon Feb 3 18:13:30 2003
4681+++ apache_1.3.28/src/modules/standard/mod_usertrack.c Fri Jul 25 13:13:43 2003
4682@@ -162,7 +162,7 @@
4683 long reqtime = (long) r->request_time;
4684 long clocktime;
4685
4686- unsigned long ipaddr = ntohl(r->connection->remote_addr.sin_addr.s_addr);
4687+ unsigned long ipaddr = ntohl(((struct sockaddr_in*)&r->connection->remote_addr)->sin_addr.s_addr);
4688 const char *rname = ap_get_remote_host(r->connection, r->per_dir_config,
4689 REMOTE_NAME);
4690 dcfg = ap_get_module_config(r->per_dir_config, &usertrack_module);
2af413f1
JB
4691--- apache_1.3.31/src/modules/standard/mod_rewrite.c.orig Wed May 12 14:57:09 2004
4692+++ apache_1.3.31/src/modules/standard/mod_rewrite.c Wed May 12 15:40:04 2004
fe2915d4
JB
4693@@ -48,6 +48,7 @@
4694
4695
4696 #include "mod_rewrite.h"
4697+#include "sa_len.h"
4698
4699 #ifndef NO_WRITEV
4700 #ifndef NETWARE
4701@@ -3651,8 +3652,19 @@
2af413f1
JB
4702 result = r->connection->remote_ip;
4703 }
4704 else if (strcasecmp(var, "REMOTE_PORT") == 0) {
4705- return ap_psprintf(r->pool, "%d",
4706- ntohs(r->connection->remote_addr.sin_port));
4707+ char servbuf[NI_MAXSERV];
4708+ servbuf[0] = '\0';
4709+ if (!getnameinfo((struct sockaddr *)&r->connection->remote_addr,
4710+#ifndef HAVE_SOCKADDR_LEN
4711+ SA_LEN((struct sockaddr *)&r->connection->remote_addr),
4712+#else
4713+ r->connection->remote_addr.ss_len,
4714+#endif
4715+ NULL, 0, servbuf, sizeof(servbuf), NI_NUMERICSERV)) {
4716+ return ap_pstrdup(r->pool, servbuf);
4717+ } else {
4718+ return ap_pstrdup(r->pool, "");
4719+ }
4720 }
4721 else if (strcasecmp(var, "REMOTE_HOST") == 0) {
4722 result = (char *)ap_get_remote_host(r->connection,
This page took 1.181114 seconds and 4 git commands to generate.