summaryrefslogtreecommitdiffstats
path: root/contrib/bsnmp
diff options
context:
space:
mode:
authorharti <harti@FreeBSD.org>2006-01-10 11:59:31 +0000
committerharti <harti@FreeBSD.org>2006-01-10 11:59:31 +0000
commit574aae598d1e035d328c6398f2a307490de6cdfc (patch)
tree247ae6e729de8225e91130e5a376c22e1c611c4d /contrib/bsnmp
parent3a835f07a439e6b66009a773e3bd57b577be5f86 (diff)
downloadFreeBSD-src-574aae598d1e035d328c6398f2a307490de6cdfc.zip
FreeBSD-src-574aae598d1e035d328c6398f2a307490de6cdfc.tar.gz
Vendor fix: the routing table can change while we are fetching it from
the kernel. Instead of complaining if we get an ENOMEM (meaning it got larger than our buffer is) reallocate the buffer and loop. Submitted by: maxim
Diffstat (limited to 'contrib/bsnmp')
-rw-r--r--contrib/bsnmp/snmp_mibII/mibII.c28
1 files changed, 19 insertions, 9 deletions
diff --git a/contrib/bsnmp/snmp_mibII/mibII.c b/contrib/bsnmp/snmp_mibII/mibII.c
index 2f7881f..aa5cb83 100644
--- a/contrib/bsnmp/snmp_mibII/mibII.c
+++ b/contrib/bsnmp/snmp_mibII/mibII.c
@@ -1030,7 +1030,7 @@ u_char *
mib_fetch_rtab(int af, int info, int arg, size_t *lenp)
{
int name[6];
- u_char *buf;
+ u_char *buf, *newbuf;
name[0] = CTL_NET;
name[1] = PF_ROUTE;
@@ -1041,6 +1041,7 @@ mib_fetch_rtab(int af, int info, int arg, size_t *lenp)
*lenp = 0;
+ /* initial estimate */
if (sysctl(name, 6, NULL, lenp, NULL, 0) == -1) {
syslog(LOG_ERR, "sysctl estimate (%d,%d,%d,%d,%d,%d): %m",
name[0], name[1], name[2], name[3], name[4], name[5]);
@@ -1049,15 +1050,24 @@ mib_fetch_rtab(int af, int info, int arg, size_t *lenp)
if (*lenp == 0)
return (NULL);
- if ((buf = malloc(*lenp)) == NULL) {
- syslog(LOG_ERR, "sysctl buffer: %m");
- return (NULL);
- }
+ buf = NULL;
+ for (;;) {
+ if ((newbuf = realloc(buf, *lenp)) == NULL) {
+ syslog(LOG_ERR, "sysctl buffer: %m");
+ free(buf);
+ return (NULL);
+ }
+ buf = newbuf;
+
+ if (sysctl(name, 6, buf, lenp, NULL, 0) == 0)
+ break;
- if (sysctl(name, 6, buf, lenp, NULL, 0) == -1) {
- syslog(LOG_ERR, "sysctl get: %m");
- free(buf);
- return (NULL);
+ if (errno != ENOMEM) {
+ syslog(LOG_ERR, "sysctl get: %m");
+ free(buf);
+ return (NULL);
+ }
+ *lenp += *lenp / 8 + 1;
}
return (buf);
OpenPOWER on IntegriCloud