Mercurial > illumos > illumos-gate
changeset 4085:f5fd2bc7debd
6548762 picl snmplib frees unallocated memory
author | venki |
---|---|
date | Mon, 23 Apr 2007 12:06:47 -0700 |
parents | 1838f1bb1fda |
children | 5214f82452a7 |
files | usr/src/cmd/picl/plugins/sun4v/lib/snmp/pdu.c |
diffstat | 1 files changed, 32 insertions(+), 16 deletions(-) [+] |
line wrap: on
line diff
--- a/usr/src/cmd/picl/plugins/sun4v/lib/snmp/pdu.c Mon Apr 23 09:35:29 2007 -0700 +++ b/usr/src/cmd/picl/plugins/sun4v/lib/snmp/pdu.c Mon Apr 23 12:06:47 2007 -0700 @@ -48,6 +48,9 @@ uchar_t, void *, size_t); static uchar_t *snmp_parse_pdu(int, uchar_t *, size_t *, snmp_pdu_t *); static uchar_t *snmp_parse_variable(uchar_t *, size_t *, pdu_varlist_t *); +static void snmp_free_null_vars(pdu_varlist_t *); + +static uchar_t *snmp_def_community = (uchar_t *)SNMP_DEF_COMMUNITY; /* * Allocates and creates a PDU for the specified SNMP command. Currently @@ -80,7 +83,7 @@ pdu->command = cmd; pdu->reqid = snmp_get_reqid(); - pdu->community = (uchar_t *)SNMP_DEF_COMMUNITY; + pdu->community = snmp_def_community; pdu->community_len = SNMP_DEF_COMMUNITY_LEN; if (snmp_add_null_vars(pdu, oidstrs, n_oids, row) < 0) { @@ -246,40 +249,38 @@ snmp_add_null_vars(snmp_pdu_t *pdu, char *oidstrs, int n_oids, int row) { pdu_varlist_t *vp, *prev; - pdu_varlist_t *varblock_p; + pdu_varlist_t *varblock_p = NULL; char *p; int i; - /* - * It's much easier to allocate for all variables in one go, - * so we can release it quickly if there's any failure. - */ - varblock_p = (pdu_varlist_t *)calloc(n_oids, sizeof (pdu_varlist_t)); - if (varblock_p == NULL) - return (-1); - prev = NULL; p = oidstrs; - vp = varblock_p; for (i = 0; i < n_oids; i++) { + if ((vp = calloc(1, sizeof (pdu_varlist_t))) == NULL) { + snmp_free_null_vars(varblock_p); + return (-1); + } else if (i == 0) { + varblock_p = vp; + } else { + prev->nextvar = vp; + } + vp->name = snmp_oidstr_to_oid(pdu->command, p, row, &vp->name_len); if (vp->name == NULL) { - free((void *) varblock_p); + snmp_free_null_vars(varblock_p); return (-1); } vp->val.str = NULL; vp->val_len = 0; vp->type = ASN_NULL; - vp->nextvar = vp + 1; + vp->nextvar = NULL; LOGVAR(TAG_NULL_VAR, vp); prev = vp; p += strlen(p) + 1; - vp++; } - prev->nextvar = NULL; /* * append the varlist to the PDU @@ -294,6 +295,7 @@ return (0); } + /* * Some assumptions are in place here to eliminate unnecessary complexity. * All OID strings passed are assumed to be in the numeric string form, have @@ -644,7 +646,7 @@ pdu_varlist_t *vp, *nxt; if (pdu) { - if (pdu->community) + if ((pdu->community) && (pdu->community != snmp_def_community)) free((void *) pdu->community); for (vp = pdu->vars; vp; vp = nxt) { @@ -666,3 +668,17 @@ free((void *) pdu); } } + +static void +snmp_free_null_vars(pdu_varlist_t *varblock_p) +{ + pdu_varlist_t *vp, *nxt; + + for (vp = varblock_p; vp; vp = nxt) { + nxt = vp->nextvar; + + if (vp->name) + free(vp->name); + free(vp); + } +}