linux/fs/nfsd/nfs4idmap.c
<<
>>
Prefs
   1/*
   2 *  Mapping of UID/GIDs to name and vice versa.
   3 *
   4 *  Copyright (c) 2002, 2003 The Regents of the University of
   5 *  Michigan.  All rights reserved.
   6 *
   7 *  Marius Aamodt Eriksen <marius@umich.edu>
   8 *
   9 *  Redistribution and use in source and binary forms, with or without
  10 *  modification, are permitted provided that the following conditions
  11 *  are met:
  12 *
  13 *  1. Redistributions of source code must retain the above copyright
  14 *     notice, this list of conditions and the following disclaimer.
  15 *  2. Redistributions in binary form must reproduce the above copyright
  16 *     notice, this list of conditions and the following disclaimer in the
  17 *     documentation and/or other materials provided with the distribution.
  18 *  3. Neither the name of the University nor the names of its
  19 *     contributors may be used to endorse or promote products derived
  20 *     from this software without specific prior written permission.
  21 *
  22 *  THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
  23 *  WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
  24 *  MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  25 *  DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  26 *  FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
  27 *  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
  28 *  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
  29 *  BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  30 *  LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  31 *  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  32 *  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  33 */
  34
  35#include <linux/module.h>
  36#include <linux/seq_file.h>
  37#include <linux/sched.h>
  38#include <linux/slab.h>
  39#include <linux/sunrpc/svc_xprt.h>
  40#include <net/net_namespace.h>
  41#include "idmap.h"
  42#include "nfsd.h"
  43#include "netns.h"
  44
  45/*
  46 * Turn off idmapping when using AUTH_SYS.
  47 */
  48static bool nfs4_disable_idmapping = true;
  49module_param(nfs4_disable_idmapping, bool, 0644);
  50MODULE_PARM_DESC(nfs4_disable_idmapping,
  51                "Turn off server's NFSv4 idmapping when using 'sec=sys'");
  52
  53/*
  54 * Cache entry
  55 */
  56
  57/*
  58 * XXX we know that IDMAP_NAMESZ < PAGE_SIZE, but it's ugly to rely on
  59 * that.
  60 */
  61
  62struct ent {
  63        struct cache_head h;
  64        int               type;                /* User / Group */
  65        u32               id;
  66        char              name[IDMAP_NAMESZ];
  67        char              authname[IDMAP_NAMESZ];
  68        struct rcu_head   rcu_head;
  69};
  70
  71/* Common entry handling */
  72
  73#define ENT_HASHBITS          8
  74#define ENT_HASHMAX           (1 << ENT_HASHBITS)
  75
  76static void
  77ent_init(struct cache_head *cnew, struct cache_head *citm)
  78{
  79        struct ent *new = container_of(cnew, struct ent, h);
  80        struct ent *itm = container_of(citm, struct ent, h);
  81
  82        new->id = itm->id;
  83        new->type = itm->type;
  84
  85        strlcpy(new->name, itm->name, sizeof(new->name));
  86        strlcpy(new->authname, itm->authname, sizeof(new->authname));
  87}
  88
  89static void
  90ent_put(struct kref *ref)
  91{
  92        struct ent *map = container_of(ref, struct ent, h.ref);
  93        kfree_rcu(map, rcu_head);
  94}
  95
  96static struct cache_head *
  97ent_alloc(void)
  98{
  99        struct ent *e = kmalloc(sizeof(*e), GFP_KERNEL);
 100        if (e)
 101                return &e->h;
 102        else
 103                return NULL;
 104}
 105
 106/*
 107 * ID -> Name cache
 108 */
 109
 110static uint32_t
 111idtoname_hash(struct ent *ent)
 112{
 113        uint32_t hash;
 114
 115        hash = hash_str(ent->authname, ENT_HASHBITS);
 116        hash = hash_long(hash ^ ent->id, ENT_HASHBITS);
 117
 118        /* Flip LSB for user/group */
 119        if (ent->type == IDMAP_TYPE_GROUP)
 120                hash ^= 1;
 121
 122        return hash;
 123}
 124
 125static int
 126idtoname_upcall(struct cache_detail *cd, struct cache_head *h)
 127{
 128        return sunrpc_cache_pipe_upcall_timeout(cd, h);
 129}
 130
 131static void
 132idtoname_request(struct cache_detail *cd, struct cache_head *ch, char **bpp,
 133    int *blen)
 134{
 135        struct ent *ent = container_of(ch, struct ent, h);
 136        char idstr[11];
 137
 138        qword_add(bpp, blen, ent->authname);
 139        snprintf(idstr, sizeof(idstr), "%u", ent->id);
 140        qword_add(bpp, blen, ent->type == IDMAP_TYPE_GROUP ? "group" : "user");
 141        qword_add(bpp, blen, idstr);
 142
 143        (*bpp)[-1] = '\n';
 144}
 145
 146static int
 147idtoname_match(struct cache_head *ca, struct cache_head *cb)
 148{
 149        struct ent *a = container_of(ca, struct ent, h);
 150        struct ent *b = container_of(cb, struct ent, h);
 151
 152        return (a->id == b->id && a->type == b->type &&
 153            strcmp(a->authname, b->authname) == 0);
 154}
 155
 156static int
 157idtoname_show(struct seq_file *m, struct cache_detail *cd, struct cache_head *h)
 158{
 159        struct ent *ent;
 160
 161        if (h == NULL) {
 162                seq_puts(m, "#domain type id [name]\n");
 163                return 0;
 164        }
 165        ent = container_of(h, struct ent, h);
 166        seq_printf(m, "%s %s %u", ent->authname,
 167                        ent->type == IDMAP_TYPE_GROUP ? "group" : "user",
 168                        ent->id);
 169        if (test_bit(CACHE_VALID, &h->flags))
 170                seq_printf(m, " %s", ent->name);
 171        seq_putc(m, '\n');
 172        return 0;
 173}
 174
 175static void
 176warn_no_idmapd(struct cache_detail *detail, int has_died)
 177{
 178        printk("nfsd: nfsv4 idmapping failing: has idmapd %s?\n",
 179                        has_died ? "died" : "not been started");
 180}
 181
 182
 183static int         idtoname_parse(struct cache_detail *, char *, int);
 184static struct ent *idtoname_lookup(struct cache_detail *, struct ent *);
 185static struct ent *idtoname_update(struct cache_detail *, struct ent *,
 186                                   struct ent *);
 187
 188static const struct cache_detail idtoname_cache_template = {
 189        .owner          = THIS_MODULE,
 190        .hash_size      = ENT_HASHMAX,
 191        .name           = "nfs4.idtoname",
 192        .cache_put      = ent_put,
 193        .cache_upcall   = idtoname_upcall,
 194        .cache_request  = idtoname_request,
 195        .cache_parse    = idtoname_parse,
 196        .cache_show     = idtoname_show,
 197        .warn_no_listener = warn_no_idmapd,
 198        .match          = idtoname_match,
 199        .init           = ent_init,
 200        .update         = ent_init,
 201        .alloc          = ent_alloc,
 202};
 203
 204static int
 205idtoname_parse(struct cache_detail *cd, char *buf, int buflen)
 206{
 207        struct ent ent, *res;
 208        char *buf1, *bp;
 209        int len;
 210        int error = -EINVAL;
 211
 212        if (buf[buflen - 1] != '\n')
 213                return (-EINVAL);
 214        buf[buflen - 1]= '\0';
 215
 216        buf1 = kmalloc(PAGE_SIZE, GFP_KERNEL);
 217        if (buf1 == NULL)
 218                return (-ENOMEM);
 219
 220        memset(&ent, 0, sizeof(ent));
 221
 222        /* Authentication name */
 223        len = qword_get(&buf, buf1, PAGE_SIZE);
 224        if (len <= 0 || len >= IDMAP_NAMESZ)
 225                goto out;
 226        memcpy(ent.authname, buf1, sizeof(ent.authname));
 227
 228        /* Type */
 229        if (qword_get(&buf, buf1, PAGE_SIZE) <= 0)
 230                goto out;
 231        ent.type = strcmp(buf1, "user") == 0 ?
 232                IDMAP_TYPE_USER : IDMAP_TYPE_GROUP;
 233
 234        /* ID */
 235        if (qword_get(&buf, buf1, PAGE_SIZE) <= 0)
 236                goto out;
 237        ent.id = simple_strtoul(buf1, &bp, 10);
 238        if (bp == buf1)
 239                goto out;
 240
 241        /* expiry */
 242        ent.h.expiry_time = get_expiry(&buf);
 243        if (ent.h.expiry_time == 0)
 244                goto out;
 245
 246        error = -ENOMEM;
 247        res = idtoname_lookup(cd, &ent);
 248        if (!res)
 249                goto out;
 250
 251        /* Name */
 252        error = -EINVAL;
 253        len = qword_get(&buf, buf1, PAGE_SIZE);
 254        if (len < 0 || len >= IDMAP_NAMESZ)
 255                goto out;
 256        if (len == 0)
 257                set_bit(CACHE_NEGATIVE, &ent.h.flags);
 258        else
 259                memcpy(ent.name, buf1, sizeof(ent.name));
 260        error = -ENOMEM;
 261        res = idtoname_update(cd, &ent, res);
 262        if (res == NULL)
 263                goto out;
 264
 265        cache_put(&res->h, cd);
 266        error = 0;
 267out:
 268        kfree(buf1);
 269        return error;
 270}
 271
 272static struct ent *
 273idtoname_lookup(struct cache_detail *cd, struct ent *item)
 274{
 275        struct cache_head *ch = sunrpc_cache_lookup_rcu(cd, &item->h,
 276                                                        idtoname_hash(item));
 277        if (ch)
 278                return container_of(ch, struct ent, h);
 279        else
 280                return NULL;
 281}
 282
 283static struct ent *
 284idtoname_update(struct cache_detail *cd, struct ent *new, struct ent *old)
 285{
 286        struct cache_head *ch = sunrpc_cache_update(cd, &new->h, &old->h,
 287                                                    idtoname_hash(new));
 288        if (ch)
 289                return container_of(ch, struct ent, h);
 290        else
 291                return NULL;
 292}
 293
 294
 295/*
 296 * Name -> ID cache
 297 */
 298
 299static inline int
 300nametoid_hash(struct ent *ent)
 301{
 302        return hash_str(ent->name, ENT_HASHBITS);
 303}
 304
 305static int
 306nametoid_upcall(struct cache_detail *cd, struct cache_head *h)
 307{
 308        return sunrpc_cache_pipe_upcall_timeout(cd, h);
 309}
 310
 311static void
 312nametoid_request(struct cache_detail *cd, struct cache_head *ch, char **bpp,
 313    int *blen)
 314{
 315        struct ent *ent = container_of(ch, struct ent, h);
 316
 317        qword_add(bpp, blen, ent->authname);
 318        qword_add(bpp, blen, ent->type == IDMAP_TYPE_GROUP ? "group" : "user");
 319        qword_add(bpp, blen, ent->name);
 320
 321        (*bpp)[-1] = '\n';
 322}
 323
 324static int
 325nametoid_match(struct cache_head *ca, struct cache_head *cb)
 326{
 327        struct ent *a = container_of(ca, struct ent, h);
 328        struct ent *b = container_of(cb, struct ent, h);
 329
 330        return (a->type == b->type && strcmp(a->name, b->name) == 0 &&
 331            strcmp(a->authname, b->authname) == 0);
 332}
 333
 334static int
 335nametoid_show(struct seq_file *m, struct cache_detail *cd, struct cache_head *h)
 336{
 337        struct ent *ent;
 338
 339        if (h == NULL) {
 340                seq_puts(m, "#domain type name [id]\n");
 341                return 0;
 342        }
 343        ent = container_of(h, struct ent, h);
 344        seq_printf(m, "%s %s %s", ent->authname,
 345                        ent->type == IDMAP_TYPE_GROUP ? "group" : "user",
 346                        ent->name);
 347        if (test_bit(CACHE_VALID, &h->flags))
 348                seq_printf(m, " %u", ent->id);
 349        seq_putc(m, '\n');
 350        return 0;
 351}
 352
 353static struct ent *nametoid_lookup(struct cache_detail *, struct ent *);
 354static struct ent *nametoid_update(struct cache_detail *, struct ent *,
 355                                   struct ent *);
 356static int         nametoid_parse(struct cache_detail *, char *, int);
 357
 358static const struct cache_detail nametoid_cache_template = {
 359        .owner          = THIS_MODULE,
 360        .hash_size      = ENT_HASHMAX,
 361        .name           = "nfs4.nametoid",
 362        .cache_put      = ent_put,
 363        .cache_upcall   = nametoid_upcall,
 364        .cache_request  = nametoid_request,
 365        .cache_parse    = nametoid_parse,
 366        .cache_show     = nametoid_show,
 367        .warn_no_listener = warn_no_idmapd,
 368        .match          = nametoid_match,
 369        .init           = ent_init,
 370        .update         = ent_init,
 371        .alloc          = ent_alloc,
 372};
 373
 374static int
 375nametoid_parse(struct cache_detail *cd, char *buf, int buflen)
 376{
 377        struct ent ent, *res;
 378        char *buf1;
 379        int len, error = -EINVAL;
 380
 381        if (buf[buflen - 1] != '\n')
 382                return (-EINVAL);
 383        buf[buflen - 1]= '\0';
 384
 385        buf1 = kmalloc(PAGE_SIZE, GFP_KERNEL);
 386        if (buf1 == NULL)
 387                return (-ENOMEM);
 388
 389        memset(&ent, 0, sizeof(ent));
 390
 391        /* Authentication name */
 392        len = qword_get(&buf, buf1, PAGE_SIZE);
 393        if (len <= 0 || len >= IDMAP_NAMESZ)
 394                goto out;
 395        memcpy(ent.authname, buf1, sizeof(ent.authname));
 396
 397        /* Type */
 398        if (qword_get(&buf, buf1, PAGE_SIZE) <= 0)
 399                goto out;
 400        ent.type = strcmp(buf1, "user") == 0 ?
 401                IDMAP_TYPE_USER : IDMAP_TYPE_GROUP;
 402
 403        /* Name */
 404        len = qword_get(&buf, buf1, PAGE_SIZE);
 405        if (len <= 0 || len >= IDMAP_NAMESZ)
 406                goto out;
 407        memcpy(ent.name, buf1, sizeof(ent.name));
 408
 409        /* expiry */
 410        ent.h.expiry_time = get_expiry(&buf);
 411        if (ent.h.expiry_time == 0)
 412                goto out;
 413
 414        /* ID */
 415        error = get_int(&buf, &ent.id);
 416        if (error == -EINVAL)
 417                goto out;
 418        if (error == -ENOENT)
 419                set_bit(CACHE_NEGATIVE, &ent.h.flags);
 420
 421        error = -ENOMEM;
 422        res = nametoid_lookup(cd, &ent);
 423        if (res == NULL)
 424                goto out;
 425        res = nametoid_update(cd, &ent, res);
 426        if (res == NULL)
 427                goto out;
 428
 429        cache_put(&res->h, cd);
 430        error = 0;
 431out:
 432        kfree(buf1);
 433        return (error);
 434}
 435
 436
 437static struct ent *
 438nametoid_lookup(struct cache_detail *cd, struct ent *item)
 439{
 440        struct cache_head *ch = sunrpc_cache_lookup_rcu(cd, &item->h,
 441                                                        nametoid_hash(item));
 442        if (ch)
 443                return container_of(ch, struct ent, h);
 444        else
 445                return NULL;
 446}
 447
 448static struct ent *
 449nametoid_update(struct cache_detail *cd, struct ent *new, struct ent *old)
 450{
 451        struct cache_head *ch = sunrpc_cache_update(cd, &new->h, &old->h,
 452                                                    nametoid_hash(new));
 453        if (ch)
 454                return container_of(ch, struct ent, h);
 455        else
 456                return NULL;
 457}
 458
 459/*
 460 * Exported API
 461 */
 462
 463int
 464nfsd_idmap_init(struct net *net)
 465{
 466        int rv;
 467        struct nfsd_net *nn = net_generic(net, nfsd_net_id);
 468
 469        nn->idtoname_cache = cache_create_net(&idtoname_cache_template, net);
 470        if (IS_ERR(nn->idtoname_cache))
 471                return PTR_ERR(nn->idtoname_cache);
 472        rv = cache_register_net(nn->idtoname_cache, net);
 473        if (rv)
 474                goto destroy_idtoname_cache;
 475        nn->nametoid_cache = cache_create_net(&nametoid_cache_template, net);
 476        if (IS_ERR(nn->nametoid_cache)) {
 477                rv = PTR_ERR(nn->nametoid_cache);
 478                goto unregister_idtoname_cache;
 479        }
 480        rv = cache_register_net(nn->nametoid_cache, net);
 481        if (rv)
 482                goto destroy_nametoid_cache;
 483        return 0;
 484
 485destroy_nametoid_cache:
 486        cache_destroy_net(nn->nametoid_cache, net);
 487unregister_idtoname_cache:
 488        cache_unregister_net(nn->idtoname_cache, net);
 489destroy_idtoname_cache:
 490        cache_destroy_net(nn->idtoname_cache, net);
 491        return rv;
 492}
 493
 494void
 495nfsd_idmap_shutdown(struct net *net)
 496{
 497        struct nfsd_net *nn = net_generic(net, nfsd_net_id);
 498
 499        cache_unregister_net(nn->idtoname_cache, net);
 500        cache_unregister_net(nn->nametoid_cache, net);
 501        cache_destroy_net(nn->idtoname_cache, net);
 502        cache_destroy_net(nn->nametoid_cache, net);
 503}
 504
 505static int
 506idmap_lookup(struct svc_rqst *rqstp,
 507                struct ent *(*lookup_fn)(struct cache_detail *, struct ent *),
 508                struct ent *key, struct cache_detail *detail, struct ent **item)
 509{
 510        int ret;
 511
 512        *item = lookup_fn(detail, key);
 513        if (!*item)
 514                return -ENOMEM;
 515 retry:
 516        ret = cache_check(detail, &(*item)->h, &rqstp->rq_chandle);
 517
 518        if (ret == -ETIMEDOUT) {
 519                struct ent *prev_item = *item;
 520                *item = lookup_fn(detail, key);
 521                if (*item != prev_item)
 522                        goto retry;
 523                cache_put(&(*item)->h, detail);
 524        }
 525        return ret;
 526}
 527
 528static char *
 529rqst_authname(struct svc_rqst *rqstp)
 530{
 531        struct auth_domain *clp;
 532
 533        clp = rqstp->rq_gssclient ? rqstp->rq_gssclient : rqstp->rq_client;
 534        return clp->name;
 535}
 536
 537static __be32
 538idmap_name_to_id(struct svc_rqst *rqstp, int type, const char *name, u32 namelen,
 539                u32 *id)
 540{
 541        struct ent *item, key = {
 542                .type = type,
 543        };
 544        int ret;
 545        struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id);
 546
 547        if (namelen + 1 > sizeof(key.name))
 548                return nfserr_badowner;
 549        memcpy(key.name, name, namelen);
 550        key.name[namelen] = '\0';
 551        strlcpy(key.authname, rqst_authname(rqstp), sizeof(key.authname));
 552        ret = idmap_lookup(rqstp, nametoid_lookup, &key, nn->nametoid_cache, &item);
 553        if (ret == -ENOENT)
 554                return nfserr_badowner;
 555        if (ret)
 556                return nfserrno(ret);
 557        *id = item->id;
 558        cache_put(&item->h, nn->nametoid_cache);
 559        return 0;
 560}
 561
 562static __be32 encode_ascii_id(struct xdr_stream *xdr, u32 id)
 563{
 564        char buf[11];
 565        int len;
 566        __be32 *p;
 567
 568        len = sprintf(buf, "%u", id);
 569        p = xdr_reserve_space(xdr, len + 4);
 570        if (!p)
 571                return nfserr_resource;
 572        p = xdr_encode_opaque(p, buf, len);
 573        return 0;
 574}
 575
 576static __be32 idmap_id_to_name(struct xdr_stream *xdr,
 577                               struct svc_rqst *rqstp, int type, u32 id)
 578{
 579        struct ent *item, key = {
 580                .id = id,
 581                .type = type,
 582        };
 583        __be32 *p;
 584        int ret;
 585        struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id);
 586
 587        strlcpy(key.authname, rqst_authname(rqstp), sizeof(key.authname));
 588        ret = idmap_lookup(rqstp, idtoname_lookup, &key, nn->idtoname_cache, &item);
 589        if (ret == -ENOENT)
 590                return encode_ascii_id(xdr, id);
 591        if (ret)
 592                return nfserrno(ret);
 593        ret = strlen(item->name);
 594        WARN_ON_ONCE(ret > IDMAP_NAMESZ);
 595        p = xdr_reserve_space(xdr, ret + 4);
 596        if (!p)
 597                return nfserr_resource;
 598        p = xdr_encode_opaque(p, item->name, ret);
 599        cache_put(&item->h, nn->idtoname_cache);
 600        return 0;
 601}
 602
 603static bool
 604numeric_name_to_id(struct svc_rqst *rqstp, int type, const char *name, u32 namelen, u32 *id)
 605{
 606        int ret;
 607        char buf[11];
 608
 609        if (namelen + 1 > sizeof(buf))
 610                /* too long to represent a 32-bit id: */
 611                return false;
 612        /* Just to make sure it's null-terminated: */
 613        memcpy(buf, name, namelen);
 614        buf[namelen] = '\0';
 615        ret = kstrtouint(buf, 10, id);
 616        return ret == 0;
 617}
 618
 619static __be32
 620do_name_to_id(struct svc_rqst *rqstp, int type, const char *name, u32 namelen, u32 *id)
 621{
 622        if (nfs4_disable_idmapping && rqstp->rq_cred.cr_flavor < RPC_AUTH_GSS)
 623                if (numeric_name_to_id(rqstp, type, name, namelen, id))
 624                        return 0;
 625                /*
 626                 * otherwise, fall through and try idmapping, for
 627                 * backwards compatibility with clients sending names:
 628                 */
 629        return idmap_name_to_id(rqstp, type, name, namelen, id);
 630}
 631
 632static __be32 encode_name_from_id(struct xdr_stream *xdr,
 633                                  struct svc_rqst *rqstp, int type, u32 id)
 634{
 635        if (nfs4_disable_idmapping && rqstp->rq_cred.cr_flavor < RPC_AUTH_GSS)
 636                return encode_ascii_id(xdr, id);
 637        return idmap_id_to_name(xdr, rqstp, type, id);
 638}
 639
 640__be32
 641nfsd_map_name_to_uid(struct svc_rqst *rqstp, const char *name, size_t namelen,
 642                kuid_t *uid)
 643{
 644        __be32 status;
 645        u32 id = -1;
 646
 647        if (name == NULL || namelen == 0)
 648                return nfserr_inval;
 649
 650        status = do_name_to_id(rqstp, IDMAP_TYPE_USER, name, namelen, &id);
 651        *uid = make_kuid(nfsd_user_namespace(rqstp), id);
 652        if (!uid_valid(*uid))
 653                status = nfserr_badowner;
 654        return status;
 655}
 656
 657__be32
 658nfsd_map_name_to_gid(struct svc_rqst *rqstp, const char *name, size_t namelen,
 659                kgid_t *gid)
 660{
 661        __be32 status;
 662        u32 id = -1;
 663
 664        if (name == NULL || namelen == 0)
 665                return nfserr_inval;
 666
 667        status = do_name_to_id(rqstp, IDMAP_TYPE_GROUP, name, namelen, &id);
 668        *gid = make_kgid(nfsd_user_namespace(rqstp), id);
 669        if (!gid_valid(*gid))
 670                status = nfserr_badowner;
 671        return status;
 672}
 673
 674__be32 nfsd4_encode_user(struct xdr_stream *xdr, struct svc_rqst *rqstp,
 675                         kuid_t uid)
 676{
 677        u32 id = from_kuid_munged(nfsd_user_namespace(rqstp), uid);
 678        return encode_name_from_id(xdr, rqstp, IDMAP_TYPE_USER, id);
 679}
 680
 681__be32 nfsd4_encode_group(struct xdr_stream *xdr, struct svc_rqst *rqstp,
 682                          kgid_t gid)
 683{
 684        u32 id = from_kgid_munged(nfsd_user_namespace(rqstp), gid);
 685        return encode_name_from_id(xdr, rqstp, IDMAP_TYPE_GROUP, id);
 686}
 687