diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 4d78fcfed70d9ea6945a3d037d247d8efc61c43c..2050e5e915da1fb353f8716f84c49bd4cbc5b387 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1003,6 +1003,7 @@ virFilePid; virFileReadAll; virFileReadLimFD; virFileReadPid; +virFileReadPidPath; virFileResolveLink; virFileSanitizePath; virFileStripSuffix; diff --git a/src/qemu/qemu_domain.h b/src/qemu/qemu_domain.h index d78c4b4c55040cdc913935b3175f67961f42c755..f4647a0921c693ef1fd0521b94ac2c60b3cc18cc 100644 --- a/src/qemu/qemu_domain.h +++ b/src/qemu/qemu_domain.h @@ -88,6 +88,7 @@ struct _qemuDomainObjPrivate { bool monError; unsigned long long monStart; bool gotShutdown; + char *pidfile; int nvcpupids; int *vcpupids; diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c index c9145cbe9804be174ed6a083cec61374b5ae0515..ae45f12cafb4247d9ec4dd6e67849164a4ce01bc 100644 --- a/src/qemu/qemu_process.c +++ b/src/qemu/qemu_process.c @@ -76,6 +76,7 @@ qemuProcessRemoveDomainStatus(struct qemud_driver *driver, { char ebuf[1024]; char *file = NULL; + qemuDomainObjPrivatePtr priv = vm->privateData; if (virAsprintf(&file, "%s/%s.xml", driver->stateDir, vm->def->name) < 0) { virReportOOMError(); @@ -87,11 +88,12 @@ qemuProcessRemoveDomainStatus(struct qemud_driver *driver, vm->def->name, virStrerror(errno, ebuf, sizeof(ebuf))); VIR_FREE(file); - if (virFileDeletePid(driver->stateDir, vm->def->name) != 0) + if (priv->pidfile && + unlink(priv->pidfile) < 0 && + errno != ENOENT) VIR_WARN("Failed to remove PID file for %s: %s", vm->def->name, virStrerror(errno, ebuf, sizeof(ebuf))); - return 0; } @@ -2339,7 +2341,6 @@ int qemuProcessStart(virConnectPtr conn, int ret; off_t pos = -1; char ebuf[1024]; - char *pidfile = NULL; int logfile = -1; char *timestamp; qemuDomainObjPrivatePtr priv = vm->privateData; @@ -2491,16 +2492,18 @@ int qemuProcessStart(virConnectPtr conn, priv->monStart = 0; priv->gotShutdown = false; - if ((ret = virFileDeletePid(driver->stateDir, vm->def->name)) != 0) { - virReportSystemError(ret, - _("Cannot remove stale PID file for %s"), - vm->def->name); + VIR_FREE(priv->pidfile); + if (!(priv->pidfile = virFilePid(driver->stateDir, vm->def->name))) { + virReportSystemError(errno, + "%s", _("Failed to build pidfile path.")); goto cleanup; } - if (!(pidfile = virFilePid(driver->stateDir, vm->def->name))) { + if (unlink(priv->pidfile) < 0 && + errno != ENOENT) { virReportSystemError(errno, - "%s", _("Failed to build pidfile path.")); + _("Cannot remove stale PID file %s"), + priv->pidfile); goto cleanup; } @@ -2591,16 +2594,15 @@ int qemuProcessStart(virConnectPtr conn, virCommandSetOutputFD(cmd, &logfile); virCommandSetErrorFD(cmd, &logfile); virCommandNonblockingFDs(cmd); - virCommandSetPidFile(cmd, pidfile); + virCommandSetPidFile(cmd, priv->pidfile); virCommandDaemonize(cmd); virCommandRequireHandshake(cmd); ret = virCommandRun(cmd, NULL); - VIR_FREE(pidfile); /* wait for qemu process to show up */ if (ret == 0) { - if (virFileReadPid(driver->stateDir, vm->def->name, &vm->pid)) { + if (virFileReadPidPath(priv->pidfile, &vm->pid)) { qemuReportError(VIR_ERR_INTERNAL_ERROR, _("Domain %s didn't show up"), vm->def->name); ret = -1; @@ -2946,6 +2948,7 @@ retry: priv->nvcpupids = 0; qemuCapsFree(priv->qemuCaps); priv->qemuCaps = NULL; + VIR_FREE(priv->pidfile); /* The "release" hook cleans up additional resources */ if (virHookPresent(VIR_HOOK_DRIVER_QEMU)) { diff --git a/src/util/util.c b/src/util/util.c index 2165f264049acdd8f681a426abae4af076342a33..62e0152c3e75bf3c7fe0a8b87c03054c2439f8c9 100644 --- a/src/util/util.c +++ b/src/util/util.c @@ -1236,42 +1236,57 @@ cleanup: return rc; } -int virFileReadPid(const char *dir, - const char *name, - pid_t *pid) + +int virFileReadPidPath(const char *path, + pid_t *pid) { - int rc; FILE *file; - char *pidfile = NULL; + int rc; + *pid = 0; - if (name == NULL || dir == NULL) { - rc = EINVAL; + if (!(file = fopen(path, "r"))) { + rc = errno; goto cleanup; } - if (!(pidfile = virFilePid(dir, name))) { - rc = ENOMEM; + if (fscanf(file, "%d", pid) != 1) { + rc = EINVAL; + VIR_FORCE_FCLOSE(file); goto cleanup; } - if (!(file = fopen(pidfile, "r"))) { + if (VIR_FCLOSE(file) < 0) { rc = errno; goto cleanup; } - if (fscanf(file, "%d", pid) != 1) { + rc = 0; + + cleanup: + return rc; +} + + +int virFileReadPid(const char *dir, + const char *name, + pid_t *pid) +{ + int rc; + char *pidfile = NULL; + *pid = 0; + + if (name == NULL || dir == NULL) { rc = EINVAL; - VIR_FORCE_FCLOSE(file); goto cleanup; } - if (VIR_FCLOSE(file) < 0) { - rc = errno; + if (!(pidfile = virFilePid(dir, name))) { + rc = ENOMEM; goto cleanup; } - rc = 0; + rc = virFileReadPidPath(pidfile, pid); cleanup: VIR_FREE(pidfile); diff --git a/src/util/util.h b/src/util/util.h index 6f07f8c8368a44c1bd9c1811d1c79b46b0dd5575..e8197be0d94fbabd058ec709dd44f48f22f4af12 100644 --- a/src/util/util.h +++ b/src/util/util.h @@ -125,6 +125,8 @@ int virFileWritePidPath(const char *path, int virFileWritePid(const char *dir, const char *name, pid_t pid) ATTRIBUTE_RETURN_CHECK; +int virFileReadPidPath(const char *path, + pid_t *pid) ATTRIBUTE_RETURN_CHECK; int virFileReadPid(const char *dir, const char *name, pid_t *pid) ATTRIBUTE_RETURN_CHECK;