diff options
Diffstat (limited to 'sbin/ipf/libipf/parsewhoisline.c')
| -rw-r--r-- | sbin/ipf/libipf/parsewhoisline.c | 129 |
1 files changed, 129 insertions, 0 deletions
diff --git a/sbin/ipf/libipf/parsewhoisline.c b/sbin/ipf/libipf/parsewhoisline.c new file mode 100644 index 000000000000..529372f91fe2 --- /dev/null +++ b/sbin/ipf/libipf/parsewhoisline.c @@ -0,0 +1,129 @@ +/* + * Copyright (C) 2012 by Darren Reed. + * + * See the IPFILTER.LICENCE file for details on licencing. + * + * $Id: parsewhoisline.c,v 1.2.2.5 2012/07/22 08:04:24 darren_r Exp $ + */ +#include "ipf.h" + +/* +Microsoft Corp MICROSOFT19 (NET-198-136-97-0-1) 198.137.97.0 - 198.137.97.255 +Microsoft Corp SAVV-S233053-6 (NET-206-79-74-32-1) 206.79.74.32 - 206.79.74.47 + */ +int +parsewhoisline(char *line, addrfamily_t *addrp, addrfamily_t *maskp) +{ + struct in_addr a1, a2; + char *src = line; + char *s = NULL; + + if (line == NULL) + return (-1); + + while (*src != '\0') { + s = strchr(src, '('); + if (s == NULL) + break; + + if (strncmp(s, "(NET", 4)) { + src = s + 1; + } + break; + } + + if (s == NULL) + return (-1); + + memset(addrp, 0x00, sizeof(*maskp)); + memset(maskp, 0x00, sizeof(*maskp)); + + if (*(s + 4) == '6') { +#ifdef USE_INET6 + i6addr_t a61, a62; + + s = strchr(s, ')'); + if (s == NULL || *++s != ' ') + return (-1); + /* + * Parse the IPv6 + */ + if (inet_pton(AF_INET6, s, &a61.in6) != 1) + return (-1); + + s = strchr(s, ' '); + if (s == NULL || strncmp(s, " - ", 3)) + return (-1); + + s += 3; + if (inet_pton(AF_INET6, s, &a62) != 1) + return (-1); + + addrp->adf_addr = a61; + addrp->adf_family = AF_INET6; + addrp->adf_len = offsetof(addrfamily_t, adf_addr) + + sizeof(struct in6_addr); + + maskp->adf_addr.i6[0] = ~(a62.i6[0] ^ a61.i6[0]); + maskp->adf_addr.i6[1] = ~(a62.i6[1] ^ a61.i6[1]); + maskp->adf_addr.i6[2] = ~(a62.i6[2] ^ a61.i6[2]); + maskp->adf_addr.i6[3] = ~(a62.i6[3] ^ a61.i6[3]); + + /* + * If the mask that's been generated isn't a consecutive mask + * then we can't add it into a pool. + */ + if (count6bits(maskp->adf_addr.i6) == -1) + return (-1); + + maskp->adf_family = AF_INET6; + maskp->adf_len = addrp->adf_len; + + if (IP6_MASKNEQ(&addrp->adf_addr.in6, &maskp->adf_addr.in6, + &addrp->adf_addr.in6)) { + return (-1); + } + return (0); +#else + return (-1); +#endif + } + + s = strchr(s, ')'); + if (s == NULL || *++s != ' ') + return (-1); + + s++; + + if (inet_aton(s, &a1) != 1) + return (-1); + + s = strchr(s, ' '); + if (s == NULL || strncmp(s, " - ", 3)) + return (-1); + + s += 3; + if (inet_aton(s, &a2) != 1) + return (-1); + + addrp->adf_addr.in4 = a1; + addrp->adf_family = AF_INET; + addrp->adf_len = offsetof(addrfamily_t, adf_addr) + + sizeof(struct in_addr); + maskp->adf_addr.in4.s_addr = ~(a2.s_addr ^ a1.s_addr); + + /* + * If the mask that's been generated isn't a consecutive mask then + * we can't add it into a pool. + */ + if (count4bits(maskp->adf_addr.in4.s_addr) == -1) + return (-1); + + maskp->adf_family = AF_INET; + maskp->adf_len = addrp->adf_len; + bzero((char *)maskp + maskp->adf_len, sizeof(*maskp) - maskp->adf_len); + if ((addrp->adf_addr.in4.s_addr & maskp->adf_addr.in4.s_addr) != + addrp->adf_addr.in4.s_addr) + return (-1); + return (0); +} |
