/*
* This file and its contents are supplied under the terms of the
* Common Development and Distribution License ("CDDL"), version 1.0.
* You may only use this file in accordance with the terms of version
* 1.0 of the CDDL.
*
* A full copy of the text of the CDDL should have accompanied this
* source. A copy of the CDDL is also available via the Internet at
*/
/*
* Copyright 2016 Nexenta Systems, Inc.
*/
/*
* inet_matchaddr
*
* Match IPv4 or IPv6 address provided in sa (sockaddr_in/sockaddr_in6)
* against standard text representation specified in name:
*
* IPv4:
* IPv4
*
* IPv6:
* [IPv6]
* [IPv6]/prefix
*
* Return values:
*
* 0 mismatch
* 1 match
* -1 error occured, caller should check errno:
* EINVAL access list entry is invalid
* ENOMEM failed to allocate memory
*/
#include <ctype.h>
#include <errno.h>
#include <netdb.h>
#include <stdlib.h>
#include <strings.h>
int
{
char *ep;
return (-1);
}
*mp++ = '\0';
case AF_INET6: {
char *pp;
if (!IN6_IS_ADDR_V4MAPPED(claddr6)) {
/* IPv6 address */
if (*p != '[') {
break;
}
p++;
break;
}
*pp = '\0';
break;
}
/* Match only first prefix bits */
long prefix6;
errno = 0;
break;
}
break;
} else {
/* No prefix, exact match */
&hcaddr6) ? 1 : 0;
break;
}
} else {
/* IPv4-mapped IPv6 address, fallthrough to IPv4 */
}
/*FALLTHROUGH*/
}
case AF_INET: {
int i;
if (claddr4 == 0) {
}
for (i = 0; i < 4; i++) {
long qaddr4;
errno = 0;
break;
}
if (*ep == '\0')
break;
p = ep + 1;
}
if (errno != 0)
break;
/* Mask is specified explicitly */
long mb;
errno = 0;
break;
}
- mb) : 0;
} else {
/*
* Use old-fashioned implicit netmasking by checking
* for lower-end zeroes. On the off chance we don't
* match any well-known prefixes, return an exact-
* match prefix which is misleadingly labelled as
* IN_CLASSE_NET.
*/
if ((hcaddr4 & IN_CLASSA_HOST) == 0)
else if ((hcaddr4 & IN_CLASSB_HOST) == 0)
else if ((hcaddr4 & IN_CLASSC_HOST) == 0)
else
}
break;
}
}
if (ret != -1)
return (ret);
}