]> git.decadent.org.uk Git - nfs-utils.git/blobdiff - utils/svcgssd/svcgssd_proc.c
rerun autoconf
[nfs-utils.git] / utils / svcgssd / svcgssd_proc.c
index c2470c60f42604f6a8bf5880db1c3a520d6c5b3d..8faddc1321ac3cded03e4ae9b63ae7912286a2b9 100644 (file)
@@ -44,6 +44,7 @@
 #include <string.h>
 #include <fcntl.h>
 #include <errno.h>
+#include <nfsidmap.h>
 
 #include "svcgssd.h"
 #include "gss_util.h"
@@ -63,6 +64,7 @@ extern char * mech2file(gss_OID mech);
 struct svc_cred {
        uid_t   cr_uid;
        gid_t   cr_gid;
+       int     cr_ngroups;
        gid_t   cr_groups[NGROUPS];
 };
 
@@ -71,7 +73,7 @@ do_svc_downcall(gss_buffer_desc *out_handle, struct svc_cred *cred,
                gss_OID mech, gss_buffer_desc *context_token)
 {
        FILE *f;
-       int i, ngroups;
+       int i;
        char *fname = NULL;
 
        printerr(1, "doing downcall\n");
@@ -89,15 +91,8 @@ do_svc_downcall(gss_buffer_desc *out_handle, struct svc_cred *cred,
        qword_printint(f, 0x7fffffff); /*XXX need a better timeout */
        qword_printint(f, cred->cr_uid);
        qword_printint(f, cred->cr_gid);
-       ngroups = NGROUPS;
-       for (i=0; i < NGROUPS; i++) {
-               if (cred->cr_groups[i] == NOGROUP) {
-                       ngroups = i;
-                       break;
-               }
-       }
-       qword_printint(f, ngroups);
-       for (i=0; i < ngroups; i++)
+       qword_printint(f, cred->cr_ngroups);
+       for (i=0; i < cred->cr_ngroups; i++)
                qword_printint(f, cred->cr_groups[i]);
        qword_print(f, fname);
        qword_printhex(f, context_token->value, context_token->length);
@@ -167,17 +162,16 @@ send_response(FILE *f, gss_buffer_desc *in_handle, gss_buffer_desc *in_token,
 #define rpcsec_gsserr_credproblem      13
 #define rpcsec_gsserr_ctxproblem       14
 
-/* XXX memory leaks everywhere: */
 static int
-get_ids(gss_name_t client_name, gss_OID *mech, struct svc_cred *cred)
+get_ids(gss_name_t client_name, gss_OID mech, struct svc_cred *cred)
 {
        u_int32_t       maj_stat, min_stat;
        gss_buffer_desc name;
        char            *sname;
        int             res = -1;
-       struct passwd   *pw = NULL;
+       uid_t           uid, gid;
        gss_OID         name_type;
-       char            *c;
+       char            *secname;
 
        maj_stat = gss_display_name(&min_stat, client_name, &name, &name_type);
        if (maj_stat != GSS_S_COMPLETE)
@@ -186,20 +180,21 @@ get_ids(gss_name_t client_name, gss_OID *mech, struct svc_cred *cred)
                goto out;
        memcpy(sname, name.value, name.length);
        printerr(1, "sname = %s\n", sname);
-       /* XXX: should use same mapping as idmapd?  Or something; for now
-        * I'm just chopping off the domain. */
-       /* XXX: note that idmapd also does this!  It doesn't check the domain
-        * name. */
-       if ((c = strchr(sname, '@')) != NULL)
-               *c = '\0';
-       /* XXX? mapping unknown users (including machine creds) to nobody: */
-       if ( !(pw = getpwnam(sname)) && !(pw = getpwnam("nobody")) )
-               goto out;
-       cred->cr_uid = pw->pw_uid;
-       cred->cr_gid = pw->pw_gid;
-       /* XXX Read password file?  Use initgroups? I dunno...*/
-       cred->cr_groups[0] = NOGROUP;
+
+       res = -EINVAL;
+       if ((secname = mech2file(mech)) == NULL)
+               goto out_free;
+       nfs4_init_name_mapping(NULL); /* XXX: should only do this once */
+       res = nfs4_gss_princ_to_ids(secname, sname, &uid, &gid);
+       if (res < 0)
+               goto out_free;
+       cred->cr_uid = uid;
+       cred->cr_gid = gid;
+       /*XXX: want add_supplementary_groups(secname, sname, cred)? */
+       cred->cr_ngroups = 0;
        res = 0;
+out_free:
+       free(sname);
 out:
        if (res)
                printerr(0, "WARNING: get_uid failed\n");
@@ -315,7 +310,7 @@ handle_nullreq(FILE *f) {
                                &null_token, &null_token);
                goto out_err;
        }
-       if (get_ids(client_name, &mech, &cred)) {
+       if (get_ids(client_name, mech, &cred)) {
                printerr(0, "WARNING: handle_nullreq: get_uid failed\n");
                send_response(f, &in_handle, &in_tok, GSS_S_BAD_NAME /* XXX? */,
                                0, &null_token, &null_token);