diff options
author | Gilles Chehade <gilles@cvs.openbsd.org> | 2012-06-22 19:13:38 +0000 |
---|---|---|
committer | Gilles Chehade <gilles@cvs.openbsd.org> | 2012-06-22 19:13:38 +0000 |
commit | 7788c70d5ebd523ca5c123a535946b2b0ffd2bf7 (patch) | |
tree | 6f3bf6ce42eb67af71fd24dc883045ee95a97ab4 /lib | |
parent | 209006f6ded942fc3ac4388ad6bc5916a481907d (diff) |
add support for AF_INET6 to inet_net_pton() and inet_net_ntop()
using inet_pton() and inet_ntop() as suggested by claudio
ok claudio@
Diffstat (limited to 'lib')
-rw-r--r-- | lib/libc/net/inet_net_ntop.c | 29 | ||||
-rw-r--r-- | lib/libc/net/inet_net_pton.c | 41 |
2 files changed, 68 insertions, 2 deletions
diff --git a/lib/libc/net/inet_net_ntop.c b/lib/libc/net/inet_net_ntop.c index fc9071798ad..35ae7909d3c 100644 --- a/lib/libc/net/inet_net_ntop.c +++ b/lib/libc/net/inet_net_ntop.c @@ -1,6 +1,7 @@ -/* $OpenBSD: inet_net_ntop.c,v 1.6 2005/08/06 20:30:03 espie Exp $ */ +/* $OpenBSD: inet_net_ntop.c,v 1.7 2012/06/22 19:13:37 gilles Exp $ */ /* + * Copyright (c) 2012 by Gilles Chehade <gilles@openbsd.org> * Copyright (c) 1996 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any @@ -28,6 +29,7 @@ #include <stdlib.h> static char *inet_net_ntop_ipv4(const u_char *, int, char *, size_t); +static char *inet_net_ntop_ipv6(const u_char *, int, char *, size_t); /* * char * @@ -45,6 +47,8 @@ inet_net_ntop(int af, const void *src, int bits, char *dst, size_t size) switch (af) { case AF_INET: return (inet_net_ntop_ipv4(src, bits, dst, size)); + case AF_INET6: + return (inet_net_ntop_ipv6(src, bits, dst, size)); default: errno = EAFNOSUPPORT; return (NULL); @@ -133,3 +137,26 @@ inet_net_ntop_ipv4(const u_char *src, int bits, char *dst, size_t size) errno = EMSGSIZE; return (NULL); } + +static char * +inet_net_ntop_ipv6(const u_char *src, int bits, char *dst, size_t size) +{ + int ret; + char buf[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255:255:255:255/128")]; + + if (bits < 0 || bits > 128) { + errno = EINVAL; + return (NULL); + } + + if (inet_ntop(AF_INET6, src, buf, size) == NULL) + return (NULL); + + ret = snprintf(dst, size, "%s/%d", buf, bits); + if (ret == -1 || ret >= size) { + errno = EMSGSIZE; + return (NULL); + } + + return (dst); +} diff --git a/lib/libc/net/inet_net_pton.c b/lib/libc/net/inet_net_pton.c index 3105c33b434..74261399f77 100644 --- a/lib/libc/net/inet_net_pton.c +++ b/lib/libc/net/inet_net_pton.c @@ -1,6 +1,7 @@ -/* $OpenBSD: inet_net_pton.c,v 1.6 2008/09/01 09:40:43 markus Exp $ */ +/* $OpenBSD: inet_net_pton.c,v 1.7 2012/06/22 19:13:37 gilles Exp $ */ /* + * Copyright (c) 2012 by Gilles Chehade <gilles@openbsd.org> * Copyright (c) 1996 by Internet Software Consortium. * * Permission to use, copy, modify, and distribute this software for any @@ -30,6 +31,7 @@ #include <stdlib.h> static int inet_net_pton_ipv4(const char *, u_char *, size_t); +static int inet_net_pton_ipv6(const char *, u_char *, size_t); /* * static int @@ -50,6 +52,8 @@ inet_net_pton(int af, const char *src, void *dst, size_t size) switch (af) { case AF_INET: return (inet_net_pton_ipv4(src, dst, size)); + case AF_INET6: + return (inet_net_pton_ipv6(src, dst, size)); default: errno = EAFNOSUPPORT; return (-1); @@ -189,3 +193,38 @@ inet_net_pton_ipv4(const char *src, u_char *dst, size_t size) errno = EMSGSIZE; return (-1); } + + +static int +inet_net_pton_ipv6(const char *src, u_char *dst, size_t size) +{ + int ret; + int bits; + char buf[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255:255:255:255/128")]; + char *sep; + const char *errstr; + + if (strlcpy(buf, src, sizeof buf) >= sizeof buf) { + errno = EMSGSIZE; + return (-1); + } + + sep = strchr(buf, '/'); + if (sep != NULL) + *sep++ = '\0'; + + ret = inet_pton(AF_INET6, buf, dst); + if (ret != 1) + return (-1); + + if (sep == NULL) + return 128; + + bits = strtonum(sep, 0, 128, &errstr); + if (errstr) { + errno = EINVAL; + return (-1); + } + + return bits; +} |