1999-01-19 23:59:39 -05:00
|
|
|
require 'mkmf'
|
2000-12-21 22:22:25 -05:00
|
|
|
|
2000-05-13 12:13:31 -04:00
|
|
|
case RUBY_PLATFORM
|
2005-02-09 23:55:34 -05:00
|
|
|
when /(ms|bcc)win32|mingw/
|
2002-06-10 21:27:48 -04:00
|
|
|
test_func = "WSACleanup"
|
|
|
|
have_library("ws2_32", "WSACleanup")
|
1999-08-13 01:37:52 -04:00
|
|
|
when /cygwin/
|
1999-01-19 23:59:39 -05:00
|
|
|
test_func = "socket"
|
|
|
|
when /beos/
|
|
|
|
test_func = "socket"
|
|
|
|
have_library("net", "socket")
|
2008-08-06 16:52:44 -04:00
|
|
|
when /haiku/
|
|
|
|
test_func = "socket"
|
|
|
|
have_library("network", "socket")
|
1999-08-13 01:37:52 -04:00
|
|
|
when /i386-os2_emx/
|
|
|
|
test_func = "socket"
|
|
|
|
have_library("socket", "socket")
|
1998-01-16 07:19:22 -05:00
|
|
|
else
|
|
|
|
test_func = "socket"
|
1999-01-19 23:59:39 -05:00
|
|
|
have_library("nsl", "t_open")
|
1998-01-16 07:19:22 -05:00
|
|
|
have_library("socket", "socket")
|
|
|
|
end
|
1999-08-13 01:37:52 -04:00
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
unless $mswin or $bccwin or $mingw
|
|
|
|
headers = %w<sys/types.h netdb.h string.h sys/socket.h netinet/in.h>
|
|
|
|
end
|
|
|
|
if /solaris/ =~ RUBY_PLATFORM and !try_compile("")
|
|
|
|
# bug of gcc 3.0 on Solaris 8 ?
|
|
|
|
headers << "sys/feature_tests.h"
|
|
|
|
end
|
2006-09-02 15:44:42 -04:00
|
|
|
if have_header("arpa/inet.h")
|
|
|
|
headers << "arpa/inet.h"
|
|
|
|
end
|
2005-02-06 09:51:44 -05:00
|
|
|
|
2006-05-25 19:44:08 -04:00
|
|
|
ipv6 = false
|
2008-08-06 16:52:44 -04:00
|
|
|
default_ipv6 = /cygwin|beos|haiku/ !~ RUBY_PLATFORM
|
2002-06-04 05:33:39 -04:00
|
|
|
if enable_config("ipv6", default_ipv6)
|
2005-02-06 09:51:44 -05:00
|
|
|
if checking_for("ipv6") {try_link(<<EOF)}
|
1999-08-13 01:37:52 -04:00
|
|
|
#include <sys/types.h>
|
|
|
|
#include <sys/socket.h>
|
2008-08-09 19:15:08 -04:00
|
|
|
int
|
1999-08-13 01:37:52 -04:00
|
|
|
main()
|
|
|
|
{
|
|
|
|
socket(AF_INET6, SOCK_STREAM, 0);
|
|
|
|
}
|
|
|
|
EOF
|
2006-05-25 19:44:08 -04:00
|
|
|
$defs << "-DENABLE_IPV6" << "-DINET6"
|
|
|
|
ipv6 = true
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
2006-05-25 19:44:08 -04:00
|
|
|
if ipv6
|
|
|
|
ipv6lib = nil
|
|
|
|
class << (fmt = "unknown")
|
|
|
|
def %(s) s || self end
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
2006-05-25 19:44:08 -04:00
|
|
|
idirs, ldirs = dir_config("inet6", %w[/usr/inet6 /usr/local/v6].find {|d| File.directory?(d)})
|
|
|
|
checking_for("ipv6 type", fmt) do
|
|
|
|
if have_macro("IPV6_INRIA_VERSION", "netinet/in.h")
|
|
|
|
"inria"
|
|
|
|
elsif have_macro("__KAME__", "netinet/in.h")
|
|
|
|
have_library(ipv6lib = "inet6")
|
|
|
|
"kame"
|
|
|
|
elsif have_macro("_TOSHIBA_INET6", "sys/param.h")
|
|
|
|
have_library(ipv6lib = "inet6") and "toshiba"
|
|
|
|
elsif have_macro("__V6D__", "sys/v6config.h")
|
|
|
|
have_library(ipv6lib = "v6") and "v6d"
|
|
|
|
elsif have_macro("_ZETA_MINAMI_INET6", "sys/param.h")
|
|
|
|
have_library(ipv6lib = "inet6") and "zeta"
|
|
|
|
elsif ipv6lib = with_config("ipv6-lib")
|
|
|
|
warn <<EOS
|
|
|
|
--with-ipv6-lib and --with-ipv6-libdir option will be obsolete, use
|
|
|
|
--with-inet6lib and --with-inet6-{include,lib} options instead.
|
1999-08-13 01:37:52 -04:00
|
|
|
EOS
|
2006-05-25 19:44:08 -04:00
|
|
|
find_library(ipv6lib, nil, with_config("ipv6-libdir", ldirs)) and
|
|
|
|
ipv6lib
|
|
|
|
elsif have_library("inet6")
|
|
|
|
"inet6"
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
2006-05-25 19:44:08 -04:00
|
|
|
end or not ipv6lib or abort <<EOS
|
|
|
|
|
|
|
|
Fatal: no #{ipv6lib} library found. cannot continue.
|
|
|
|
You need to fetch lib#{ipv6lib}.a from appropriate
|
|
|
|
ipv6 kit and compile beforehand.
|
|
|
|
EOS
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
if have_struct_member("struct sockaddr_in", "sin_len", headers)
|
|
|
|
$defs[-1] = "-DHAVE_SIN_LEN"
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
# doug's fix, NOW add -Dss_family... only if required!
|
|
|
|
doug = proc {have_struct_member("struct sockaddr_storage", "ss_family", headers)}
|
2005-02-09 23:55:34 -05:00
|
|
|
if (doug[] or
|
2005-02-06 12:12:31 -05:00
|
|
|
with_cppflags($CPPFLAGS + " -Dss_family=__ss_family -Dss_len=__ss_len", &doug))
|
2005-02-06 09:51:44 -05:00
|
|
|
$defs[-1] = "-DHAVE_SOCKADDR_STORAGE"
|
2000-01-31 22:12:21 -05:00
|
|
|
end
|
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
if have_struct_member("struct sockaddr", "sa_len", headers)
|
|
|
|
$defs[-1] = "-DHAVE_SA_LEN "
|
1999-08-13 01:37:52 -04:00
|
|
|
end
|
|
|
|
|
2002-06-04 05:33:39 -04:00
|
|
|
have_header("netinet/tcp.h") if not /cygwin/ =~ RUBY_PLATFORM # for cygwin 1.1.5
|
1999-10-12 00:53:36 -04:00
|
|
|
have_header("netinet/udp.h")
|
1999-08-13 01:37:52 -04:00
|
|
|
|
2003-10-06 07:11:07 -04:00
|
|
|
if have_func("sendmsg") | have_func("recvmsg")
|
2003-10-06 21:04:07 -04:00
|
|
|
have_struct_member('struct msghdr', 'msg_control', ['sys/types.h', 'sys/socket.h'])
|
|
|
|
have_struct_member('struct msghdr', 'msg_accrights', ['sys/types.h', 'sys/socket.h'])
|
2003-07-29 20:32:03 -04:00
|
|
|
end
|
2002-02-28 16:31:35 -05:00
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
getaddr_info_ok = enable_config("wide-getaddrinfo") do
|
|
|
|
checking_for("wide getaddrinfo") {try_run(<<EOF)}
|
|
|
|
#{cpp_include(headers)}
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
|
|
|
#ifndef EXIT_SUCCESS
|
|
|
|
#define EXIT_SUCCESS 0
|
|
|
|
#endif
|
|
|
|
#ifndef EXIT_FAILURE
|
|
|
|
#define EXIT_FAILURE 1
|
|
|
|
#endif
|
1999-08-13 01:37:52 -04:00
|
|
|
|
1999-10-18 05:03:16 -04:00
|
|
|
#ifndef AF_LOCAL
|
|
|
|
#define AF_LOCAL AF_UNIX
|
|
|
|
#endif
|
|
|
|
|
2008-08-09 19:15:08 -04:00
|
|
|
int
|
1999-08-13 01:37:52 -04:00
|
|
|
main()
|
|
|
|
{
|
|
|
|
int passive, gaierr, inet4 = 0, inet6 = 0;
|
|
|
|
struct addrinfo hints, *ai, *aitop;
|
|
|
|
char straddr[INET6_ADDRSTRLEN], strport[16];
|
2008-07-14 00:37:21 -04:00
|
|
|
#ifdef _WIN32
|
|
|
|
WSADATA retdata;
|
|
|
|
|
|
|
|
WSAStartup(MAKEWORD(2, 0), &retdata);
|
|
|
|
#endif
|
1999-08-13 01:37:52 -04:00
|
|
|
|
|
|
|
for (passive = 0; passive <= 1; passive++) {
|
|
|
|
memset(&hints, 0, sizeof(hints));
|
|
|
|
hints.ai_family = AF_UNSPEC;
|
2003-05-06 12:48:51 -04:00
|
|
|
hints.ai_protocol = IPPROTO_TCP;
|
1999-08-13 01:37:52 -04:00
|
|
|
hints.ai_flags = passive ? AI_PASSIVE : 0;
|
|
|
|
hints.ai_socktype = SOCK_STREAM;
|
|
|
|
if ((gaierr = getaddrinfo(NULL, "54321", &hints, &aitop)) != 0) {
|
|
|
|
(void)gai_strerror(gaierr);
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
for (ai = aitop; ai; ai = ai->ai_next) {
|
1999-10-18 05:03:16 -04:00
|
|
|
if (ai->ai_family == AF_LOCAL) continue;
|
2005-06-07 12:33:01 -04:00
|
|
|
if (ai->ai_addr == NULL)
|
|
|
|
goto bad;
|
|
|
|
#if defined(_AIX)
|
2006-11-02 10:38:59 -05:00
|
|
|
if (ai->ai_family == AF_INET6 && passive) {
|
|
|
|
inet6++;
|
|
|
|
continue;
|
|
|
|
}
|
2005-06-07 12:33:01 -04:00
|
|
|
ai->ai_addr->sa_len = ai->ai_addrlen;
|
|
|
|
ai->ai_addr->sa_family = ai->ai_family;
|
|
|
|
#endif
|
|
|
|
if (ai->ai_addrlen == 0 ||
|
1999-08-13 01:37:52 -04:00
|
|
|
getnameinfo(ai->ai_addr, ai->ai_addrlen,
|
|
|
|
straddr, sizeof(straddr), strport, sizeof(strport),
|
|
|
|
NI_NUMERICHOST|NI_NUMERICSERV) != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
if (strcmp(strport, "54321") != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
switch (ai->ai_family) {
|
|
|
|
case AF_INET:
|
|
|
|
if (passive) {
|
|
|
|
if (strcmp(straddr, "0.0.0.0") != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
if (strcmp(straddr, "127.0.0.1") != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
inet4++;
|
|
|
|
break;
|
|
|
|
case AF_INET6:
|
|
|
|
if (passive) {
|
|
|
|
if (strcmp(straddr, "::") != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
if (strcmp(straddr, "::1") != 0) {
|
|
|
|
goto bad;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
inet6++;
|
|
|
|
break;
|
|
|
|
case AF_UNSPEC:
|
|
|
|
goto bad;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
/* another family support? */
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2000-02-23 00:23:12 -05:00
|
|
|
if (!(inet4 == 0 || inet4 == 2))
|
|
|
|
goto bad;
|
|
|
|
if (!(inet6 == 0 || inet6 == 2))
|
1999-08-13 01:37:52 -04:00
|
|
|
goto bad;
|
|
|
|
|
|
|
|
if (aitop)
|
|
|
|
freeaddrinfo(aitop);
|
2005-02-06 09:51:44 -05:00
|
|
|
exit(EXIT_SUCCESS);
|
1999-08-13 01:37:52 -04:00
|
|
|
|
|
|
|
bad:
|
|
|
|
if (aitop)
|
|
|
|
freeaddrinfo(aitop);
|
2005-02-06 09:51:44 -05:00
|
|
|
exit(EXIT_FAILURE);
|
1999-08-13 01:37:52 -04:00
|
|
|
}
|
|
|
|
EOF
|
|
|
|
end
|
2006-05-25 19:44:08 -04:00
|
|
|
if ipv6 and not getaddr_info_ok
|
2005-02-06 09:51:44 -05:00
|
|
|
abort <<EOS
|
1999-08-13 01:37:52 -04:00
|
|
|
|
|
|
|
Fatal: --enable-ipv6 is specified, and your OS seems to support IPv6 feature.
|
|
|
|
But your getaddrinfo() and getnameinfo() are appeared to be broken. Sorry,
|
|
|
|
you cannot compile IPv6 socket classes with broken these functions.
|
2002-06-04 03:34:19 -04:00
|
|
|
You can try --enable-wide-getaddrinfo.
|
1999-08-13 01:37:52 -04:00
|
|
|
EOS
|
|
|
|
end
|
2005-02-06 09:51:44 -05:00
|
|
|
|
2000-05-30 00:24:17 -04:00
|
|
|
case with_config("lookup-order-hack", "UNSPEC")
|
2000-05-18 00:32:13 -04:00
|
|
|
when "INET"
|
2005-02-06 09:51:44 -05:00
|
|
|
$defs << "-DLOOKUP_ORDER_HACK_INET"
|
2000-05-18 00:32:13 -04:00
|
|
|
when "INET6"
|
2005-02-06 09:51:44 -05:00
|
|
|
$defs << "-DLOOKUP_ORDER_HACK_INET6"
|
2000-05-18 00:32:13 -04:00
|
|
|
when "UNSPEC"
|
2000-05-30 00:24:17 -04:00
|
|
|
# nothing special
|
2000-05-18 00:32:13 -04:00
|
|
|
else
|
2005-02-06 09:51:44 -05:00
|
|
|
abort <<EOS
|
2000-05-18 00:32:13 -04:00
|
|
|
|
2000-05-30 00:24:17 -04:00
|
|
|
Fatal: invalid value for --with-lookup-order-hack (expected INET, INET6 or UNSPEC)
|
2000-05-18 00:32:13 -04:00
|
|
|
EOS
|
|
|
|
end
|
1999-08-13 01:37:52 -04:00
|
|
|
|
2009-01-16 23:11:27 -05:00
|
|
|
$objs = [
|
|
|
|
"init.#{$OBJEXT}",
|
|
|
|
"constants.#{$OBJEXT}",
|
|
|
|
"basicsocket.#{$OBJEXT}",
|
|
|
|
"socket.#{$OBJEXT}",
|
|
|
|
"ipsocket.#{$OBJEXT}",
|
|
|
|
"tcpsocket.#{$OBJEXT}",
|
|
|
|
"tcpserver.#{$OBJEXT}",
|
|
|
|
"sockssocket.#{$OBJEXT}",
|
|
|
|
"udpsocket.#{$OBJEXT}",
|
|
|
|
"unixsocket.#{$OBJEXT}",
|
|
|
|
"unixserver.#{$OBJEXT}",
|
2009-02-01 20:53:02 -05:00
|
|
|
"option.#{$OBJEXT}",
|
2009-02-01 21:51:02 -05:00
|
|
|
"ancdata.#{$OBJEXT}",
|
2009-01-16 23:11:27 -05:00
|
|
|
"raddrinfo.#{$OBJEXT}"
|
|
|
|
]
|
1999-08-13 01:37:52 -04:00
|
|
|
|
2009-01-12 12:59:45 -05:00
|
|
|
unless getaddr_info_ok and have_func("getnameinfo", headers) and have_func("getaddrinfo", headers)
|
2005-02-06 09:51:44 -05:00
|
|
|
if have_struct_member("struct in6_addr", "s6_addr8", headers)
|
|
|
|
$defs[-1] = "-DHAVE_ADDR8"
|
|
|
|
end
|
|
|
|
$CPPFLAGS="-I. "+$CPPFLAGS
|
1999-08-13 01:37:52 -04:00
|
|
|
$objs += ["getaddrinfo.#{$OBJEXT}"]
|
|
|
|
$objs += ["getnameinfo.#{$OBJEXT}"]
|
2009-01-13 07:41:12 -05:00
|
|
|
$defs << "-DGETADDRINFO_EMU"
|
1999-08-13 01:37:52 -04:00
|
|
|
have_func("inet_ntop") or have_func("inet_ntoa")
|
|
|
|
have_func("inet_pton") or have_func("inet_aton")
|
2000-07-10 00:49:24 -04:00
|
|
|
have_func("getservbyport")
|
2009-01-13 23:09:05 -05:00
|
|
|
if have_func("gai_strerror")
|
|
|
|
unless checking_for("gai_strerror() returns const pointer") {!try_compile(<<EOF)}
|
|
|
|
#{cpp_include(headers)}
|
|
|
|
#include <stdlib.h>
|
|
|
|
void
|
|
|
|
conftest_gai_strerror_is_const()
|
|
|
|
{
|
|
|
|
*gai_strerror(0) = 0;
|
|
|
|
}
|
|
|
|
EOF
|
|
|
|
$defs << "-DGAI_STRERROR_CONST"
|
|
|
|
end
|
|
|
|
end
|
1999-08-13 01:37:52 -04:00
|
|
|
have_header("arpa/nameser.h")
|
|
|
|
have_header("resolv.h")
|
|
|
|
end
|
|
|
|
|
2009-01-20 06:19:09 -05:00
|
|
|
have_header("ifaddrs.h")
|
|
|
|
have_func("getifaddrs")
|
|
|
|
have_header("sys/ioctl.h")
|
|
|
|
have_header("sys/sockio.h")
|
2009-02-06 21:44:07 -05:00
|
|
|
have_header("net/if.h", headers)
|
2009-01-20 06:19:09 -05:00
|
|
|
|
2009-02-08 10:37:55 -05:00
|
|
|
have_header("sys/param.h", headers)
|
|
|
|
have_header("sys/ucred.h", headers)
|
|
|
|
|
2005-02-06 09:51:44 -05:00
|
|
|
unless have_type("socklen_t", headers)
|
|
|
|
$defs << "-Dsocklen_t=int"
|
2000-05-09 00:53:16 -04:00
|
|
|
end
|
|
|
|
|
1998-01-16 07:13:05 -05:00
|
|
|
have_header("sys/un.h")
|
2002-02-28 16:31:35 -05:00
|
|
|
have_header("sys/uio.h")
|
2009-02-03 11:29:23 -05:00
|
|
|
have_type("struct in_pktinfo", headers) {|src|
|
2009-02-02 17:58:03 -05:00
|
|
|
src.sub(%r'^/\*top\*/', '\1'"\n#if defined(IPPROTO_IP) && defined(IP_PKTINFO)") <<
|
2009-02-03 11:40:42 -05:00
|
|
|
"#else\n" << "#error\n" << ">>>>>> no in_pktinfo <<<<<<\n" << "#endif\n"
|
2009-02-02 17:58:03 -05:00
|
|
|
}
|
2009-02-03 11:29:23 -05:00
|
|
|
have_type("struct in6_pktinfo", headers) {|src|
|
2009-02-02 17:58:03 -05:00
|
|
|
src.sub(%r'^/\*top\*/', '\1'"\n#if defined(IPPROTO_IPV6) && defined(IPV6_PKTINFO)") <<
|
2009-02-03 11:40:42 -05:00
|
|
|
"#else\n" << "#error\n" << ">>>>>> no in6_pktinfo <<<<<<\n" << "#endif\n"
|
2009-02-02 17:58:03 -05:00
|
|
|
}
|
1999-08-13 01:37:52 -04:00
|
|
|
|
2009-02-08 06:36:18 -05:00
|
|
|
have_type("struct sockcred", headers)
|
2009-02-08 07:53:55 -05:00
|
|
|
have_type("struct cmsgcred", headers)
|
2009-02-08 06:36:18 -05:00
|
|
|
|
2009-02-10 20:22:08 -05:00
|
|
|
have_func("getpeereid")
|
|
|
|
|
2009-02-12 07:43:04 -05:00
|
|
|
have_header("ucred.h", headers)
|
|
|
|
have_func("getpeerucred")
|
|
|
|
|
2009-01-22 03:02:41 -05:00
|
|
|
$distcleanfiles << "constants.h" << "constdefs.*"
|
2005-10-17 22:01:24 -04:00
|
|
|
|
1998-01-16 07:19:22 -05:00
|
|
|
if have_func(test_func)
|
1998-01-16 07:13:05 -05:00
|
|
|
have_func("hsterror")
|
2003-10-01 09:41:35 -04:00
|
|
|
have_func("getipnodebyname") or have_func("gethostbyname2")
|
2005-02-06 09:51:44 -05:00
|
|
|
have_func("socketpair")
|
1998-01-16 07:13:05 -05:00
|
|
|
unless have_func("gethostname")
|
|
|
|
have_func("uname")
|
|
|
|
end
|
2003-07-29 14:26:55 -04:00
|
|
|
if enable_config("socks", ENV["SOCKS_SERVER"])
|
1999-09-22 00:30:11 -04:00
|
|
|
if have_library("socks5", "SOCKSinit")
|
2005-02-06 09:51:44 -05:00
|
|
|
$defs << "-DSOCKS5" << "-DSOCKS"
|
1999-09-22 00:30:11 -04:00
|
|
|
elsif have_library("socks", "Rconnect")
|
2005-02-06 09:51:44 -05:00
|
|
|
$defs << "-DSOCKS"
|
1998-01-16 07:13:05 -05:00
|
|
|
end
|
|
|
|
end
|
|
|
|
create_makefile("socket")
|
|
|
|
end
|