mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-01-03 11:35:19 +00:00
remote: fix stream use-after-free
Inside daemonStreamHandleWrite on stream completion (status=OK) we reuse msg object to send confirmation. Only after that, msg is poped from the queue and checked for continue. By that time, msg might've already been processed for the confirmation and freed. Signed-off-by: Oleg Vasilev <oleg.vasilev@virtuozzo.com> Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
This commit is contained in:
parent
54e59e9135
commit
411cbe7199
@ -740,10 +740,11 @@ static int
|
||||
daemonStreamHandleWrite(virNetServerClient *client,
|
||||
daemonClientStream *stream)
|
||||
{
|
||||
virNetMessageStatus status = VIR_NET_OK;
|
||||
VIR_DEBUG("client=%p, stream=%p", client, stream);
|
||||
|
||||
while (stream->rx && !stream->closed) {
|
||||
virNetMessage *msg = stream->rx;
|
||||
virNetMessage *msg = virNetMessageQueueServe(&stream->rx);
|
||||
int ret;
|
||||
|
||||
if (msg->header.type == VIR_NET_STREAM_HOLE) {
|
||||
@ -752,7 +753,8 @@ daemonStreamHandleWrite(virNetServerClient *client,
|
||||
* data. */
|
||||
ret = daemonStreamHandleHole(client, stream, msg);
|
||||
} else if (msg->header.type == VIR_NET_STREAM) {
|
||||
switch (msg->header.status) {
|
||||
status = msg->header.status;
|
||||
switch (status) {
|
||||
case VIR_NET_OK:
|
||||
ret = daemonStreamHandleFinish(client, stream, msg);
|
||||
break;
|
||||
@ -776,7 +778,6 @@ daemonStreamHandleWrite(virNetServerClient *client,
|
||||
if (ret > 0)
|
||||
break; /* still processing data from msg */
|
||||
|
||||
virNetMessageQueueServe(&stream->rx);
|
||||
if (ret < 0) {
|
||||
virNetMessageFree(msg);
|
||||
virNetServerClientImmediateClose(client);
|
||||
@ -789,7 +790,7 @@ daemonStreamHandleWrite(virNetServerClient *client,
|
||||
* onto the wire, but this causes the client to reset
|
||||
* its active request count / throttling
|
||||
*/
|
||||
if (msg->header.status == VIR_NET_CONTINUE) {
|
||||
if (status == VIR_NET_CONTINUE) {
|
||||
virNetMessageClear(msg);
|
||||
msg->header.type = VIR_NET_REPLY;
|
||||
if (virNetServerClientSendMessage(client, msg) < 0) {
|
||||
|
Loading…
Reference in New Issue
Block a user