diff options
-rw-r--r-- | fs/nfsd/nfs4state.c | 11 | ||||
-rw-r--r-- | include/linux/nfsd/state.h | 1 | ||||
-rw-r--r-- | include/linux/sunrpc/svcauth_gss.h | 1 | ||||
-rw-r--r-- | net/sunrpc/auth_gss/svcauth_gss.c | 23 |
4 files changed, 36 insertions, 0 deletions
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index 1a052ac2bde9..f3b9a8d064f3 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c | |||
@@ -54,6 +54,7 @@ | |||
54 | #include <linux/mutex.h> | 54 | #include <linux/mutex.h> |
55 | #include <linux/lockd/bind.h> | 55 | #include <linux/lockd/bind.h> |
56 | #include <linux/module.h> | 56 | #include <linux/module.h> |
57 | #include <linux/sunrpc/svcauth_gss.h> | ||
57 | 58 | ||
58 | #define NFSDDBG_FACILITY NFSDDBG_PROC | 59 | #define NFSDDBG_FACILITY NFSDDBG_PROC |
59 | 60 | ||
@@ -377,6 +378,7 @@ free_client(struct nfs4_client *clp) | |||
377 | shutdown_callback_client(clp); | 378 | shutdown_callback_client(clp); |
378 | if (clp->cl_cred.cr_group_info) | 379 | if (clp->cl_cred.cr_group_info) |
379 | put_group_info(clp->cl_cred.cr_group_info); | 380 | put_group_info(clp->cl_cred.cr_group_info); |
381 | kfree(clp->cl_principal); | ||
380 | kfree(clp->cl_name.data); | 382 | kfree(clp->cl_name.data); |
381 | kfree(clp); | 383 | kfree(clp); |
382 | } | 384 | } |
@@ -696,6 +698,7 @@ nfsd4_setclientid(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, | |||
696 | unsigned int strhashval; | 698 | unsigned int strhashval; |
697 | struct nfs4_client *conf, *unconf, *new; | 699 | struct nfs4_client *conf, *unconf, *new; |
698 | __be32 status; | 700 | __be32 status; |
701 | char *princ; | ||
699 | char dname[HEXDIR_LEN]; | 702 | char dname[HEXDIR_LEN]; |
700 | 703 | ||
701 | if (!check_name(clname)) | 704 | if (!check_name(clname)) |
@@ -783,6 +786,14 @@ nfsd4_setclientid(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, | |||
783 | } | 786 | } |
784 | copy_verf(new, &clverifier); | 787 | copy_verf(new, &clverifier); |
785 | new->cl_addr = sin->sin_addr.s_addr; | 788 | new->cl_addr = sin->sin_addr.s_addr; |
789 | princ = svc_gss_principal(rqstp); | ||
790 | if (princ) { | ||
791 | new->cl_principal = kstrdup(princ, GFP_KERNEL); | ||
792 | if (new->cl_principal == NULL) { | ||
793 | free_client(new); | ||
794 | goto out; | ||
795 | } | ||
796 | } | ||
786 | copy_cred(&new->cl_cred, &rqstp->rq_cred); | 797 | copy_cred(&new->cl_cred, &rqstp->rq_cred); |
787 | gen_confirm(new); | 798 | gen_confirm(new); |
788 | gen_callback(new, setclid); | 799 | gen_callback(new, setclid); |
diff --git a/include/linux/nfsd/state.h b/include/linux/nfsd/state.h index d0fe2e378452..ce7cbf4b7c93 100644 --- a/include/linux/nfsd/state.h +++ b/include/linux/nfsd/state.h | |||
@@ -124,6 +124,7 @@ struct nfs4_client { | |||
124 | nfs4_verifier cl_verifier; /* generated by client */ | 124 | nfs4_verifier cl_verifier; /* generated by client */ |
125 | time_t cl_time; /* time of last lease renewal */ | 125 | time_t cl_time; /* time of last lease renewal */ |
126 | __be32 cl_addr; /* client ipaddress */ | 126 | __be32 cl_addr; /* client ipaddress */ |
127 | char *cl_principal; /* setclientid principal name */ | ||
127 | struct svc_cred cl_cred; /* setclientid principal */ | 128 | struct svc_cred cl_cred; /* setclientid principal */ |
128 | clientid_t cl_clientid; /* generated by server */ | 129 | clientid_t cl_clientid; /* generated by server */ |
129 | nfs4_verifier cl_confirm; /* generated by server */ | 130 | nfs4_verifier cl_confirm; /* generated by server */ |
diff --git a/include/linux/sunrpc/svcauth_gss.h b/include/linux/sunrpc/svcauth_gss.h index c9165d9771a8..ca7d725861fc 100644 --- a/include/linux/sunrpc/svcauth_gss.h +++ b/include/linux/sunrpc/svcauth_gss.h | |||
@@ -20,6 +20,7 @@ int gss_svc_init(void); | |||
20 | void gss_svc_shutdown(void); | 20 | void gss_svc_shutdown(void); |
21 | int svcauth_gss_register_pseudoflavor(u32 pseudoflavor, char * name); | 21 | int svcauth_gss_register_pseudoflavor(u32 pseudoflavor, char * name); |
22 | u32 svcauth_gss_flavor(struct auth_domain *dom); | 22 | u32 svcauth_gss_flavor(struct auth_domain *dom); |
23 | char *svc_gss_principal(struct svc_rqst *); | ||
23 | 24 | ||
24 | #endif /* __KERNEL__ */ | 25 | #endif /* __KERNEL__ */ |
25 | #endif /* _LINUX_SUNRPC_SVCAUTH_GSS_H */ | 26 | #endif /* _LINUX_SUNRPC_SVCAUTH_GSS_H */ |
diff --git a/net/sunrpc/auth_gss/svcauth_gss.c b/net/sunrpc/auth_gss/svcauth_gss.c index 12803da95dc4..e9baa6ebb1dd 100644 --- a/net/sunrpc/auth_gss/svcauth_gss.c +++ b/net/sunrpc/auth_gss/svcauth_gss.c | |||
@@ -332,6 +332,7 @@ struct rsc { | |||
332 | struct svc_cred cred; | 332 | struct svc_cred cred; |
333 | struct gss_svc_seq_data seqdata; | 333 | struct gss_svc_seq_data seqdata; |
334 | struct gss_ctx *mechctx; | 334 | struct gss_ctx *mechctx; |
335 | char *client_name; | ||
335 | }; | 336 | }; |
336 | 337 | ||
337 | static struct cache_head *rsc_table[RSC_HASHMAX]; | 338 | static struct cache_head *rsc_table[RSC_HASHMAX]; |
@@ -346,6 +347,7 @@ static void rsc_free(struct rsc *rsci) | |||
346 | gss_delete_sec_context(&rsci->mechctx); | 347 | gss_delete_sec_context(&rsci->mechctx); |
347 | if (rsci->cred.cr_group_info) | 348 | if (rsci->cred.cr_group_info) |
348 | put_group_info(rsci->cred.cr_group_info); | 349 | put_group_info(rsci->cred.cr_group_info); |
350 | kfree(rsci->client_name); | ||
349 | } | 351 | } |
350 | 352 | ||
351 | static void rsc_put(struct kref *ref) | 353 | static void rsc_put(struct kref *ref) |
@@ -383,6 +385,7 @@ rsc_init(struct cache_head *cnew, struct cache_head *ctmp) | |||
383 | tmp->handle.data = NULL; | 385 | tmp->handle.data = NULL; |
384 | new->mechctx = NULL; | 386 | new->mechctx = NULL; |
385 | new->cred.cr_group_info = NULL; | 387 | new->cred.cr_group_info = NULL; |
388 | new->client_name = NULL; | ||
386 | } | 389 | } |
387 | 390 | ||
388 | static void | 391 | static void |
@@ -397,6 +400,8 @@ update_rsc(struct cache_head *cnew, struct cache_head *ctmp) | |||
397 | spin_lock_init(&new->seqdata.sd_lock); | 400 | spin_lock_init(&new->seqdata.sd_lock); |
398 | new->cred = tmp->cred; | 401 | new->cred = tmp->cred; |
399 | tmp->cred.cr_group_info = NULL; | 402 | tmp->cred.cr_group_info = NULL; |
403 | new->client_name = tmp->client_name; | ||
404 | tmp->client_name = NULL; | ||
400 | } | 405 | } |
401 | 406 | ||
402 | static struct cache_head * | 407 | static struct cache_head * |
@@ -486,6 +491,15 @@ static int rsc_parse(struct cache_detail *cd, | |||
486 | status = gss_import_sec_context(buf, len, gm, &rsci.mechctx); | 491 | status = gss_import_sec_context(buf, len, gm, &rsci.mechctx); |
487 | if (status) | 492 | if (status) |
488 | goto out; | 493 | goto out; |
494 | |||
495 | /* get client name */ | ||
496 | len = qword_get(&mesg, buf, mlen); | ||
497 | if (len > 0) { | ||
498 | rsci.client_name = kstrdup(buf, GFP_KERNEL); | ||
499 | if (!rsci.client_name) | ||
500 | goto out; | ||
501 | } | ||
502 | |||
489 | } | 503 | } |
490 | rsci.h.expiry_time = expiry; | 504 | rsci.h.expiry_time = expiry; |
491 | rscp = rsc_update(&rsci, rscp); | 505 | rscp = rsc_update(&rsci, rscp); |
@@ -913,6 +927,15 @@ struct gss_svc_data { | |||
913 | struct rsc *rsci; | 927 | struct rsc *rsci; |
914 | }; | 928 | }; |
915 | 929 | ||
930 | char *svc_gss_principal(struct svc_rqst *rqstp) | ||
931 | { | ||
932 | struct gss_svc_data *gd = (struct gss_svc_data *)rqstp->rq_auth_data; | ||
933 | |||
934 | if (gd && gd->rsci) | ||
935 | return gd->rsci->client_name; | ||
936 | return NULL; | ||
937 | } | ||
938 | |||
916 | static int | 939 | static int |
917 | svcauth_gss_set_client(struct svc_rqst *rqstp) | 940 | svcauth_gss_set_client(struct svc_rqst *rqstp) |
918 | { | 941 | { |