You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by mt...@apache.org on 2011/05/04 15:34:13 UTC
svn commit: r1099442 - in /commons/sandbox/runtime/trunk/src/main/native:
Makefile.msc.in Makefile.unx.in configure include/acr/netapi.h
include/acr/netdefs.h include/acr/string.h os/win32/config.hw
shared/netaddr.c shared/string.c
Author: mturk
Date: Wed May 4 13:34:13 2011
New Revision: 1099442
URL: http://svn.apache.org/viewvc?rev=1099442&view=rev
Log:
APR's socladdr
Added:
commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h (with props)
commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h (with props)
commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c (with props)
Modified:
commons/sandbox/runtime/trunk/src/main/native/Makefile.msc.in
commons/sandbox/runtime/trunk/src/main/native/Makefile.unx.in
commons/sandbox/runtime/trunk/src/main/native/configure
commons/sandbox/runtime/trunk/src/main/native/include/acr/string.h
commons/sandbox/runtime/trunk/src/main/native/os/win32/config.hw
commons/sandbox/runtime/trunk/src/main/native/shared/string.c
Modified: commons/sandbox/runtime/trunk/src/main/native/Makefile.msc.in
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/Makefile.msc.in?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/Makefile.msc.in (original)
+++ commons/sandbox/runtime/trunk/src/main/native/Makefile.msc.in Wed May 4 13:34:13 2011
@@ -118,6 +118,7 @@ LIBSOURCES=\
$(TOPDIR)\shared\iofd.c \
$(TOPDIR)\shared\memory.c \
$(TOPDIR)\shared\native.c \
+ $(TOPDIR)\shared\netaddr.c \
$(TOPDIR)\shared\pointer.c \
$(TOPDIR)\shared\psock.c \
$(TOPDIR)\shared\psockimpl.c \
Modified: commons/sandbox/runtime/trunk/src/main/native/Makefile.unx.in
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/Makefile.unx.in?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/Makefile.unx.in (original)
+++ commons/sandbox/runtime/trunk/src/main/native/Makefile.unx.in Wed May 4 13:34:13 2011
@@ -111,6 +111,7 @@ LIBSOURCES=\
$(TOPDIR)/shared/iofd.c \
$(TOPDIR)/shared/memory.c \
$(TOPDIR)/shared/native.c \
+ $(TOPDIR)/shared/netaddr.c \
$(TOPDIR)/shared/pointer.c \
$(TOPDIR)/shared/psock.c \
$(TOPDIR)/shared/psockimpl.c \
Modified: commons/sandbox/runtime/trunk/src/main/native/configure
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/configure?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/configure (original)
+++ commons/sandbox/runtime/trunk/src/main/native/configure Wed May 4 13:34:13 2011
@@ -1086,6 +1086,35 @@ EOF
echo $rc
}
+have_working_getnameinfo()
+{
+ do_printf 'Checking for %-32s' "working getnameinfo"
+ cat > $cccsrc.c << EOF
+#include <netdb.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+int rc = 0;
+int main(void) {
+ struct sockaddr_in sa;
+ char hbuf[256];
+ int error;
+ sa.sin_family = AF_INET;
+ sa.sin_port = 0;
+ sa.sin_addr.s_addr = inet_addr("127.0.0.1");
+#ifdef SIN6_LEN
+ sa.sin_len = sizeof(sa);
+#endif
+ if (getnameinfo((const struct sockaddr *)&sa, sizeof(sa),
+ hbuf, 256, NULL, 0, NI_NUMERICHOST) == 0) rc=1;
+ printf("%d", rc);return 0;
+}
+EOF
+ rc=`test_compile z 0`
+ echo $rc
+}
+
check_sizeof()
{
do_printf 'Checking for sizeof %-25s' "$1"
@@ -1258,6 +1287,7 @@ extern "C" {
#define HAVE_SYS_SIGNALFD_H `have_include sys/signalfd`
#define HAVE_SYS_INOTIFY_H `have_include sys/inotify`
#define HAVE_SYS_TIME_H `have_include sys/time`
+#define HAVE_SYS_UN_H `have_include sys/un`
#define HAVE_LIMITS_H `have_include limits`
#define HAVE_NETDB_H `have_include netdb`
#define HAVE_NETINET_IN_H `have_include netinet/in`
@@ -1340,6 +1370,7 @@ extern "C" {
#define HAVE_STRTOULL `have_function x strtoull`
#define HAVE_STRTONUM `have_function x strtonum`
#define HAVE_SHM_OPEN `have_function x shm_open`
+#define HAVE_GETNAMEINFO `have_working_getnameinfo`
#define HAVE_GETHOSTBYADDR_R `have_function x gethostbyaddr_r`
#define HAVE_GETHOSTBYNAME2 `have_function x gethostbyname2`
#define HAVE_GETHOSTBYNAME_R `have_function x gethostbyname_r`
@@ -1363,6 +1394,7 @@ extern "C" {
#define HAVE_INTPTR_T `have_typedef intptr_t`
#define HAVE_UINTPTR_T `have_typedef uintptr_t`
#define HAVE_UNION_SEMUN `have_typedef 'union semun' sys/sem`
+#define HAVE_SOCKADDR_STORAGE `have_typedef 'struct sockaddr_storage' netinet/in`
#define HAVE_PRETTY_FUNCTION `have_defined __PRETTY_FUNCTION__`
#define HAVE_FUNCTION `have_defined __FUNCTION__`
#define HAVE_FUNCSIG `have_defined __FUNCSIG__`
Added: commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h?rev=1099442&view=auto
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h (added)
+++ commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h Wed May 4 13:34:13 2011
@@ -0,0 +1,72 @@
+/* Copyright (c) 2011 The MyoMake Project <http://www.myomake.org>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef _ACR_NETAPI_H_
+#define _ACR_NETAPI_H_
+
+#include "acr/stdtypes.h"
+#include "acr/netdefs.h"
+
+typedef struct acr_sockaddr_t acr_sockaddr_t;
+struct acr_sockaddr_t {
+ /** The hostname */
+ char hostname[256];
+ /** Either a string of the port number or the service name for the port */
+ char servname[256];
+ /** The numeric port */
+ int port;
+ /** The family */
+ int family;
+ /** How big is the sockaddr we're using? */
+ int salen;
+ /** How big is the ip address structure we're using? */
+ int iplen;
+ /** How big should the address buffer be? 16 for v4 or 46 for v6
+ * used in inet_ntop... */
+ int addrlen;
+ /** This points to the IP address structure within the appropriate
+ * sockaddr structure. */
+ void *ipaddr;
+ /** If multiple addresses were found by AcrGetSockaddrInfo(), this
+ * points to a representation of the next address. */
+ acr_sockaddr_t *next;
+ /** Union of either IPv4 or IPv6 sockaddr. */
+ union {
+ /** IPv4 sockaddr structure */
+ struct sockaddr_in sin;
+ /** IPv6 sockaddr structure */
+ struct sockaddr_in6 sin6;
+#if HAVE_SOCKADDR_STORAGE
+ /** Placeholder to ensure that the size of this union is not
+ * dependent on whether APR_HAVE_IPV6 is defined. */
+ struct sockaddr_storage sas;
+#endif
+#if HAVE_SYS_UN_H
+ /** Unix domain socket sockaddr structure */
+ struct sockaddr_un unx;
+#endif
+ } sa;
+};
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _ACR_NETAPI_H_ */
Propchange: commons/sandbox/runtime/trunk/src/main/native/include/acr/netapi.h
------------------------------------------------------------------------------
svn:eol-style = native
Added: commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h?rev=1099442&view=auto
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h (added)
+++ commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h Wed May 4 13:34:13 2011
@@ -0,0 +1,58 @@
+/* Copyright (c) 2011 The MyoMake Project <http://www.myomake.org>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef _ACR_NETDEFS_H_
+#define _ACR_NETDEFS_H_
+
+#if HAVE_SYS_UN_H
+# if !defined(AF_LOCAL)
+# if defined(AF_UNIX)
+# define AF_LOCAL AF_UNIX
+# else
+# error "Neither AF_UNIX nor AF_LOCAL is defined"
+# endif
+# endif
+#else
+# define AF_LOCAL 127
+#endif
+
+#if !defined(AF_UNSPEC)
+# define AF_UNSPEC 0
+#endif
+
+#if !defined(INADDR_NONE)
+# define INADDR_NONE ((unsigned int) 0xffffffff)
+#endif
+
+#ifndef IN6ADDRSZ
+#define IN6ADDRSZ 16
+#endif
+#ifndef INADDRSZ
+#define INADDRSZ 4
+#endif
+#ifndef INT16SZ
+#define INT16SZ 2
+#endif
+
+#if !defined(EAFNOSUPPORT) && defined(WSAEAFNOSUPPORT)
+#define EAFNOSUPPORT WSAEAFNOSUPPORT
+#endif
+
+#define ACR_IPV4_ADDR_OK 0x01
+#define ACR_IPV6_ADDR_OK 0x02
+
+
+#endif /* _ACR_IODEFS_H */
Propchange: commons/sandbox/runtime/trunk/src/main/native/include/acr/netdefs.h
------------------------------------------------------------------------------
svn:eol-style = native
Modified: commons/sandbox/runtime/trunk/src/main/native/include/acr/string.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/include/acr/string.h?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/include/acr/string.h (original)
+++ commons/sandbox/runtime/trunk/src/main/native/include/acr/string.h Wed May 4 13:34:13 2011
@@ -225,6 +225,11 @@ wchar_t *
AcrGetNativePathW(JNI_STDENV, jstring str, wchar_t *b);
#endif
+/** Convert n to string
+ * buf must be of size 16
+ */
+char *AcrItoa(char *buf, int n);
+
#ifdef __cplusplus
}
#endif
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/config.hw
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/config.hw?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/config.hw (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/config.hw Wed May 4 13:34:13 2011
@@ -28,6 +28,7 @@
#define HAVE_SYS_SIGNALFD_H 0
#define HAVE_SYS_INOTIFY_H 0
#define HAVE_SYS_TIME_H 0
+#define HAVE_SYS_UN_H 0
#define HAVE_LIMITS_H 1
#define HAVE_NETDB_H 0
#define HAVE_NETINET_IN_H 0
@@ -131,6 +132,7 @@
#define HAVE_INTPTR_T 1
#define HAVE_UINTPTR_T 1
#define HAVE_UNION_SEMUN 0
+#define HAVE_SOCKADDR_STORAGE 1
#define HAVE_PRETTY_FUNCTION 0
#define HAVE_FUNCTION 1
#define HAVE_FUNC 0
Added: commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c?rev=1099442&view=auto
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c (added)
+++ commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c Wed May 4 13:34:13 2011
@@ -0,0 +1,721 @@
+/* Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/*
+ *
+ * @author Mladen Turk
+ */
+
+#include "acr/netapi.h"
+#include "acr/memory.h"
+#include "acr/string.h"
+#include "acr/port.h"
+
+#define V4MAPPED_EQUAL(a,b) \
+ ((a)->sa.sin.sin_family == AF_INET && \
+ (b)->sa.sin.sin_family == AF_INET6 && \
+ IN6_IS_ADDR_V4MAPPED((struct in6_addr *)(b)->ipaddr) && \
+ memcmp((a)->ipaddr, \
+ &((struct in6_addr *)(b)->ipaddr)->s6_addr[12], \
+ (a)->iplen) == 0)
+
+#if !defined(WINDOWS)
+# if defined(HAVE_SET_H_ERRNO)
+# define SET_H_ERRNO(newval) set_h_errno(newval)
+# else
+# define SET_H_ERRNO(newval) h_errno = (newval)
+# endif
+#else
+# define SET_H_ERRNO(newval)
+#endif
+
+/* const char *
+ * inet_ntop4(src, dst, size)
+ * format an IPv4 address, more or less like inet_ntoa()
+ * return:
+ * `dst' (as a const)
+ * notes:
+ * (1) uses no statics
+ * (2) takes a u_char* not an in_addr as input
+ * author:
+ * Paul Vixie, 1996.
+ */
+static const char *
+inet_ntop4(const unsigned char *src, char *dst, int size)
+{
+ int MIN_SIZE = 16; /* space for 255.255.255.255\0 */
+ int n = 0;
+ char *next = dst;
+
+ if (size < MIN_SIZE) {
+ ACR_SET_OS_ERROR(ACR_ENOSPC);
+ return 0;
+ }
+ do {
+ unsigned char u = *src++;
+ if (u > 99) {
+ *next++ = '0' + u/100;
+ u %= 100;
+ *next++ = '0' + u/10;
+ u %= 10;
+ }
+ else if (u > 9) {
+ *next++ = '0' + u/10;
+ u %= 10;
+ }
+ *next++ = '0' + u;
+ *next++ = '.';
+ n++;
+ } while (n < 4);
+ *--next = 0;
+ return dst;
+}
+
+/* const char *
+ * inet_ntop6(src, dst, size)
+ * convert IPv6 binary address into presentation (printable) format
+ * author:
+ * Paul Vixie, 1996.
+ */
+static const char *
+inet_ntop6(const unsigned char *src, char *dst, int size)
+{
+ /*
+ * Note that int32_t and int16_t need only be "at least" large enough
+ * to contain a value of the specified size. On some systems, like
+ * Crays, there is no such thing as an integer variable with 16 bits.
+ * Keep this in mind if you think this function should have been coded
+ * to use pointer overlays. All the world's not a VAX.
+ */
+ char tmp[sizeof("ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255")], *tp;
+ struct { int base, len; } best = {-1, 0}, cur = {-1, 0};
+ unsigned int words[IN6ADDRSZ / INT16SZ];
+ int i;
+ const unsigned char *next_src, *src_end;
+ unsigned int *next_dest;
+
+ /*
+ * Preprocess:
+ * Copy the input (bytewise) array into a wordwise array.
+ * Find the longest run of 0x00's in src[] for :: shorthanding.
+ */
+ next_src = src;
+ src_end = src + IN6ADDRSZ;
+ next_dest = words;
+ i = 0;
+ do {
+ unsigned int next_word = (unsigned int)*next_src++;
+ next_word <<= 8;
+ next_word |= (unsigned int)*next_src++;
+ *next_dest++ = next_word;
+
+ if (next_word == 0) {
+ if (cur.base == -1) {
+ cur.base = i;
+ cur.len = 1;
+ }
+ else {
+ cur.len++;
+ }
+ } else {
+ if (cur.base != -1) {
+ if (best.base == -1 || cur.len > best.len) {
+ best = cur;
+ }
+ cur.base = -1;
+ }
+ }
+
+ i++;
+ } while (next_src < src_end);
+
+ if (cur.base != -1) {
+ if (best.base == -1 || cur.len > best.len) {
+ best = cur;
+ }
+ }
+ if (best.base != -1 && best.len < 2) {
+ best.base = -1;
+ }
+
+ /*
+ * Format the result.
+ */
+ tp = tmp;
+ for (i = 0; i < (IN6ADDRSZ / INT16SZ);) {
+ /* Are we inside the best run of 0x00's? */
+ if (i == best.base) {
+ *tp++ = ':';
+ i += best.len;
+ continue;
+ }
+ /* Are we following an initial run of 0x00s or any real hex? */
+ if (i != 0) {
+ *tp++ = ':';
+ }
+ /* Is this address an encapsulated IPv4? */
+ if (i == 6 && best.base == 0 &&
+ (best.len == 6 || (best.len == 5 && words[5] == 0xffff))) {
+ if (!inet_ntop4(src+12, tp, sizeof(tmp) - (tp - tmp))) {
+ return 0;
+ }
+ tp += strlen(tp);
+ break;
+ }
+ tp += snprintf(tp, sizeof(tmp) - (tp - tmp), "%x", words[i]);
+ i++;
+ }
+ /* Was it a trailing run of 0x00's? */
+ if (best.base != -1 && (best.base + best.len) == (IN6ADDRSZ / INT16SZ)) {
+ *tp++ = ':';
+ }
+ *tp++ = '\0';
+
+ /*
+ * Check for overflow, copy, and we're done.
+ */
+ if ((int)(tp - tmp) > size) {
+ ACR_SET_OS_ERROR(ACR_ENOSPC);
+ return 0;
+ }
+ strcpy(dst, tmp);
+ return dst;
+}
+
+/* int
+ * inet_pton4(src, dst)
+ * like inet_aton() but without all the hexadecimal and shorthand.
+ * return:
+ * 1 if `src' is a valid dotted quad, else 0.
+ * notice:
+ * does not touch `dst' unless it's returning 1.
+ * author:
+ * Paul Vixie, 1996.
+ */
+static int
+inet_pton4(const char *src, unsigned char *dst)
+{
+ static const char digits[] = "0123456789";
+ int saw_digit, octets, ch;
+ unsigned char tmp[INADDRSZ], *tp;
+
+ saw_digit = 0;
+ octets = 0;
+ *(tp = tmp) = 0;
+ while ((ch = *src++) != '\0') {
+ const char *pch;
+
+ if ((pch = strchr(digits, ch)) != 0) {
+ unsigned int new = *tp * 10 + (unsigned int)(pch - digits);
+
+ if (new > 255)
+ return 0;
+ *tp = new;
+ if (! saw_digit) {
+ if (++octets > 4)
+ return 0;
+ saw_digit = 1;
+ }
+ } else if (ch == '.' && saw_digit) {
+ if (octets == 4)
+ return 0;
+ *++tp = 0;
+ saw_digit = 0;
+ } else
+ return 0;
+ }
+ if (octets < 4)
+ return 0;
+
+ memcpy(dst, tmp, INADDRSZ);
+ return 1;
+}
+
+/* int
+ * inet_pton6(src, dst)
+ * convert presentation level address to network order binary form.
+ * return:
+ * 1 if `src' is a valid [RFC1884 2.2] address, else 0.
+ * notice:
+ * (1) does not touch `dst' unless it's returning 1.
+ * (2) :: in a full address is silently ignored.
+ * credit:
+ * inspired by Mark Andrews.
+ * author:
+ * Paul Vixie, 1996.
+ */
+static int
+inet_pton6(const char *src, unsigned char *dst)
+{
+ static const char xdigits_l[] = "0123456789abcdef",
+ xdigits_u[] = "0123456789ABCDEF";
+ unsigned char tmp[IN6ADDRSZ], *tp, *endp, *colonp;
+ const char *xdigits, *curtok;
+ int ch, saw_xdigit;
+ unsigned int val;
+
+ memset((tp = tmp), '\0', IN6ADDRSZ);
+ endp = tp + IN6ADDRSZ;
+ colonp = 0;
+ /* Leading :: requires some special handling. */
+ if (*src == ':') {
+ if (*++src != ':')
+ return 0;
+ }
+ curtok = src;
+ saw_xdigit = 0;
+ val = 0;
+ while ((ch = *src++) != '\0') {
+ const char *pch;
+
+ if ((pch = strchr((xdigits = xdigits_l), ch)) == 0)
+ pch = strchr((xdigits = xdigits_u), ch);
+ if (pch != 0) {
+ val <<= 4;
+ val |= (pch - xdigits);
+ if (val > 0xffff)
+ return 0;
+ saw_xdigit = 1;
+ continue;
+ }
+ if (ch == ':') {
+ curtok = src;
+ if (!saw_xdigit) {
+ if (colonp)
+ return 0;
+ colonp = tp;
+ continue;
+ }
+ if (tp + INT16SZ > endp)
+ return 0;
+ *tp++ = (unsigned char) (val >> 8) & 0xff;
+ *tp++ = (unsigned char) val & 0xff;
+ saw_xdigit = 0;
+ val = 0;
+ continue;
+ }
+ if (ch == '.' && ((tp + INADDRSZ) <= endp) && inet_pton4(curtok, tp) > 0) {
+ tp += INADDRSZ;
+ saw_xdigit = 0;
+ break; /* '\0' was seen by inet_pton4(). */
+ }
+ return (0);
+ }
+ if (saw_xdigit) {
+ if (tp + INT16SZ > endp)
+ return 0;
+ *tp++ = (unsigned char) (val >> 8) & 0xff;
+ *tp++ = (unsigned char) val & 0xff;
+ }
+ if (colonp != 0) {
+ /*
+ * Since some memmove()'s erroneously fail to handle
+ * overlapping regions, we'll do the shift by hand.
+ */
+ int n = (int)(tp - colonp);
+ int i;
+
+ for (i = 1; i <= n; i++) {
+ endp[- i] = colonp[n - i];
+ colonp[n - i] = 0;
+ }
+ tp = endp;
+ }
+ if (tp != endp)
+ return 0;
+ memcpy(dst, tmp, IN6ADDRSZ);
+ return 1;
+}
+
+/* char *
+ * inet_ntop(af, src, dst, size)
+ * convert a network format address to presentation format.
+ * return:
+ * pointer to presentation format address (`dst'), or NULL (see errno).
+ * author:
+ * Paul Vixie, 1996.
+ */
+const char *
+AcrInetNtop(int af, const void *src, char *dst, int size)
+{
+ switch (af) {
+ case AF_INET:
+ return inet_ntop4(src, dst, size);
+ case AF_INET6:
+ return inet_ntop6(src, dst, size);
+ default:
+ ACR_SET_OS_ERROR(EAFNOSUPPORT);
+ return 0;
+ }
+ /* NOTREACHED */
+}
+
+int
+AcrInetPton(int af, const char *src, void *dst)
+{
+ switch (af) {
+ case AF_INET:
+ return inet_pton4(src, dst);
+ case AF_INET6:
+ return inet_pton6(src, dst);
+ default:
+ ACR_SET_OS_ERROR(EAFNOSUPPORT);
+ return -1;
+ }
+ /* NOTREACHED */
+}
+
+
+static void
+sockaddr_vars_set(acr_sockaddr_t *addr, int family, int port)
+{
+ addr->family = family;
+ addr->sa.sin.sin_family = family;
+
+ if (port > 0) {
+ /* XXX IPv6: assumes sin_port and sin6_port at same offset */
+ addr->sa.sin.sin_port = htons(port);
+ addr->port = port;
+ }
+ if (family == AF_INET) {
+ addr->salen = ISIZEOF(struct sockaddr_in);
+ addr->addrlen = 16;
+ addr->ipaddr = &(addr->sa.sin.sin_addr);
+ addr->iplen = sizeof(struct in_addr);
+ }
+ else if (family == AF_INET6) {
+ addr->salen = ISIZEOF(struct sockaddr_in6);
+ addr->addrlen = 46;
+ addr->ipaddr = &(addr->sa.sin6.sin6_addr);
+ addr->iplen = sizeof(struct in6_addr);
+ }
+#if HAVE_SYS_UN_H
+ else if (family == AF_LOCAL) {
+ addr->salen = ISIZEOF(struct sockaddr_un);
+ addr->addrlen = ISIZEOF(addr->sa.unx.sun_path);;
+ addr->ipaddr = &(addr->sa.unx.sun_path);
+ addr->iplen = addr->addrlen;
+ }
+#endif
+}
+
+static int
+call_resolver(acr_sockaddr_t **sa, const char *hostname,
+ int family, int port, int flags)
+{
+ struct addrinfo hints, *ai, *ai_list;
+ acr_sockaddr_t *prev_sa;
+ int error;
+ char *servname = 0;
+ char buf[16];
+
+ memset(&hints, 0, sizeof(hints));
+ hints.ai_family = family;
+ hints.ai_socktype = SOCK_STREAM;
+#if defined(AI_ADDRCONFIG)
+ if (family == AF_UNSPEC) {
+ /* By default, only look up addresses using address types for
+ * which a local interface is configured, i.e. no IPv6 if no
+ * IPv6 interfaces configured. */
+ hints.ai_flags = AI_ADDRCONFIG;
+ }
+#endif
+ if(hostname == 0) {
+#if defined(AI_PASSIVE)
+ /* If hostname is NULL, assume we are trying to bind to all
+ * interfaces. */
+ hints.ai_flags |= AI_PASSIVE;
+#endif
+ /* getaddrinfo according to RFC 2553 must have either hostname
+ * or servname non-NULL.
+ */
+ servname = AcrItoa(buf, port);
+ }
+ error = getaddrinfo(hostname, servname, &hints, &ai_list);
+#if defined(AI_ADDRCONFIG)
+ if (error == EAI_BADFLAGS && family == AF_UNSPEC) {
+ /* Retry with no flags if AI_ADDRCONFIG was rejected. */
+ hints.ai_flags = 0;
+ error = getaddrinfo(hostname, servname, &hints, &ai_list);
+ }
+#endif
+ if (error) {
+#if defined(WINDOWS)
+ return ACR_GET_NETOS_ERROR();
+#else
+ if (error == EAI_SYSTEM) {
+ return errno;
+ }
+ else
+ {
+ /* issues with representing this with APR's error scheme:
+ * glibc uses negative values for these numbers, perhaps so
+ * they don't conflict with h_errno values... Tru64 uses
+ * positive values which conflict with h_errno values
+ */
+#if defined(NEGATIVE_EAI)
+ error = -error;
+#endif
+ return error + ACR_OS_START_EAIERR;
+ }
+#endif /* WIN32 */
+ }
+
+ prev_sa = NULL;
+ ai = ai_list;
+
+ while (ai) { /* while more addresses to report */
+ acr_sockaddr_t *new_sa;
+
+ /* Ignore anything bogus: getaddrinfo in some old versions of
+ * glibc will return AF_LOCAL entries for APR_UNSPEC+AI_PASSIVE
+ * lookups. */
+ if (ai->ai_family != AF_INET && ai->ai_family != AF_INET6) {
+ ai = ai->ai_next;
+ continue;
+ }
+
+ new_sa = calloc(1, sizeof(acr_sockaddr_t));
+ if (new_sa == 0)
+ return ACR_ENOMEM;
+ memcpy(&new_sa->sa, ai->ai_addr, ai->ai_addrlen);
+ sockaddr_vars_set(new_sa, ai->ai_family, port);
+
+ if (!prev_sa) { /* first element in new list */
+ if (hostname != 0)
+ strlcpy(new_sa->hostname, hostname, 256);
+ *sa = new_sa;
+ }
+ else {
+ strlcpy(new_sa->hostname, prev_sa->hostname, 256);
+ prev_sa->next = new_sa;
+ }
+
+ prev_sa = new_sa;
+ ai = ai->ai_next;
+ }
+ freeaddrinfo(ai_list);
+ return 0;
+}
+
+static int
+find_addresses(acr_sockaddr_t **sa, const char *hostname,
+ int family, int port, int flags)
+{
+ if (flags & ACR_IPV4_ADDR_OK) {
+ int rc = call_resolver(sa, hostname, AF_INET, port, flags);
+ if (rc != 0)
+ family = AF_INET6; /* try again */
+ else
+ return 0;
+ }
+ else if (flags & ACR_IPV6_ADDR_OK) {
+ int rc = call_resolver(sa, hostname, AF_INET6, port, flags);
+ if (rc != 0)
+ family = AF_INET; /* try again */
+ else
+ return 0;
+ }
+ return call_resolver(sa, hostname, family, port, flags);
+}
+
+int
+AcrGetSockaddrInfo(acr_sockaddr_t **sa, const char *hostname,
+ int family, int port, int flags)
+{
+ int masked;
+ *sa = 0;
+
+ if ((masked = flags & (ACR_IPV4_ADDR_OK | ACR_IPV6_ADDR_OK))) {
+ if (hostname == 0 || family != AF_UNSPEC ||
+ masked == (ACR_IPV4_ADDR_OK | ACR_IPV6_ADDR_OK)) {
+ return ACR_EINVAL;
+ }
+ }
+ if (family == AF_UNSPEC && hostname != 0 && *hostname == '/')
+ family = AF_LOCAL;
+ if (family == AF_LOCAL) {
+ if (hostname != 0) {
+#if HAVE_SYS_UN_H
+ *sa = calloc(1, sizeof(acr_sockaddr_t));
+ if (*sa == 0)
+ return ACR_ENOMEM;
+ strlcpy((*sa)->sa.unx.sun_path, hostname, sizeof((*sa)->sa.unx.sun_path));
+ strlcpy((*sa)->hostname, hostname, sizeof((*sa)->hostname));
+ (*sa)->sa.unx.sun_family = AF_LOCAL;
+ (*sa)->family = AF_LOCAL;
+ (*sa)->salen = ISIZEOF(struct sockaddr_un);
+ (*sa)->addrlen = ISIZEOF((*sa)->sa.unx.sun_path);
+ (*sa)->ipaddr = &((*sa)->sa.unx.sun_path);
+ (*sa)->iplen = (*sa)->addrlen;
+ return 0;
+#elif defined(WINDOWS)
+ *sa = calloc(1, sizeof(acr_sockaddr_t));
+ if (*sa == 0)
+ return ACR_ENOMEM;
+ strlcpy((*sa)->hostname, hostname, sizeof((*sa)->hostname));
+ (*sa)->family = AF_LOCAL;
+ (*sa)->addrlen = ISIZEOF((*sa)->hostname);
+ (*sa)->ipaddr = &((*sa)->hostname);
+ (*sa)->iplen = (*sa)->addrlen;
+ return 0;
+#else
+ *sa = 0;
+ return ACR_ENOTIMPL;
+#endif
+ }
+ else {
+ *sa = 0;
+ return ACR_EINVAL;
+ }
+ }
+ return find_addresses(sa, hostname, family, port, flags);
+}
+
+int
+AcrIsSockaddrEqual(const acr_sockaddr_t *addr1,
+ const acr_sockaddr_t *addr2)
+{
+ if (addr1->iplen == addr2->iplen &&
+ !memcmp(addr1->ipaddr, addr2->ipaddr, addr1->iplen)) {
+ return 1;
+ }
+ if (V4MAPPED_EQUAL(addr1, addr2))
+ return 1;
+ if (V4MAPPED_EQUAL(addr2, addr1))
+ return 1;
+ return 0; /* not equal */
+}
+
+#define GETHOSTBYNAME_BUFLEN 512
+
+int
+AcrGetNameInfo(char **hostname, acr_sockaddr_t *sockaddr, int flags)
+{
+#if defined(HAVE_GETNAMEINFO)
+ int rc;
+#if !defined(NI_MAXHOST)
+# define NI_MAXHOST 256
+#endif
+ char tmphostname[NI_MAXHOST];
+
+ /* don't know if it is portable for getnameinfo() to set h_errno;
+ * clear it then see if it was set */
+ SET_H_ERRNO(0);
+
+ /* default flags are NI_NAMREQD; otherwise, getnameinfo() will return
+ * a numeric address string if it fails to resolve the host name;
+ * that is *not* what we want here
+ *
+ * For IPv4-mapped IPv6 addresses, drop down to IPv4 before calling
+ * getnameinfo() to avoid getnameinfo bugs (MacOS X, glibc).
+ */
+ if (sockaddr->family == AF_INET6 &&
+ IN6_IS_ADDR_V4MAPPED(&sockaddr->sa.sin6.sin6_addr)) {
+ struct sockaddr_in tmpsa;
+ tmpsa.sin_family = AF_INET;
+ tmpsa.sin_port = 0;
+ tmpsa.sin_addr.s_addr = ((acr_u32_t *)sockaddr->ipaddr)[3];
+#ifdef SIN6_LEN
+ tmpsa.sin_len = sizeof(tmpsa);
+#endif
+
+ rc = getnameinfo((const struct sockaddr *)&tmpsa, sizeof(tmpsa),
+ tmphostname, NI_MAXHOST, NULL, 0,
+ flags != 0 ? flags : NI_NAMEREQD);
+ }
+ else if (sockaddr->family == AF_UNIX) {
+ *hostname = sockaddr->hostname;
+ return 0;
+ }
+ else
+ rc = getnameinfo((const struct sockaddr *)&sockaddr->sa, sockaddr->salen,
+ tmphostname, NI_MAXHOST, NULL, 0,
+ flags != 0 ? flags : NI_NAMEREQD);
+ if (rc != 0) {
+ *hostname = 0;
+
+#if !defined(WINDOWS)
+ /* something went wrong. Look at the EAI_ error code */
+ if (rc == EAI_SYSTEM) {
+ /* EAI_SYSTEM System error returned in errno. */
+ /* IMHO, Implementations that set h_errno a simply broken. */
+ if (h_errno) /* for broken implementations which set h_errno */
+ return h_errno + ACR_OS_START_SYSERR;
+ else /* "normal" case */
+ return errno + ACR_OS_START_SYSERR;
+ }
+ else
+#endif
+ {
+#if defined(NEGATIVE_EAI)
+ if (rc < 0) rc = -rc;
+#endif
+ return rc + ACR_OS_START_EAIERR; /* return the EAI_ error */
+ }
+ }
+ strlcpy(sockaddr->hostname, tmphostname, 256);
+ *hostname = sockaddr->hostname;
+ return 0;
+#else
+/* XXX: Do we need the following block
+ */
+#if HAVE_GETHOSTBYADDR_R
+ char tmp[GETHOSTBYNAME_BUFLEN];
+ int hosterror;
+ struct hostent hs, *hptr;
+
+#if defined(HPUX) || defined(AIX)
+ /* AIX, HP/UX, D/UX et alia */
+ gethostbyaddr_r((char *)&sockaddr->sa.sin.sin_addr,
+ sizeof(struct in_addr), AF_INET, &hs, &hd);
+ hptr = &hs;
+#else
+#if defined(LINUX)
+ /* Linux glibc2+ */
+ gethostbyaddr_r((char *)&sockaddr->sa.sin.sin_addr,
+ sizeof(struct in_addr), AF_INET,
+ &hs, tmp, GETHOSTBYNAME_BUFLEN - 1, &hptr, &hosterror);
+#else
+ /* Solaris, Irix et alia */
+ hptr = gethostbyaddr_r((char *)&sockaddr->sa.sin.sin_addr,
+ sizeof(struct in_addr), AF_INET,
+ &hs, tmp, GETHOSTBYNAME_BUFLEN, &hosterror);
+#endif
+ if (!hptr) {
+ *hostname = 0;
+ return hosterror + ACR_OS_START_SYSERR;
+ }
+#endif
+#else
+ struct hostent *hptr;
+ hptr = gethostbyaddr((char *)&sockaddr->sa.sin.sin_addr,
+ sizeof(struct in_addr), AF_INET);
+#endif
+
+ if (hptr) {
+ strlcpy(sockaddr->hostname, hptr->h_name, 256);
+ *hostname = sockaddr->hostname;
+ return 0;
+ }
+ *hostname = 0;
+#if defined(WINDOWS)
+ return ACR_GET_NETOS_ERROR();
+#else
+ return h_errno + ACR_OS_START_SYSERR;
+#endif
+#endif
+}
Propchange: commons/sandbox/runtime/trunk/src/main/native/shared/netaddr.c
------------------------------------------------------------------------------
svn:eol-style = native
Modified: commons/sandbox/runtime/trunk/src/main/native/shared/string.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/shared/string.c?rev=1099442&r1=1099441&r2=1099442&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/shared/string.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/shared/string.c Wed May 4 13:34:13 2011
@@ -18,6 +18,25 @@
#include "acr/clazz.h"
#include "acr/unsafe.h"
+#define NCONVSETN() \
+ start = buf + BUFFER_SIZE - 1; \
+ if (n < 0) { \
+ negative = 1; \
+ n = -n; \
+ } \
+ else \
+ negative = 0
+
+#define NCONVSETU() \
+ start = buf + BUFFER_SIZE - 1 \
+
+#define NCONVLOOP() \
+ *start = '\0'; \
+ do { \
+ *--start = (char)('0' + (n % 10)); \
+ n /= 10; \
+ } while (n)
+
J_DECLARE_CLAZZ = {
INVALID_FIELD_BASE,
0,
@@ -1244,6 +1263,20 @@ ACR_JNI_EXPORT(jcharArray, Unsafe, getch
return 0;
}
+char *AcrItoa(char *buf, int n)
+{
+#define BUFFER_SIZE 16
+ char *start;
+ int negative;
+
+ NCONVSETN();
+ NCONVLOOP();
+ if (negative)
+ *--start = '-';
+ return start;
+#undef BUFFER_SIZE
+}
+
#if defined(ENABLE_TEST_PRIVATE)
ACR_JNI_EXPORT(jint, TestString, test0)(JNI_STDARGS, jstring s)