socket: Fix memory leak in sendmsg() and sendmsg_afalg()

Issue #27744:

* Release msg.msg_iov memory block.
* Release memory on PyMem_Malloc(controllen) failure
This commit is contained in:
Victor Stinner 2016-09-12 11:41:58 +02:00
parent 288b5bf624
commit 52d61e485e
1 changed files with 12 additions and 5 deletions

View File

@ -4072,11 +4072,13 @@ sock_sendmsg(PySocketSockObject *s, PyObject *args)
if (ncmsgbufs > 0) { if (ncmsgbufs > 0) {
struct cmsghdr *cmsgh = NULL; struct cmsghdr *cmsgh = NULL;
if ((msg.msg_control = controlbuf = controlbuf = PyMem_Malloc(controllen);
PyMem_Malloc(controllen)) == NULL) { if (controlbuf == NULL) {
PyErr_NoMemory(); PyErr_NoMemory();
goto finally; goto finally;
} }
msg.msg_control = controlbuf;
msg.msg_controllen = controllen; msg.msg_controllen = controllen;
/* Need to zero out the buffer as a workaround for glibc's /* Need to zero out the buffer as a workaround for glibc's
@ -4141,8 +4143,10 @@ finally:
PyBuffer_Release(&cmsgs[i].data); PyBuffer_Release(&cmsgs[i].data);
PyMem_Free(cmsgs); PyMem_Free(cmsgs);
Py_XDECREF(cmsg_fast); Py_XDECREF(cmsg_fast);
for (i = 0; i < ndatabufs; i++) PyMem_Free(msg.msg_iov);
for (i = 0; i < ndatabufs; i++) {
PyBuffer_Release(&databufs[i]); PyBuffer_Release(&databufs[i]);
}
PyMem_Free(databufs); PyMem_Free(databufs);
return retval; return retval;
} }
@ -4243,7 +4247,8 @@ sock_sendmsg_afalg(PySocketSockObject *self, PyObject *args, PyObject *kwds)
controlbuf = PyMem_Malloc(controllen); controlbuf = PyMem_Malloc(controllen);
if (controlbuf == NULL) { if (controlbuf == NULL) {
return PyErr_NoMemory(); PyErr_NoMemory();
goto finally;
} }
memset(controlbuf, 0, controllen); memset(controlbuf, 0, controllen);
@ -4315,8 +4320,10 @@ sock_sendmsg_afalg(PySocketSockObject *self, PyObject *args, PyObject *kwds)
if (iv.buf != NULL) { if (iv.buf != NULL) {
PyBuffer_Release(&iv); PyBuffer_Release(&iv);
} }
for (i = 0; i < ndatabufs; i++) PyMem_Free(msg.msg_iov);
for (i = 0; i < ndatabufs; i++) {
PyBuffer_Release(&databufs[i]); PyBuffer_Release(&databufs[i]);
}
PyMem_Free(databufs); PyMem_Free(databufs);
return retval; return retval;
} }