GNU Linux-libre 5.4.257-gnu1
[releases.git] / fs / nfsd / nfs3xdr.c
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * XDR support for nfsd/protocol version 3.
4  *
5  * Copyright (C) 1995, 1996, 1997 Olaf Kirch <okir@monad.swb.de>
6  *
7  * 2003-08-09 Jamie Lokier: Use htonl() for nanoseconds, not htons()!
8  */
9
10 #include <linux/namei.h>
11 #include <linux/sunrpc/svc_xprt.h>
12 #include "xdr3.h"
13 #include "auth.h"
14 #include "netns.h"
15 #include "vfs.h"
16
17 #define NFSDDBG_FACILITY                NFSDDBG_XDR
18
19
20 /*
21  * Mapping of S_IF* types to NFS file types
22  */
23 static u32      nfs3_ftypes[] = {
24         NF3NON,  NF3FIFO, NF3CHR, NF3BAD,
25         NF3DIR,  NF3BAD,  NF3BLK, NF3BAD,
26         NF3REG,  NF3BAD,  NF3LNK, NF3BAD,
27         NF3SOCK, NF3BAD,  NF3LNK, NF3BAD,
28 };
29
30
31 /*
32  * XDR functions for basic NFS types
33  */
34 static __be32 *
35 encode_time3(__be32 *p, struct timespec *time)
36 {
37         *p++ = htonl((u32) time->tv_sec); *p++ = htonl(time->tv_nsec);
38         return p;
39 }
40
41 static __be32 *
42 decode_time3(__be32 *p, struct timespec *time)
43 {
44         time->tv_sec = ntohl(*p++);
45         time->tv_nsec = ntohl(*p++);
46         return p;
47 }
48
49 static __be32 *
50 decode_fh(__be32 *p, struct svc_fh *fhp)
51 {
52         unsigned int size;
53         fh_init(fhp, NFS3_FHSIZE);
54         size = ntohl(*p++);
55         if (size > NFS3_FHSIZE)
56                 return NULL;
57
58         memcpy(&fhp->fh_handle.fh_base, p, size);
59         fhp->fh_handle.fh_size = size;
60         return p + XDR_QUADLEN(size);
61 }
62
63 /* Helper function for NFSv3 ACL code */
64 __be32 *nfs3svc_decode_fh(__be32 *p, struct svc_fh *fhp)
65 {
66         return decode_fh(p, fhp);
67 }
68
69 static __be32 *
70 encode_fh(__be32 *p, struct svc_fh *fhp)
71 {
72         unsigned int size = fhp->fh_handle.fh_size;
73         *p++ = htonl(size);
74         if (size) p[XDR_QUADLEN(size)-1]=0;
75         memcpy(p, &fhp->fh_handle.fh_base, size);
76         return p + XDR_QUADLEN(size);
77 }
78
79 /*
80  * Decode a file name and make sure that the path contains
81  * no slashes or null bytes.
82  */
83 static __be32 *
84 decode_filename(__be32 *p, char **namp, unsigned int *lenp)
85 {
86         char            *name;
87         unsigned int    i;
88
89         if ((p = xdr_decode_string_inplace(p, namp, lenp, NFS3_MAXNAMLEN)) != NULL) {
90                 for (i = 0, name = *namp; i < *lenp; i++, name++) {
91                         if (*name == '\0' || *name == '/')
92                                 return NULL;
93                 }
94         }
95
96         return p;
97 }
98
99 static __be32 *
100 decode_sattr3(__be32 *p, struct iattr *iap, struct user_namespace *userns)
101 {
102         u32     tmp;
103
104         iap->ia_valid = 0;
105
106         if (*p++) {
107                 iap->ia_valid |= ATTR_MODE;
108                 iap->ia_mode = ntohl(*p++);
109         }
110         if (*p++) {
111                 iap->ia_uid = make_kuid(userns, ntohl(*p++));
112                 if (uid_valid(iap->ia_uid))
113                         iap->ia_valid |= ATTR_UID;
114         }
115         if (*p++) {
116                 iap->ia_gid = make_kgid(userns, ntohl(*p++));
117                 if (gid_valid(iap->ia_gid))
118                         iap->ia_valid |= ATTR_GID;
119         }
120         if (*p++) {
121                 u64     newsize;
122
123                 iap->ia_valid |= ATTR_SIZE;
124                 p = xdr_decode_hyper(p, &newsize);
125                 iap->ia_size = min_t(u64, newsize, NFS_OFFSET_MAX);
126         }
127         if ((tmp = ntohl(*p++)) == 1) { /* set to server time */
128                 iap->ia_valid |= ATTR_ATIME;
129         } else if (tmp == 2) {          /* set to client time */
130                 iap->ia_valid |= ATTR_ATIME | ATTR_ATIME_SET;
131                 iap->ia_atime.tv_sec = ntohl(*p++);
132                 iap->ia_atime.tv_nsec = ntohl(*p++);
133         }
134         if ((tmp = ntohl(*p++)) == 1) { /* set to server time */
135                 iap->ia_valid |= ATTR_MTIME;
136         } else if (tmp == 2) {          /* set to client time */
137                 iap->ia_valid |= ATTR_MTIME | ATTR_MTIME_SET;
138                 iap->ia_mtime.tv_sec = ntohl(*p++);
139                 iap->ia_mtime.tv_nsec = ntohl(*p++);
140         }
141         return p;
142 }
143
144 static __be32 *encode_fsid(__be32 *p, struct svc_fh *fhp)
145 {
146         u64 f;
147         switch(fsid_source(fhp)) {
148         default:
149         case FSIDSOURCE_DEV:
150                 p = xdr_encode_hyper(p, (u64)huge_encode_dev
151                                      (fhp->fh_dentry->d_sb->s_dev));
152                 break;
153         case FSIDSOURCE_FSID:
154                 p = xdr_encode_hyper(p, (u64) fhp->fh_export->ex_fsid);
155                 break;
156         case FSIDSOURCE_UUID:
157                 f = ((u64*)fhp->fh_export->ex_uuid)[0];
158                 f ^= ((u64*)fhp->fh_export->ex_uuid)[1];
159                 p = xdr_encode_hyper(p, f);
160                 break;
161         }
162         return p;
163 }
164
165 static __be32 *
166 encode_fattr3(struct svc_rqst *rqstp, __be32 *p, struct svc_fh *fhp,
167               struct kstat *stat)
168 {
169         struct user_namespace *userns = nfsd_user_namespace(rqstp);
170         struct timespec ts;
171         *p++ = htonl(nfs3_ftypes[(stat->mode & S_IFMT) >> 12]);
172         *p++ = htonl((u32) (stat->mode & S_IALLUGO));
173         *p++ = htonl((u32) stat->nlink);
174         *p++ = htonl((u32) from_kuid_munged(userns, stat->uid));
175         *p++ = htonl((u32) from_kgid_munged(userns, stat->gid));
176         if (S_ISLNK(stat->mode) && stat->size > NFS3_MAXPATHLEN) {
177                 p = xdr_encode_hyper(p, (u64) NFS3_MAXPATHLEN);
178         } else {
179                 p = xdr_encode_hyper(p, (u64) stat->size);
180         }
181         p = xdr_encode_hyper(p, ((u64)stat->blocks) << 9);
182         *p++ = htonl((u32) MAJOR(stat->rdev));
183         *p++ = htonl((u32) MINOR(stat->rdev));
184         p = encode_fsid(p, fhp);
185         p = xdr_encode_hyper(p, stat->ino);
186         ts = timespec64_to_timespec(stat->atime);
187         p = encode_time3(p, &ts);
188         ts = timespec64_to_timespec(stat->mtime);
189         p = encode_time3(p, &ts);
190         ts = timespec64_to_timespec(stat->ctime);
191         p = encode_time3(p, &ts);
192
193         return p;
194 }
195
196 static __be32 *
197 encode_saved_post_attr(struct svc_rqst *rqstp, __be32 *p, struct svc_fh *fhp)
198 {
199         /* Attributes to follow */
200         *p++ = xdr_one;
201         return encode_fattr3(rqstp, p, fhp, &fhp->fh_post_attr);
202 }
203
204 /*
205  * Encode post-operation attributes.
206  * The inode may be NULL if the call failed because of a stale file
207  * handle. In this case, no attributes are returned.
208  */
209 static __be32 *
210 encode_post_op_attr(struct svc_rqst *rqstp, __be32 *p, struct svc_fh *fhp)
211 {
212         struct dentry *dentry = fhp->fh_dentry;
213         if (dentry && d_really_is_positive(dentry)) {
214                 __be32 err;
215                 struct kstat stat;
216
217                 err = fh_getattr(fhp, &stat);
218                 if (!err) {
219                         *p++ = xdr_one;         /* attributes follow */
220                         lease_get_mtime(d_inode(dentry), &stat.mtime);
221                         return encode_fattr3(rqstp, p, fhp, &stat);
222                 }
223         }
224         *p++ = xdr_zero;
225         return p;
226 }
227
228 /* Helper for NFSv3 ACLs */
229 __be32 *
230 nfs3svc_encode_post_op_attr(struct svc_rqst *rqstp, __be32 *p, struct svc_fh *fhp)
231 {
232         return encode_post_op_attr(rqstp, p, fhp);
233 }
234
235 /*
236  * Enocde weak cache consistency data
237  */
238 static __be32 *
239 encode_wcc_data(struct svc_rqst *rqstp, __be32 *p, struct svc_fh *fhp)
240 {
241         struct dentry   *dentry = fhp->fh_dentry;
242
243         if (dentry && d_really_is_positive(dentry) && fhp->fh_post_saved) {
244                 if (fhp->fh_pre_saved) {
245                         *p++ = xdr_one;
246                         p = xdr_encode_hyper(p, (u64) fhp->fh_pre_size);
247                         p = encode_time3(p, &fhp->fh_pre_mtime);
248                         p = encode_time3(p, &fhp->fh_pre_ctime);
249                 } else {
250                         *p++ = xdr_zero;
251                 }
252                 return encode_saved_post_attr(rqstp, p, fhp);
253         }
254         /* no pre- or post-attrs */
255         *p++ = xdr_zero;
256         return encode_post_op_attr(rqstp, p, fhp);
257 }
258
259 /*
260  * Fill in the pre_op attr for the wcc data
261  */
262 void fill_pre_wcc(struct svc_fh *fhp)
263 {
264         struct inode    *inode;
265         struct kstat    stat;
266         __be32 err;
267
268         if (fhp->fh_pre_saved)
269                 return;
270
271         inode = d_inode(fhp->fh_dentry);
272         err = fh_getattr(fhp, &stat);
273         if (err) {
274                 /* Grab the times from inode anyway */
275                 stat.mtime = inode->i_mtime;
276                 stat.ctime = inode->i_ctime;
277                 stat.size  = inode->i_size;
278         }
279
280         fhp->fh_pre_mtime = timespec64_to_timespec(stat.mtime);
281         fhp->fh_pre_ctime = timespec64_to_timespec(stat.ctime);
282         fhp->fh_pre_size  = stat.size;
283         fhp->fh_pre_change = nfsd4_change_attribute(&stat, inode);
284         fhp->fh_pre_saved = true;
285 }
286
287 /*
288  * Fill in the post_op attr for the wcc data
289  */
290 void fill_post_wcc(struct svc_fh *fhp)
291 {
292         __be32 err;
293
294         if (fhp->fh_post_saved)
295                 printk("nfsd: inode locked twice during operation.\n");
296
297         err = fh_getattr(fhp, &fhp->fh_post_attr);
298         fhp->fh_post_change = nfsd4_change_attribute(&fhp->fh_post_attr,
299                                                      d_inode(fhp->fh_dentry));
300         if (err) {
301                 fhp->fh_post_saved = false;
302                 /* Grab the ctime anyway - set_change_info might use it */
303                 fhp->fh_post_attr.ctime = d_inode(fhp->fh_dentry)->i_ctime;
304         } else
305                 fhp->fh_post_saved = true;
306 }
307
308 /*
309  * XDR decode functions
310  */
311 int
312 nfs3svc_decode_fhandle(struct svc_rqst *rqstp, __be32 *p)
313 {
314         struct nfsd_fhandle *args = rqstp->rq_argp;
315
316         p = decode_fh(p, &args->fh);
317         if (!p)
318                 return 0;
319         return xdr_argsize_check(rqstp, p);
320 }
321
322 int
323 nfs3svc_decode_sattrargs(struct svc_rqst *rqstp, __be32 *p)
324 {
325         struct nfsd3_sattrargs *args = rqstp->rq_argp;
326
327         p = decode_fh(p, &args->fh);
328         if (!p)
329                 return 0;
330         p = decode_sattr3(p, &args->attrs, nfsd_user_namespace(rqstp));
331
332         if ((args->check_guard = ntohl(*p++)) != 0) { 
333                 struct timespec time; 
334                 p = decode_time3(p, &time);
335                 args->guardtime = time.tv_sec;
336         }
337
338         return xdr_argsize_check(rqstp, p);
339 }
340
341 int
342 nfs3svc_decode_diropargs(struct svc_rqst *rqstp, __be32 *p)
343 {
344         struct nfsd3_diropargs *args = rqstp->rq_argp;
345
346         if (!(p = decode_fh(p, &args->fh))
347          || !(p = decode_filename(p, &args->name, &args->len)))
348                 return 0;
349
350         return xdr_argsize_check(rqstp, p);
351 }
352
353 int
354 nfs3svc_decode_accessargs(struct svc_rqst *rqstp, __be32 *p)
355 {
356         struct nfsd3_accessargs *args = rqstp->rq_argp;
357
358         p = decode_fh(p, &args->fh);
359         if (!p)
360                 return 0;
361         args->access = ntohl(*p++);
362
363         return xdr_argsize_check(rqstp, p);
364 }
365
366 int
367 nfs3svc_decode_readargs(struct svc_rqst *rqstp, __be32 *p)
368 {
369         struct nfsd3_readargs *args = rqstp->rq_argp;
370         unsigned int len;
371         int v;
372         u32 max_blocksize = svc_max_payload(rqstp);
373
374         p = decode_fh(p, &args->fh);
375         if (!p)
376                 return 0;
377         p = xdr_decode_hyper(p, &args->offset);
378
379         args->count = ntohl(*p++);
380         len = min(args->count, max_blocksize);
381
382         /* set up the kvec */
383         v=0;
384         while (len > 0) {
385                 struct page *p = *(rqstp->rq_next_page++);
386
387                 rqstp->rq_vec[v].iov_base = page_address(p);
388                 rqstp->rq_vec[v].iov_len = min_t(unsigned int, len, PAGE_SIZE);
389                 len -= rqstp->rq_vec[v].iov_len;
390                 v++;
391         }
392         args->vlen = v;
393         return xdr_argsize_check(rqstp, p);
394 }
395
396 int
397 nfs3svc_decode_writeargs(struct svc_rqst *rqstp, __be32 *p)
398 {
399         struct nfsd3_writeargs *args = rqstp->rq_argp;
400         unsigned int len, hdr, dlen;
401         u32 max_blocksize = svc_max_payload(rqstp);
402         struct kvec *head = rqstp->rq_arg.head;
403         struct kvec *tail = rqstp->rq_arg.tail;
404
405         p = decode_fh(p, &args->fh);
406         if (!p)
407                 return 0;
408         p = xdr_decode_hyper(p, &args->offset);
409
410         args->count = ntohl(*p++);
411         args->stable = ntohl(*p++);
412         len = args->len = ntohl(*p++);
413         if ((void *)p > head->iov_base + head->iov_len)
414                 return 0;
415         /*
416          * The count must equal the amount of data passed.
417          */
418         if (args->count != args->len)
419                 return 0;
420
421         /*
422          * Check to make sure that we got the right number of
423          * bytes.
424          */
425         hdr = (void*)p - head->iov_base;
426         dlen = head->iov_len + rqstp->rq_arg.page_len + tail->iov_len - hdr;
427         /*
428          * Round the length of the data which was specified up to
429          * the next multiple of XDR units and then compare that
430          * against the length which was actually received.
431          * Note that when RPCSEC/GSS (for example) is used, the
432          * data buffer can be padded so dlen might be larger
433          * than required.  It must never be smaller.
434          */
435         if (dlen < XDR_QUADLEN(len)*4)
436                 return 0;
437
438         if (args->count > max_blocksize) {
439                 args->count = max_blocksize;
440                 len = args->len = max_blocksize;
441         }
442
443         args->first.iov_base = (void *)p;
444         args->first.iov_len = head->iov_len - hdr;
445         return 1;
446 }
447
448 int
449 nfs3svc_decode_createargs(struct svc_rqst *rqstp, __be32 *p)
450 {
451         struct nfsd3_createargs *args = rqstp->rq_argp;
452
453         if (!(p = decode_fh(p, &args->fh))
454          || !(p = decode_filename(p, &args->name, &args->len)))
455                 return 0;
456
457         switch (args->createmode = ntohl(*p++)) {
458         case NFS3_CREATE_UNCHECKED:
459         case NFS3_CREATE_GUARDED:
460                 p = decode_sattr3(p, &args->attrs, nfsd_user_namespace(rqstp));
461                 break;
462         case NFS3_CREATE_EXCLUSIVE:
463                 args->verf = p;
464                 p += 2;
465                 break;
466         default:
467                 return 0;
468         }
469
470         return xdr_argsize_check(rqstp, p);
471 }
472
473 int
474 nfs3svc_decode_mkdirargs(struct svc_rqst *rqstp, __be32 *p)
475 {
476         struct nfsd3_createargs *args = rqstp->rq_argp;
477
478         if (!(p = decode_fh(p, &args->fh)) ||
479             !(p = decode_filename(p, &args->name, &args->len)))
480                 return 0;
481         p = decode_sattr3(p, &args->attrs, nfsd_user_namespace(rqstp));
482
483         return xdr_argsize_check(rqstp, p);
484 }
485
486 int
487 nfs3svc_decode_symlinkargs(struct svc_rqst *rqstp, __be32 *p)
488 {
489         struct nfsd3_symlinkargs *args = rqstp->rq_argp;
490         char *base = (char *)p;
491         size_t dlen;
492
493         if (!(p = decode_fh(p, &args->ffh)) ||
494             !(p = decode_filename(p, &args->fname, &args->flen)))
495                 return 0;
496         p = decode_sattr3(p, &args->attrs, nfsd_user_namespace(rqstp));
497
498         args->tlen = ntohl(*p++);
499
500         args->first.iov_base = p;
501         args->first.iov_len = rqstp->rq_arg.head[0].iov_len;
502         args->first.iov_len -= (char *)p - base;
503
504         dlen = args->first.iov_len + rqstp->rq_arg.page_len +
505                rqstp->rq_arg.tail[0].iov_len;
506         if (dlen < XDR_QUADLEN(args->tlen) << 2)
507                 return 0;
508         return 1;
509 }
510
511 int
512 nfs3svc_decode_mknodargs(struct svc_rqst *rqstp, __be32 *p)
513 {
514         struct nfsd3_mknodargs *args = rqstp->rq_argp;
515
516         if (!(p = decode_fh(p, &args->fh))
517          || !(p = decode_filename(p, &args->name, &args->len)))
518                 return 0;
519
520         args->ftype = ntohl(*p++);
521
522         if (args->ftype == NF3BLK  || args->ftype == NF3CHR
523          || args->ftype == NF3SOCK || args->ftype == NF3FIFO)
524                 p = decode_sattr3(p, &args->attrs, nfsd_user_namespace(rqstp));
525
526         if (args->ftype == NF3BLK || args->ftype == NF3CHR) {
527                 args->major = ntohl(*p++);
528                 args->minor = ntohl(*p++);
529         }
530
531         return xdr_argsize_check(rqstp, p);
532 }
533
534 int
535 nfs3svc_decode_renameargs(struct svc_rqst *rqstp, __be32 *p)
536 {
537         struct nfsd3_renameargs *args = rqstp->rq_argp;
538
539         if (!(p = decode_fh(p, &args->ffh))
540          || !(p = decode_filename(p, &args->fname, &args->flen))
541          || !(p = decode_fh(p, &args->tfh))
542          || !(p = decode_filename(p, &args->tname, &args->tlen)))
543                 return 0;
544
545         return xdr_argsize_check(rqstp, p);
546 }
547
548 int
549 nfs3svc_decode_readlinkargs(struct svc_rqst *rqstp, __be32 *p)
550 {
551         struct nfsd3_readlinkargs *args = rqstp->rq_argp;
552
553         p = decode_fh(p, &args->fh);
554         if (!p)
555                 return 0;
556         args->buffer = page_address(*(rqstp->rq_next_page++));
557
558         return xdr_argsize_check(rqstp, p);
559 }
560
561 int
562 nfs3svc_decode_linkargs(struct svc_rqst *rqstp, __be32 *p)
563 {
564         struct nfsd3_linkargs *args = rqstp->rq_argp;
565
566         if (!(p = decode_fh(p, &args->ffh))
567          || !(p = decode_fh(p, &args->tfh))
568          || !(p = decode_filename(p, &args->tname, &args->tlen)))
569                 return 0;
570
571         return xdr_argsize_check(rqstp, p);
572 }
573
574 int
575 nfs3svc_decode_readdirargs(struct svc_rqst *rqstp, __be32 *p)
576 {
577         struct nfsd3_readdirargs *args = rqstp->rq_argp;
578         int len;
579         u32 max_blocksize = svc_max_payload(rqstp);
580
581         p = decode_fh(p, &args->fh);
582         if (!p)
583                 return 0;
584         p = xdr_decode_hyper(p, &args->cookie);
585         args->verf   = p; p += 2;
586         args->dircount = ~0;
587         args->count  = ntohl(*p++);
588         len = args->count  = min_t(u32, args->count, max_blocksize);
589
590         while (len > 0) {
591                 struct page *p = *(rqstp->rq_next_page++);
592                 if (!args->buffer)
593                         args->buffer = page_address(p);
594                 len -= PAGE_SIZE;
595         }
596
597         return xdr_argsize_check(rqstp, p);
598 }
599
600 int
601 nfs3svc_decode_readdirplusargs(struct svc_rqst *rqstp, __be32 *p)
602 {
603         struct nfsd3_readdirargs *args = rqstp->rq_argp;
604         int len;
605         u32 max_blocksize = svc_max_payload(rqstp);
606
607         p = decode_fh(p, &args->fh);
608         if (!p)
609                 return 0;
610         p = xdr_decode_hyper(p, &args->cookie);
611         args->verf     = p; p += 2;
612         args->dircount = ntohl(*p++);
613         args->count    = ntohl(*p++);
614
615         len = args->count = min(args->count, max_blocksize);
616         while (len > 0) {
617                 struct page *p = *(rqstp->rq_next_page++);
618                 if (!args->buffer)
619                         args->buffer = page_address(p);
620                 len -= PAGE_SIZE;
621         }
622
623         return xdr_argsize_check(rqstp, p);
624 }
625
626 int
627 nfs3svc_decode_commitargs(struct svc_rqst *rqstp, __be32 *p)
628 {
629         struct nfsd3_commitargs *args = rqstp->rq_argp;
630         p = decode_fh(p, &args->fh);
631         if (!p)
632                 return 0;
633         p = xdr_decode_hyper(p, &args->offset);
634         args->count = ntohl(*p++);
635
636         return xdr_argsize_check(rqstp, p);
637 }
638
639 /*
640  * XDR encode functions
641  */
642 /*
643  * There must be an encoding function for void results so svc_process
644  * will work properly.
645  */
646 int
647 nfs3svc_encode_voidres(struct svc_rqst *rqstp, __be32 *p)
648 {
649         return xdr_ressize_check(rqstp, p);
650 }
651
652 /* GETATTR */
653 int
654 nfs3svc_encode_attrstat(struct svc_rqst *rqstp, __be32 *p)
655 {
656         struct nfsd3_attrstat *resp = rqstp->rq_resp;
657
658         if (resp->status == 0) {
659                 lease_get_mtime(d_inode(resp->fh.fh_dentry),
660                                 &resp->stat.mtime);
661                 p = encode_fattr3(rqstp, p, &resp->fh, &resp->stat);
662         }
663         return xdr_ressize_check(rqstp, p);
664 }
665
666 /* SETATTR, REMOVE, RMDIR */
667 int
668 nfs3svc_encode_wccstat(struct svc_rqst *rqstp, __be32 *p)
669 {
670         struct nfsd3_attrstat *resp = rqstp->rq_resp;
671
672         p = encode_wcc_data(rqstp, p, &resp->fh);
673         return xdr_ressize_check(rqstp, p);
674 }
675
676 /* LOOKUP */
677 int
678 nfs3svc_encode_diropres(struct svc_rqst *rqstp, __be32 *p)
679 {
680         struct nfsd3_diropres *resp = rqstp->rq_resp;
681
682         if (resp->status == 0) {
683                 p = encode_fh(p, &resp->fh);
684                 p = encode_post_op_attr(rqstp, p, &resp->fh);
685         }
686         p = encode_post_op_attr(rqstp, p, &resp->dirfh);
687         return xdr_ressize_check(rqstp, p);
688 }
689
690 /* ACCESS */
691 int
692 nfs3svc_encode_accessres(struct svc_rqst *rqstp, __be32 *p)
693 {
694         struct nfsd3_accessres *resp = rqstp->rq_resp;
695
696         p = encode_post_op_attr(rqstp, p, &resp->fh);
697         if (resp->status == 0)
698                 *p++ = htonl(resp->access);
699         return xdr_ressize_check(rqstp, p);
700 }
701
702 /* READLINK */
703 int
704 nfs3svc_encode_readlinkres(struct svc_rqst *rqstp, __be32 *p)
705 {
706         struct nfsd3_readlinkres *resp = rqstp->rq_resp;
707
708         p = encode_post_op_attr(rqstp, p, &resp->fh);
709         if (resp->status == 0) {
710                 *p++ = htonl(resp->len);
711                 xdr_ressize_check(rqstp, p);
712                 rqstp->rq_res.page_len = resp->len;
713                 if (resp->len & 3) {
714                         /* need to pad the tail */
715                         rqstp->rq_res.tail[0].iov_base = p;
716                         *p = 0;
717                         rqstp->rq_res.tail[0].iov_len = 4 - (resp->len&3);
718                 }
719                 return 1;
720         } else
721                 return xdr_ressize_check(rqstp, p);
722 }
723
724 /* READ */
725 int
726 nfs3svc_encode_readres(struct svc_rqst *rqstp, __be32 *p)
727 {
728         struct nfsd3_readres *resp = rqstp->rq_resp;
729
730         p = encode_post_op_attr(rqstp, p, &resp->fh);
731         if (resp->status == 0) {
732                 *p++ = htonl(resp->count);
733                 *p++ = htonl(resp->eof);
734                 *p++ = htonl(resp->count);      /* xdr opaque count */
735                 xdr_ressize_check(rqstp, p);
736                 /* now update rqstp->rq_res to reflect data as well */
737                 rqstp->rq_res.page_len = resp->count;
738                 if (resp->count & 3) {
739                         /* need to pad the tail */
740                         rqstp->rq_res.tail[0].iov_base = p;
741                         *p = 0;
742                         rqstp->rq_res.tail[0].iov_len = 4 - (resp->count & 3);
743                 }
744                 return 1;
745         } else
746                 return xdr_ressize_check(rqstp, p);
747 }
748
749 /* WRITE */
750 int
751 nfs3svc_encode_writeres(struct svc_rqst *rqstp, __be32 *p)
752 {
753         struct nfsd3_writeres *resp = rqstp->rq_resp;
754         struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id);
755         __be32 verf[2];
756
757         p = encode_wcc_data(rqstp, p, &resp->fh);
758         if (resp->status == 0) {
759                 *p++ = htonl(resp->count);
760                 *p++ = htonl(resp->committed);
761                 /* unique identifier, y2038 overflow can be ignored */
762                 nfsd_copy_boot_verifier(verf, nn);
763                 *p++ = verf[0];
764                 *p++ = verf[1];
765         }
766         return xdr_ressize_check(rqstp, p);
767 }
768
769 /* CREATE, MKDIR, SYMLINK, MKNOD */
770 int
771 nfs3svc_encode_createres(struct svc_rqst *rqstp, __be32 *p)
772 {
773         struct nfsd3_diropres *resp = rqstp->rq_resp;
774
775         if (resp->status == 0) {
776                 *p++ = xdr_one;
777                 p = encode_fh(p, &resp->fh);
778                 p = encode_post_op_attr(rqstp, p, &resp->fh);
779         }
780         p = encode_wcc_data(rqstp, p, &resp->dirfh);
781         return xdr_ressize_check(rqstp, p);
782 }
783
784 /* RENAME */
785 int
786 nfs3svc_encode_renameres(struct svc_rqst *rqstp, __be32 *p)
787 {
788         struct nfsd3_renameres *resp = rqstp->rq_resp;
789
790         p = encode_wcc_data(rqstp, p, &resp->ffh);
791         p = encode_wcc_data(rqstp, p, &resp->tfh);
792         return xdr_ressize_check(rqstp, p);
793 }
794
795 /* LINK */
796 int
797 nfs3svc_encode_linkres(struct svc_rqst *rqstp, __be32 *p)
798 {
799         struct nfsd3_linkres *resp = rqstp->rq_resp;
800
801         p = encode_post_op_attr(rqstp, p, &resp->fh);
802         p = encode_wcc_data(rqstp, p, &resp->tfh);
803         return xdr_ressize_check(rqstp, p);
804 }
805
806 /* READDIR */
807 int
808 nfs3svc_encode_readdirres(struct svc_rqst *rqstp, __be32 *p)
809 {
810         struct nfsd3_readdirres *resp = rqstp->rq_resp;
811
812         p = encode_post_op_attr(rqstp, p, &resp->fh);
813
814         if (resp->status == 0) {
815                 /* stupid readdir cookie */
816                 memcpy(p, resp->verf, 8); p += 2;
817                 xdr_ressize_check(rqstp, p);
818                 if (rqstp->rq_res.head[0].iov_len + (2<<2) > PAGE_SIZE)
819                         return 1; /*No room for trailer */
820                 rqstp->rq_res.page_len = (resp->count) << 2;
821
822                 /* add the 'tail' to the end of the 'head' page - page 0. */
823                 rqstp->rq_res.tail[0].iov_base = p;
824                 *p++ = 0;               /* no more entries */
825                 *p++ = htonl(resp->common.err == nfserr_eof);
826                 rqstp->rq_res.tail[0].iov_len = 2<<2;
827                 return 1;
828         } else
829                 return xdr_ressize_check(rqstp, p);
830 }
831
832 static __be32 *
833 encode_entry_baggage(struct nfsd3_readdirres *cd, __be32 *p, const char *name,
834              int namlen, u64 ino)
835 {
836         *p++ = xdr_one;                          /* mark entry present */
837         p    = xdr_encode_hyper(p, ino);         /* file id */
838         p    = xdr_encode_array(p, name, namlen);/* name length & name */
839
840         cd->offset = p;                         /* remember pointer */
841         p = xdr_encode_hyper(p, NFS_OFFSET_MAX);/* offset of next entry */
842
843         return p;
844 }
845
846 static __be32
847 compose_entry_fh(struct nfsd3_readdirres *cd, struct svc_fh *fhp,
848                  const char *name, int namlen, u64 ino)
849 {
850         struct svc_export       *exp;
851         struct dentry           *dparent, *dchild;
852         __be32 rv = nfserr_noent;
853
854         dparent = cd->fh.fh_dentry;
855         exp  = cd->fh.fh_export;
856
857         if (isdotent(name, namlen)) {
858                 if (namlen == 2) {
859                         dchild = dget_parent(dparent);
860                         /*
861                          * Don't return filehandle for ".." if we're at
862                          * the filesystem or export root:
863                          */
864                         if (dchild == dparent)
865                                 goto out;
866                         if (dparent == exp->ex_path.dentry)
867                                 goto out;
868                 } else
869                         dchild = dget(dparent);
870         } else
871                 dchild = lookup_positive_unlocked(name, dparent, namlen);
872         if (IS_ERR(dchild))
873                 return rv;
874         if (d_mountpoint(dchild))
875                 goto out;
876         if (dchild->d_inode->i_ino != ino)
877                 goto out;
878         rv = fh_compose(fhp, exp, dchild, &cd->fh);
879 out:
880         dput(dchild);
881         return rv;
882 }
883
884 static __be32 *encode_entryplus_baggage(struct nfsd3_readdirres *cd, __be32 *p, const char *name, int namlen, u64 ino)
885 {
886         struct svc_fh   *fh = &cd->scratch;
887         __be32 err;
888
889         fh_init(fh, NFS3_FHSIZE);
890         err = compose_entry_fh(cd, fh, name, namlen, ino);
891         if (err) {
892                 *p++ = 0;
893                 *p++ = 0;
894                 goto out;
895         }
896         p = encode_post_op_attr(cd->rqstp, p, fh);
897         *p++ = xdr_one;                 /* yes, a file handle follows */
898         p = encode_fh(p, fh);
899 out:
900         fh_put(fh);
901         return p;
902 }
903
904 /*
905  * Encode a directory entry. This one works for both normal readdir
906  * and readdirplus.
907  * The normal readdir reply requires 2 (fileid) + 1 (stringlen)
908  * + string + 2 (cookie) + 1 (next) words, i.e. 6 + strlen.
909  * 
910  * The readdirplus baggage is 1+21 words for post_op_attr, plus the
911  * file handle.
912  */
913
914 #define NFS3_ENTRY_BAGGAGE      (2 + 1 + 2 + 1)
915 #define NFS3_ENTRYPLUS_BAGGAGE  (1 + 21 + 1 + (NFS3_FHSIZE >> 2))
916 static int
917 encode_entry(struct readdir_cd *ccd, const char *name, int namlen,
918              loff_t offset, u64 ino, unsigned int d_type, int plus)
919 {
920         struct nfsd3_readdirres *cd = container_of(ccd, struct nfsd3_readdirres,
921                                                         common);
922         __be32          *p = cd->buffer;
923         caddr_t         curr_page_addr = NULL;
924         struct page **  page;
925         int             slen;           /* string (name) length */
926         int             elen;           /* estimated entry length in words */
927         int             num_entry_words = 0;    /* actual number of words */
928
929         if (cd->offset) {
930                 u64 offset64 = offset;
931
932                 if (unlikely(cd->offset1)) {
933                         /* we ended up with offset on a page boundary */
934                         *cd->offset = htonl(offset64 >> 32);
935                         *cd->offset1 = htonl(offset64 & 0xffffffff);
936                         cd->offset1 = NULL;
937                 } else {
938                         xdr_encode_hyper(cd->offset, offset64);
939                 }
940                 cd->offset = NULL;
941         }
942
943         /*
944         dprintk("encode_entry(%.*s @%ld%s)\n",
945                 namlen, name, (long) offset, plus? " plus" : "");
946          */
947
948         /* truncate filename if too long */
949         namlen = min(namlen, NFS3_MAXNAMLEN);
950
951         slen = XDR_QUADLEN(namlen);
952         elen = slen + NFS3_ENTRY_BAGGAGE
953                 + (plus? NFS3_ENTRYPLUS_BAGGAGE : 0);
954
955         if (cd->buflen < elen) {
956                 cd->common.err = nfserr_toosmall;
957                 return -EINVAL;
958         }
959
960         /* determine which page in rq_respages[] we are currently filling */
961         for (page = cd->rqstp->rq_respages + 1;
962                                 page < cd->rqstp->rq_next_page; page++) {
963                 curr_page_addr = page_address(*page);
964
965                 if (((caddr_t)cd->buffer >= curr_page_addr) &&
966                     ((caddr_t)cd->buffer <  curr_page_addr + PAGE_SIZE))
967                         break;
968         }
969
970         if ((caddr_t)(cd->buffer + elen) < (curr_page_addr + PAGE_SIZE)) {
971                 /* encode entry in current page */
972
973                 p = encode_entry_baggage(cd, p, name, namlen, ino);
974
975                 if (plus)
976                         p = encode_entryplus_baggage(cd, p, name, namlen, ino);
977                 num_entry_words = p - cd->buffer;
978         } else if (*(page+1) != NULL) {
979                 /* temporarily encode entry into next page, then move back to
980                  * current and next page in rq_respages[] */
981                 __be32 *p1, *tmp;
982                 int len1, len2;
983
984                 /* grab next page for temporary storage of entry */
985                 p1 = tmp = page_address(*(page+1));
986
987                 p1 = encode_entry_baggage(cd, p1, name, namlen, ino);
988
989                 if (plus)
990                         p1 = encode_entryplus_baggage(cd, p1, name, namlen, ino);
991
992                 /* determine entry word length and lengths to go in pages */
993                 num_entry_words = p1 - tmp;
994                 len1 = curr_page_addr + PAGE_SIZE - (caddr_t)cd->buffer;
995                 if ((num_entry_words << 2) < len1) {
996                         /* the actual number of words in the entry is less
997                          * than elen and can still fit in the current page
998                          */
999                         memmove(p, tmp, num_entry_words << 2);
1000                         p += num_entry_words;
1001
1002                         /* update offset */
1003                         cd->offset = cd->buffer + (cd->offset - tmp);
1004                 } else {
1005                         unsigned int offset_r = (cd->offset - tmp) << 2;
1006
1007                         /* update pointer to offset location.
1008                          * This is a 64bit quantity, so we need to
1009                          * deal with 3 cases:
1010                          *  -   entirely in first page
1011                          *  -   entirely in second page
1012                          *  -   4 bytes in each page
1013                          */
1014                         if (offset_r + 8 <= len1) {
1015                                 cd->offset = p + (cd->offset - tmp);
1016                         } else if (offset_r >= len1) {
1017                                 cd->offset -= len1 >> 2;
1018                         } else {
1019                                 /* sitting on the fence */
1020                                 BUG_ON(offset_r != len1 - 4);
1021                                 cd->offset = p + (cd->offset - tmp);
1022                                 cd->offset1 = tmp;
1023                         }
1024
1025                         len2 = (num_entry_words << 2) - len1;
1026
1027                         /* move from temp page to current and next pages */
1028                         memmove(p, tmp, len1);
1029                         memmove(tmp, (caddr_t)tmp+len1, len2);
1030
1031                         p = tmp + (len2 >> 2);
1032                 }
1033         }
1034         else {
1035                 cd->common.err = nfserr_toosmall;
1036                 return -EINVAL;
1037         }
1038
1039         cd->buflen -= num_entry_words;
1040         cd->buffer = p;
1041         cd->common.err = nfs_ok;
1042         return 0;
1043
1044 }
1045
1046 int
1047 nfs3svc_encode_entry(void *cd, const char *name,
1048                      int namlen, loff_t offset, u64 ino, unsigned int d_type)
1049 {
1050         return encode_entry(cd, name, namlen, offset, ino, d_type, 0);
1051 }
1052
1053 int
1054 nfs3svc_encode_entry_plus(void *cd, const char *name,
1055                           int namlen, loff_t offset, u64 ino,
1056                           unsigned int d_type)
1057 {
1058         return encode_entry(cd, name, namlen, offset, ino, d_type, 1);
1059 }
1060
1061 /* FSSTAT */
1062 int
1063 nfs3svc_encode_fsstatres(struct svc_rqst *rqstp, __be32 *p)
1064 {
1065         struct nfsd3_fsstatres *resp = rqstp->rq_resp;
1066         struct kstatfs  *s = &resp->stats;
1067         u64             bs = s->f_bsize;
1068
1069         *p++ = xdr_zero;        /* no post_op_attr */
1070
1071         if (resp->status == 0) {
1072                 p = xdr_encode_hyper(p, bs * s->f_blocks);      /* total bytes */
1073                 p = xdr_encode_hyper(p, bs * s->f_bfree);       /* free bytes */
1074                 p = xdr_encode_hyper(p, bs * s->f_bavail);      /* user available bytes */
1075                 p = xdr_encode_hyper(p, s->f_files);    /* total inodes */
1076                 p = xdr_encode_hyper(p, s->f_ffree);    /* free inodes */
1077                 p = xdr_encode_hyper(p, s->f_ffree);    /* user available inodes */
1078                 *p++ = htonl(resp->invarsec);   /* mean unchanged time */
1079         }
1080         return xdr_ressize_check(rqstp, p);
1081 }
1082
1083 /* FSINFO */
1084 int
1085 nfs3svc_encode_fsinfores(struct svc_rqst *rqstp, __be32 *p)
1086 {
1087         struct nfsd3_fsinfores *resp = rqstp->rq_resp;
1088
1089         *p++ = xdr_zero;        /* no post_op_attr */
1090
1091         if (resp->status == 0) {
1092                 *p++ = htonl(resp->f_rtmax);
1093                 *p++ = htonl(resp->f_rtpref);
1094                 *p++ = htonl(resp->f_rtmult);
1095                 *p++ = htonl(resp->f_wtmax);
1096                 *p++ = htonl(resp->f_wtpref);
1097                 *p++ = htonl(resp->f_wtmult);
1098                 *p++ = htonl(resp->f_dtpref);
1099                 p = xdr_encode_hyper(p, resp->f_maxfilesize);
1100                 *p++ = xdr_one;
1101                 *p++ = xdr_zero;
1102                 *p++ = htonl(resp->f_properties);
1103         }
1104
1105         return xdr_ressize_check(rqstp, p);
1106 }
1107
1108 /* PATHCONF */
1109 int
1110 nfs3svc_encode_pathconfres(struct svc_rqst *rqstp, __be32 *p)
1111 {
1112         struct nfsd3_pathconfres *resp = rqstp->rq_resp;
1113
1114         *p++ = xdr_zero;        /* no post_op_attr */
1115
1116         if (resp->status == 0) {
1117                 *p++ = htonl(resp->p_link_max);
1118                 *p++ = htonl(resp->p_name_max);
1119                 *p++ = htonl(resp->p_no_trunc);
1120                 *p++ = htonl(resp->p_chown_restricted);
1121                 *p++ = htonl(resp->p_case_insensitive);
1122                 *p++ = htonl(resp->p_case_preserving);
1123         }
1124
1125         return xdr_ressize_check(rqstp, p);
1126 }
1127
1128 /* COMMIT */
1129 int
1130 nfs3svc_encode_commitres(struct svc_rqst *rqstp, __be32 *p)
1131 {
1132         struct nfsd3_commitres *resp = rqstp->rq_resp;
1133         struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id);
1134         __be32 verf[2];
1135
1136         p = encode_wcc_data(rqstp, p, &resp->fh);
1137         /* Write verifier */
1138         if (resp->status == 0) {
1139                 /* unique identifier, y2038 overflow can be ignored */
1140                 nfsd_copy_boot_verifier(verf, nn);
1141                 *p++ = verf[0];
1142                 *p++ = verf[1];
1143         }
1144         return xdr_ressize_check(rqstp, p);
1145 }
1146
1147 /*
1148  * XDR release functions
1149  */
1150 void
1151 nfs3svc_release_fhandle(struct svc_rqst *rqstp)
1152 {
1153         struct nfsd3_attrstat *resp = rqstp->rq_resp;
1154
1155         fh_put(&resp->fh);
1156 }
1157
1158 void
1159 nfs3svc_release_fhandle2(struct svc_rqst *rqstp)
1160 {
1161         struct nfsd3_fhandle_pair *resp = rqstp->rq_resp;
1162
1163         fh_put(&resp->fh1);
1164         fh_put(&resp->fh2);
1165 }