summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoman Bogorodskiy <bogorodskiy@gmail.com>2012-12-14 22:06:33 +0400
committerEric Blake <eblake@redhat.com>2012-12-14 11:49:31 -0700
commit0c94357f9d1dbf36145ab50dc01db0876ee218c8 (patch)
tree7af3c43aff115f0cd1567aa80ef6cbfbe2b38d8a
parente3802e13df9dccd047aa888dc3294ae6c1eda445 (diff)
downloadlibvirt-0c94357f9d1dbf36145ab50dc01db0876ee218c8.tar.gz
Socket identity support for FreeBSD.
This adds an implementation of virNetSocketGetUNIXIdentity() using LOCAL_PEERCRED socket option and xucred struct, defined in <sys/ucred.h> on systems that have it.
-rw-r--r--configure.ac3
-rw-r--r--src/rpc/virnetsocket.c30
2 files changed, 31 insertions, 2 deletions
diff --git a/configure.ac b/configure.ac
index 19369828c6..6c35afc651 100644
--- a/configure.ac
+++ b/configure.ac
@@ -187,7 +187,8 @@ LIBS=$old_libs
dnl Availability of various common headers (non-fatal if missing).
AC_CHECK_HEADERS([pwd.h paths.h regex.h sys/un.h \
sys/poll.h syslog.h mntent.h net/ethernet.h linux/magic.h \
- sys/un.h sys/syscall.h netinet/tcp.h ifaddrs.h libtasn1.h])
+ sys/un.h sys/syscall.h netinet/tcp.h ifaddrs.h libtasn1.h \
+ sys/ucred.h])
dnl Check whether endian provides handy macros.
AC_CHECK_DECLS([htole64], [], [], [[#include <endian.h>]])
diff --git a/src/rpc/virnetsocket.c b/src/rpc/virnetsocket.c
index a1b64d7309..70c621f636 100644
--- a/src/rpc/virnetsocket.c
+++ b/src/rpc/virnetsocket.c
@@ -35,6 +35,10 @@
# include <netinet/tcp.h>
#endif
+#ifdef HAVE_SYS_UCRED_H
+# include <sys/ucred.h>
+#endif
+
#include "c-ctype.h"
#include "virnetsocket.h"
#include "util.h"
@@ -1091,7 +1095,7 @@ int virNetSocketGetPort(virNetSocketPtr sock)
}
-#ifdef SO_PEERCRED
+#if defined(SO_PEERCRED)
int virNetSocketGetUNIXIdentity(virNetSocketPtr sock,
uid_t *uid,
gid_t *gid,
@@ -1115,6 +1119,30 @@ int virNetSocketGetUNIXIdentity(virNetSocketPtr sock,
virMutexUnlock(&sock->lock);
return 0;
}
+#elif defined(LOCAL_PEERCRED)
+int virNetSocketGetUNIXIdentity(virNetSocketPtr sock,
+ uid_t *uid,
+ gid_t *gid,
+ pid_t *pid)
+{
+ struct xucred cr;
+ socklen_t cr_len = sizeof(cr);
+ virMutexLock(&sock->lock);
+
+ if (getsockopt(sock->fd, SOL_SOCKET, LOCAL_PEERCRED, &cr, &cr_len) < 0) {
+ virReportSystemError(errno, "%s",
+ _("Failed to get client socket identity"));
+ virMutexUnlock(&sock->lock);
+ return -1;
+ }
+
+ *pid = -1;
+ *uid = cr.cr_uid;
+ *gid = cr.cr_gid;
+
+ virMutexUnlock(&sock->lock);
+ return 0;
+}
#else
int virNetSocketGetUNIXIdentity(virNetSocketPtr sock ATTRIBUTE_UNUSED,
uid_t *uid ATTRIBUTE_UNUSED,