diff options
author | 2012-04-13 19:18:58 +0000 | |
---|---|---|
committer | 2012-04-13 19:18:58 +0000 | |
commit | 8301b91f0ada6f59103497102e4b33993bfcd033 (patch) | |
tree | 0b07ec35cc1b2cd4edb33ddb9d565e6f8edc7be5 | |
parent | Backout a tiny part of the previous commit. Decrementing ps_singlecount in (diff) | |
download | wireguard-openbsd-8301b91f0ada6f59103497102e4b33993bfcd033.tar.xz wireguard-openbsd-8301b91f0ada6f59103497102e4b33993bfcd033.zip |
Don't convert a mbuf to a cluster and think the data in the mbuf is still
valid after that. Copy the data into a temp buffer and then copy it back
into the shiny new cluster. Problem found by deraadt@. Ok deraadt@
-rw-r--r-- | sys/kern/uipc_usrreq.c | 12 |
1 files changed, 9 insertions, 3 deletions
diff --git a/sys/kern/uipc_usrreq.c b/sys/kern/uipc_usrreq.c index c8c37890a2e..3c951f900d9 100644 --- a/sys/kern/uipc_usrreq.c +++ b/sys/kern/uipc_usrreq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: uipc_usrreq.c,v 1.59 2012/04/13 19:16:11 deraadt Exp $ */ +/* $OpenBSD: uipc_usrreq.c,v 1.60 2012/04/13 19:18:58 claudio Exp $ */ /* $NetBSD: uipc_usrreq.c,v 1.18 1996/02/09 19:00:50 christos Exp $ */ /* @@ -785,18 +785,24 @@ morespace: neededspace = CMSG_SPACE(nfds * sizeof(struct file *)) - control->m_len; if (neededspace > M_TRAILINGSPACE(control)) { + char *tmp; /* if we already have a cluster, the message is just too big */ if (control->m_flags & M_EXT) return (E2BIG); + /* copy cmsg data temporarily out of the mbuf */ + tmp = malloc(control->m_len, M_TEMP, M_WAITOK); + memcpy(tmp, mtod(control, caddr_t), control->m_len); + /* allocate a cluster and try again */ MCLGET(control, M_WAIT); if ((control->m_flags & M_EXT) == 0) return (ENOBUFS); /* allocation failed */ - /* copy the data to the cluster */ - memcpy(mtod(control, char *), cm, cm->cmsg_len); + /* copy the data back into the cluster */ cm = mtod(control, struct cmsghdr *); + memcpy(cm, tmp, control->m_len); + free(tmp, M_TEMP); goto morespace; } |