aboutsummaryrefslogtreecommitdiffstats
path: root/libsbusd.c
diff options
context:
space:
mode:
Diffstat (limited to 'libsbusd.c')
-rw-r--r--libsbusd.c75
1 files changed, 75 insertions, 0 deletions
diff --git a/libsbusd.c b/libsbusd.c
index 7c0596e..f8b49ab 100644
--- a/libsbusd.c
+++ b/libsbusd.c
@@ -41,6 +41,81 @@ libsbusd_weprintf(const char *fmt, ...)
}
int
+libsbusd_who(int fd, char *buf, const char *prefix)
+{
+ struct ucred cred;
+ if (getsockopt(fd, SOL_SOCKET, SO_PEERCRED, &cred, &(socklen_t){sizeof(cred)}) < 0) {
+ weprintf("getsockopt <client> SOL_SOCKET SO_PEERCRED:");
+ return -1;
+ }
+ return sprintf(buf, "%s!/cred/%lli/%lli/%lli",
+ prefix,
+ (long long int)cred.gid,
+ (long long int)cred.uid,
+ (long long int)cred.pid);
+}
+
+int
+libsbusd_iscredok(int fd, const char *key, const char *prefix)
+{
+ struct ucred cred;
+ long long int tmp;
+ const char *p;
+ size_t n = strlen(prefix);
+ if (strncmp(key, prefix, n))
+ return 0;
+ key = &key[n];
+ if (strncmp(key, "!/cred/", sizeof("!/cred/") - 1))
+ return 0;
+ if (getsockopt(fd, SOL_SOCKET, SO_PEERCRED, &cred, &(socklen_t){sizeof(cred)}) < 0) {
+ weprintf("getsockopt <client> SOL_SOCKET SO_PEERCRED:");
+ return -1;
+ }
+ errno = 0;
+ p = &key[sizeof("!/cred/") - 1];
+#define TEST_CRED(ID)\
+ if (!*p) {\
+ return 0;\
+ } else if (*p++ != '/') {\
+ if (!isdigit(*p))\
+ return 0;\
+ tmp = strtoll(p, (void *)&p, 10);\
+ if (errno || (*p && *p != '/') || (ID##_t)tmp != cred.ID)\
+ return 0;\
+ }
+ TEST_CRED(gid);
+ TEST_CRED(uid);
+ TEST_CRED(pid);
+#undef TEST_CRED
+ return 1;
+}
+
+int
+libsbusd_checkuser(int fd, uid_t *users, size_t nusers)
+{
+ struct ucred cred;
+ size_t i;
+ if (fd < 0) {
+ weprintf("accept <server>:");
+ return -1;
+ }
+ if (nusers) {
+ if (getsockopt(fd, SOL_SOCKET, SO_PEERCRED, &cred, &(socklen_t){sizeof(cred)}) < 0) {
+ weprintf("getsockopt <client> SOL_SOCKET SO_PEERCRED:");
+ close(fd);
+ return -1;
+ }
+ for (i = nusers; i--;)
+ if (users[i] == cred.uid)
+ return 0;
+ weprintf("rejected connection from user %li\n", (long int)cred.uid);
+ close(fd);
+ return -1;
+ }
+ return 0;
+}
+
+int
libsbusd_doessubmatch(const char *sub, const char *key)
{
const char *sub_start = sub;