From 51fb15be2c4c9ae7646659fad93358a3b080a521 Mon Sep 17 00:00:00 2001 From: Robert James Kaes Date: Sun, 15 Jun 2008 21:22:07 -0400 Subject: Refactored netmask array fill with range check When building a numeric ACL with netmask, range check the supplied value. In addition, the code to walk the array has been extracted and "simplified". Signed-off-by: Robert James Kaes --- src/acl.c | 47 +++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 39 insertions(+), 8 deletions(-) diff --git a/src/acl.c b/src/acl.c index 3e13b96..0d40386 100644 --- a/src/acl.c +++ b/src/acl.c @@ -57,6 +57,41 @@ struct acl_s { */ static vector_t access_list = NULL; + +/* + * Fills in the netmask array given a numeric value. + * + * Returns: + * 0 on success + * -1 on failure (invalid mask value) + * + */ +inline static int +fill_netmask_array(long int mask, unsigned char array[], unsigned int len) +{ + unsigned int i; + + if (mask < 0 || mask > (8 * len)) + return -1; + + for (i = 0; i != len; ++i) { + if (mask >= 8) { + array[i] = 0xff; + mask -= 8; + } + else if (mask > 0) { + array[i] = (unsigned char)(0xff << (8 - mask)); + mask = 0; + } + else { + array[i] = 0; + } + } + + return 0; +} + + /* * Inserts a new access control into the list. The function will figure out * whether the location is an IP address (with optional netmask) or a @@ -70,7 +105,8 @@ int insert_acl(char *location, acl_access_t access_type) { struct acl_s acl; - int i, ret, mask; + int ret; + long int mask; char *p, ip_dst[IPV6_LEN]; assert(location != NULL); @@ -119,13 +155,8 @@ insert_acl(char *location, acl_access_t access_type) memcpy(acl.address.ip.octet, ip_dst, IPV6_LEN); mask = strtol(p + 1, NULL, 10); - for (i = 0; i != IPV6_LEN; ++i) { - if (mask >= ((i + 1) * 8)) - acl.address.ip.mask[i] = 0xff; - else - acl.address.ip.mask[i] = - 0xff << (8 - (mask - i * 8)); - } + if (fill_netmask_array(mask, &(acl.address.ip.mask[0]), IPV6_LEN) < 0) + return -1; } else { /* In all likelihood a string */ acl.type = ACL_STRING; -- cgit v1.2.3