util: unify SO_PEERCRED/SO_PEERSEC invocations

Introduce new call getpeercred() which internally just uses SO_PEERCRED
but checks if the returned data is actually useful due to namespace
quirks.
This commit is contained in:
Lennart Poettering
2013-12-24 15:53:04 +01:00
parent 96415cad2f
commit eff0527098
9 changed files with 81 additions and 67 deletions
+4 -3
View File
@@ -579,6 +579,7 @@ int sockaddr_pretty(const struct sockaddr *_sa, socklen_t salen, bool translate_
int getpeername_pretty(int fd, char **ret) {
union sockaddr_union sa;
socklen_t salen;
int r;
assert(fd >= 0);
assert(ret);
@@ -593,9 +594,9 @@ int getpeername_pretty(int fd, char **ret) {
/* UNIX connection sockets are anonymous, so let's use
* PID/UID as pretty credentials instead */
salen = sizeof(ucred);
if (getsockopt(fd, SOL_SOCKET, SO_PEERCRED, &ucred, &salen) < 0)
return -errno;
r = getpeercred(fd, &ucred);
if (r < 0)
return r;
if (asprintf(ret, "PID %lu/UID %lu", (unsigned long) ucred.pid, (unsigned long) ucred.pid) < 0)
return -ENOMEM;
+58
View File
@@ -6117,3 +6117,61 @@ bool pid_valid(pid_t pid) {
return errno != ESRCH;
}
int getpeercred(int fd, struct ucred *ucred) {
socklen_t n = sizeof(struct ucred);
struct ucred u;
int r;
assert(fd >= 0);
assert(ucred);
r = getsockopt(fd, SOL_SOCKET, SO_PEERCRED, &u, &n);
if (r < 0)
return -errno;
if (n != sizeof(struct ucred))
return -EIO;
/* Check if the data is actually useful and not suppressed due
* to namespacing issues */
if (u.pid <= 0)
return -ENODATA;
*ucred = u;
return 0;
}
int getpeersec(int fd, char **ret) {
socklen_t n = 64;
char *s;
int r;
assert(fd >= 0);
assert(ret);
s = new0(char, n);
if (!s)
return -ENOMEM;
r = getsockopt(fd, SOL_SOCKET, SO_PEERSEC, s, &n);
if (r < 0) {
free(s);
if (errno != ERANGE)
return -errno;
s = new0(char, n);
if (!s)
return -ENOMEM;
r = getsockopt(fd, SOL_SOCKET, SO_PEERSEC, s, &n);
if (r < 0) {
free(s);
return -errno;
}
}
*ret = s;
return 0;
}
+4
View File
@@ -40,6 +40,7 @@
#include <unistd.h>
#include <locale.h>
#include <mntent.h>
#include <sys/socket.h>
#include "macro.h"
#include "time-util.h"
@@ -811,3 +812,6 @@ int namespace_open(pid_t pid, int *pidns_fd, int *mntns_fd, int *root_fd);
int namespace_enter(int pidns_fd, int mntns_fd, int root_fd);
bool pid_valid(pid_t pid);
int getpeercred(int fd, struct ucred *ucred);
int getpeersec(int fd, char **ret);