aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKristof Provost <kp@FreeBSD.org>2021-06-01 14:05:47 +0000
committerKristof Provost <kp@FreeBSD.org>2021-06-04 08:12:11 +0000
commit364c6a71a840e8cf48eeea3bef81623d6f3574ff (patch)
tree327d0a239856d80ed55e2b5c8163876c0eccc598
parentb1461cdd30a96b8e54b6b5efb30b520ca527d8b4 (diff)
downloadsrc-364c6a71a840e8cf48eeea3bef81623d6f3574ff.tar.gz
src-364c6a71a840e8cf48eeea3bef81623d6f3574ff.zip
pf: Fix more ioctl memory leaks
We must also remember to free nvlists added to a parent nvlist with nvlist_append_nvlist_array(). More importantly, when nvlist_pack() allocates memory for us it does so in the M_NVLIST zone, so we must free it with free(.., M_NVLIST). Using free(.., M_TEMP) as we did silently failed to free the memory. MFC after: 3 days Reported by: kib@ Tested by: kib@ Sponsored by: Rubicon Communications, LLC ("Netgate") Differential Revision: https://reviews.freebsd.org/D30595 (cherry picked from commit 0f86492b09ca82042166a41f6f21b2dbe4f4a464)
-rw-r--r--sys/netpfil/pf/pf_ioctl.c27
-rw-r--r--sys/netpfil/pf/pf_nv.c1
2 files changed, 15 insertions, 13 deletions
diff --git a/sys/netpfil/pf/pf_ioctl.c b/sys/netpfil/pf/pf_ioctl.c
index af89ddf80daf..be7b8be23a31 100644
--- a/sys/netpfil/pf/pf_ioctl.c
+++ b/sys/netpfil/pf/pf_ioctl.c
@@ -2427,7 +2427,7 @@ DIOCADDRULENV_error:
ERROUT(ENOMEM);
/* Copy the request in */
- nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
+ nvlpacked = malloc(nv->len, M_NVLIST, M_WAITOK);
if (nvlpacked == NULL)
ERROUT(ENOMEM);
@@ -2505,7 +2505,7 @@ DIOCADDRULENV_error:
ERROUT(EBUSY);
}
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlpacked = nvlist_pack(nvl, &nv->len);
if (nvlpacked == NULL) {
PF_RULES_WUNLOCK();
@@ -2535,7 +2535,7 @@ DIOCADDRULENV_error:
#undef ERROUT
DIOCGETRULENV_error:
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlist_destroy(nvrule);
nvlist_destroy(nvl);
@@ -4919,7 +4919,7 @@ pf_killstates_nv(struct pfioc_nv *nv)
if (nv->len > pf_ioctl_maxcount)
ERROUT(ENOMEM);
- nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
+ nvlpacked = malloc(nv->len, M_NVLIST, M_WAITOK);
if (nvlpacked == NULL)
ERROUT(ENOMEM);
@@ -4937,7 +4937,7 @@ pf_killstates_nv(struct pfioc_nv *nv)
error = pf_killstates(&kill, &killed);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlpacked = NULL;
nvlist_destroy(nvl);
nvl = nvlist_create(0);
@@ -4959,7 +4959,7 @@ pf_killstates_nv(struct pfioc_nv *nv)
on_error:
nvlist_destroy(nvl);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
return (error);
}
@@ -4977,7 +4977,7 @@ pf_clearstates_nv(struct pfioc_nv *nv)
if (nv->len > pf_ioctl_maxcount)
ERROUT(ENOMEM);
- nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
+ nvlpacked = malloc(nv->len, M_NVLIST, M_WAITOK);
if (nvlpacked == NULL)
ERROUT(ENOMEM);
@@ -4995,7 +4995,7 @@ pf_clearstates_nv(struct pfioc_nv *nv)
killed = pf_clear_states(&kill);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlpacked = NULL;
nvlist_destroy(nvl);
nvl = nvlist_create(0);
@@ -5018,7 +5018,7 @@ pf_clearstates_nv(struct pfioc_nv *nv)
#undef ERROUT
on_error:
nvlist_destroy(nvl);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
return (error);
}
@@ -5036,7 +5036,7 @@ pf_getstate(struct pfioc_nv *nv)
if (nv->len > pf_ioctl_maxcount)
ERROUT(ENOMEM);
- nvlpacked = malloc(nv->len, M_TEMP, M_WAITOK);
+ nvlpacked = malloc(nv->len, M_NVLIST, M_WAITOK);
if (nvlpacked == NULL)
ERROUT(ENOMEM);
@@ -5055,7 +5055,7 @@ pf_getstate(struct pfioc_nv *nv)
if (s == NULL)
ERROUT(ENOENT);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlpacked = NULL;
nvlist_destroy(nvl);
nvl = nvlist_create(0);
@@ -5084,7 +5084,7 @@ pf_getstate(struct pfioc_nv *nv)
errout:
if (s != NULL)
PF_STATE_UNLOCK(s);
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlist_destroy(nvl);
return (error);
}
@@ -5126,6 +5126,7 @@ pf_getstates(struct pfioc_nv *nv)
goto DIOCGETSTATESNV_full;
}
nvlist_append_nvlist_array(nvl, "states", nvls);
+ nvlist_destroy(nvls);
count++;
}
PF_HASHROW_UNLOCK(ih);
@@ -5152,7 +5153,7 @@ DIOCGETSTATESNV_full:
#undef ERROUT
errout:
- free(nvlpacked, M_TEMP);
+ free(nvlpacked, M_NVLIST);
nvlist_destroy(nvl);
return (error);
}
diff --git a/sys/netpfil/pf/pf_nv.c b/sys/netpfil/pf/pf_nv.c
index 863259dbf9aa..dab72f04d138 100644
--- a/sys/netpfil/pf/pf_nv.c
+++ b/sys/netpfil/pf/pf_nv.c
@@ -846,6 +846,7 @@ pf_state_key_to_nvstate_key(const struct pf_state_key *key)
if (tmp == NULL)
goto errout;
nvlist_append_nvlist_array(nvl, "addr", tmp);
+ nvlist_destroy(tmp);
nvlist_append_number_array(nvl, "port", key->port[i]);
}
nvlist_add_number(nvl, "af", key->af);