From: "Daniel P. Berrange" <berrange(a)redhat.com>
If no user identity is available, some operations may wish to
use the system identity. ie the identity of the current process
itself. Add an API to get such an identity.
Signed-off-by: Daniel P. Berrange <berrange(a)redhat.com>
---
src/util/viridentity.c | 71 ++++++++++++++++++++++++++++++++++++++++++++++++++
src/util/viridentity.h | 2 ++
2 files changed, 73 insertions(+)
diff --git a/src/util/viridentity.c b/src/util/viridentity.c
index 2b4198b..004b8dc 100644
--- a/src/util/viridentity.c
+++ b/src/util/viridentity.c
@@ -21,6 +21,11 @@
#include <config.h>
+#include <unistd.h>
+#if HAVE_SELINUX
+# include <selinux/selinux.h>
+#endif
+
#include "internal.h"
#include "viralloc.h"
#include "virerror.h"
@@ -28,6 +33,7 @@
#include "virlog.h"
#include "virobject.h"
#include "virthread.h"
+#include "virutil.h"
#define VIR_FROM_THIS VIR_FROM_IDENTITY
@@ -116,6 +122,71 @@ int virIdentitySetCurrent(virIdentityPtr ident)
/**
+ * virIdentityGetSystem:
+ *
+ * Returns an identity that represents the system itself.
+ * This is the identity that the process is running as
+ *
+ * Returns a reference to the system identity, or NULL
+ */
+virIdentityPtr virIdentityGetSystem(void)
+{
+ char *username = NULL;
+ char *groupname = NULL;
+ char *seccontext = NULL;
+ virIdentityPtr ret = NULL;
+ gid_t gid = getgid();
+ uid_t uid = getuid();
+#if HAVE_SELINUX
+ security_context_t con;
+#endif
+
+ if (!(username = virGetUserName(uid)))
+ goto cleanup;
+ if (!(groupname = virGetGroupName(gid)))
+ goto cleanup;
+
+#if HAVE_SELINUX
+ if (getcon(&con) < 0) {
+ virReportSystemError(errno, "%s",
+ _("Unable to lookup SELinux process context"));
+ goto cleanup;
+ }
+ seccontext = strdup(con);
+ freecon(con);
+ if (!seccontext) {
+ virReportOOMError();
+ goto cleanup;
+ }
+#endif
+
+ if (!(ret = virIdentityNew()))
+ goto cleanup;
+
+ if (username &&
+ virIdentitySetAttr(ret, VIR_IDENTITY_ATTR_UNIX_USER_NAME, username) < 0)
+ goto error;
+ if (groupname &&
+ virIdentitySetAttr(ret, VIR_IDENTITY_ATTR_UNIX_GROUP_NAME, groupname) < 0)
+ goto error;
+ if (seccontext &&
+ virIdentitySetAttr(ret, VIR_IDENTITY_ATTR_SECURITY_CONTEXT, seccontext) < 0)
+ goto error;
+
+cleanup:
+ VIR_FREE(username);
+ VIR_FREE(groupname);
+ VIR_FREE(seccontext);
+ return ret;
+
+error:
+ virObjectUnref(ret);
+ ret = NULL;
+ goto cleanup;
+}
+
+
+/**
* virIdentityNew:
*
* Creates a new empty identity object. After creating, one or
diff --git a/src/util/viridentity.h b/src/util/viridentity.h
index 0825c90..ceaddf7 100644
--- a/src/util/viridentity.h
+++ b/src/util/viridentity.h
@@ -41,6 +41,8 @@ typedef enum {
virIdentityPtr virIdentityGetCurrent(void);
int virIdentitySetCurrent(virIdentityPtr ident);
+virIdentityPtr virIdentityGetSystem(void);
+
virIdentityPtr virIdentityNew(void);
int virIdentitySetAttr(virIdentityPtr ident,
--
1.8.1.4