[libvirt] [PATCH] Move user libvirtd socket out of abstract namespace
by Daniel P. Berrange
From: "Daniel P. Berrange" <berrange(a)redhat.com>
The current unprivileged user libvirtd sockets are in the abstract
namespace. This has a number of problems
- You can't connect to them remotely using the nc/ssh tunnel
- This is not portable for OS-X
- Parent directory permissions don't apply
---
daemon/libvirtd.c | 2 +-
src/remote/remote_driver.c | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c
index 5830069..2696c54 100644
--- a/daemon/libvirtd.c
+++ b/daemon/libvirtd.c
@@ -300,7 +300,7 @@ daemonUnixSocketPaths(struct daemonConfig *config,
}
umask(old_umask);
- if (virAsprintf(sockfile, "@%s/libvirt-sock", rundir) < 0) {
+ if (virAsprintf(sockfile, "%s/libvirt-sock", rundir) < 0) {
VIR_FREE(rundir);
goto no_memory;
}
diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c
index 4a9299a..5c87561 100644
--- a/src/remote/remote_driver.c
+++ b/src/remote/remote_driver.c
@@ -583,7 +583,7 @@ doRemoteOpen (virConnectPtr conn,
if (!userdir)
goto failed;
- if (virAsprintf(&sockname, "@%s/" LIBVIRTD_USER_UNIX_SOCKET, userdir) < 0) {
+ if (virAsprintf(&sockname, "%s/" LIBVIRTD_USER_UNIX_SOCKET, userdir) < 0) {
VIR_FREE(userdir);
goto out_of_memory;
}
--
1.7.10.1
12 years, 6 months
[libvirt] [PATCHv4] Use XDG Base Directories instead of storing in home directory
by William Jon McCann
As defined in:
http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html
This offers a number of advantages:
* Allows sharing a home directory between different machines, or
sessions (eg. using NFS)
* Cleanly separates cache, runtime (eg. sockets), or app data from
user settings
* Supports performing smart or selective migration of settings
between different OS versions
* Supports reseting settings without breaking things
* Makes it possible to clear cache data to make room when the disk
is filling up
* Allows us to write a robust and efficient backup solution
* Allows an admin flexibility to change where data and settings are stored
* Dramatically reduces the complexity and incoherence of the
system for administrators
---
AUTHORS | 1 +
daemon/libvirtd-config.c | 10 +--
daemon/libvirtd.c | 144 +++++++++++++++++++++++++++++++++-------
daemon/libvirtd.pod.in | 2 +-
docs/auth.html.in | 2 +-
docs/uri.html.in | 2 +-
src/libvirt.c | 4 +-
src/libvirt_private.syms | 4 ++
src/network/bridge_driver.c | 8 ++-
src/nwfilter/nwfilter_driver.c | 11 +--
src/qemu/qemu_driver.c | 32 ++++++---
src/remote/remote_driver.c | 4 +-
src/remote/remote_driver.h | 2 +-
src/secret/secret_driver.c | 11 +--
src/storage/storage_driver.c | 13 +---
src/uml/uml_driver.c | 10 +--
src/util/util.c | 62 +++++++++++++++++
src/util/util.h | 4 ++
src/util/virauth.c | 4 +-
tools/virsh.c | 6 +-
20 files changed, 247 insertions(+), 89 deletions(-)
diff --git a/AUTHORS b/AUTHORS
index 31e3772..29b2c1d 100644
--- a/AUTHORS
+++ b/AUTHORS
@@ -236,6 +236,7 @@ Patches have also been contributed by:
Wido den Hollander <wido(a)widodh.nl>
Eugen Feller <eugen.feller(a)inria.fr>
Dmitry Guryanov <dguryanov(a)parallels.com>
+ William Jon McCann <jmccann(a)redhat.com>
[....send patches to get your name here....]
diff --git a/daemon/libvirtd-config.c b/daemon/libvirtd-config.c
index 471236c..8b95969 100644
--- a/daemon/libvirtd-config.c
+++ b/daemon/libvirtd-config.c
@@ -205,16 +205,16 @@ daemonConfigFilePath(bool privileged, char **configfile)
if (!(*configfile = strdup(SYSCONFDIR "/libvirt/libvirtd.conf")))
goto no_memory;
} else {
- char *userdir = NULL;
+ char *configdir = NULL;
- if (!(userdir = virGetUserDirectory(geteuid())))
+ if (!(configdir = virGetUserConfigDirectory(geteuid())))
goto error;
- if (virAsprintf(configfile, "%s/.libvirt/libvirtd.conf", userdir) < 0) {
- VIR_FREE(userdir);
+ if (virAsprintf(configfile, "%s/libvirtd.conf", configdir) < 0) {
+ VIR_FREE(configdir);
goto no_memory;
}
- VIR_FREE(userdir);
+ VIR_FREE(configdir);
}
return 0;
diff --git a/daemon/libvirtd.c b/daemon/libvirtd.c
index b098f6a..67248b3 100644
--- a/daemon/libvirtd.c
+++ b/daemon/libvirtd.c
@@ -239,17 +239,25 @@ daemonPidFilePath(bool privileged,
if (!(*pidfile = strdup(LOCALSTATEDIR "/run/libvirtd.pid")))
goto no_memory;
} else {
- char *userdir = NULL;
+ char *rundir = NULL;
+ mode_t old_umask;
- if (!(userdir = virGetUserDirectory(geteuid())))
+ if (!(rundir = virGetUserRuntimeDirectory(geteuid())))
goto error;
- if (virAsprintf(pidfile, "%s/.libvirt/libvirtd.pid", userdir) < 0) {
- VIR_FREE(userdir);
+ old_umask = umask(077);
+ if (virFileMakePath(rundir) < 0) {
+ umask(old_umask);
+ goto error;
+ }
+ umask(old_umask);
+
+ if (virAsprintf(pidfile, "%s/libvirtd.pid", rundir) < 0) {
+ VIR_FREE(rundir);
goto no_memory;
}
- VIR_FREE(userdir);
+ VIR_FREE(rundir);
}
return 0;
@@ -279,17 +287,25 @@ daemonUnixSocketPaths(struct daemonConfig *config,
if (!(*rosockfile = strdup(LOCALSTATEDIR "/run/libvirt/libvirt-sock-ro")))
goto no_memory;
} else {
- char *userdir = NULL;
+ char *rundir = NULL;
+ mode_t old_umask;
- if (!(userdir = virGetUserDirectory(geteuid())))
+ if (!(rundir = virGetUserRuntimeDirectory(geteuid())))
goto error;
- if (virAsprintf(sockfile, "@%s/.libvirt/libvirt-sock", userdir) < 0) {
- VIR_FREE(userdir);
+ old_umask = umask(077);
+ if (virFileMakePath(rundir) < 0) {
+ umask(old_umask);
+ goto error;
+ }
+ umask(old_umask);
+
+ if (virAsprintf(sockfile, "@%s/libvirt-sock", rundir) < 0) {
+ VIR_FREE(rundir);
goto no_memory;
}
- VIR_FREE(userdir);
+ VIR_FREE(rundir);
}
}
return 0;
@@ -593,16 +609,25 @@ daemonSetupLogging(struct daemonConfig *config,
LOCALSTATEDIR) == -1)
goto no_memory;
} else {
- char *userdir = virGetUserDirectory(geteuid());
- if (!userdir)
+ char *logdir = virGetUserCacheDirectory(geteuid());
+ mode_t old_umask;
+
+ if (!logdir)
+ goto error;
+
+ old_umask = umask(077);
+ if (virFileMakePath(logdir) < 0) {
+ umask(old_umask);
goto error;
+ }
+ umask(old_umask);
- if (virAsprintf(&tmp, "%d:file:%s/.libvirt/libvirtd.log",
- virLogGetDefaultPriority(), userdir) == -1) {
- VIR_FREE(userdir);
+ if (virAsprintf(&tmp, "%d:file:%s/libvirtd.log",
+ virLogGetDefaultPriority(), logdir) == -1) {
+ VIR_FREE(logdir);
goto no_memory;
}
- VIR_FREE(userdir);
+ VIR_FREE(logdir);
}
} else {
if (virAsprintf(&tmp, "%d:stderr", virLogGetDefaultPriority()) < 0)
@@ -722,6 +747,76 @@ static int daemonStateInit(virNetServerPtr srv)
return 0;
}
+static int migrateProfile(void)
+{
+ char *old_base = NULL;
+ char *updated = NULL;
+ char *home = NULL;
+ char *xdg_dir = NULL;
+ char *config_dir = NULL;
+ const char *config_home;
+ int ret = -1;
+ mode_t old_umask;
+
+ if (!(home = virGetUserDirectory(geteuid())))
+ goto cleanup;
+
+ if (virAsprintf(&old_base, "%s/.libvirt", home) < 0) {
+ goto cleanup;
+ }
+
+ /* if the new directory is there or the old one is not: do nothing */
+ if (!(config_dir = virGetUserConfigDirectory(geteuid())))
+ goto cleanup;
+
+ if (!virFileIsDir(old_base) || virFileExists(config_dir)) {
+ ret = 0;
+ goto cleanup;
+ }
+
+ /* test if we already attempted to migrate first */
+ if (virAsprintf(&updated, "%s/DEPRECATED-DIRECTORY", old_base) < 0) {
+ goto cleanup;
+ }
+ if (virFileExists(updated)) {
+ goto cleanup;
+ }
+
+ config_home = getenv("XDG_CONFIG_HOME");
+ if (config_home && config_home[0] != '\0') {
+ xdg_dir = strdup(config_home);
+ } else {
+ if (virAsprintf(&xdg_dir, "%s/.config", home) < 0) {
+ goto cleanup;
+ }
+ }
+
+ old_umask = umask(077);
+ if (virFileMakePath(xdg_dir) < 0) {
+ umask(old_umask);
+ goto cleanup;
+ }
+ umask(old_umask);
+
+ if (rename(old_base, config_dir) < 0) {
+ int fd = creat(updated, 0600);
+ VIR_FORCE_CLOSE(fd);
+ VIR_ERROR(_("Unable to migrate %s to %s"), old_base, config_dir);
+ goto cleanup;
+ }
+
+ ret = 0;
+
+ cleanup:
+ VIR_FREE(home);
+ VIR_FREE(old_base);
+ VIR_FREE(xdg_dir);
+ VIR_FREE(config_dir);
+ VIR_FREE(updated);
+
+ return ret;
+}
+
/* Print command-line usage. */
static void
daemonUsage(const char *argv0, bool privileged)
@@ -775,10 +870,10 @@ libvirt management daemon:\n"), argv0);
Default paths:\n\
\n\
Configuration file (unless overridden by -f):\n\
- $HOME/.libvirt/libvirtd.conf\n\
+ $XDG_CONFIG_HOME/libvirt/libvirtd.conf\n\
\n\
Sockets:\n\
- $HOME/.libvirt/libvirt-sock (in UNIX abstract namespace)\n\
+ $XDG_RUNTIME_HOME/libvirt/libvirt-sock (in UNIX abstract namespace)\n\
\n\
TLS:\n\
CA certificate: $HOME/.pki/libvirt/cacert.pem\n\
@@ -786,7 +881,7 @@ libvirt management daemon:\n"), argv0);
Server private key: $HOME/.pki/libvirt/serverkey.pem\n\
\n\
PID file:\n\
- $HOME/.libvirt/libvirtd.pid\n\
+ $XDG_RUNTIME_HOME/libvirt/libvirtd.pid\n\
\n"));
}
}
@@ -931,6 +1026,9 @@ int main(int argc, char **argv) {
exit(EXIT_FAILURE);
}
+ if (migrateProfile() < 0)
+ exit(EXIT_FAILURE);
+
if (config->host_uuid &&
virSetHostUUIDStr(config->host_uuid) < 0) {
VIR_ERROR(_("invalid host UUID: %s"), config->host_uuid);
@@ -977,21 +1075,19 @@ int main(int argc, char **argv) {
if (privileged) {
run_dir = strdup(LOCALSTATEDIR "/run/libvirt");
} else {
- char *user_dir = virGetUserDirectory(geteuid());
+ run_dir = virGetUserRuntimeDirectory(geteuid());
- if (!user_dir) {
+ if (!run_dir) {
VIR_ERROR(_("Can't determine user directory"));
goto cleanup;
}
- ignore_value(virAsprintf(&run_dir, "%s/.libvirt/", user_dir));
- VIR_FREE(user_dir);
}
if (!run_dir) {
virReportOOMError();
goto cleanup;
}
- old_umask = umask(022);
+ old_umask = umask(077);
if (virFileMakePath(run_dir) < 0) {
char ebuf[1024];
VIR_ERROR(_("unable to create rundir %s: %s"), run_dir,
diff --git a/daemon/libvirtd.pod.in b/daemon/libvirtd.pod.in
index 6e699b8..ea6c37d 100644
--- a/daemon/libvirtd.pod.in
+++ b/daemon/libvirtd.pod.in
@@ -85,7 +85,7 @@ command line using the B<-f>|B<--config> option.
The sockets libvirtd will use when B<run as root>.
-=item F<$HOME/.libvirt/libvirt-sock>
+=item F<$XDG_RUNTIME_DIR/libvirt/libvirt-sock>
The socket libvirtd will use when run as a B<non-root> user.
diff --git a/docs/auth.html.in b/docs/auth.html.in
index ecff0fc..60e4f11 100644
--- a/docs/auth.html.in
+++ b/docs/auth.html.in
@@ -25,7 +25,7 @@ for the authentication file using the following sequence:
variable.</li>
<li>The file path specified by the "authfile=/some/file" URI
query parameter</li>
- <li>The file $HOME/.libvirt/auth.conf</li>
+ <li>The file $XDG_CONFIG_DIR/libvirt/auth.conf</li>
<li>The file /etc/libvirt/auth.conf</li>
</ol>
diff --git a/docs/uri.html.in b/docs/uri.html.in
index 2f76e8f..5812ca9 100644
--- a/docs/uri.html.in
+++ b/docs/uri.html.in
@@ -30,7 +30,7 @@ virConnectPtr conn = virConnectOpenReadOnly (<b>"test:///default"</b>);
<p>
To simplify life for administrators, it is possible to setup URI aliases in a
libvirt client configuration file. The configuration file is <code>/etc/libvirt/libvirt.conf</code>
-for the root user, or <code>$HOME/.libvirt/libvirt.conf</code> for any unprivileged user.
+for the root user, or <code>$XDG_CONFIG_DIR/libvirt/libvirt.conf</code> for any unprivileged user.
In this file, the following syntax can be used to setup aliases
</p>
diff --git a/src/libvirt.c b/src/libvirt.c
index cfd7711..22fc863 100644
--- a/src/libvirt.c
+++ b/src/libvirt.c
@@ -969,11 +969,11 @@ virConnectGetConfigFilePath(void)
SYSCONFDIR) < 0)
goto no_memory;
} else {
- char *userdir = virGetUserDirectory(geteuid());
+ char *userdir = virGetUserConfigDirectory(geteuid());
if (!userdir)
goto error;
- if (virAsprintf(&path, "%s/.libvirt/libvirt.conf",
+ if (virAsprintf(&path, "%s/libvirt.conf",
userdir) < 0) {
VIR_FREE(userdir);
goto no_memory;
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 88f8a21..250c8e4 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -1112,6 +1112,7 @@ virFileFindMountPoint;
virFileHasSuffix;
virFileIsExecutable;
virFileIsLink;
+virFileIsDir;
virFileLinkPointsTo;
virFileLock;
virFileMakePath;
@@ -1132,6 +1133,9 @@ virGetGroupID;
virGetGroupName;
virGetHostname;
virGetUserDirectory;
+virGetUserConfigDirectory;
+virGetUserCacheDirectory;
+virGetUserRuntimeDirectory;
virGetUserID;
virGetUserName;
virHexToBin;
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
index d82212f..cea87c2 100644
--- a/src/network/bridge_driver.c
+++ b/src/network/bridge_driver.c
@@ -280,18 +280,20 @@ networkStartup(int privileged) {
if ((base = strdup (SYSCONFDIR "/libvirt")) == NULL)
goto out_of_memory;
} else {
- char *userdir = virGetUserDirectory(uid);
+ char *userdir = virGetUserCacheDirectory(uid);
if (!userdir)
goto error;
if (virAsprintf(&driverState->logDir,
- "%s/.libvirt/qemu/log", userdir) == -1) {
+ "%s/qemu/log", userdir) == -1) {
VIR_FREE(userdir);
goto out_of_memory;
}
+ VIR_FREE(userdir);
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1) {
+ userdir = virGetUserConfigDirectory(uid);
+ if (virAsprintf(&base, "%s", userdir) == -1) {
VIR_FREE(userdir);
goto out_of_memory;
}
diff --git a/src/nwfilter/nwfilter_driver.c b/src/nwfilter/nwfilter_driver.c
index ffb4b5d..3d732ab 100644
--- a/src/nwfilter/nwfilter_driver.c
+++ b/src/nwfilter/nwfilter_driver.c
@@ -87,16 +87,9 @@ nwfilterDriverStartup(int privileged) {
goto out_of_memory;
} else {
uid_t uid = geteuid();
- char *userdir = virGetUserDirectory(uid);
-
- if (!userdir)
+ base = virGetUserConfigDirectory(uid);
+ if (!base)
goto error;
-
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1) {
- VIR_FREE(userdir);
- goto out_of_memory;
- }
- VIR_FREE(userdir);
}
if (virAsprintf(&driverState->configDir,
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index bed8edb..954bb33 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -520,28 +520,38 @@ qemudStartup(int privileged) {
goto out_of_memory;
} else {
uid_t uid = geteuid();
- char *userdir = virGetUserDirectory(uid);
- if (!userdir)
+ char *rundir;
+ char *cachedir;
+
+ cachedir = virGetUserCacheDirectory(uid);
+ if (!cachedir)
goto error;
if (virAsprintf(&qemu_driver->logDir,
- "%s/.libvirt/qemu/log", userdir) == -1) {
- VIR_FREE(userdir);
+ "%s/qemu/log", cachedir) == -1) {
+ VIR_FREE(cachedir);
goto out_of_memory;
}
-
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1) {
- VIR_FREE(userdir);
+ if (virAsprintf(&qemu_driver->cacheDir, "%s/qemu/cache", cachedir) == -1) {
+ VIR_FREE(cachedir);
goto out_of_memory;
}
- VIR_FREE(userdir);
+ VIR_FREE(cachedir);
- if (virAsprintf(&qemu_driver->stateDir, "%s/qemu/run", base) == -1)
+ rundir = virGetUserRuntimeDirectory(uid);
+ if (!rundir)
+ goto error;
+ if (virAsprintf(&qemu_driver->stateDir, "%s/qemu/run", rundir) == -1) {
+ VIR_FREE(rundir);
goto out_of_memory;
+ }
+ VIR_FREE(rundir);
+
+ base = virGetUserConfigDirectory(uid);
+ if (!base)
+ goto error;
if (virAsprintf(&qemu_driver->libDir, "%s/qemu/lib", base) == -1)
goto out_of_memory;
- if (virAsprintf(&qemu_driver->cacheDir, "%s/qemu/cache", base) == -1)
- goto out_of_memory;
if (virAsprintf(&qemu_driver->saveDir, "%s/qemu/save", base) == -1)
goto out_of_memory;
if (virAsprintf(&qemu_driver->snapshotDir, "%s/qemu/snapshot", base) == -1)
diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c
index 7863b73..4a9299a 100644
--- a/src/remote/remote_driver.c
+++ b/src/remote/remote_driver.c
@@ -578,12 +578,12 @@ doRemoteOpen (virConnectPtr conn,
case trans_unix:
if (!sockname) {
if (flags & VIR_DRV_OPEN_REMOTE_USER) {
- char *userdir = virGetUserDirectory(getuid());
+ char *userdir = virGetUserRuntimeDirectory(getuid());
if (!userdir)
goto failed;
- if (virAsprintf(&sockname, "@%s" LIBVIRTD_USER_UNIX_SOCKET, userdir) < 0) {
+ if (virAsprintf(&sockname, "@%s/" LIBVIRTD_USER_UNIX_SOCKET, userdir) < 0) {
VIR_FREE(userdir);
goto out_of_memory;
}
diff --git a/src/remote/remote_driver.h b/src/remote/remote_driver.h
index 1504eec..aca9412 100644
--- a/src/remote/remote_driver.h
+++ b/src/remote/remote_driver.h
@@ -37,7 +37,7 @@ unsigned long remoteVersion(void);
# define LIBVIRTD_TCP_PORT "16509"
# define LIBVIRTD_PRIV_UNIX_SOCKET LOCALSTATEDIR "/run/libvirt/libvirt-sock"
# define LIBVIRTD_PRIV_UNIX_SOCKET_RO LOCALSTATEDIR "/run/libvirt/libvirt-sock-ro"
-# define LIBVIRTD_USER_UNIX_SOCKET "/.libvirt/libvirt-sock"
+# define LIBVIRTD_USER_UNIX_SOCKET "libvirt-sock"
# define LIBVIRTD_CONFIGURATION_FILE SYSCONFDIR "/libvirtd.conf"
/* Defaults for PKI directory. */
diff --git a/src/secret/secret_driver.c b/src/secret/secret_driver.c
index 088a243..f3fcce2 100644
--- a/src/secret/secret_driver.c
+++ b/src/secret/secret_driver.c
@@ -1013,16 +1013,9 @@ secretDriverStartup(int privileged)
goto out_of_memory;
} else {
uid_t uid = geteuid();
- char *userdir = virGetUserDirectory(uid);
-
- if (!userdir)
+ base = virGetUserConfigDirectory(uid);
+ if (!base)
goto error;
-
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1) {
- VIR_FREE(userdir);
- goto out_of_memory;
- }
- VIR_FREE(userdir);
}
if (virAsprintf(&driverState->directory, "%s/secrets", base) == -1)
goto out_of_memory;
diff --git a/src/storage/storage_driver.c b/src/storage/storage_driver.c
index f23ec7e..fd762c0 100644
--- a/src/storage/storage_driver.c
+++ b/src/storage/storage_driver.c
@@ -146,19 +146,12 @@ storageDriverStartup(int privileged)
goto out_of_memory;
} else {
uid_t uid = geteuid();
- char *userdir = virGetUserDirectory(uid);
-
- if (!userdir)
+ base = virGetUserConfigDirectory(uid);
+ if (!base)
goto error;
-
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1) {
- VIR_FREE(userdir);
- goto out_of_memory;
- }
- VIR_FREE(userdir);
}
- /* Configuration paths are either ~/.libvirt/storage/... (session) or
+ /* Configuration paths are either $USER_CONFIG_HOME/libvirt/storage/... (session) or
* /etc/libvirt/storage/... (system).
*/
if (virAsprintf(&driverState->configDir,
diff --git a/src/uml/uml_driver.c b/src/uml/uml_driver.c
index 4e640ff..8a39d73 100644
--- a/src/uml/uml_driver.c
+++ b/src/uml/uml_driver.c
@@ -434,12 +434,12 @@ umlStartup(int privileged)
"%s/run/libvirt/uml-guest", LOCALSTATEDIR) == -1)
goto out_of_memory;
} else {
+ base = virGetUserConfigDirectory(uid);
+ if (!base)
+ goto error;
if (virAsprintf(¨_driver->logDir,
- "%s/.libvirt/uml/log", userdir) == -1)
- goto out_of_memory;
-
- if (virAsprintf(&base, "%s/.libvirt", userdir) == -1)
+ "%s/uml/log", base) == -1)
goto out_of_memory;
if (virAsprintf(¨_driver->monitorDir,
@@ -447,7 +447,7 @@ umlStartup(int privileged)
goto out_of_memory;
}
- /* Configuration paths are either ~/.libvirt/uml/... (session) or
+ /* Configuration paths are either $XDG_CONFIG_HOME/libvirt/uml/... (session) or
* /etc/libvirt/uml/... (system).
*/
if (virAsprintf(¨_driver->configDir, "%s/uml", base) == -1)
diff --git a/src/util/util.c b/src/util/util.c
index 48358b2..ec55118 100644
--- a/src/util/util.c
+++ b/src/util/util.c
@@ -665,6 +665,12 @@ char *virFindFileInPath(const char *file)
return fullpath;
}
+bool virFileIsDir(const char *path)
+{
+ struct stat s;
+ return (stat (path, &s) == 0) && S_ISDIR (s.st_mode);
+}
+
bool virFileExists(const char *path)
{
return access(path, F_OK) == 0;
@@ -2304,6 +2310,62 @@ char *virGetUserDirectory(uid_t uid)
return virGetUserEnt(uid, VIR_USER_ENT_DIRECTORY);
}
+static char *virGetXDGDirectory(uid_t uid, const char *xdgenvname, const char *xdgdefdir)
+{
+ const char *path = NULL;
+ char *ret = NULL;
+ char *home = virGetUserEnt(uid, VIR_USER_ENT_DIRECTORY);
+
+ if (uid == getuid())
+ path = getenv(xdgenvname);
+
+ if (path && path[0]) {
+ if (virAsprintf(&ret, "%s/libvirt/", path) < 0)
+ goto no_memory;
+ } else {
+ if (virAsprintf(&ret, "%s/%s/libvirt/", home, xdgdefdir) < 0)
+ goto no_memory;
+ }
+
+ cleanup:
+ VIR_FREE(home);
+ return ret;
+ no_memory:
+ virReportOOMError();
+ goto cleanup;
+}
+
+char *virGetUserConfigDirectory(uid_t uid)
+{
+ return virGetXDGDirectory(uid, "XDG_CONFIG_HOME", ".config");
+}
+
+char *virGetUserCacheDirectory(uid_t uid)
+{
+ return virGetXDGDirectory(uid, "XDG_CACHE_HOME", ".cache");
+}
+
+char *virGetUserRuntimeDirectory(uid_t uid)
+{
+ const char *path = NULL;
+
+ if (uid == getuid ())
+ path = getenv("XDG_RUNTIME_DIR");
+
+ if (!path || !path[0]) {
+ return virGetUserCacheDirectory(uid);
+ } else {
+ char *ret;
+
+ if (virAsprintf(&ret, "%s/libvirt/", path) < 0) {
+ virReportOOMError();
+ return NULL;
+ }
+
+ return ret;
+ }
+}
+
char *virGetUserName(uid_t uid)
{
return virGetUserEnt(uid, VIR_USER_ENT_NAME);
diff --git a/src/util/util.h b/src/util/util.h
index 85e8bd6..f5fa876 100644
--- a/src/util/util.h
+++ b/src/util/util.h
@@ -85,6 +85,7 @@ int virFileIsLink(const char *linkpath)
char *virFindFileInPath(const char *file);
+bool virFileIsDir (const char *file) ATTRIBUTE_NONNULL(1);
bool virFileExists(const char *file) ATTRIBUTE_NONNULL(1);
bool virFileIsExecutable(const char *file) ATTRIBUTE_NONNULL(1);
@@ -228,6 +229,9 @@ char *virGetHostname(virConnectPtr conn);
int virKillProcess(pid_t pid, int sig);
char *virGetUserDirectory(uid_t uid);
+char *virGetUserConfigDirectory(uid_t uid);
+char *virGetUserCacheDirectory(uid_t uid);
+char *virGetUserRuntimeDirectory(uid_t uid);
char *virGetUserName(uid_t uid);
char *virGetGroupName(gid_t gid);
int virGetUserID(const char *name,
diff --git a/src/util/virauth.c b/src/util/virauth.c
index c59c55a..92ecb7c 100644
--- a/src/util/virauth.c
+++ b/src/util/virauth.c
@@ -65,10 +65,10 @@ int virAuthGetConfigFilePath(virConnectPtr conn,
}
}
- if (!(userdir = virGetUserDirectory(geteuid())))
+ if (!(userdir = virGetUserConfigDirectory(geteuid())))
goto cleanup;
- if (virAsprintf(path, "%s/.libvirt/auth.conf", userdir) < 0)
+ if (virAsprintf(path, "%s/auth.conf", userdir) < 0)
goto no_memory;
VIR_DEBUG("Checking for readability of '%s'", *path);
diff --git a/tools/virsh.c b/tools/virsh.c
index 1207ac9..2ae9b71 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -19864,15 +19864,15 @@ vshReadlineInit(vshControl *ctl)
/* Limit the total size of the history buffer */
stifle_history(500);
- /* Prepare to read/write history from/to the ~/.virsh/history file */
- userdir = virGetUserDirectory(getuid());
+ /* Prepare to read/write history from/to the $XDG_CACHE_HOME/virsh/history file */
+ userdir = virGetUserCacheDirectory(getuid());
if (userdir == NULL) {
vshError(ctl, "%s", _("Could not determine home directory"));
return -1;
}
- if (virAsprintf(&ctl->historydir, "%s/.virsh", userdir) < 0) {
+ if (virAsprintf(&ctl->historydir, "%s/virsh", userdir) < 0) {
vshError(ctl, "%s", _("Out of memory"));
VIR_FREE(userdir);
return -1;
--
1.7.10
12 years, 6 months
[libvirt] [libvirt-php PATCH] Fix installation of libvirt-php.ini
by Ivo van den Abeelen
Building/installing libvirt-php seems to create an incomplete libvirt-php.ini file.
This patch solves this issue, and replaces the '#' comments (deprecated in PHP 5.4).
---
src/Makefile.am | 16 ++++++++--------
1 file changed, 8 insertions(+), 8 deletions(-)
diff --git a/src/Makefile.am b/src/Makefile.am
index 4efd960..dd08d36 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -18,14 +18,14 @@ install-exec-local:
$(INSTALL) -m 644 -D $(PACKAGE).so $(DESTDIR)$(PHPEDIR)/$(PACKAGE).so
$(INSTALL) -m 755 -d $(DESTDIR)$(PHPCDIR)
$(ECHO) "extension=$(PACKAGE).so" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "[libvirt"] > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "# Path to ISO images for VM installations" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "libvirt.iso_path=/var/lib/libvirt/images" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "# Path where disk images for new VMs should be created" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "libvirt.image_path=/var/lib/libvirt/images" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "# Limit maximum number of libvirt connections" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
- $(ECHO) "libvirt.max_connections=5" > $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "[libvirt]" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "; Path to ISO images for VM installations" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "libvirt.iso_path=/var/lib/libvirt/images" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "; Path where disk images for new VMs should be created" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "libvirt.image_path=/var/lib/libvirt/images" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "; Limit maximum number of libvirt connections" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
+ $(ECHO) "libvirt.max_connections=5" >> $(DESTDIR)$(PHPCDIR)/libvirt-php.ini
uninstall-local:
$(RM) -f $(DESTDIR)$(PHPCDIR)/$(PACKAGE).ini
--
1.7.10.1
12 years, 6 months
[libvirt] [libvirt-glib] Add missing domain OS type enums
by Zeeshan Ali (Khattak)
From: "Zeeshan Ali (Khattak)" <zeeshanak(a)gnome.org>
---
libvirt-gconfig/libvirt-gconfig-domain-os.h | 4 +++-
1 files changed, 3 insertions(+), 1 deletions(-)
diff --git a/libvirt-gconfig/libvirt-gconfig-domain-os.h b/libvirt-gconfig/libvirt-gconfig-domain-os.h
index 44b8bdd..832e275 100644
--- a/libvirt-gconfig/libvirt-gconfig-domain-os.h
+++ b/libvirt-gconfig/libvirt-gconfig-domain-os.h
@@ -59,7 +59,9 @@ struct _GVirConfigDomainOsClass
typedef enum {
GVIR_CONFIG_DOMAIN_OS_TYPE_HVM,
GVIR_CONFIG_DOMAIN_OS_TYPE_LINUX,
- GVIR_CONFIG_DOMAIN_OS_TYPE_EXE
+ GVIR_CONFIG_DOMAIN_OS_TYPE_EXE,
+ GVIR_CONFIG_DOMAIN_OS_TYPE_XEN,
+ GVIR_CONFIG_DOMAIN_OS_TYPE_UML
} GVirConfigDomainOsType;
typedef enum {
--
1.7.7.6
12 years, 6 months
[libvirt] [PATCH 0/6] Improve security driver support for LXC
by Daniel P. Berrange
This series aims to improve the SELinux security driver support
for LXC. First it allows the SELinux driver to load different
configuration for LXC, vs SELinux. Second it makes the LXC code
use the security drivers for figuring out mount options.
The code was originally written by Dan Walsh, but split into a
6 part patch series & made to follow coding standards by myself.
12 years, 6 months
[libvirt] Re-2: [Patch] Libvirt - Fix locking for readonly devices
by David Weber
> On Tue, May 08, 2012 at 09:41:02AM +0000, David Weber wrote:
> > Hi,
> >
> > I'm currently working on getting sanlock into Debian/Ubuntu.
> > While testing, I noticed that I wasn't able to add a readonly
> > or shared device: "internal error unsupported
> > configuration: Readonly leases are not supported".
> >
> > After looking into the source, it seems to be the following
> > situation:
> > - Libvirt passes every device to the sanlock plugin, even if
> > it is readonly
> > - The sanlock plugin rejects to add a lease for the readonly
> > device, returning an error so the machine starts to fail
> >
> > The attached patch rejects passing readonly and shared devices
> > to the lock-plugin so they shouldn't be a problem anymore.
>
> This isn't good - the lock manager implementation must be the
> one to decide what todo with readonly & shared disks. The sanlock
> plugin, however, does not currently support readonly/shared leases
> hence why it rejects them. We could probably add a config param
> to allow readonly/shared leases to be skipped by the sanlock plugin.
Thanks for clarification. I've attached an updated patch which
adds such a config param. It works but I can't test
live-migration at the moment. But as far as I understood it
shouldn't be a problem.
David
----------------------------------------------------------------
commit 5a1546f328b166871fbf0e0556b5a2aafba93d63
Author: David Weber <wb(a)munzinger.de>
Date: Mon May 14 09:43:27 2012 +0200
Add ignore param for readonly and shared disk in sanlock
diff --git a/src/locking/lock_driver_sanlock.c b/src/locking/lock_driver_sanlock.c
index d344d6a..57b688a 100644
--- a/src/locking/lock_driver_sanlock.c
+++ b/src/locking/lock_driver_sanlock.c
struct _virLockManagerSanlockDriver {
bool requireLeaseForDisks;
int hostID;
bool autoDiskLease;
+ bool ignoreReadonlyShared;
char *autoDiskLeasePath;
};
static int virLockManagerSanlockLoadConfig(const char *configFile)
CHECK_TYPE("auto_disk_leases", VIR_CONF_LONG);
if (p) driver->autoDiskLease = p->l;
+ p = virConfGetValue(conf, "ignore_readonly_and_shared_disks");
+ CHECK_TYPE("ignore_readonly_and_shared_disks", VIR_CONF_LONG);
+ if (p) driver->ignoreReadonlyShared = p->l;
+
p = virConfGetValue(conf, "disk_lease_dir");
CHECK_TYPE("disk_lease_dir", VIR_CONF_STRING);
if (p && p->str) {
static int virLockManagerSanlockAddResource(virLockManagerPtr lock,
SANLK_MAX_RESOURCES);
return -1;
}
+
+ if (((flags & VIR_LOCK_MANAGER_RESOURCE_READONLY) ||
+ (flags &VIR_LOCK_MANAGER_RESOURCE_SHARED)) &&
+ (driver->ignoreReadonlyShared)) {
+ return 0;
+ }
if (flags & VIR_LOCK_MANAGER_RESOURCE_READONLY) {
virLockError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
diff --git a/src/locking/sanlock.conf b/src/locking/sanlock.conf
index efc35ee..5429522 100644
--- a/src/locking/sanlock.conf
+++ b/src/locking/sanlock.conf
# to enabled, otherwise it defaults to disabled.
#
#require_lease_for_disks = 1
+
+#
+# Ignore readonly and shared disks as they aren't supportet yet
+#
+#ignore_readonly_and_shared_disks = 1
To: berrange(a)redhat.com
Cc: libvir-list(a)redhat.com
sanlock-devel(a)lists.fedorahosted.org
12 years, 6 months
[libvirt] [PATCHv2 1/1] Assign spapr-vio address type to ibmvscsi controller
by Li Zhang
For pseries guest, the default controller model is
ibmvscsi controller, this controller only can work
on spapr-vio address.
This patch is to assign spapr-vio address type to
ibmvscsi controller.
Signed-off-by: Li Zhang <zhlcindy(a)linux.vnet.ibm.com>
---
src/qemu/qemu_command.c | 14 +++++++++++---
1 file changed, 11 insertions(+), 3 deletions(-)
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 117542f..2c6495a 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -779,6 +779,7 @@ qemuAssignSpaprVIOAddress(virDomainDefPtr def, virDomainDeviceInfoPtr info,
int qemuDomainAssignSpaprVIOAddresses(virDomainDefPtr def)
{
int i, rc;
+ int model;
/* Default values match QEMU. See spapr_(llan|vscsi|vty).c */
@@ -790,10 +791,17 @@ int qemuDomainAssignSpaprVIOAddresses(virDomainDefPtr def)
}
for (i = 0 ; i < def->ncontrollers; i++) {
- rc = qemuAssignSpaprVIOAddress(def, &def->controllers[i]->info,
+ model = def->controllers[i]->model;
+ if (model == -1 &&
+ def->controllers[i]->type == VIR_DOMAIN_CONTROLLER_TYPE_SCSI)
+ model = qemuDefaultScsiControllerModel(def);
+ if (model == VIR_DOMAIN_CONTROLLER_MODEL_SCSI_IBMVSCSI) {
+ def->controllers[i]->info.type = VIR_DOMAIN_DEVICE_ADDRESS_TYPE_SPAPRVIO;
+ rc = qemuAssignSpaprVIOAddress(def, &def->controllers[i]->info,
0x2000ul);
- if (rc)
- return rc;
+ if (rc)
+ return rc;
+ }
}
for (i = 0 ; i < def->nserials; i++) {
--
1.7.9.5
12 years, 6 months
[libvirt] [PATCH] esx: Fix memory leaks in error paths related to transferred ownership
by Matthias Bolte
Appending an item to a list transfers ownership of that item to the
list owner. But an error can occur in between item allocation and
appending it to the list. In this case the item has to be freed
explicitly. This was not done in some special cases resulting in
possible memory leaks.
Reported by Coverity.
---
This is actually a v2 for this patch
https://www.redhat.com/archives/libvir-list/2012-May/msg00115.html
src/esx/esx_driver.c | 16 ++++++++++--
src/esx/esx_vi.c | 63 ++++++++++++++++++++++++++++++++++++++++++--------
2 files changed, 66 insertions(+), 13 deletions(-)
diff --git a/src/esx/esx_driver.c b/src/esx/esx_driver.c
index d9f53f7..b3f1948 100644
--- a/src/esx/esx_driver.c
+++ b/src/esx/esx_driver.c
@@ -3489,6 +3489,7 @@ esxDomainSetAutostart(virDomainPtr domain, int autostart)
esxVI_AutoStartPowerInfo *powerInfoList = NULL;
esxVI_AutoStartPowerInfo *powerInfo = NULL;
esxVI_AutoStartPowerInfo *newPowerInfo = NULL;
+ bool newPowerInfo_isAppended = false;
if (esxVI_EnsureSession(priv->primary) < 0) {
return -1;
@@ -3546,9 +3547,7 @@ esxDomainSetAutostart(virDomainPtr domain, int autostart)
if (esxVI_AutoStartPowerInfo_Alloc(&newPowerInfo) < 0 ||
esxVI_Int_Alloc(&newPowerInfo->startOrder) < 0 ||
esxVI_Int_Alloc(&newPowerInfo->startDelay) < 0 ||
- esxVI_Int_Alloc(&newPowerInfo->stopDelay) < 0 ||
- esxVI_AutoStartPowerInfo_AppendToList(&spec->powerInfo,
- newPowerInfo) < 0) {
+ esxVI_Int_Alloc(&newPowerInfo->stopDelay) < 0) {
goto cleanup;
}
@@ -3560,6 +3559,13 @@ esxDomainSetAutostart(virDomainPtr domain, int autostart)
newPowerInfo->stopDelay->value = -1; /* use system default */
newPowerInfo->stopAction = (char *)"none";
+ if (esxVI_AutoStartPowerInfo_AppendToList(&spec->powerInfo,
+ newPowerInfo) < 0) {
+ goto cleanup;
+ }
+
+ newPowerInfo_isAppended = true;
+
if (esxVI_ReconfigureAutostart
(priv->primary,
priv->primary->hostSystem->configManager->autoStartManager,
@@ -3581,6 +3587,10 @@ esxDomainSetAutostart(virDomainPtr domain, int autostart)
esxVI_AutoStartDefaults_Free(&defaults);
esxVI_AutoStartPowerInfo_Free(&powerInfoList);
+ if (!newPowerInfo_isAppended) {
+ esxVI_AutoStartPowerInfo_Free(&newPowerInfo);
+ }
+
return result;
}
diff --git a/src/esx/esx_vi.c b/src/esx/esx_vi.c
index 42e0976..5b5ab69 100644
--- a/src/esx/esx_vi.c
+++ b/src/esx/esx_vi.c
@@ -1882,7 +1882,9 @@ esxVI_LookupObjectContentByType(esxVI_Context *ctx,
{
int result = -1;
esxVI_ObjectSpec *objectSpec = NULL;
+ bool objectSpec_isAppended = false;
esxVI_PropertySpec *propertySpec = NULL;
+ bool propertySpec_isAppended = false;
esxVI_PropertyFilterSpec *propertyFilterSpec = NULL;
if (objectContentList == NULL || *objectContentList != NULL) {
@@ -1951,10 +1953,20 @@ esxVI_LookupObjectContentByType(esxVI_Context *ctx,
if (esxVI_PropertyFilterSpec_Alloc(&propertyFilterSpec) < 0 ||
esxVI_PropertySpec_AppendToList(&propertyFilterSpec->propSet,
- propertySpec) < 0 ||
- esxVI_ObjectSpec_AppendToList(&propertyFilterSpec->objectSet,
- objectSpec) < 0 ||
- esxVI_RetrieveProperties(ctx, propertyFilterSpec,
+ propertySpec) < 0) {
+ goto cleanup;
+ }
+
+ propertySpec_isAppended = true;
+
+ if (esxVI_ObjectSpec_AppendToList(&propertyFilterSpec->objectSet,
+ objectSpec) < 0) {
+ goto cleanup;
+ }
+
+ objectSpec_isAppended = true;
+
+ if (esxVI_RetrieveProperties(ctx, propertyFilterSpec,
objectContentList) < 0) {
goto cleanup;
}
@@ -1994,13 +2006,24 @@ esxVI_LookupObjectContentByType(esxVI_Context *ctx,
* Remove values given by the caller from the data structures to prevent
* them from being freed by the call to esxVI_PropertyFilterSpec_Free().
*/
- objectSpec->obj = NULL;
- objectSpec->selectSet = NULL;
+ if (objectSpec != NULL) {
+ objectSpec->obj = NULL;
+ objectSpec->selectSet = NULL;
+ }
+
if (propertySpec != NULL) {
propertySpec->type = NULL;
propertySpec->pathSet = NULL;
}
+ if (!objectSpec_isAppended) {
+ esxVI_ObjectSpec_Free(&objectSpec);
+ }
+
+ if (!propertySpec_isAppended) {
+ esxVI_PropertySpec_Free(&propertySpec);
+ }
+
esxVI_PropertyFilterSpec_Free(&propertyFilterSpec);
return result;
@@ -3885,7 +3908,9 @@ esxVI_WaitForTaskCompletion(esxVI_Context *ctx,
{
int result = -1;
esxVI_ObjectSpec *objectSpec = NULL;
+ bool objectSpec_isAppended = false;
esxVI_PropertySpec *propertySpec = NULL;
+ bool propertySpec_isAppended = false;
esxVI_PropertyFilterSpec *propertyFilterSpec = NULL;
esxVI_ManagedObjectReference *propertyFilter = NULL;
char *version = NULL;
@@ -3927,10 +3952,20 @@ esxVI_WaitForTaskCompletion(esxVI_Context *ctx,
"info.state") < 0 ||
esxVI_PropertyFilterSpec_Alloc(&propertyFilterSpec) < 0 ||
esxVI_PropertySpec_AppendToList(&propertyFilterSpec->propSet,
- propertySpec) < 0 ||
- esxVI_ObjectSpec_AppendToList(&propertyFilterSpec->objectSet,
- objectSpec) < 0 ||
- esxVI_CreateFilter(ctx, propertyFilterSpec, esxVI_Boolean_True,
+ propertySpec) < 0) {
+ goto cleanup;
+ }
+
+ propertySpec_isAppended = true;
+
+ if (esxVI_ObjectSpec_AppendToList(&propertyFilterSpec->objectSet,
+ objectSpec) < 0) {
+ goto cleanup;
+ }
+
+ objectSpec_isAppended = true;
+
+ if (esxVI_CreateFilter(ctx, propertyFilterSpec, esxVI_Boolean_True,
&propertyFilter) < 0) {
goto cleanup;
}
@@ -4066,6 +4101,14 @@ esxVI_WaitForTaskCompletion(esxVI_Context *ctx,
propertySpec->type = NULL;
}
+ if (!objectSpec_isAppended) {
+ esxVI_ObjectSpec_Free(&objectSpec);
+ }
+
+ if (!propertySpec_isAppended) {
+ esxVI_PropertySpec_Free(&propertySpec);
+ }
+
esxVI_PropertyFilterSpec_Free(&propertyFilterSpec);
esxVI_ManagedObjectReference_Free(&propertyFilter);
VIR_FREE(version);
--
1.7.4.1
12 years, 6 months
[libvirt] [RFC PATCH] Add Qemu Network Helper
by rmarwah@linux.vnet.ibm.com
From: Richa Marwaha <rmarwah(a)linux.vnet.ibm.com>
QEMU has a new feature which allows QEMU to execute under an unprivileged user ID and still be able to add a tap device to a Linux network bridge. Below is
the link to the QEMU patches for the bridge helper feature:
http://lists.gnu.org/archive/html/qemu-devel/2012-01/msg03562.html
The existing libvirt tap network device support for adding a tap device to a bridge (-netdev tap) works only when connected to a libvirtd instance running
as the privileged system account 'root'. When connected to a libvirtd instance running as an unprivileged user (ie. using the session URI) creation of
the tap device fails as follows:
error: Failed to start domain F14_64 error: Unable to create tap device vnet%d: Operation not permitted
With this support, creating a tap device in the above scenario will be possible. Additionally, hot attaching a tap device to a bridge while running when
connected to a libvirtd instance running as an unprivileged user will be possible.
Signed-off-by: Richa Marwaha <rmarwah(a)linux.vnet.ibm.com>
Signed-off-by: Corey Bryant<coreyb(a)linux.vnet.ibm.com>
---
src/qemu/qemu_command.c | 38 +++++++++++++++++++++++++-------------
src/qemu/qemu_command.h | 1 +
src/qemu/qemu_hotplug.c | 19 +++++++++++--------
3 files changed, 37 insertions(+), 21 deletions(-)
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index 117542f..daa5381 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -2745,6 +2745,7 @@ error:
char *
qemuBuildHostNetStr(virDomainNetDefPtr net,
+ struct qemud_driver *driver,
char type_sep,
int vlan,
const char *tapfd,
@@ -2753,6 +2754,7 @@ qemuBuildHostNetStr(virDomainNetDefPtr net,
bool is_tap = false;
virBuffer buf = VIR_BUFFER_INITIALIZER;
enum virDomainNetType netType = virDomainNetGetActualType(net);
+ const char *brname = NULL;
if (net->script && netType != VIR_DOMAIN_NET_TYPE_ETHERNET) {
qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED,
@@ -2762,8 +2764,15 @@ qemuBuildHostNetStr(virDomainNetDefPtr net,
}
switch (netType) {
- case VIR_DOMAIN_NET_TYPE_NETWORK:
case VIR_DOMAIN_NET_TYPE_BRIDGE:
+ if (!driver->privileged) {
+ brname = virDomainNetGetActualBridgeName(net);
+ virBufferAsprintf(&buf, "bridge%cbr=%s", type_sep, brname);
+ type_sep = ',';
+ is_tap = true;
+ break;
+ }
+ case VIR_DOMAIN_NET_TYPE_NETWORK:
case VIR_DOMAIN_NET_TYPE_DIRECT:
virBufferAsprintf(&buf, "tap%cfd=%s", type_sep, tapfd);
type_sep = ',';
@@ -4865,7 +4874,7 @@ qemuBuildCommandLine(virConnectPtr conn,
for (i = 0 ; i < def->nnets ; i++) {
virDomainNetDefPtr net = def->nets[i];
char *nic, *host;
- char tapfd_name[50];
+ char tapfd_name[50] = "";
char vhostfd_name[50] = "";
int vlan;
int bootindex = bootNet;
@@ -4902,17 +4911,20 @@ qemuBuildCommandLine(virConnectPtr conn,
if (actualType == VIR_DOMAIN_NET_TYPE_NETWORK ||
actualType == VIR_DOMAIN_NET_TYPE_BRIDGE) {
- int tapfd = qemuNetworkIfaceConnect(def, conn, driver, net,
- qemuCaps);
- if (tapfd < 0)
- goto error;
+ if (actualType == VIR_DOMAIN_NET_TYPE_NETWORK ||
+ driver->privileged) {
+ int tapfd = qemuNetworkIfaceConnect(def, conn, driver, net,
+ qemuCaps);
+ if (tapfd < 0)
+ goto error;
- last_good_net = i;
- virCommandTransferFD(cmd, tapfd);
+ last_good_net = i;
+ virCommandTransferFD(cmd, tapfd);
- if (snprintf(tapfd_name, sizeof(tapfd_name), "%d",
- tapfd) >= sizeof(tapfd_name))
- goto no_memory;
+ if (snprintf(tapfd_name, sizeof(tapfd_name), "%d",
+ tapfd) >= sizeof(tapfd_name))
+ goto no_memory;
+ }
} else if (actualType == VIR_DOMAIN_NET_TYPE_DIRECT) {
int tapfd = qemuPhysIfaceConnect(def, driver, net,
qemuCaps, vmop);
@@ -4955,7 +4967,7 @@ qemuBuildCommandLine(virConnectPtr conn,
if (qemuCapsGet(qemuCaps, QEMU_CAPS_NETDEV) &&
qemuCapsGet(qemuCaps, QEMU_CAPS_DEVICE)) {
virCommandAddArg(cmd, "-netdev");
- if (!(host = qemuBuildHostNetStr(net, ',', vlan,
+ if (!(host = qemuBuildHostNetStr(net, driver, ',', vlan,
tapfd_name, vhostfd_name)))
goto error;
virCommandAddArg(cmd, host);
@@ -4978,7 +4990,7 @@ qemuBuildCommandLine(virConnectPtr conn,
if (!(qemuCapsGet(qemuCaps, QEMU_CAPS_NETDEV) &&
qemuCapsGet(qemuCaps, QEMU_CAPS_DEVICE))) {
virCommandAddArg(cmd, "-net");
- if (!(host = qemuBuildHostNetStr(net, ',', vlan,
+ if (!(host = qemuBuildHostNetStr(net, driver, ',', vlan,
tapfd_name, vhostfd_name)))
goto error;
virCommandAddArg(cmd, host);
diff --git a/src/qemu/qemu_command.h b/src/qemu/qemu_command.h
index 1eafeb3..04240bc 100644
--- a/src/qemu/qemu_command.h
+++ b/src/qemu/qemu_command.h
@@ -62,6 +62,7 @@ qemuBuildChrDeviceStr (virDomainChrDefPtr serial,
/* With vlan == -1, use netdev syntax, else old hostnet */
char * qemuBuildHostNetStr(virDomainNetDefPtr net,
+ struct qemud_driver *driver,
char type_sep,
int vlan,
const char *tapfd,
diff --git a/src/qemu/qemu_hotplug.c b/src/qemu/qemu_hotplug.c
index ad31eba..7f8b1e4 100644
--- a/src/qemu/qemu_hotplug.c
+++ b/src/qemu/qemu_hotplug.c
@@ -699,12 +699,15 @@ int qemuDomainAttachNetDevice(virConnectPtr conn,
if (actualType == VIR_DOMAIN_NET_TYPE_BRIDGE ||
actualType == VIR_DOMAIN_NET_TYPE_NETWORK) {
- if ((tapfd = qemuNetworkIfaceConnect(vm->def, conn, driver, net,
- priv->qemuCaps)) < 0)
- goto cleanup;
- iface_connected = true;
- if (qemuOpenVhostNet(vm->def, net, priv->qemuCaps, &vhostfd) < 0)
- goto cleanup;
+ if (actualType == VIR_DOMAIN_NET_TYPE_NETWORK ||
+ driver->privileged) {
+ if ((tapfd = qemuNetworkIfaceConnect(vm->def, conn, driver, net,
+ priv->qemuCaps)) < 0)
+ goto cleanup;
+ iface_connected = true;
+ if (qemuOpenVhostNet(vm->def, net, priv->qemuCaps, &vhostfd) < 0)
+ goto cleanup;
+ }
} else if (actualType == VIR_DOMAIN_NET_TYPE_DIRECT) {
if ((tapfd = qemuPhysIfaceConnect(vm->def, driver, net,
priv->qemuCaps,
@@ -752,11 +755,11 @@ int qemuDomainAttachNetDevice(virConnectPtr conn,
if (qemuCapsGet(priv->qemuCaps, QEMU_CAPS_NETDEV) &&
qemuCapsGet(priv->qemuCaps, QEMU_CAPS_DEVICE)) {
- if (!(netstr = qemuBuildHostNetStr(net, ',',
+ if (!(netstr = qemuBuildHostNetStr(net, driver, ',',
-1, tapfd_name, vhostfd_name)))
goto cleanup;
} else {
- if (!(netstr = qemuBuildHostNetStr(net, ' ',
+ if (!(netstr = qemuBuildHostNetStr(net, driver, ' ',
vlan, tapfd_name, vhostfd_name)))
goto cleanup;
}
--
1.7.1
12 years, 6 months
[libvirt] [PATCH] Mount fresh instance of sysfs in LXC
by Daniel P. Berrange
From: "Daniel P. Berrange" <berrange(a)redhat.com>
Currently to make sysfs readonly, we remount the existing
instance and then bind it readonly. Unfortunately this means
sysfs is still showing device objects wrt the host OS namespace.
We need it to reflect the container namespace, so we must mount
a completely new instance of it.
* src/lxc/lxc_container.c: Mount fresh sysfs instance
---
src/lxc/lxc_container.c | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/src/lxc/lxc_container.c b/src/lxc/lxc_container.c
index b953646..77d33e1 100644
--- a/src/lxc/lxc_container.c
+++ b/src/lxc/lxc_container.c
@@ -441,8 +441,7 @@ static int lxcContainerMountBasicFS(lxc_child_argv_t *argv, const char *srcprefi
{ false, "proc", "/proc", "proc", NULL, MS_NOSUID|MS_NOEXEC|MS_NODEV },
{ false, "/proc/sys", "/proc/sys", NULL, NULL, MS_BIND },
{ false, "/proc/sys", "/proc/sys", NULL, NULL, MS_BIND|MS_REMOUNT|MS_RDONLY },
- { true, "/sys", "/sys", NULL, NULL, MS_BIND },
- { true, "/sys", "/sys", NULL, NULL, MS_BIND|MS_REMOUNT|MS_RDONLY },
+ { false, "sysfs", "/sys", "sysfs", NULL, MS_NOSUID|MS_NOEXEC|MS_NODEV|MS_RDONLY },
#if HAVE_SELINUX
{ true, SELINUX_MOUNT, SELINUX_MOUNT, NULL, NULL, MS_BIND },
{ true, SELINUX_MOUNT, SELINUX_MOUNT, NULL, NULL, MS_BIND|MS_REMOUNT|MS_RDONLY },
--
1.7.10.1
12 years, 6 months