Now that 100% of libvirt code is forbidden in a SUID environment,
we no longer need to worry about whether env variables are
trustworthy or not. The virt-login-shell setuid program, which
does not link to any libvirt code, will purge all environment
variables, except $TERM, before invoking the virt-login-shell-helper
program which uses libvirt.
Signed-off-by: Daniel P. Berrangé <berrange(a)redhat.com>
---
cfg.mk | 9 ---------
src/libvirt-admin.c | 2 +-
src/libvirt.c | 2 +-
src/libvirt_private.syms | 2 --
src/network/leaseshelper.c | 14 ++++++-------
src/qemu/qemu_firmware.c | 2 +-
src/remote/remote_driver.c | 2 +-
src/rpc/virnetlibsshsession.c | 2 +-
src/rpc/virnettlscontext.c | 2 +-
src/util/virauth.c | 2 +-
src/util/vircommand.c | 2 +-
src/util/virfile.c | 4 ++--
src/util/virlease.c | 4 ++--
src/util/virlog.c | 6 +++---
src/util/virsystemd.c | 8 ++++----
src/util/virutil.c | 36 ++++-----------------------------
src/util/virutil.h | 3 ---
src/vbox/vbox_XPCOMCGlue.c | 2 +-
src/vbox/vbox_common.c | 2 +-
tools/virsh.c | 2 +-
tools/virt-login-shell-helper.c | 4 ++--
tools/vsh.c | 12 +++++------
22 files changed, 41 insertions(+), 83 deletions(-)
diff --git a/cfg.mk b/cfg.mk
index 9130b4560b..ec09550b49 100644
--- a/cfg.mk
+++ b/cfg.mk
@@ -855,12 +855,6 @@ sc_prohibit_unbounded_arrays_in_rpc:
halt='Arrays in XDR must have a upper limit set for <NNN>' \
$(_sc_search_regexp)
-sc_prohibit_getenv:
- @prohibit='\b(secure_)?getenv *\(' \
- exclude='exempt from syntax-check' \
- halt='Use virGetEnv{Allow,Block}SUID instead of getenv' \
- $(_sc_search_regexp)
-
sc_prohibit_atoi:
@prohibit='\bato(i|f|l|ll|q) *\(' \
halt='Use virStrToLong* instead of atoi, atol, atof, atoq, atoll' \
@@ -1316,9 +1310,6 @@ exclude_file_name_regexp--sc_prohibit_int_ijk = \
exclude_file_name_regexp--sc_prohibit_unsigned_pid = \
^(include/libvirt/.*\.h|src/(qemu/qemu_driver\.c|driver-hypervisor\.h|libvirt(-[a-z]*)?\.c|.*\.x|util/vir(polkit|systemd)\.c)|tests/virpolkittest\.c|tools/virsh-domain\.c)$$
-exclude_file_name_regexp--sc_prohibit_getenv = \
- ^tests/.*\.[ch]|tools/virt-login-shell\.c$$
-
exclude_file_name_regexp--sc_avoid_attribute_unused_in_header = \
^(src/util/virlog\.h|src/network/bridge_driver\.h)$$
diff --git a/src/libvirt-admin.c b/src/libvirt-admin.c
index 74dedf64d8..4ae50b188f 100644
--- a/src/libvirt-admin.c
+++ b/src/libvirt-admin.c
@@ -169,7 +169,7 @@ getSocketPath(virURIPtr uri)
static int
virAdmGetDefaultURI(virConfPtr conf, char **uristr)
{
- const char *defname = virGetEnvAllowSUID("LIBVIRT_ADMIN_DEFAULT_URI");
+ const char *defname = getenv("LIBVIRT_ADMIN_DEFAULT_URI");
if (defname && *defname) {
if (VIR_STRDUP(*uristr, defname) < 0)
return -1;
diff --git a/src/libvirt.c b/src/libvirt.c
index 161001bf48..768ad348c7 100644
--- a/src/libvirt.c
+++ b/src/libvirt.c
@@ -774,7 +774,7 @@ virConnectGetDefaultURI(virConfPtr conf,
char **name)
{
int ret = -1;
- const char *defname = virGetEnvBlockSUID("LIBVIRT_DEFAULT_URI");
+ const char *defname = getenv("LIBVIRT_DEFAULT_URI");
if (defname && *defname) {
VIR_DEBUG("Using LIBVIRT_DEFAULT_URI '%s'", defname);
if (VIR_STRDUP(*name, defname) < 0)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 983fe93d99..12c506a87a 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -3270,8 +3270,6 @@ virFormatIntDecimal;
virFormatIntPretty;
virGetDeviceID;
virGetDeviceUnprivSGIO;
-virGetEnvAllowSUID;
-virGetEnvBlockSUID;
virGetGroupID;
virGetGroupList;
virGetGroupName;
diff --git a/src/network/leaseshelper.c b/src/network/leaseshelper.c
index 2a10fbf33a..481f29aa59 100644
--- a/src/network/leaseshelper.c
+++ b/src/network/leaseshelper.c
@@ -86,10 +86,10 @@ main(int argc, char **argv)
const char *ip = NULL;
const char *mac = NULL;
const char *leases_str = NULL;
- const char *iaid = virGetEnvAllowSUID("DNSMASQ_IAID");
- const char *clientid = virGetEnvAllowSUID("DNSMASQ_CLIENT_ID");
- const char *interface = virGetEnvAllowSUID("DNSMASQ_INTERFACE");
- const char *hostname = virGetEnvAllowSUID("DNSMASQ_SUPPLIED_HOSTNAME");
+ const char *iaid = getenv("DNSMASQ_IAID");
+ const char *clientid = getenv("DNSMASQ_CLIENT_ID");
+ const char *interface = getenv("DNSMASQ_INTERFACE");
+ const char *hostname = getenv("DNSMASQ_SUPPLIED_HOSTNAME");
char *server_duid = NULL;
int action = -1;
int pid_file_fd = -1;
@@ -131,7 +131,7 @@ main(int argc, char **argv)
* events for expired leases. So, libvirtd sets another env var for this
* purpose */
if (!interface &&
- !(interface = virGetEnvAllowSUID("VIR_BRIDGE_NAME")))
+ !(interface = getenv("VIR_BRIDGE_NAME")))
goto cleanup;
ip = argv[3];
@@ -148,11 +148,11 @@ main(int argc, char **argv)
/* Check if it is an IPv6 lease */
if (iaid) {
- mac = virGetEnvAllowSUID("DNSMASQ_MAC");
+ mac = getenv("DNSMASQ_MAC");
clientid = argv[2];
}
- if (VIR_STRDUP(server_duid, virGetEnvAllowSUID("DNSMASQ_SERVER_DUID")) <
0)
+ if (VIR_STRDUP(server_duid, getenv("DNSMASQ_SERVER_DUID")) < 0)
goto cleanup;
if (virAsprintf(&custom_lease_file,
diff --git a/src/qemu/qemu_firmware.c b/src/qemu/qemu_firmware.c
index bf29b10b9a..983a7c83b2 100644
--- a/src/qemu/qemu_firmware.c
+++ b/src/qemu/qemu_firmware.c
@@ -986,7 +986,7 @@ qemuFirmwareFetchConfigs(char ***firmwares,
* much sense to parse files in root's home directory. It
* makes sense only for session daemon which runs under
* regular user. */
- if (VIR_STRDUP(xdgConfig, virGetEnvBlockSUID("XDG_CONFIG_HOME")) <
0)
+ if (VIR_STRDUP(xdgConfig, getenv("XDG_CONFIG_HOME")) < 0)
return -1;
if (!xdgConfig) {
diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c
index 5e6007d468..76ea49ed8e 100644
--- a/src/remote/remote_driver.c
+++ b/src/remote/remote_driver.c
@@ -1297,7 +1297,7 @@ remoteConnectOpen(virConnectPtr conn,
struct private_data *priv;
int ret = VIR_DRV_OPEN_ERROR;
int rflags = 0;
- const char *autostart = virGetEnvBlockSUID("LIBVIRT_AUTOSTART");
+ const char *autostart = getenv("LIBVIRT_AUTOSTART");
char *driver = NULL;
char *transport = NULL;
diff --git a/src/rpc/virnetlibsshsession.c b/src/rpc/virnetlibsshsession.c
index 093ac29071..62cbe1e06a 100644
--- a/src/rpc/virnetlibsshsession.c
+++ b/src/rpc/virnetlibsshsession.c
@@ -172,7 +172,7 @@ virNetLibsshSessionOnceInit(void)
ssh_set_log_level(TRACE_LIBSSH);
#endif
- dbgLevelStr = virGetEnvAllowSUID("LIBVIRT_LIBSSH_DEBUG");
+ dbgLevelStr = getenv("LIBVIRT_LIBSSH_DEBUG");
if (dbgLevelStr &&
virStrToLong_i(dbgLevelStr, NULL, 10, &dbgLevel) >= 0)
ssh_set_log_level(dbgLevel);
diff --git a/src/rpc/virnettlscontext.c b/src/rpc/virnettlscontext.c
index 4adc409c0b..416c8308ed 100644
--- a/src/rpc/virnettlscontext.c
+++ b/src/rpc/virnettlscontext.c
@@ -1439,7 +1439,7 @@ void virNetTLSSessionDispose(void *obj)
void virNetTLSInit(void)
{
const char *gnutlsdebug;
- if ((gnutlsdebug = virGetEnvAllowSUID("LIBVIRT_GNUTLS_DEBUG")) != NULL) {
+ if ((gnutlsdebug = getenv("LIBVIRT_GNUTLS_DEBUG")) != NULL) {
int val;
if (virStrToLong_i(gnutlsdebug, NULL, 10, &val) < 0)
val = 10;
diff --git a/src/util/virauth.c b/src/util/virauth.c
index e5994cbb7c..9de3996e92 100644
--- a/src/util/virauth.c
+++ b/src/util/virauth.c
@@ -42,7 +42,7 @@ virAuthGetConfigFilePathURI(virURIPtr uri,
char **path)
{
size_t i;
- const char *authenv = virGetEnvBlockSUID("LIBVIRT_AUTH_FILE");
+ const char *authenv = getenv("LIBVIRT_AUTH_FILE");
VIR_AUTOFREE(char *) userdir = NULL;
*path = NULL;
diff --git a/src/util/vircommand.c b/src/util/vircommand.c
index ea9a9fd622..79e1e87964 100644
--- a/src/util/vircommand.c
+++ b/src/util/vircommand.c
@@ -1424,7 +1424,7 @@ virCommandAddEnvPass(virCommandPtr cmd, const char *name)
if (!cmd || cmd->has_error)
return;
- value = virGetEnvAllowSUID(name);
+ value = getenv(name);
if (value)
virCommandAddEnvPair(cmd, name, value);
}
diff --git a/src/util/virfile.c b/src/util/virfile.c
index 775192ff00..7667c16d27 100644
--- a/src/util/virfile.c
+++ b/src/util/virfile.c
@@ -1674,7 +1674,7 @@ virFindFileInPath(const char *file)
}
/* copy PATH env so we can tweak it */
- origpath = virGetEnvBlockSUID("PATH");
+ origpath = getenv("PATH");
if (!origpath)
origpath = "/bin:/usr/bin";
@@ -1735,7 +1735,7 @@ virFileFindResourceFull(const char *filename,
const char *envname)
{
char *ret = NULL;
- const char *envval = envname ? virGetEnvBlockSUID(envname) : NULL;
+ const char *envval = envname ? getenv(envname) : NULL;
const char *path;
if (!prefix)
diff --git a/src/util/virlease.c b/src/util/virlease.c
index 93ca72e3af..87e9a3ce88 100644
--- a/src/util/virlease.c
+++ b/src/util/virlease.c
@@ -213,13 +213,13 @@ virLeaseNew(virJSONValuePtr *lease_ret,
const char *server_duid)
{
VIR_AUTOPTR(virJSONValue) lease_new = NULL;
- const char *exptime_tmp = virGetEnvAllowSUID("DNSMASQ_LEASE_EXPIRES");
+ const char *exptime_tmp = getenv("DNSMASQ_LEASE_EXPIRES");
long long expirytime = 0;
VIR_AUTOFREE(char *) exptime = NULL;
/* In case hostname is still unknown, use the last known one */
if (!hostname)
- hostname = virGetEnvAllowSUID("DNSMASQ_OLD_HOSTNAME");
+ hostname = getenv("DNSMASQ_OLD_HOSTNAME");
if (!mac)
return 0;
diff --git a/src/util/virlog.c b/src/util/virlog.c
index 6a2229ae2b..4c76fbc5a4 100644
--- a/src/util/virlog.c
+++ b/src/util/virlog.c
@@ -1308,13 +1308,13 @@ virLogSetFromEnv(void)
if (virLogInitialize() < 0)
return;
- debugEnv = virGetEnvAllowSUID("LIBVIRT_DEBUG");
+ debugEnv = getenv("LIBVIRT_DEBUG");
if (debugEnv && *debugEnv)
virLogSetDefaultPriority(virLogParseDefaultPriority(debugEnv));
- debugEnv = virGetEnvAllowSUID("LIBVIRT_LOG_FILTERS");
+ debugEnv = getenv("LIBVIRT_LOG_FILTERS");
if (debugEnv && *debugEnv)
virLogSetFilters(debugEnv);
- debugEnv = virGetEnvAllowSUID("LIBVIRT_LOG_OUTPUTS");
+ debugEnv = getenv("LIBVIRT_LOG_OUTPUTS");
if (debugEnv && *debugEnv)
virLogSetOutputs(debugEnv);
}
diff --git a/src/util/virsystemd.c b/src/util/virsystemd.c
index 1cb8874403..26b751311f 100644
--- a/src/util/virsystemd.c
+++ b/src/util/virsystemd.c
@@ -509,7 +509,7 @@ virSystemdNotifyStartup(void)
.msg_iovlen = 1,
};
- if (!(path = virGetEnvBlockSUID("NOTIFY_SOCKET"))) {
+ if (!(path = getenv("NOTIFY_SOCKET"))) {
VIR_DEBUG("Skipping systemd notify, not requested");
return;
}
@@ -798,7 +798,7 @@ virSystemdGetListenFDs(void)
VIR_DEBUG("Setting up networking from caller");
- if (!(pidstr = virGetEnvAllowSUID("LISTEN_PID"))) {
+ if (!(pidstr = getenv("LISTEN_PID"))) {
VIR_DEBUG("No LISTEN_PID from caller");
return 0;
}
@@ -814,7 +814,7 @@ virSystemdGetListenFDs(void)
return 0;
}
- if (!(fdstr = virGetEnvAllowSUID("LISTEN_FDS"))) {
+ if (!(fdstr = getenv("LISTEN_FDS"))) {
VIR_DEBUG("No LISTEN_FDS from caller");
return 0;
}
@@ -866,7 +866,7 @@ virSystemdActivationNew(virSystemdActivationMap *map,
if (!(act->fds = virHashCreate(10, virSystemdActivationEntryFree)))
goto error;
- fdnames = virGetEnvAllowSUID("LISTEN_FDNAMES");
+ fdnames = getenv("LISTEN_FDNAMES");
if (fdnames) {
if (virSystemdActivationInitFromNames(act, nfds, fdnames) < 0)
goto error;
diff --git a/src/util/virutil.c b/src/util/virutil.c
index 4e0dbe15c4..89d2cf011f 100644
--- a/src/util/virutil.c
+++ b/src/util/virutil.c
@@ -739,7 +739,7 @@ char *virGetUserShell(uid_t uid)
static char *virGetXDGDirectory(const char *xdgenvname, const char *xdgdefdir)
{
- const char *path = virGetEnvBlockSUID(xdgenvname);
+ const char *path = getenv(xdgenvname);
char *ret = NULL;
char *home = NULL;
@@ -767,7 +767,7 @@ char *virGetUserCacheDirectory(void)
char *virGetUserRuntimeDirectory(void)
{
- const char *path = virGetEnvBlockSUID("XDG_RUNTIME_DIR");
+ const char *path = getenv("XDG_RUNTIME_DIR");
if (!path || !path[0]) {
return virGetUserCacheDirectory();
@@ -1137,7 +1137,7 @@ virGetUserDirectoryByUID(uid_t uid ATTRIBUTE_UNUSED)
const char *dir;
char *ret;
- dir = virGetEnvBlockSUID("HOME");
+ dir = getenv("HOME");
/* Only believe HOME if it is an absolute path and exists */
if (dir) {
@@ -1157,7 +1157,7 @@ virGetUserDirectoryByUID(uid_t uid ATTRIBUTE_UNUSED)
if (!dir)
/* USERPROFILE is probably the closest equivalent to $HOME? */
- dir = virGetEnvBlockSUID("USERPROFILE");
+ dir = getenv("USERPROFILE");
if (VIR_STRDUP(ret, dir) < 0)
return NULL;
@@ -1722,34 +1722,6 @@ virParseOwnershipIds(const char *label, uid_t *uidPtr, gid_t
*gidPtr)
return rc;
}
-
-/**
- * virGetEnvBlockSUID:
- * @name: the environment variable name
- *
- * Obtain an environment variable which is unsafe to
- * use when running setuid. If running setuid, a NULL
- * value will be returned
- */
-const char *virGetEnvBlockSUID(const char *name)
-{
- return secure_getenv(name); /* exempt from syntax-check */
-}
-
-
-/**
- * virGetEnvAllowSUID:
- * @name: the environment variable name
- *
- * Obtain an environment variable which is safe to
- * use when running setuid. The value will be returned
- * even when running setuid
- */
-const char *virGetEnvAllowSUID(const char *name)
-{
- return getenv(name); /* exempt from syntax-check */
-}
-
static time_t selfLastChanged;
time_t virGetSelfLastChanged(void)
diff --git a/src/util/virutil.h b/src/util/virutil.h
index 52d0c33773..b64a85f49e 100644
--- a/src/util/virutil.h
+++ b/src/util/virutil.h
@@ -141,9 +141,6 @@ char *virGetUnprivSGIOSysfsPath(const char *path,
int virParseOwnershipIds(const char *label, uid_t *uidPtr, gid_t *gidPtr);
-const char *virGetEnvBlockSUID(const char *name);
-const char *virGetEnvAllowSUID(const char *name);
-
time_t virGetSelfLastChanged(void);
void virUpdateSelfLastChanged(const char *path);
diff --git a/src/vbox/vbox_XPCOMCGlue.c b/src/vbox/vbox_XPCOMCGlue.c
index 2a054f02d6..72ae49b6b2 100644
--- a/src/vbox/vbox_XPCOMCGlue.c
+++ b/src/vbox/vbox_XPCOMCGlue.c
@@ -190,7 +190,7 @@ VBoxCGlueInit(unsigned int *version)
"/usr/local/lib/VirtualBox",
"/Applications/VirtualBox.app/Contents/MacOS"
};
- const char *home = virGetEnvBlockSUID("VBOX_APP_HOME");
+ const char *home = getenv("VBOX_APP_HOME");
/* If the user specifies the location, try only that. */
if (home != NULL) {
diff --git a/src/vbox/vbox_common.c b/src/vbox/vbox_common.c
index 8a912da50c..6a4ef01e64 100644
--- a/src/vbox/vbox_common.c
+++ b/src/vbox/vbox_common.c
@@ -3558,7 +3558,7 @@ vboxDumpDisplay(virDomainDefPtr def, vboxDriverPtr data, IMachine
*machine)
graphics->type = VIR_DOMAIN_GRAPHICS_TYPE_DESKTOP;
if (VIR_STRDUP(graphics->data.desktop.display,
- virGetEnvBlockSUID("DISPLAY")) < 0)
+ getenv("DISPLAY")) < 0)
goto cleanup;
}
diff --git a/tools/virsh.c b/tools/virsh.c
index f09ce1ec98..692a1ff16d 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -913,7 +913,7 @@ main(int argc, char **argv)
if (!ctl->connname)
ctl->connname = vshStrdup(ctl,
-
virGetEnvBlockSUID("VIRSH_DEFAULT_CONNECT_URI"));
+ getenv("VIRSH_DEFAULT_CONNECT_URI"));
if (!ctl->imode) {
ret = vshCommandRun(ctl, ctl->cmd);
diff --git a/tools/virt-login-shell-helper.c b/tools/virt-login-shell-helper.c
index 8dc3bedaa0..d062c07a27 100644
--- a/tools/virt-login-shell-helper.c
+++ b/tools/virt-login-shell-helper.c
@@ -372,8 +372,8 @@ main(int argc, char **argv)
/* We're duping the string because the clearenv()
* call will shortly release the pointer we get
- * back from virGetEnvAllowSUID() right here */
- if (VIR_STRDUP(term, virGetEnvAllowSUID("TERM")) < 0)
+ * back from getenv() right here */
+ if (VIR_STRDUP(term, getenv("TERM")) < 0)
goto cleanup;
/* A fork is required to create new process in correct pid namespace. */
diff --git a/tools/vsh.c b/tools/vsh.c
index 5de082cb34..9bdd90e362 100644
--- a/tools/vsh.c
+++ b/tools/vsh.c
@@ -2429,7 +2429,7 @@ vshEditWriteToTempFile(vshControl *ctl, const char *doc)
int fd;
char ebuf[1024];
- tmpdir = virGetEnvBlockSUID("TMPDIR");
+ tmpdir = getenv("TMPDIR");
if (!tmpdir) tmpdir = "/tmp";
if (virAsprintf(&ret, "%s/virshXXXXXX.xml", tmpdir) < 0) {
vshError(ctl, "%s", _("out of memory"));
@@ -2476,9 +2476,9 @@ vshEditFile(vshControl *ctl, const char *filename)
int outfd = STDOUT_FILENO;
int errfd = STDERR_FILENO;
- editor = virGetEnvBlockSUID("VISUAL");
+ editor = getenv("VISUAL");
if (!editor)
- editor = virGetEnvBlockSUID("EDITOR");
+ editor = getenv("EDITOR");
if (!editor)
editor = DEFAULT_EDITOR;
@@ -2956,7 +2956,7 @@ vshReadlineInit(vshControl *ctl)
goto cleanup;
/* Limit the total size of the history buffer */
- if ((histsize_str = virGetEnvBlockSUID(histsize_env))) {
+ if ((histsize_str = getenv(histsize_env))) {
if (virStrToLong_i(histsize_str, NULL, 10, &max_history) < 0) {
vshError(ctl, _("Bad $%s value."), histsize_env);
goto cleanup;
@@ -3072,7 +3072,7 @@ vshInitDebug(vshControl *ctl)
return -1;
/* log level not set from commandline, check env variable */
- debugEnv = virGetEnvAllowSUID(env);
+ debugEnv = getenv(env);
if (debugEnv) {
int debug;
if (virStrToLong_i(debugEnv, NULL, 10, &debug) < 0 ||
@@ -3091,7 +3091,7 @@ vshInitDebug(vshControl *ctl)
return -1;
/* log file not set from cmdline */
- debugEnv = virGetEnvBlockSUID(env);
+ debugEnv = getenv(env);
if (debugEnv && *debugEnv) {
ctl->logfile = vshStrdup(ctl, debugEnv);
vshOpenLogFile(ctl);
--
2.21.0