Add Linux/BSD switch for Unix auth.
authorfredrik <fredrik@959494ce-11ee-0310-bf91-de5d638817bd>
Tue, 29 May 2007 15:01:40 +0000 (15:01 +0000)
committerfredrik <fredrik@959494ce-11ee-0310-bf91-de5d638817bd>
Tue, 29 May 2007 15:01:40 +0000 (15:01 +0000)
git-svn-id: svn+ssh://svn.dolda2000.com/srv/svn/repos/src/doldaconnect@1046 959494ce-11ee-0310-bf91-de5d638817bd

configure.in
daemon/auth-unix.c
daemon/net.c
daemon/net.h
lib/uilib.c

index 6d8ed05..691b9e2 100644 (file)
@@ -216,6 +216,21 @@ AH_TEMPLATE(HAVE_KEYUTILS, [define if your system supports the Linux keyring fun
 AC_CHECK_LIB(keyutils, keyctl_search, [ AC_DEFINE(HAVE_KEYUTILS)
                                        LDFLAGS="$LDFLAGS -lkeyutils" ])
 
+# Unix credentials selector
+AH_TEMPLATE(UNIX_AUTH_STYLE, [undefine for no Unix auth, 1 for Linux style, 2 for BSD style])
+AC_CHECK_MEMBER(struct ucred.pid, [ linuxcreds=y ], [ linuxcreds=n ], [#include <sys/socket.h>])
+AC_CHECK_FUNC(getpeereid, [ bsdcreds=y ], [ bsdcreds=n ])
+AC_MSG_CHECKING([for Unix auth style])
+if test $linuxcreds = y; then
+       AC_DEFINE(UNIX_AUTH_STYLE, 1)
+       AC_MSG_RESULT(linux)
+elif test $bsdcreds = y; then
+       AC_DEFINE(UNIX_AUTH_STYLE, 2)
+       AC_MSG_RESULT(bsd)
+else
+       AC_MSG_RESULT(none)
+fi
+
 AC_HEADER_STDC
 AC_HEADER_DIRENT
 AC_HEADER_SYS_WAIT
index 9707bfd..47a1c24 100644 (file)
@@ -63,12 +63,12 @@ static int unixauth(struct authhandle *auth, struct socket *sk, char *passdata)
     data = auth->mechdata;
     if((pwd = getpwnam(data->username)) == NULL)
        return(AUTH_ERR);
-    if(sk->ucred.pid == 0) {
+    if(sk->ucred.uid == -1) {
        errno = EBADE;
        return(AUTH_ERR);
     }
     if(pwd->pw_uid == sk->ucred.uid) {
-       flog(LOG_INFO, "process %i successfully authenticated as %s with Unix credentials (uid=%i, gid=%i)", sk->ucred.pid, data->username, sk->ucred.uid, sk->ucred.gid);
+       flog(LOG_INFO, "successful authentication as %s with Unix credentials (uid=%i, gid=%i)", data->username, sk->ucred.uid, sk->ucred.gid);
        return(AUTH_SUCCESS);
     }
     auth->text = swcsdup(L"Unix credentials do not match supplied user name");
@@ -77,7 +77,7 @@ static int unixauth(struct authhandle *auth, struct socket *sk, char *passdata)
 
 static int available(struct socket *sk)
 {
-    return((sk->family == PF_UNIX) && (sk->ucred.pid != 0));
+    return((sk->family == PF_UNIX) && (sk->ucred.uid != -1));
 }
 
 static struct authmech mechdesc = {
index 0fc9e45..5471e45 100644 (file)
@@ -183,7 +183,8 @@ static struct socket *newsock(int type)
     new->close = 0;
     new->remote = NULL;
     new->remotelen = 0;
-    memset(&new->ucred, 0, sizeof(new->ucred));
+    new->ucred.uid = -1;
+    new->ucred.gid = -1;
     switch(type)
     {
     case SOCK_STREAM:
@@ -350,18 +351,21 @@ void *sockgetinbuf(struct socket *sk, size_t *size)
 static void recvcmsg(struct socket *sk, struct msghdr *msg)
 {
     struct cmsghdr *cmsg;
-    struct ucred *cred;
     
     for(cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg))
     {
+#if UNIX_AUTH_STYLE == 1
        if((cmsg->cmsg_level == SOL_SOCKET) && (cmsg->cmsg_type == SCM_CREDENTIALS))
        {
-           if(sk->ucred.pid == 0)
+           struct ucred *cred;
+           if(sk->ucred.uid == -1)
            {
                cred = (struct ucred *)CMSG_DATA(cmsg);
-               memcpy(&sk->ucred, cred, sizeof(*cred));
+               sk->ucred.uid = cred->uid;
+               sk->ucred.gid = cred->gid;
            }
        }
+#endif
     }
 }
 
@@ -819,8 +823,17 @@ static void acceptunix(struct socket *sk)
     int buf;
     
     buf = 1;
+#if UNIX_AUTH_STYLE == 1
     if(setsockopt(sk->fd, SOL_SOCKET, SO_PASSCRED, &buf, sizeof(buf)) < 0)
        flog(LOG_WARNING, "could not enable SO_PASSCRED on Unix socket %i: %s", sk->fd, strerror(errno));
+#elif UNIX_AUTH_STYLE == 2
+    if(getpeereid(sk->fd, &sk->ucred.uid, &sk->ucred.gid) < 0)
+    {
+       flog(LOG_WARNING, "could not get peer creds on Unix socket %i: %s", sk->fd, strerror(errno));
+       sk->ucred.uid = -1;
+       sk->ucred.gid = -1;
+    }
+#endif
 }
 
 int pollsocks(int timeout)
index f9b7a29..6457033 100644 (file)
@@ -55,7 +55,11 @@ struct socket
     int close;
     struct sockaddr *remote;
     socklen_t remotelen;
-    struct ucred ucred;
+    struct
+    {
+       uid_t uid;
+       gid_t gid;
+    } ucred;
     union
     {
        struct
index 303ed0c..973a2b3 100644 (file)
@@ -762,6 +762,7 @@ int dc_handleread(void)
     return(0);
 }
 
+#if UNIX_AUTH_STYLE == 1
 static void mkcreds(struct msghdr *msg)
 {
     struct ucred *ucred;
@@ -780,6 +781,7 @@ static void mkcreds(struct msghdr *msg)
     ucred->gid = getgid();
     msg->msg_controllen = cmsg->cmsg_len;
 }
+#endif
 
 int dc_handlewrite(void)
 {
@@ -798,11 +800,13 @@ int dc_handlewrite(void)
            msg.msg_iovlen = 1;
            bufvec.iov_base = queue->buf;
            bufvec.iov_len = queue->buflen;
+#if UNIX_AUTH_STYLE == 1
            if((servinfo.family == PF_UNIX) && !servinfo.sentcreds)
            {
                mkcreds(&msg);
                servinfo.sentcreds = 1;
            }
+#endif
            ret = sendmsg(fd, &msg, MSG_NOSIGNAL | MSG_DONTWAIT);
            if(ret < 0)
            {