Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0
0002 /*
0003  * linux/fs/nfs/nfs2xdr.c
0004  *
0005  * XDR functions to encode/decode NFS RPC arguments and results.
0006  *
0007  * Copyright (C) 1992, 1993, 1994  Rick Sladkey
0008  * Copyright (C) 1996 Olaf Kirch
0009  * 04 Aug 1998  Ion Badulescu <ionut@cs.columbia.edu>
0010  *      FIFO's need special handling in NFSv2
0011  */
0012 
0013 #include <linux/param.h>
0014 #include <linux/time.h>
0015 #include <linux/mm.h>
0016 #include <linux/errno.h>
0017 #include <linux/string.h>
0018 #include <linux/in.h>
0019 #include <linux/pagemap.h>
0020 #include <linux/proc_fs.h>
0021 #include <linux/sunrpc/clnt.h>
0022 #include <linux/nfs.h>
0023 #include <linux/nfs2.h>
0024 #include <linux/nfs_fs.h>
0025 #include "nfstrace.h"
0026 #include "internal.h"
0027 
0028 #define NFSDBG_FACILITY     NFSDBG_XDR
0029 
0030 /* Mapping from NFS error code to "errno" error code. */
0031 #define errno_NFSERR_IO     EIO
0032 
0033 /*
0034  * Declare the space requirements for NFS arguments and replies as
0035  * number of 32bit-words
0036  */
0037 #define NFS_pagepad_sz      (1) /* Page padding */
0038 #define NFS_fhandle_sz      (8)
0039 #define NFS_sattr_sz        (8)
0040 #define NFS_filename_sz     (1+(NFS2_MAXNAMLEN>>2))
0041 #define NFS_path_sz     (1+(NFS2_MAXPATHLEN>>2))
0042 #define NFS_fattr_sz        (17)
0043 #define NFS_info_sz     (5)
0044 #define NFS_entry_sz        (NFS_filename_sz+3)
0045 
0046 #define NFS_diropargs_sz    (NFS_fhandle_sz+NFS_filename_sz)
0047 #define NFS_removeargs_sz   (NFS_fhandle_sz+NFS_filename_sz)
0048 #define NFS_sattrargs_sz    (NFS_fhandle_sz+NFS_sattr_sz)
0049 #define NFS_readlinkargs_sz (NFS_fhandle_sz)
0050 #define NFS_readargs_sz     (NFS_fhandle_sz+3)
0051 #define NFS_writeargs_sz    (NFS_fhandle_sz+4)
0052 #define NFS_createargs_sz   (NFS_diropargs_sz+NFS_sattr_sz)
0053 #define NFS_renameargs_sz   (NFS_diropargs_sz+NFS_diropargs_sz)
0054 #define NFS_linkargs_sz     (NFS_fhandle_sz+NFS_diropargs_sz)
0055 #define NFS_symlinkargs_sz  (NFS_diropargs_sz+1+NFS_sattr_sz)
0056 #define NFS_readdirargs_sz  (NFS_fhandle_sz+2)
0057 
0058 #define NFS_attrstat_sz     (1+NFS_fattr_sz)
0059 #define NFS_diropres_sz     (1+NFS_fhandle_sz+NFS_fattr_sz)
0060 #define NFS_readlinkres_sz  (2+NFS_pagepad_sz)
0061 #define NFS_readres_sz      (1+NFS_fattr_sz+1+NFS_pagepad_sz)
0062 #define NFS_writeres_sz         (NFS_attrstat_sz)
0063 #define NFS_stat_sz     (1)
0064 #define NFS_readdirres_sz   (1+NFS_pagepad_sz)
0065 #define NFS_statfsres_sz    (1+NFS_info_sz)
0066 
0067 static int nfs_stat_to_errno(enum nfs_stat);
0068 
0069 /*
0070  * Encode/decode NFSv2 basic data types
0071  *
0072  * Basic NFSv2 data types are defined in section 2.3 of RFC 1094:
0073  * "NFS: Network File System Protocol Specification".
0074  *
0075  * Not all basic data types have their own encoding and decoding
0076  * functions.  For run-time efficiency, some data types are encoded
0077  * or decoded inline.
0078  */
0079 
0080 static struct user_namespace *rpc_userns(const struct rpc_clnt *clnt)
0081 {
0082     if (clnt && clnt->cl_cred)
0083         return clnt->cl_cred->user_ns;
0084     return &init_user_ns;
0085 }
0086 
0087 static struct user_namespace *rpc_rqst_userns(const struct rpc_rqst *rqstp)
0088 {
0089     if (rqstp->rq_task)
0090         return rpc_userns(rqstp->rq_task->tk_client);
0091     return &init_user_ns;
0092 }
0093 
0094 /*
0095  *  typedef opaque  nfsdata<>;
0096  */
0097 static int decode_nfsdata(struct xdr_stream *xdr, struct nfs_pgio_res *result)
0098 {
0099     u32 recvd, count;
0100     __be32 *p;
0101 
0102     p = xdr_inline_decode(xdr, 4);
0103     if (unlikely(!p))
0104         return -EIO;
0105     count = be32_to_cpup(p);
0106     recvd = xdr_read_pages(xdr, count);
0107     if (unlikely(count > recvd))
0108         goto out_cheating;
0109 out:
0110     result->eof = 0;    /* NFSv2 does not pass EOF flag on the wire. */
0111     result->count = count;
0112     return count;
0113 out_cheating:
0114     dprintk("NFS: server cheating in read result: "
0115         "count %u > recvd %u\n", count, recvd);
0116     count = recvd;
0117     goto out;
0118 }
0119 
0120 /*
0121  *  enum stat {
0122  *      NFS_OK = 0,
0123  *      NFSERR_PERM = 1,
0124  *      NFSERR_NOENT = 2,
0125  *      NFSERR_IO = 5,
0126  *      NFSERR_NXIO = 6,
0127  *      NFSERR_ACCES = 13,
0128  *      NFSERR_EXIST = 17,
0129  *      NFSERR_NODEV = 19,
0130  *      NFSERR_NOTDIR = 20,
0131  *      NFSERR_ISDIR = 21,
0132  *      NFSERR_FBIG = 27,
0133  *      NFSERR_NOSPC = 28,
0134  *      NFSERR_ROFS = 30,
0135  *      NFSERR_NAMETOOLONG = 63,
0136  *      NFSERR_NOTEMPTY = 66,
0137  *      NFSERR_DQUOT = 69,
0138  *      NFSERR_STALE = 70,
0139  *      NFSERR_WFLUSH = 99
0140  *  };
0141  */
0142 static int decode_stat(struct xdr_stream *xdr, enum nfs_stat *status)
0143 {
0144     __be32 *p;
0145 
0146     p = xdr_inline_decode(xdr, 4);
0147     if (unlikely(!p))
0148         return -EIO;
0149     if (unlikely(*p != cpu_to_be32(NFS_OK)))
0150         goto out_status;
0151     *status = 0;
0152     return 0;
0153 out_status:
0154     *status = be32_to_cpup(p);
0155     trace_nfs_xdr_status(xdr, (int)*status);
0156     return 0;
0157 }
0158 
0159 /*
0160  * 2.3.2.  ftype
0161  *
0162  *  enum ftype {
0163  *      NFNON = 0,
0164  *      NFREG = 1,
0165  *      NFDIR = 2,
0166  *      NFBLK = 3,
0167  *      NFCHR = 4,
0168  *      NFLNK = 5
0169  *  };
0170  *
0171  */
0172 static __be32 *xdr_decode_ftype(__be32 *p, u32 *type)
0173 {
0174     *type = be32_to_cpup(p++);
0175     if (unlikely(*type > NF2FIFO))
0176         *type = NFBAD;
0177     return p;
0178 }
0179 
0180 /*
0181  * 2.3.3.  fhandle
0182  *
0183  *  typedef opaque fhandle[FHSIZE];
0184  */
0185 static void encode_fhandle(struct xdr_stream *xdr, const struct nfs_fh *fh)
0186 {
0187     __be32 *p;
0188 
0189     p = xdr_reserve_space(xdr, NFS2_FHSIZE);
0190     memcpy(p, fh->data, NFS2_FHSIZE);
0191 }
0192 
0193 static int decode_fhandle(struct xdr_stream *xdr, struct nfs_fh *fh)
0194 {
0195     __be32 *p;
0196 
0197     p = xdr_inline_decode(xdr, NFS2_FHSIZE);
0198     if (unlikely(!p))
0199         return -EIO;
0200     fh->size = NFS2_FHSIZE;
0201     memcpy(fh->data, p, NFS2_FHSIZE);
0202     return 0;
0203 }
0204 
0205 /*
0206  * 2.3.4.  timeval
0207  *
0208  *  struct timeval {
0209  *      unsigned int seconds;
0210  *      unsigned int useconds;
0211  *  };
0212  */
0213 static __be32 *xdr_encode_time(__be32 *p, const struct timespec64 *timep)
0214 {
0215     *p++ = cpu_to_be32((u32)timep->tv_sec);
0216     if (timep->tv_nsec != 0)
0217         *p++ = cpu_to_be32(timep->tv_nsec / NSEC_PER_USEC);
0218     else
0219         *p++ = cpu_to_be32(0);
0220     return p;
0221 }
0222 
0223 /*
0224  * Passing the invalid value useconds=1000000 is a Sun convention for
0225  * "set to current server time".  It's needed to make permissions checks
0226  * for the "touch" program across v2 mounts to Solaris and Irix servers
0227  * work correctly.  See description of sattr in section 6.1 of "NFS
0228  * Illustrated" by Brent Callaghan, Addison-Wesley, ISBN 0-201-32750-5.
0229  */
0230 static __be32 *xdr_encode_current_server_time(__be32 *p,
0231                           const struct timespec64 *timep)
0232 {
0233     *p++ = cpu_to_be32(timep->tv_sec);
0234     *p++ = cpu_to_be32(1000000);
0235     return p;
0236 }
0237 
0238 static __be32 *xdr_decode_time(__be32 *p, struct timespec64 *timep)
0239 {
0240     timep->tv_sec = be32_to_cpup(p++);
0241     timep->tv_nsec = be32_to_cpup(p++) * NSEC_PER_USEC;
0242     return p;
0243 }
0244 
0245 /*
0246  * 2.3.5.  fattr
0247  *
0248  *  struct fattr {
0249  *      ftype       type;
0250  *      unsigned int    mode;
0251  *      unsigned int    nlink;
0252  *      unsigned int    uid;
0253  *      unsigned int    gid;
0254  *      unsigned int    size;
0255  *      unsigned int    blocksize;
0256  *      unsigned int    rdev;
0257  *      unsigned int    blocks;
0258  *      unsigned int    fsid;
0259  *      unsigned int    fileid;
0260  *      timeval     atime;
0261  *      timeval     mtime;
0262  *      timeval     ctime;
0263  *  };
0264  *
0265  */
0266 static int decode_fattr(struct xdr_stream *xdr, struct nfs_fattr *fattr,
0267         struct user_namespace *userns)
0268 {
0269     u32 rdev, type;
0270     __be32 *p;
0271 
0272     p = xdr_inline_decode(xdr, NFS_fattr_sz << 2);
0273     if (unlikely(!p))
0274         return -EIO;
0275 
0276     fattr->valid |= NFS_ATTR_FATTR_V2;
0277 
0278     p = xdr_decode_ftype(p, &type);
0279 
0280     fattr->mode = be32_to_cpup(p++);
0281     fattr->nlink = be32_to_cpup(p++);
0282     fattr->uid = make_kuid(userns, be32_to_cpup(p++));
0283     if (!uid_valid(fattr->uid))
0284         goto out_uid;
0285     fattr->gid = make_kgid(userns, be32_to_cpup(p++));
0286     if (!gid_valid(fattr->gid))
0287         goto out_gid;
0288         
0289     fattr->size = be32_to_cpup(p++);
0290     fattr->du.nfs2.blocksize = be32_to_cpup(p++);
0291 
0292     rdev = be32_to_cpup(p++);
0293     fattr->rdev = new_decode_dev(rdev);
0294     if (type == (u32)NFCHR && rdev == (u32)NFS2_FIFO_DEV) {
0295         fattr->mode = (fattr->mode & ~S_IFMT) | S_IFIFO;
0296         fattr->rdev = 0;
0297     }
0298 
0299     fattr->du.nfs2.blocks = be32_to_cpup(p++);
0300     fattr->fsid.major = be32_to_cpup(p++);
0301     fattr->fsid.minor = 0;
0302     fattr->fileid = be32_to_cpup(p++);
0303 
0304     p = xdr_decode_time(p, &fattr->atime);
0305     p = xdr_decode_time(p, &fattr->mtime);
0306     xdr_decode_time(p, &fattr->ctime);
0307     fattr->change_attr = nfs_timespec_to_change_attr(&fattr->ctime);
0308 
0309     return 0;
0310 out_uid:
0311     dprintk("NFS: returned invalid uid\n");
0312     return -EINVAL;
0313 out_gid:
0314     dprintk("NFS: returned invalid gid\n");
0315     return -EINVAL;
0316 }
0317 
0318 /*
0319  * 2.3.6.  sattr
0320  *
0321  *  struct sattr {
0322  *      unsigned int    mode;
0323  *      unsigned int    uid;
0324  *      unsigned int    gid;
0325  *      unsigned int    size;
0326  *      timeval     atime;
0327  *      timeval     mtime;
0328  *  };
0329  */
0330 
0331 #define NFS2_SATTR_NOT_SET  (0xffffffff)
0332 
0333 static __be32 *xdr_time_not_set(__be32 *p)
0334 {
0335     *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0336     *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0337     return p;
0338 }
0339 
0340 static void encode_sattr(struct xdr_stream *xdr, const struct iattr *attr,
0341         struct user_namespace *userns)
0342 {
0343     __be32 *p;
0344 
0345     p = xdr_reserve_space(xdr, NFS_sattr_sz << 2);
0346 
0347     if (attr->ia_valid & ATTR_MODE)
0348         *p++ = cpu_to_be32(attr->ia_mode);
0349     else
0350         *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0351     if (attr->ia_valid & ATTR_UID)
0352         *p++ = cpu_to_be32(from_kuid_munged(userns, attr->ia_uid));
0353     else
0354         *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0355     if (attr->ia_valid & ATTR_GID)
0356         *p++ = cpu_to_be32(from_kgid_munged(userns, attr->ia_gid));
0357     else
0358         *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0359     if (attr->ia_valid & ATTR_SIZE)
0360         *p++ = cpu_to_be32((u32)attr->ia_size);
0361     else
0362         *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
0363 
0364     if (attr->ia_valid & ATTR_ATIME_SET)
0365         p = xdr_encode_time(p, &attr->ia_atime);
0366     else if (attr->ia_valid & ATTR_ATIME)
0367         p = xdr_encode_current_server_time(p, &attr->ia_atime);
0368     else
0369         p = xdr_time_not_set(p);
0370     if (attr->ia_valid & ATTR_MTIME_SET)
0371         xdr_encode_time(p, &attr->ia_mtime);
0372     else if (attr->ia_valid & ATTR_MTIME)
0373         xdr_encode_current_server_time(p, &attr->ia_mtime);
0374     else
0375         xdr_time_not_set(p);
0376 }
0377 
0378 /*
0379  * 2.3.7.  filename
0380  *
0381  *  typedef string filename<MAXNAMLEN>;
0382  */
0383 static void encode_filename(struct xdr_stream *xdr,
0384                 const char *name, u32 length)
0385 {
0386     __be32 *p;
0387 
0388     WARN_ON_ONCE(length > NFS2_MAXNAMLEN);
0389     p = xdr_reserve_space(xdr, 4 + length);
0390     xdr_encode_opaque(p, name, length);
0391 }
0392 
0393 static int decode_filename_inline(struct xdr_stream *xdr,
0394                   const char **name, u32 *length)
0395 {
0396     __be32 *p;
0397     u32 count;
0398 
0399     p = xdr_inline_decode(xdr, 4);
0400     if (unlikely(!p))
0401         return -EIO;
0402     count = be32_to_cpup(p);
0403     if (count > NFS3_MAXNAMLEN)
0404         goto out_nametoolong;
0405     p = xdr_inline_decode(xdr, count);
0406     if (unlikely(!p))
0407         return -EIO;
0408     *name = (const char *)p;
0409     *length = count;
0410     return 0;
0411 out_nametoolong:
0412     dprintk("NFS: returned filename too long: %u\n", count);
0413     return -ENAMETOOLONG;
0414 }
0415 
0416 /*
0417  * 2.3.8.  path
0418  *
0419  *  typedef string path<MAXPATHLEN>;
0420  */
0421 static void encode_path(struct xdr_stream *xdr, struct page **pages, u32 length)
0422 {
0423     __be32 *p;
0424 
0425     p = xdr_reserve_space(xdr, 4);
0426     *p = cpu_to_be32(length);
0427     xdr_write_pages(xdr, pages, 0, length);
0428 }
0429 
0430 static int decode_path(struct xdr_stream *xdr)
0431 {
0432     u32 length, recvd;
0433     __be32 *p;
0434 
0435     p = xdr_inline_decode(xdr, 4);
0436     if (unlikely(!p))
0437         return -EIO;
0438     length = be32_to_cpup(p);
0439     if (unlikely(length >= xdr->buf->page_len || length > NFS_MAXPATHLEN))
0440         goto out_size;
0441     recvd = xdr_read_pages(xdr, length);
0442     if (unlikely(length > recvd))
0443         goto out_cheating;
0444     xdr_terminate_string(xdr->buf, length);
0445     return 0;
0446 out_size:
0447     dprintk("NFS: returned pathname too long: %u\n", length);
0448     return -ENAMETOOLONG;
0449 out_cheating:
0450     dprintk("NFS: server cheating in pathname result: "
0451         "length %u > received %u\n", length, recvd);
0452     return -EIO;
0453 }
0454 
0455 /*
0456  * 2.3.9.  attrstat
0457  *
0458  *  union attrstat switch (stat status) {
0459  *  case NFS_OK:
0460  *      fattr attributes;
0461  *  default:
0462  *      void;
0463  *  };
0464  */
0465 static int decode_attrstat(struct xdr_stream *xdr, struct nfs_fattr *result,
0466                __u32 *op_status,
0467                struct user_namespace *userns)
0468 {
0469     enum nfs_stat status;
0470     int error;
0471 
0472     error = decode_stat(xdr, &status);
0473     if (unlikely(error))
0474         goto out;
0475     if (op_status)
0476         *op_status = status;
0477     if (status != NFS_OK)
0478         goto out_default;
0479     error = decode_fattr(xdr, result, userns);
0480 out:
0481     return error;
0482 out_default:
0483     return nfs_stat_to_errno(status);
0484 }
0485 
0486 /*
0487  * 2.3.10.  diropargs
0488  *
0489  *  struct diropargs {
0490  *      fhandle  dir;
0491  *      filename name;
0492  *  };
0493  */
0494 static void encode_diropargs(struct xdr_stream *xdr, const struct nfs_fh *fh,
0495                  const char *name, u32 length)
0496 {
0497     encode_fhandle(xdr, fh);
0498     encode_filename(xdr, name, length);
0499 }
0500 
0501 /*
0502  * 2.3.11.  diropres
0503  *
0504  *  union diropres switch (stat status) {
0505  *  case NFS_OK:
0506  *      struct {
0507  *          fhandle file;
0508  *          fattr   attributes;
0509  *      } diropok;
0510  *  default:
0511  *      void;
0512  *  };
0513  */
0514 static int decode_diropok(struct xdr_stream *xdr, struct nfs_diropok *result,
0515         struct user_namespace *userns)
0516 {
0517     int error;
0518 
0519     error = decode_fhandle(xdr, result->fh);
0520     if (unlikely(error))
0521         goto out;
0522     error = decode_fattr(xdr, result->fattr, userns);
0523 out:
0524     return error;
0525 }
0526 
0527 static int decode_diropres(struct xdr_stream *xdr, struct nfs_diropok *result,
0528         struct user_namespace *userns)
0529 {
0530     enum nfs_stat status;
0531     int error;
0532 
0533     error = decode_stat(xdr, &status);
0534     if (unlikely(error))
0535         goto out;
0536     if (status != NFS_OK)
0537         goto out_default;
0538     error = decode_diropok(xdr, result, userns);
0539 out:
0540     return error;
0541 out_default:
0542     return nfs_stat_to_errno(status);
0543 }
0544 
0545 
0546 /*
0547  * NFSv2 XDR encode functions
0548  *
0549  * NFSv2 argument types are defined in section 2.2 of RFC 1094:
0550  * "NFS: Network File System Protocol Specification".
0551  */
0552 
0553 static void nfs2_xdr_enc_fhandle(struct rpc_rqst *req,
0554                  struct xdr_stream *xdr,
0555                  const void *data)
0556 {
0557     const struct nfs_fh *fh = data;
0558 
0559     encode_fhandle(xdr, fh);
0560 }
0561 
0562 /*
0563  * 2.2.3.  sattrargs
0564  *
0565  *  struct sattrargs {
0566  *      fhandle file;
0567  *      sattr attributes;
0568  *  };
0569  */
0570 static void nfs2_xdr_enc_sattrargs(struct rpc_rqst *req,
0571                    struct xdr_stream *xdr,
0572                    const void *data)
0573 {
0574     const struct nfs_sattrargs *args = data;
0575 
0576     encode_fhandle(xdr, args->fh);
0577     encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
0578 }
0579 
0580 static void nfs2_xdr_enc_diropargs(struct rpc_rqst *req,
0581                    struct xdr_stream *xdr,
0582                    const void *data)
0583 {
0584     const struct nfs_diropargs *args = data;
0585 
0586     encode_diropargs(xdr, args->fh, args->name, args->len);
0587 }
0588 
0589 static void nfs2_xdr_enc_readlinkargs(struct rpc_rqst *req,
0590                       struct xdr_stream *xdr,
0591                       const void *data)
0592 {
0593     const struct nfs_readlinkargs *args = data;
0594 
0595     encode_fhandle(xdr, args->fh);
0596     rpc_prepare_reply_pages(req, args->pages, args->pgbase, args->pglen,
0597                 NFS_readlinkres_sz - NFS_pagepad_sz);
0598 }
0599 
0600 /*
0601  * 2.2.7.  readargs
0602  *
0603  *  struct readargs {
0604  *      fhandle file;
0605  *      unsigned offset;
0606  *      unsigned count;
0607  *      unsigned totalcount;
0608  *  };
0609  */
0610 static void encode_readargs(struct xdr_stream *xdr,
0611                 const struct nfs_pgio_args *args)
0612 {
0613     u32 offset = args->offset;
0614     u32 count = args->count;
0615     __be32 *p;
0616 
0617     encode_fhandle(xdr, args->fh);
0618 
0619     p = xdr_reserve_space(xdr, 4 + 4 + 4);
0620     *p++ = cpu_to_be32(offset);
0621     *p++ = cpu_to_be32(count);
0622     *p = cpu_to_be32(count);
0623 }
0624 
0625 static void nfs2_xdr_enc_readargs(struct rpc_rqst *req,
0626                   struct xdr_stream *xdr,
0627                   const void *data)
0628 {
0629     const struct nfs_pgio_args *args = data;
0630 
0631     encode_readargs(xdr, args);
0632     rpc_prepare_reply_pages(req, args->pages, args->pgbase, args->count,
0633                 NFS_readres_sz - NFS_pagepad_sz);
0634     req->rq_rcv_buf.flags |= XDRBUF_READ;
0635 }
0636 
0637 /*
0638  * 2.2.9.  writeargs
0639  *
0640  *  struct writeargs {
0641  *      fhandle file;
0642  *      unsigned beginoffset;
0643  *      unsigned offset;
0644  *      unsigned totalcount;
0645  *      nfsdata data;
0646  *  };
0647  */
0648 static void encode_writeargs(struct xdr_stream *xdr,
0649                  const struct nfs_pgio_args *args)
0650 {
0651     u32 offset = args->offset;
0652     u32 count = args->count;
0653     __be32 *p;
0654 
0655     encode_fhandle(xdr, args->fh);
0656 
0657     p = xdr_reserve_space(xdr, 4 + 4 + 4 + 4);
0658     *p++ = cpu_to_be32(offset);
0659     *p++ = cpu_to_be32(offset);
0660     *p++ = cpu_to_be32(count);
0661 
0662     /* nfsdata */
0663     *p = cpu_to_be32(count);
0664     xdr_write_pages(xdr, args->pages, args->pgbase, count);
0665 }
0666 
0667 static void nfs2_xdr_enc_writeargs(struct rpc_rqst *req,
0668                    struct xdr_stream *xdr,
0669                    const void *data)
0670 {
0671     const struct nfs_pgio_args *args = data;
0672 
0673     encode_writeargs(xdr, args);
0674     xdr->buf->flags |= XDRBUF_WRITE;
0675 }
0676 
0677 /*
0678  * 2.2.10.  createargs
0679  *
0680  *  struct createargs {
0681  *      diropargs where;
0682  *      sattr attributes;
0683  *  };
0684  */
0685 static void nfs2_xdr_enc_createargs(struct rpc_rqst *req,
0686                     struct xdr_stream *xdr,
0687                     const void *data)
0688 {
0689     const struct nfs_createargs *args = data;
0690 
0691     encode_diropargs(xdr, args->fh, args->name, args->len);
0692     encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
0693 }
0694 
0695 static void nfs2_xdr_enc_removeargs(struct rpc_rqst *req,
0696                     struct xdr_stream *xdr,
0697                     const void *data)
0698 {
0699     const struct nfs_removeargs *args = data;
0700 
0701     encode_diropargs(xdr, args->fh, args->name.name, args->name.len);
0702 }
0703 
0704 /*
0705  * 2.2.12.  renameargs
0706  *
0707  *  struct renameargs {
0708  *      diropargs from;
0709  *      diropargs to;
0710  *  };
0711  */
0712 static void nfs2_xdr_enc_renameargs(struct rpc_rqst *req,
0713                     struct xdr_stream *xdr,
0714                     const void *data)
0715 {
0716     const struct nfs_renameargs *args = data;
0717     const struct qstr *old = args->old_name;
0718     const struct qstr *new = args->new_name;
0719 
0720     encode_diropargs(xdr, args->old_dir, old->name, old->len);
0721     encode_diropargs(xdr, args->new_dir, new->name, new->len);
0722 }
0723 
0724 /*
0725  * 2.2.13.  linkargs
0726  *
0727  *  struct linkargs {
0728  *      fhandle from;
0729  *      diropargs to;
0730  *  };
0731  */
0732 static void nfs2_xdr_enc_linkargs(struct rpc_rqst *req,
0733                   struct xdr_stream *xdr,
0734                   const void *data)
0735 {
0736     const struct nfs_linkargs *args = data;
0737 
0738     encode_fhandle(xdr, args->fromfh);
0739     encode_diropargs(xdr, args->tofh, args->toname, args->tolen);
0740 }
0741 
0742 /*
0743  * 2.2.14.  symlinkargs
0744  *
0745  *  struct symlinkargs {
0746  *      diropargs from;
0747  *      path to;
0748  *      sattr attributes;
0749  *  };
0750  */
0751 static void nfs2_xdr_enc_symlinkargs(struct rpc_rqst *req,
0752                      struct xdr_stream *xdr,
0753                      const void *data)
0754 {
0755     const struct nfs_symlinkargs *args = data;
0756 
0757     encode_diropargs(xdr, args->fromfh, args->fromname, args->fromlen);
0758     encode_path(xdr, args->pages, args->pathlen);
0759     encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
0760 }
0761 
0762 /*
0763  * 2.2.17.  readdirargs
0764  *
0765  *  struct readdirargs {
0766  *      fhandle dir;
0767  *      nfscookie cookie;
0768  *      unsigned count;
0769  *  };
0770  */
0771 static void encode_readdirargs(struct xdr_stream *xdr,
0772                    const struct nfs_readdirargs *args)
0773 {
0774     __be32 *p;
0775 
0776     encode_fhandle(xdr, args->fh);
0777 
0778     p = xdr_reserve_space(xdr, 4 + 4);
0779     *p++ = cpu_to_be32(args->cookie);
0780     *p = cpu_to_be32(args->count);
0781 }
0782 
0783 static void nfs2_xdr_enc_readdirargs(struct rpc_rqst *req,
0784                      struct xdr_stream *xdr,
0785                      const void *data)
0786 {
0787     const struct nfs_readdirargs *args = data;
0788 
0789     encode_readdirargs(xdr, args);
0790     rpc_prepare_reply_pages(req, args->pages, 0, args->count,
0791                 NFS_readdirres_sz - NFS_pagepad_sz);
0792 }
0793 
0794 /*
0795  * NFSv2 XDR decode functions
0796  *
0797  * NFSv2 result types are defined in section 2.2 of RFC 1094:
0798  * "NFS: Network File System Protocol Specification".
0799  */
0800 
0801 static int nfs2_xdr_dec_stat(struct rpc_rqst *req, struct xdr_stream *xdr,
0802                  void *__unused)
0803 {
0804     enum nfs_stat status;
0805     int error;
0806 
0807     error = decode_stat(xdr, &status);
0808     if (unlikely(error))
0809         goto out;
0810     if (status != NFS_OK)
0811         goto out_default;
0812 out:
0813     return error;
0814 out_default:
0815     return nfs_stat_to_errno(status);
0816 }
0817 
0818 static int nfs2_xdr_dec_attrstat(struct rpc_rqst *req, struct xdr_stream *xdr,
0819                  void *result)
0820 {
0821     return decode_attrstat(xdr, result, NULL, rpc_rqst_userns(req));
0822 }
0823 
0824 static int nfs2_xdr_dec_diropres(struct rpc_rqst *req, struct xdr_stream *xdr,
0825                  void *result)
0826 {
0827     return decode_diropres(xdr, result, rpc_rqst_userns(req));
0828 }
0829 
0830 /*
0831  * 2.2.6.  readlinkres
0832  *
0833  *  union readlinkres switch (stat status) {
0834  *  case NFS_OK:
0835  *      path data;
0836  *  default:
0837  *      void;
0838  *  };
0839  */
0840 static int nfs2_xdr_dec_readlinkres(struct rpc_rqst *req,
0841                     struct xdr_stream *xdr, void *__unused)
0842 {
0843     enum nfs_stat status;
0844     int error;
0845 
0846     error = decode_stat(xdr, &status);
0847     if (unlikely(error))
0848         goto out;
0849     if (status != NFS_OK)
0850         goto out_default;
0851     error = decode_path(xdr);
0852 out:
0853     return error;
0854 out_default:
0855     return nfs_stat_to_errno(status);
0856 }
0857 
0858 /*
0859  * 2.2.7.  readres
0860  *
0861  *  union readres switch (stat status) {
0862  *  case NFS_OK:
0863  *      fattr attributes;
0864  *      nfsdata data;
0865  *  default:
0866  *      void;
0867  *  };
0868  */
0869 static int nfs2_xdr_dec_readres(struct rpc_rqst *req, struct xdr_stream *xdr,
0870                 void *data)
0871 {
0872     struct nfs_pgio_res *result = data;
0873     enum nfs_stat status;
0874     int error;
0875 
0876     error = decode_stat(xdr, &status);
0877     if (unlikely(error))
0878         goto out;
0879     result->op_status = status;
0880     if (status != NFS_OK)
0881         goto out_default;
0882     error = decode_fattr(xdr, result->fattr, rpc_rqst_userns(req));
0883     if (unlikely(error))
0884         goto out;
0885     error = decode_nfsdata(xdr, result);
0886 out:
0887     return error;
0888 out_default:
0889     return nfs_stat_to_errno(status);
0890 }
0891 
0892 static int nfs2_xdr_dec_writeres(struct rpc_rqst *req, struct xdr_stream *xdr,
0893                  void *data)
0894 {
0895     struct nfs_pgio_res *result = data;
0896 
0897     /* All NFSv2 writes are "file sync" writes */
0898     result->verf->committed = NFS_FILE_SYNC;
0899     return decode_attrstat(xdr, result->fattr, &result->op_status,
0900             rpc_rqst_userns(req));
0901 }
0902 
0903 /**
0904  * nfs2_decode_dirent - Decode a single NFSv2 directory entry stored in
0905  *                      the local page cache.
0906  * @xdr: XDR stream where entry resides
0907  * @entry: buffer to fill in with entry data
0908  * @plus: boolean indicating whether this should be a readdirplus entry
0909  *
0910  * Returns zero if successful, otherwise a negative errno value is
0911  * returned.
0912  *
0913  * This function is not invoked during READDIR reply decoding, but
0914  * rather whenever an application invokes the getdents(2) system call
0915  * on a directory already in our cache.
0916  *
0917  * 2.2.17.  entry
0918  *
0919  *  struct entry {
0920  *      unsigned    fileid;
0921  *      filename    name;
0922  *      nfscookie   cookie;
0923  *      entry       *nextentry;
0924  *  };
0925  */
0926 int nfs2_decode_dirent(struct xdr_stream *xdr, struct nfs_entry *entry,
0927                bool plus)
0928 {
0929     __be32 *p;
0930     int error;
0931 
0932     p = xdr_inline_decode(xdr, 4);
0933     if (unlikely(!p))
0934         return -EAGAIN;
0935     if (*p++ == xdr_zero) {
0936         p = xdr_inline_decode(xdr, 4);
0937         if (unlikely(!p))
0938             return -EAGAIN;
0939         if (*p++ == xdr_zero)
0940             return -EAGAIN;
0941         entry->eof = 1;
0942         return -EBADCOOKIE;
0943     }
0944 
0945     p = xdr_inline_decode(xdr, 4);
0946     if (unlikely(!p))
0947         return -EAGAIN;
0948     entry->ino = be32_to_cpup(p);
0949 
0950     error = decode_filename_inline(xdr, &entry->name, &entry->len);
0951     if (unlikely(error))
0952         return -EAGAIN;
0953 
0954     /*
0955      * The type (size and byte order) of nfscookie isn't defined in
0956      * RFC 1094.  This implementation assumes that it's an XDR uint32.
0957      */
0958     p = xdr_inline_decode(xdr, 4);
0959     if (unlikely(!p))
0960         return -EAGAIN;
0961     entry->cookie = be32_to_cpup(p);
0962 
0963     entry->d_type = DT_UNKNOWN;
0964 
0965     return 0;
0966 }
0967 
0968 /*
0969  * 2.2.17.  readdirres
0970  *
0971  *  union readdirres switch (stat status) {
0972  *  case NFS_OK:
0973  *      struct {
0974  *          entry *entries;
0975  *          bool eof;
0976  *      } readdirok;
0977  *  default:
0978  *      void;
0979  *  };
0980  *
0981  * Read the directory contents into the page cache, but don't
0982  * touch them.  The actual decoding is done by nfs2_decode_dirent()
0983  * during subsequent nfs_readdir() calls.
0984  */
0985 static int decode_readdirok(struct xdr_stream *xdr)
0986 {
0987     return xdr_read_pages(xdr, xdr->buf->page_len);
0988 }
0989 
0990 static int nfs2_xdr_dec_readdirres(struct rpc_rqst *req,
0991                    struct xdr_stream *xdr, void *__unused)
0992 {
0993     enum nfs_stat status;
0994     int error;
0995 
0996     error = decode_stat(xdr, &status);
0997     if (unlikely(error))
0998         goto out;
0999     if (status != NFS_OK)
1000         goto out_default;
1001     error = decode_readdirok(xdr);
1002 out:
1003     return error;
1004 out_default:
1005     return nfs_stat_to_errno(status);
1006 }
1007 
1008 /*
1009  * 2.2.18.  statfsres
1010  *
1011  *  union statfsres (stat status) {
1012  *  case NFS_OK:
1013  *      struct {
1014  *          unsigned tsize;
1015  *          unsigned bsize;
1016  *          unsigned blocks;
1017  *          unsigned bfree;
1018  *          unsigned bavail;
1019  *      } info;
1020  *  default:
1021  *      void;
1022  *  };
1023  */
1024 static int decode_info(struct xdr_stream *xdr, struct nfs2_fsstat *result)
1025 {
1026     __be32 *p;
1027 
1028     p = xdr_inline_decode(xdr, NFS_info_sz << 2);
1029     if (unlikely(!p))
1030         return -EIO;
1031     result->tsize  = be32_to_cpup(p++);
1032     result->bsize  = be32_to_cpup(p++);
1033     result->blocks = be32_to_cpup(p++);
1034     result->bfree  = be32_to_cpup(p++);
1035     result->bavail = be32_to_cpup(p);
1036     return 0;
1037 }
1038 
1039 static int nfs2_xdr_dec_statfsres(struct rpc_rqst *req, struct xdr_stream *xdr,
1040                   void *result)
1041 {
1042     enum nfs_stat status;
1043     int error;
1044 
1045     error = decode_stat(xdr, &status);
1046     if (unlikely(error))
1047         goto out;
1048     if (status != NFS_OK)
1049         goto out_default;
1050     error = decode_info(xdr, result);
1051 out:
1052     return error;
1053 out_default:
1054     return nfs_stat_to_errno(status);
1055 }
1056 
1057 
1058 /*
1059  * We need to translate between nfs status return values and
1060  * the local errno values which may not be the same.
1061  */
1062 static const struct {
1063     int stat;
1064     int errno;
1065 } nfs_errtbl[] = {
1066     { NFS_OK,       0       },
1067     { NFSERR_PERM,      -EPERM      },
1068     { NFSERR_NOENT,     -ENOENT     },
1069     { NFSERR_IO,        -errno_NFSERR_IO},
1070     { NFSERR_NXIO,      -ENXIO      },
1071 /*  { NFSERR_EAGAIN,    -EAGAIN     }, */
1072     { NFSERR_ACCES,     -EACCES     },
1073     { NFSERR_EXIST,     -EEXIST     },
1074     { NFSERR_XDEV,      -EXDEV      },
1075     { NFSERR_NODEV,     -ENODEV     },
1076     { NFSERR_NOTDIR,    -ENOTDIR    },
1077     { NFSERR_ISDIR,     -EISDIR     },
1078     { NFSERR_INVAL,     -EINVAL     },
1079     { NFSERR_FBIG,      -EFBIG      },
1080     { NFSERR_NOSPC,     -ENOSPC     },
1081     { NFSERR_ROFS,      -EROFS      },
1082     { NFSERR_MLINK,     -EMLINK     },
1083     { NFSERR_NAMETOOLONG,   -ENAMETOOLONG   },
1084     { NFSERR_NOTEMPTY,  -ENOTEMPTY  },
1085     { NFSERR_DQUOT,     -EDQUOT     },
1086     { NFSERR_STALE,     -ESTALE     },
1087     { NFSERR_REMOTE,    -EREMOTE    },
1088 #ifdef EWFLUSH
1089     { NFSERR_WFLUSH,    -EWFLUSH    },
1090 #endif
1091     { NFSERR_BADHANDLE, -EBADHANDLE },
1092     { NFSERR_NOT_SYNC,  -ENOTSYNC   },
1093     { NFSERR_BAD_COOKIE,    -EBADCOOKIE },
1094     { NFSERR_NOTSUPP,   -ENOTSUPP   },
1095     { NFSERR_TOOSMALL,  -ETOOSMALL  },
1096     { NFSERR_SERVERFAULT,   -EREMOTEIO  },
1097     { NFSERR_BADTYPE,   -EBADTYPE   },
1098     { NFSERR_JUKEBOX,   -EJUKEBOX   },
1099     { -1,           -EIO        }
1100 };
1101 
1102 /**
1103  * nfs_stat_to_errno - convert an NFS status code to a local errno
1104  * @status: NFS status code to convert
1105  *
1106  * Returns a local errno value, or -EIO if the NFS status code is
1107  * not recognized.  This function is used jointly by NFSv2 and NFSv3.
1108  */
1109 static int nfs_stat_to_errno(enum nfs_stat status)
1110 {
1111     int i;
1112 
1113     for (i = 0; nfs_errtbl[i].stat != -1; i++) {
1114         if (nfs_errtbl[i].stat == (int)status)
1115             return nfs_errtbl[i].errno;
1116     }
1117     dprintk("NFS: Unrecognized nfs status value: %u\n", status);
1118     return nfs_errtbl[i].errno;
1119 }
1120 
1121 #define PROC(proc, argtype, restype, timer)             \
1122 [NFSPROC_##proc] = {                            \
1123     .p_proc     =  NFSPROC_##proc,                  \
1124     .p_encode   =  nfs2_xdr_enc_##argtype,              \
1125     .p_decode   =  nfs2_xdr_dec_##restype,              \
1126     .p_arglen   =  NFS_##argtype##_sz,              \
1127     .p_replen   =  NFS_##restype##_sz,              \
1128     .p_timer    =  timer,                       \
1129     .p_statidx  =  NFSPROC_##proc,                  \
1130     .p_name     =  #proc,                       \
1131     }
1132 const struct rpc_procinfo nfs_procedures[] = {
1133     PROC(GETATTR,   fhandle,    attrstat,   1),
1134     PROC(SETATTR,   sattrargs,  attrstat,   0),
1135     PROC(LOOKUP,    diropargs,  diropres,   2),
1136     PROC(READLINK,  readlinkargs,   readlinkres,    3),
1137     PROC(READ,  readargs,   readres,    3),
1138     PROC(WRITE, writeargs,  writeres,   4),
1139     PROC(CREATE,    createargs, diropres,   0),
1140     PROC(REMOVE,    removeargs, stat,       0),
1141     PROC(RENAME,    renameargs, stat,       0),
1142     PROC(LINK,  linkargs,   stat,       0),
1143     PROC(SYMLINK,   symlinkargs,    stat,       0),
1144     PROC(MKDIR, createargs, diropres,   0),
1145     PROC(RMDIR, diropargs,  stat,       0),
1146     PROC(READDIR,   readdirargs,    readdirres, 3),
1147     PROC(STATFS,    fhandle,    statfsres,  0),
1148 };
1149 
1150 static unsigned int nfs_version2_counts[ARRAY_SIZE(nfs_procedures)];
1151 const struct rpc_version nfs_version2 = {
1152     .number         = 2,
1153     .nrprocs        = ARRAY_SIZE(nfs_procedures),
1154     .procs          = nfs_procedures,
1155     .counts         = nfs_version2_counts,
1156 };