From 10ec0725453d9f54ce26ae5895e42d4c586f0339 Mon Sep 17 00:00:00 2001 From: "Daniel P. Berrange" Date: Wed, 5 Mar 2014 17:20:50 +0000 Subject: [PATCH] Add helper APIs to track if libvirtd or loadable modules have changed The future QEMU capabilities cache needs to be able to invalidate itself if the libvirtd binary or any loadable modules are changed on disk. Record the 'ctime' value for these binaries and provide helper APIs to query it. This approach assumes that if libvirt.so is changed, then libvirtd will also change, which should usually be the case with libtool's wrapper scripts that cause libvirtd to get re-linked Signed-off-by: Daniel P. Berrange --- daemon/libvirtd.c | 2 ++ src/driver.c | 2 ++ src/libvirt_private.syms | 2 ++ src/util/virutil.c | 23 +++++++++++++++++++++++ src/util/virutil.h | 4 ++++ 5 files changed, 33 insertions(+) diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c index 72f0e81e67..36adaf09c7 100644 --- a/daemon/libvirtd.c +++ b/daemon/libvirtd.c @@ -1152,6 +1152,8 @@ int main(int argc, char **argv) { exit(EXIT_FAILURE); } + virUpdateSelfLastChanged(argv[0]); + if (strstr(argv[0], "lt-libvirtd") || strstr(argv[0], "/daemon/.libs/libvirtd")) { char *tmp = strrchr(argv[0], '/'); diff --git a/src/driver.c b/src/driver.c index ab2a2538a0..721cbeb9f5 100644 --- a/src/driver.c +++ b/src/driver.c @@ -74,6 +74,8 @@ virDriverLoadModule(const char *name) goto cleanup; } + virUpdateSelfLastChanged(modfile); + handle = dlopen(modfile, RTLD_NOW | RTLD_GLOBAL); if (!handle) { VIR_ERROR(_("failed to load module %s %s"), modfile, dlerror()); diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 00e3d9cd23..f1607cd6ac 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -1954,6 +1954,7 @@ virGetGroupID; virGetGroupList; virGetGroupName; virGetHostname; +virGetSelfLastChanged; virGetUnprivSGIOSysfsPath; virGetUserCacheDirectory; virGetUserConfigDirectory; @@ -1983,6 +1984,7 @@ virSetNonBlock; virSetUIDGID; virSetUIDGIDWithCaps; virStrIsPrint; +virUpdateSelfLastChanged; virValidateWWN; diff --git a/src/util/virutil.c b/src/util/virutil.c index 7a2fbb0561..b6106fce2a 100644 --- a/src/util/virutil.c +++ b/src/util/virutil.c @@ -2173,3 +2173,26 @@ bool virIsSUID(void) { return getuid() != geteuid(); } + + +static time_t selfLastChanged; + +time_t virGetSelfLastChanged(void) +{ + return selfLastChanged; +} + + +void virUpdateSelfLastChanged(const char *path) +{ + struct stat sb; + + if (stat(path, &sb) < 0) + return; + + if (sb.st_ctime > selfLastChanged) { + VIR_DEBUG("Setting self last changed to %lld for '%s'", + (long long)sb.st_ctime, path); + selfLastChanged = sb.st_ctime; + } +} diff --git a/src/util/virutil.h b/src/util/virutil.h index 029265c2c0..cffe1ede48 100644 --- a/src/util/virutil.h +++ b/src/util/virutil.h @@ -194,4 +194,8 @@ const char *virGetEnvBlockSUID(const char *name); const char *virGetEnvAllowSUID(const char *name); bool virIsSUID(void); + +time_t virGetSelfLastChanged(void); +void virUpdateSelfLastChanged(const char *path); + #endif /* __VIR_UTIL_H__ */