diff --git a/daemon/stream.c b/daemon/stream.c index 7df9952a2048219c4c50b673948d5e7f4c05ce14..50f8fd4ed838cd412194db91d3f3679b6ddeed56 100644 --- a/daemon/stream.c +++ b/daemon/stream.c @@ -143,7 +143,8 @@ daemonStreamEvent(virStreamPtr st, int events, void *opaque) VIR_DEBUG("st=%p events=%d EOF=%d closed=%d", st, events, stream->recvEOF, stream->closed); - if (events & VIR_STREAM_EVENT_WRITABLE) { + if (!stream->closed && + (events & VIR_STREAM_EVENT_WRITABLE)) { if (daemonStreamHandleWrite(client, stream) < 0) { daemonRemoveClientStream(client, stream); virNetServerClientClose(client); @@ -151,9 +152,9 @@ daemonStreamEvent(virStreamPtr st, int events, void *opaque) } } - if (!stream->recvEOF && - (events & (VIR_STREAM_EVENT_READABLE | VIR_STREAM_EVENT_HANGUP))) { - events = events & ~(VIR_STREAM_EVENT_READABLE | VIR_STREAM_EVENT_HANGUP); + if (!stream->closed && !stream->recvEOF && + (events & (VIR_STREAM_EVENT_READABLE))) { + events = events & ~(VIR_STREAM_EVENT_READABLE); if (daemonStreamHandleRead(client, stream) < 0) { daemonRemoveClientStream(client, stream); virNetServerClientClose(client); @@ -190,6 +191,37 @@ daemonStreamEvent(virStreamPtr st, int events, void *opaque) } } + + /* If we got HANGUP, we need to only send an empty + * packet so the client sees an EOF and cleans up + */ + if (!stream->closed && !stream->recvEOF && + (events & VIR_STREAM_EVENT_HANGUP)) { + virNetMessagePtr msg; + events &= ~(VIR_STREAM_EVENT_HANGUP); + stream->tx = 0; + stream->recvEOF = 1; + if (!(msg = virNetMessageNew(false))) { + daemonRemoveClientStream(client, stream); + virNetServerClientClose(client); + goto cleanup; + } + msg->cb = daemonStreamMessageFinished; + msg->opaque = stream; + stream->refs++; + if (virNetServerProgramSendStreamData(remoteProgram, + client, + msg, + stream->procedure, + stream->serial, + "", 0) < 0) { + virNetMessageFree(msg); + daemonRemoveClientStream(client, stream); + virNetServerClientClose(client); + goto cleanup; + } + } + if (!stream->closed && (events & (VIR_STREAM_EVENT_ERROR | VIR_STREAM_EVENT_HANGUP))) { int ret;