summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorRichard W.M. Jones <rjones@redhat.com>2012-06-26 14:39:16 +0100
committerRichard W.M. Jones <rjones@redhat.com>2012-06-28 09:49:08 +0100
commit84f5e3d4e37597fb71879dd5f1e8a6fc852a0d5b (patch)
tree4a1268bed1881a872efe0200edd5b81bb90a484f /src
parent429b909bf4d0f6c1321ee32c35ae7e0546d09fcb (diff)
downloadlibguestfs-84f5e3d4e37597fb71879dd5f1e8a6fc852a0d5b.tar.gz
libguestfs-84f5e3d4e37597fb71879dd5f1e8a6fc852a0d5b.tar.xz
libguestfs-84f5e3d4e37597fb71879dd5f1e8a6fc852a0d5b.zip
launch: Avoid double-close when qemu exits early.
The stdin and stdout of the qemu process are aliased to g->fd: g->fd[0] = wfd[1]; g->fd[1] = rfd[0]; However if the child exits early, then child_cleanup closes g->fd[0], g->fd[1], AND the code at the cleanup1 label closes wfd[1], rfd[0], resulting in a double-close. Avoid this case by setting wfd[1], rfd[0] to -1. In the cleanup1 label, only close wfd[1], rfd[0] if they are not -1, and add the same for g->fd[0], g->fd[1]. (cherry picked from commit c87956837e962072fff61edef5b18e55ad42d730)
Diffstat (limited to 'src')
-rw-r--r--src/launch.c8
1 files changed, 6 insertions, 2 deletions
diff --git a/src/launch.c b/src/launch.c
index 34c13a0b..fb0172b9 100644
--- a/src/launch.c
+++ b/src/launch.c
@@ -923,6 +923,7 @@ launch_appliance (guestfs_h *g)
g->fd[0] = wfd[1]; /* stdin of child */
g->fd[1] = rfd[0]; /* stdout of child */
+ wfd[1] = rfd[0] = -1;
} else {
g->fd[0] = open ("/dev/null", O_RDWR);
if (g->fd[0] == -1) {
@@ -933,6 +934,7 @@ launch_appliance (guestfs_h *g)
if (g->fd[1] == -1) {
perrorf (g, "dup");
close (g->fd[0]);
+ g->fd[0] = -1;
goto cleanup1;
}
}
@@ -1003,13 +1005,15 @@ launch_appliance (guestfs_h *g)
cleanup1:
if (!g->direct) {
- close (wfd[1]);
- close (rfd[0]);
+ if (wfd[1] >= 0) close (wfd[1]);
+ if (rfd[1] >= 0) close (rfd[0]);
}
if (g->pid > 0) kill (g->pid, 9);
if (g->recoverypid > 0) kill (g->recoverypid, 9);
if (g->pid > 0) waitpid (g->pid, NULL, 0);
if (g->recoverypid > 0) waitpid (g->recoverypid, NULL, 0);
+ if (g->fd[0] >= 0) close (g->fd[0]);
+ if (g->fd[1] >= 0) close (g->fd[1]);
g->fd[0] = -1;
g->fd[1] = -1;
g->pid = 0;