xref: /linux/fs/nfs/nfs3xdr.c (revision ec63e2a4897075e427c121d863bd89c44578094f)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * linux/fs/nfs/nfs3xdr.c
4  *
5  * XDR functions to encode/decode NFSv3 RPC arguments and results.
6  *
7  * Copyright (C) 1996, 1997 Olaf Kirch
8  */
9 
10 #include <linux/param.h>
11 #include <linux/time.h>
12 #include <linux/mm.h>
13 #include <linux/errno.h>
14 #include <linux/string.h>
15 #include <linux/in.h>
16 #include <linux/pagemap.h>
17 #include <linux/proc_fs.h>
18 #include <linux/kdev_t.h>
19 #include <linux/sunrpc/clnt.h>
20 #include <linux/nfs.h>
21 #include <linux/nfs3.h>
22 #include <linux/nfs_fs.h>
23 #include <linux/nfsacl.h>
24 #include "nfstrace.h"
25 #include "internal.h"
26 
27 #define NFSDBG_FACILITY		NFSDBG_XDR
28 
29 /* Mapping from NFS error code to "errno" error code. */
30 #define errno_NFSERR_IO		EIO
31 
32 /*
33  * Declare the space requirements for NFS arguments and replies as
34  * number of 32bit-words
35  */
36 #define NFS3_fhandle_sz		(1+16)
37 #define NFS3_fh_sz		(NFS3_fhandle_sz)	/* shorthand */
38 #define NFS3_sattr_sz		(15)
39 #define NFS3_filename_sz	(1+(NFS3_MAXNAMLEN>>2))
40 #define NFS3_path_sz		(1+(NFS3_MAXPATHLEN>>2))
41 #define NFS3_fattr_sz		(21)
42 #define NFS3_cookieverf_sz	(NFS3_COOKIEVERFSIZE>>2)
43 #define NFS3_wcc_attr_sz	(6)
44 #define NFS3_pre_op_attr_sz	(1+NFS3_wcc_attr_sz)
45 #define NFS3_post_op_attr_sz	(1+NFS3_fattr_sz)
46 #define NFS3_wcc_data_sz	(NFS3_pre_op_attr_sz+NFS3_post_op_attr_sz)
47 #define NFS3_diropargs_sz	(NFS3_fh_sz+NFS3_filename_sz)
48 
49 #define NFS3_getattrargs_sz	(NFS3_fh_sz)
50 #define NFS3_setattrargs_sz	(NFS3_fh_sz+NFS3_sattr_sz+3)
51 #define NFS3_lookupargs_sz	(NFS3_fh_sz+NFS3_filename_sz)
52 #define NFS3_accessargs_sz	(NFS3_fh_sz+1)
53 #define NFS3_readlinkargs_sz	(NFS3_fh_sz)
54 #define NFS3_readargs_sz	(NFS3_fh_sz+3)
55 #define NFS3_writeargs_sz	(NFS3_fh_sz+5)
56 #define NFS3_createargs_sz	(NFS3_diropargs_sz+NFS3_sattr_sz)
57 #define NFS3_mkdirargs_sz	(NFS3_diropargs_sz+NFS3_sattr_sz)
58 #define NFS3_symlinkargs_sz	(NFS3_diropargs_sz+1+NFS3_sattr_sz)
59 #define NFS3_mknodargs_sz	(NFS3_diropargs_sz+2+NFS3_sattr_sz)
60 #define NFS3_removeargs_sz	(NFS3_fh_sz+NFS3_filename_sz)
61 #define NFS3_renameargs_sz	(NFS3_diropargs_sz+NFS3_diropargs_sz)
62 #define NFS3_linkargs_sz		(NFS3_fh_sz+NFS3_diropargs_sz)
63 #define NFS3_readdirargs_sz	(NFS3_fh_sz+NFS3_cookieverf_sz+3)
64 #define NFS3_readdirplusargs_sz	(NFS3_fh_sz+NFS3_cookieverf_sz+4)
65 #define NFS3_commitargs_sz	(NFS3_fh_sz+3)
66 
67 #define NFS3_getattrres_sz	(1+NFS3_fattr_sz)
68 #define NFS3_setattrres_sz	(1+NFS3_wcc_data_sz)
69 #define NFS3_removeres_sz	(NFS3_setattrres_sz)
70 #define NFS3_lookupres_sz	(1+NFS3_fh_sz+(2 * NFS3_post_op_attr_sz))
71 #define NFS3_accessres_sz	(1+NFS3_post_op_attr_sz+1)
72 #define NFS3_readlinkres_sz	(1+NFS3_post_op_attr_sz+1+1)
73 #define NFS3_readres_sz		(1+NFS3_post_op_attr_sz+3+1)
74 #define NFS3_writeres_sz	(1+NFS3_wcc_data_sz+4)
75 #define NFS3_createres_sz	(1+NFS3_fh_sz+NFS3_post_op_attr_sz+NFS3_wcc_data_sz)
76 #define NFS3_renameres_sz	(1+(2 * NFS3_wcc_data_sz))
77 #define NFS3_linkres_sz		(1+NFS3_post_op_attr_sz+NFS3_wcc_data_sz)
78 #define NFS3_readdirres_sz	(1+NFS3_post_op_attr_sz+2+1)
79 #define NFS3_fsstatres_sz	(1+NFS3_post_op_attr_sz+13)
80 #define NFS3_fsinfores_sz	(1+NFS3_post_op_attr_sz+12)
81 #define NFS3_pathconfres_sz	(1+NFS3_post_op_attr_sz+6)
82 #define NFS3_commitres_sz	(1+NFS3_wcc_data_sz+2)
83 
84 #define ACL3_getaclargs_sz	(NFS3_fh_sz+1)
85 #define ACL3_setaclargs_sz	(NFS3_fh_sz+1+ \
86 				XDR_QUADLEN(NFS_ACL_INLINE_BUFSIZE))
87 #define ACL3_getaclres_sz	(1+NFS3_post_op_attr_sz+1+ \
88 				XDR_QUADLEN(NFS_ACL_INLINE_BUFSIZE)+1)
89 #define ACL3_setaclres_sz	(1+NFS3_post_op_attr_sz)
90 
91 static int nfs3_stat_to_errno(enum nfs_stat);
92 
93 /*
94  * Map file type to S_IFMT bits
95  */
96 static const umode_t nfs_type2fmt[] = {
97 	[NF3BAD] = 0,
98 	[NF3REG] = S_IFREG,
99 	[NF3DIR] = S_IFDIR,
100 	[NF3BLK] = S_IFBLK,
101 	[NF3CHR] = S_IFCHR,
102 	[NF3LNK] = S_IFLNK,
103 	[NF3SOCK] = S_IFSOCK,
104 	[NF3FIFO] = S_IFIFO,
105 };
106 
107 /*
108  * Encode/decode NFSv3 basic data types
109  *
110  * Basic NFSv3 data types are defined in section 2.5 of RFC 1813:
111  * "NFS Version 3 Protocol Specification".
112  *
113  * Not all basic data types have their own encoding and decoding
114  * functions.  For run-time efficiency, some data types are encoded
115  * or decoded inline.
116  */
117 
118 static void encode_uint32(struct xdr_stream *xdr, u32 value)
119 {
120 	__be32 *p = xdr_reserve_space(xdr, 4);
121 	*p = cpu_to_be32(value);
122 }
123 
124 static int decode_uint32(struct xdr_stream *xdr, u32 *value)
125 {
126 	__be32 *p;
127 
128 	p = xdr_inline_decode(xdr, 4);
129 	if (unlikely(!p))
130 		return -EIO;
131 	*value = be32_to_cpup(p);
132 	return 0;
133 }
134 
135 static int decode_uint64(struct xdr_stream *xdr, u64 *value)
136 {
137 	__be32 *p;
138 
139 	p = xdr_inline_decode(xdr, 8);
140 	if (unlikely(!p))
141 		return -EIO;
142 	xdr_decode_hyper(p, value);
143 	return 0;
144 }
145 
146 /*
147  * fileid3
148  *
149  *	typedef uint64 fileid3;
150  */
151 static __be32 *xdr_decode_fileid3(__be32 *p, u64 *fileid)
152 {
153 	return xdr_decode_hyper(p, fileid);
154 }
155 
156 static int decode_fileid3(struct xdr_stream *xdr, u64 *fileid)
157 {
158 	return decode_uint64(xdr, fileid);
159 }
160 
161 /*
162  * filename3
163  *
164  *	typedef string filename3<>;
165  */
166 static void encode_filename3(struct xdr_stream *xdr,
167 			     const char *name, u32 length)
168 {
169 	__be32 *p;
170 
171 	WARN_ON_ONCE(length > NFS3_MAXNAMLEN);
172 	p = xdr_reserve_space(xdr, 4 + length);
173 	xdr_encode_opaque(p, name, length);
174 }
175 
176 static int decode_inline_filename3(struct xdr_stream *xdr,
177 				   const char **name, u32 *length)
178 {
179 	__be32 *p;
180 	u32 count;
181 
182 	p = xdr_inline_decode(xdr, 4);
183 	if (unlikely(!p))
184 		return -EIO;
185 	count = be32_to_cpup(p);
186 	if (count > NFS3_MAXNAMLEN)
187 		goto out_nametoolong;
188 	p = xdr_inline_decode(xdr, count);
189 	if (unlikely(!p))
190 		return -EIO;
191 	*name = (const char *)p;
192 	*length = count;
193 	return 0;
194 
195 out_nametoolong:
196 	dprintk("NFS: returned filename too long: %u\n", count);
197 	return -ENAMETOOLONG;
198 }
199 
200 /*
201  * nfspath3
202  *
203  *	typedef string nfspath3<>;
204  */
205 static void encode_nfspath3(struct xdr_stream *xdr, struct page **pages,
206 			    const u32 length)
207 {
208 	encode_uint32(xdr, length);
209 	xdr_write_pages(xdr, pages, 0, length);
210 }
211 
212 static int decode_nfspath3(struct xdr_stream *xdr)
213 {
214 	u32 recvd, count;
215 	__be32 *p;
216 
217 	p = xdr_inline_decode(xdr, 4);
218 	if (unlikely(!p))
219 		return -EIO;
220 	count = be32_to_cpup(p);
221 	if (unlikely(count >= xdr->buf->page_len || count > NFS3_MAXPATHLEN))
222 		goto out_nametoolong;
223 	recvd = xdr_read_pages(xdr, count);
224 	if (unlikely(count > recvd))
225 		goto out_cheating;
226 	xdr_terminate_string(xdr->buf, count);
227 	return 0;
228 
229 out_nametoolong:
230 	dprintk("NFS: returned pathname too long: %u\n", count);
231 	return -ENAMETOOLONG;
232 out_cheating:
233 	dprintk("NFS: server cheating in pathname result: "
234 		"count %u > recvd %u\n", count, recvd);
235 	return -EIO;
236 }
237 
238 /*
239  * cookie3
240  *
241  *	typedef uint64 cookie3
242  */
243 static __be32 *xdr_encode_cookie3(__be32 *p, u64 cookie)
244 {
245 	return xdr_encode_hyper(p, cookie);
246 }
247 
248 static int decode_cookie3(struct xdr_stream *xdr, u64 *cookie)
249 {
250 	return decode_uint64(xdr, cookie);
251 }
252 
253 /*
254  * cookieverf3
255  *
256  *	typedef opaque cookieverf3[NFS3_COOKIEVERFSIZE];
257  */
258 static __be32 *xdr_encode_cookieverf3(__be32 *p, const __be32 *verifier)
259 {
260 	memcpy(p, verifier, NFS3_COOKIEVERFSIZE);
261 	return p + XDR_QUADLEN(NFS3_COOKIEVERFSIZE);
262 }
263 
264 static int decode_cookieverf3(struct xdr_stream *xdr, __be32 *verifier)
265 {
266 	__be32 *p;
267 
268 	p = xdr_inline_decode(xdr, NFS3_COOKIEVERFSIZE);
269 	if (unlikely(!p))
270 		return -EIO;
271 	memcpy(verifier, p, NFS3_COOKIEVERFSIZE);
272 	return 0;
273 }
274 
275 /*
276  * createverf3
277  *
278  *	typedef opaque createverf3[NFS3_CREATEVERFSIZE];
279  */
280 static void encode_createverf3(struct xdr_stream *xdr, const __be32 *verifier)
281 {
282 	__be32 *p;
283 
284 	p = xdr_reserve_space(xdr, NFS3_CREATEVERFSIZE);
285 	memcpy(p, verifier, NFS3_CREATEVERFSIZE);
286 }
287 
288 static int decode_writeverf3(struct xdr_stream *xdr, struct nfs_write_verifier *verifier)
289 {
290 	__be32 *p;
291 
292 	p = xdr_inline_decode(xdr, NFS3_WRITEVERFSIZE);
293 	if (unlikely(!p))
294 		return -EIO;
295 	memcpy(verifier->data, p, NFS3_WRITEVERFSIZE);
296 	return 0;
297 }
298 
299 /*
300  * size3
301  *
302  *	typedef uint64 size3;
303  */
304 static __be32 *xdr_decode_size3(__be32 *p, u64 *size)
305 {
306 	return xdr_decode_hyper(p, size);
307 }
308 
309 /*
310  * nfsstat3
311  *
312  *	enum nfsstat3 {
313  *		NFS3_OK = 0,
314  *		...
315  *	}
316  */
317 #define NFS3_OK		NFS_OK
318 
319 static int decode_nfsstat3(struct xdr_stream *xdr, enum nfs_stat *status)
320 {
321 	__be32 *p;
322 
323 	p = xdr_inline_decode(xdr, 4);
324 	if (unlikely(!p))
325 		return -EIO;
326 	if (unlikely(*p != cpu_to_be32(NFS3_OK)))
327 		goto out_status;
328 	*status = 0;
329 	return 0;
330 out_status:
331 	*status = be32_to_cpup(p);
332 	trace_nfs_xdr_status((int)*status);
333 	return 0;
334 }
335 
336 /*
337  * ftype3
338  *
339  *	enum ftype3 {
340  *		NF3REG	= 1,
341  *		NF3DIR	= 2,
342  *		NF3BLK	= 3,
343  *		NF3CHR	= 4,
344  *		NF3LNK	= 5,
345  *		NF3SOCK	= 6,
346  *		NF3FIFO	= 7
347  *	};
348  */
349 static void encode_ftype3(struct xdr_stream *xdr, const u32 type)
350 {
351 	encode_uint32(xdr, type);
352 }
353 
354 static __be32 *xdr_decode_ftype3(__be32 *p, umode_t *mode)
355 {
356 	u32 type;
357 
358 	type = be32_to_cpup(p++);
359 	if (type > NF3FIFO)
360 		type = NF3NON;
361 	*mode = nfs_type2fmt[type];
362 	return p;
363 }
364 
365 /*
366  * specdata3
367  *
368  *     struct specdata3 {
369  *             uint32  specdata1;
370  *             uint32  specdata2;
371  *     };
372  */
373 static void encode_specdata3(struct xdr_stream *xdr, const dev_t rdev)
374 {
375 	__be32 *p;
376 
377 	p = xdr_reserve_space(xdr, 8);
378 	*p++ = cpu_to_be32(MAJOR(rdev));
379 	*p = cpu_to_be32(MINOR(rdev));
380 }
381 
382 static __be32 *xdr_decode_specdata3(__be32 *p, dev_t *rdev)
383 {
384 	unsigned int major, minor;
385 
386 	major = be32_to_cpup(p++);
387 	minor = be32_to_cpup(p++);
388 	*rdev = MKDEV(major, minor);
389 	if (MAJOR(*rdev) != major || MINOR(*rdev) != minor)
390 		*rdev = 0;
391 	return p;
392 }
393 
394 /*
395  * nfs_fh3
396  *
397  *	struct nfs_fh3 {
398  *		opaque       data<NFS3_FHSIZE>;
399  *	};
400  */
401 static void encode_nfs_fh3(struct xdr_stream *xdr, const struct nfs_fh *fh)
402 {
403 	__be32 *p;
404 
405 	WARN_ON_ONCE(fh->size > NFS3_FHSIZE);
406 	p = xdr_reserve_space(xdr, 4 + fh->size);
407 	xdr_encode_opaque(p, fh->data, fh->size);
408 }
409 
410 static int decode_nfs_fh3(struct xdr_stream *xdr, struct nfs_fh *fh)
411 {
412 	u32 length;
413 	__be32 *p;
414 
415 	p = xdr_inline_decode(xdr, 4);
416 	if (unlikely(!p))
417 		return -EIO;
418 	length = be32_to_cpup(p++);
419 	if (unlikely(length > NFS3_FHSIZE))
420 		goto out_toobig;
421 	p = xdr_inline_decode(xdr, length);
422 	if (unlikely(!p))
423 		return -EIO;
424 	fh->size = length;
425 	memcpy(fh->data, p, length);
426 	return 0;
427 out_toobig:
428 	dprintk("NFS: file handle size (%u) too big\n", length);
429 	return -E2BIG;
430 }
431 
432 static void zero_nfs_fh3(struct nfs_fh *fh)
433 {
434 	memset(fh, 0, sizeof(*fh));
435 }
436 
437 /*
438  * nfstime3
439  *
440  *	struct nfstime3 {
441  *		uint32	seconds;
442  *		uint32	nseconds;
443  *	};
444  */
445 static __be32 *xdr_encode_nfstime3(__be32 *p, const struct timespec *timep)
446 {
447 	*p++ = cpu_to_be32(timep->tv_sec);
448 	*p++ = cpu_to_be32(timep->tv_nsec);
449 	return p;
450 }
451 
452 static __be32 *xdr_decode_nfstime3(__be32 *p, struct timespec *timep)
453 {
454 	timep->tv_sec = be32_to_cpup(p++);
455 	timep->tv_nsec = be32_to_cpup(p++);
456 	return p;
457 }
458 
459 /*
460  * sattr3
461  *
462  *	enum time_how {
463  *		DONT_CHANGE		= 0,
464  *		SET_TO_SERVER_TIME	= 1,
465  *		SET_TO_CLIENT_TIME	= 2
466  *	};
467  *
468  *	union set_mode3 switch (bool set_it) {
469  *	case TRUE:
470  *		mode3	mode;
471  *	default:
472  *		void;
473  *	};
474  *
475  *	union set_uid3 switch (bool set_it) {
476  *	case TRUE:
477  *		uid3	uid;
478  *	default:
479  *		void;
480  *	};
481  *
482  *	union set_gid3 switch (bool set_it) {
483  *	case TRUE:
484  *		gid3	gid;
485  *	default:
486  *		void;
487  *	};
488  *
489  *	union set_size3 switch (bool set_it) {
490  *	case TRUE:
491  *		size3	size;
492  *	default:
493  *		void;
494  *	};
495  *
496  *	union set_atime switch (time_how set_it) {
497  *	case SET_TO_CLIENT_TIME:
498  *		nfstime3	atime;
499  *	default:
500  *		void;
501  *	};
502  *
503  *	union set_mtime switch (time_how set_it) {
504  *	case SET_TO_CLIENT_TIME:
505  *		nfstime3  mtime;
506  *	default:
507  *		void;
508  *	};
509  *
510  *	struct sattr3 {
511  *		set_mode3	mode;
512  *		set_uid3	uid;
513  *		set_gid3	gid;
514  *		set_size3	size;
515  *		set_atime	atime;
516  *		set_mtime	mtime;
517  *	};
518  */
519 static void encode_sattr3(struct xdr_stream *xdr, const struct iattr *attr)
520 {
521 	struct timespec ts;
522 	u32 nbytes;
523 	__be32 *p;
524 
525 	/*
526 	 * In order to make only a single xdr_reserve_space() call,
527 	 * pre-compute the total number of bytes to be reserved.
528 	 * Six boolean values, one for each set_foo field, are always
529 	 * present in the encoded result, so start there.
530 	 */
531 	nbytes = 6 * 4;
532 	if (attr->ia_valid & ATTR_MODE)
533 		nbytes += 4;
534 	if (attr->ia_valid & ATTR_UID)
535 		nbytes += 4;
536 	if (attr->ia_valid & ATTR_GID)
537 		nbytes += 4;
538 	if (attr->ia_valid & ATTR_SIZE)
539 		nbytes += 8;
540 	if (attr->ia_valid & ATTR_ATIME_SET)
541 		nbytes += 8;
542 	if (attr->ia_valid & ATTR_MTIME_SET)
543 		nbytes += 8;
544 	p = xdr_reserve_space(xdr, nbytes);
545 
546 	if (attr->ia_valid & ATTR_MODE) {
547 		*p++ = xdr_one;
548 		*p++ = cpu_to_be32(attr->ia_mode & S_IALLUGO);
549 	} else
550 		*p++ = xdr_zero;
551 
552 	if (attr->ia_valid & ATTR_UID) {
553 		*p++ = xdr_one;
554 		*p++ = cpu_to_be32(from_kuid(&init_user_ns, attr->ia_uid));
555 	} else
556 		*p++ = xdr_zero;
557 
558 	if (attr->ia_valid & ATTR_GID) {
559 		*p++ = xdr_one;
560 		*p++ = cpu_to_be32(from_kgid(&init_user_ns, attr->ia_gid));
561 	} else
562 		*p++ = xdr_zero;
563 
564 	if (attr->ia_valid & ATTR_SIZE) {
565 		*p++ = xdr_one;
566 		p = xdr_encode_hyper(p, (u64)attr->ia_size);
567 	} else
568 		*p++ = xdr_zero;
569 
570 	if (attr->ia_valid & ATTR_ATIME_SET) {
571 		struct timespec ts;
572 		*p++ = xdr_two;
573 		ts = timespec64_to_timespec(attr->ia_atime);
574 		p = xdr_encode_nfstime3(p, &ts);
575 	} else if (attr->ia_valid & ATTR_ATIME) {
576 		*p++ = xdr_one;
577 	} else
578 		*p++ = xdr_zero;
579 
580 	if (attr->ia_valid & ATTR_MTIME_SET) {
581 		*p++ = xdr_two;
582 		ts = timespec64_to_timespec(attr->ia_mtime);
583 		xdr_encode_nfstime3(p, &ts);
584 	} else if (attr->ia_valid & ATTR_MTIME) {
585 		*p = xdr_one;
586 	} else
587 		*p = xdr_zero;
588 }
589 
590 /*
591  * fattr3
592  *
593  *	struct fattr3 {
594  *		ftype3		type;
595  *		mode3		mode;
596  *		uint32		nlink;
597  *		uid3		uid;
598  *		gid3		gid;
599  *		size3		size;
600  *		size3		used;
601  *		specdata3	rdev;
602  *		uint64		fsid;
603  *		fileid3		fileid;
604  *		nfstime3	atime;
605  *		nfstime3	mtime;
606  *		nfstime3	ctime;
607  *	};
608  */
609 static int decode_fattr3(struct xdr_stream *xdr, struct nfs_fattr *fattr)
610 {
611 	umode_t fmode;
612 	__be32 *p;
613 
614 	p = xdr_inline_decode(xdr, NFS3_fattr_sz << 2);
615 	if (unlikely(!p))
616 		return -EIO;
617 
618 	p = xdr_decode_ftype3(p, &fmode);
619 
620 	fattr->mode = (be32_to_cpup(p++) & ~S_IFMT) | fmode;
621 	fattr->nlink = be32_to_cpup(p++);
622 	fattr->uid = make_kuid(&init_user_ns, be32_to_cpup(p++));
623 	if (!uid_valid(fattr->uid))
624 		goto out_uid;
625 	fattr->gid = make_kgid(&init_user_ns, be32_to_cpup(p++));
626 	if (!gid_valid(fattr->gid))
627 		goto out_gid;
628 
629 	p = xdr_decode_size3(p, &fattr->size);
630 	p = xdr_decode_size3(p, &fattr->du.nfs3.used);
631 	p = xdr_decode_specdata3(p, &fattr->rdev);
632 
633 	p = xdr_decode_hyper(p, &fattr->fsid.major);
634 	fattr->fsid.minor = 0;
635 
636 	p = xdr_decode_fileid3(p, &fattr->fileid);
637 	p = xdr_decode_nfstime3(p, &fattr->atime);
638 	p = xdr_decode_nfstime3(p, &fattr->mtime);
639 	xdr_decode_nfstime3(p, &fattr->ctime);
640 	fattr->change_attr = nfs_timespec_to_change_attr(&fattr->ctime);
641 
642 	fattr->valid |= NFS_ATTR_FATTR_V3;
643 	return 0;
644 out_uid:
645 	dprintk("NFS: returned invalid uid\n");
646 	return -EINVAL;
647 out_gid:
648 	dprintk("NFS: returned invalid gid\n");
649 	return -EINVAL;
650 }
651 
652 /*
653  * post_op_attr
654  *
655  *	union post_op_attr switch (bool attributes_follow) {
656  *	case TRUE:
657  *		fattr3	attributes;
658  *	case FALSE:
659  *		void;
660  *	};
661  */
662 static int decode_post_op_attr(struct xdr_stream *xdr, struct nfs_fattr *fattr)
663 {
664 	__be32 *p;
665 
666 	p = xdr_inline_decode(xdr, 4);
667 	if (unlikely(!p))
668 		return -EIO;
669 	if (*p != xdr_zero)
670 		return decode_fattr3(xdr, fattr);
671 	return 0;
672 }
673 
674 /*
675  * wcc_attr
676  *	struct wcc_attr {
677  *		size3		size;
678  *		nfstime3	mtime;
679  *		nfstime3	ctime;
680  *	};
681  */
682 static int decode_wcc_attr(struct xdr_stream *xdr, struct nfs_fattr *fattr)
683 {
684 	__be32 *p;
685 
686 	p = xdr_inline_decode(xdr, NFS3_wcc_attr_sz << 2);
687 	if (unlikely(!p))
688 		return -EIO;
689 
690 	fattr->valid |= NFS_ATTR_FATTR_PRESIZE
691 		| NFS_ATTR_FATTR_PRECHANGE
692 		| NFS_ATTR_FATTR_PREMTIME
693 		| NFS_ATTR_FATTR_PRECTIME;
694 
695 	p = xdr_decode_size3(p, &fattr->pre_size);
696 	p = xdr_decode_nfstime3(p, &fattr->pre_mtime);
697 	xdr_decode_nfstime3(p, &fattr->pre_ctime);
698 	fattr->pre_change_attr = nfs_timespec_to_change_attr(&fattr->pre_ctime);
699 
700 	return 0;
701 }
702 
703 /*
704  * pre_op_attr
705  *	union pre_op_attr switch (bool attributes_follow) {
706  *	case TRUE:
707  *		wcc_attr	attributes;
708  *	case FALSE:
709  *		void;
710  *	};
711  *
712  * wcc_data
713  *
714  *	struct wcc_data {
715  *		pre_op_attr	before;
716  *		post_op_attr	after;
717  *	};
718  */
719 static int decode_pre_op_attr(struct xdr_stream *xdr, struct nfs_fattr *fattr)
720 {
721 	__be32 *p;
722 
723 	p = xdr_inline_decode(xdr, 4);
724 	if (unlikely(!p))
725 		return -EIO;
726 	if (*p != xdr_zero)
727 		return decode_wcc_attr(xdr, fattr);
728 	return 0;
729 }
730 
731 static int decode_wcc_data(struct xdr_stream *xdr, struct nfs_fattr *fattr)
732 {
733 	int error;
734 
735 	error = decode_pre_op_attr(xdr, fattr);
736 	if (unlikely(error))
737 		goto out;
738 	error = decode_post_op_attr(xdr, fattr);
739 out:
740 	return error;
741 }
742 
743 /*
744  * post_op_fh3
745  *
746  *	union post_op_fh3 switch (bool handle_follows) {
747  *	case TRUE:
748  *		nfs_fh3  handle;
749  *	case FALSE:
750  *		void;
751  *	};
752  */
753 static int decode_post_op_fh3(struct xdr_stream *xdr, struct nfs_fh *fh)
754 {
755 	__be32 *p = xdr_inline_decode(xdr, 4);
756 	if (unlikely(!p))
757 		return -EIO;
758 	if (*p != xdr_zero)
759 		return decode_nfs_fh3(xdr, fh);
760 	zero_nfs_fh3(fh);
761 	return 0;
762 }
763 
764 /*
765  * diropargs3
766  *
767  *	struct diropargs3 {
768  *		nfs_fh3		dir;
769  *		filename3	name;
770  *	};
771  */
772 static void encode_diropargs3(struct xdr_stream *xdr, const struct nfs_fh *fh,
773 			      const char *name, u32 length)
774 {
775 	encode_nfs_fh3(xdr, fh);
776 	encode_filename3(xdr, name, length);
777 }
778 
779 
780 /*
781  * NFSv3 XDR encode functions
782  *
783  * NFSv3 argument types are defined in section 3.3 of RFC 1813:
784  * "NFS Version 3 Protocol Specification".
785  */
786 
787 /*
788  * 3.3.1  GETATTR3args
789  *
790  *	struct GETATTR3args {
791  *		nfs_fh3  object;
792  *	};
793  */
794 static void nfs3_xdr_enc_getattr3args(struct rpc_rqst *req,
795 				      struct xdr_stream *xdr,
796 				      const void *data)
797 {
798 	const struct nfs_fh *fh = data;
799 
800 	encode_nfs_fh3(xdr, fh);
801 }
802 
803 /*
804  * 3.3.2  SETATTR3args
805  *
806  *	union sattrguard3 switch (bool check) {
807  *	case TRUE:
808  *		nfstime3  obj_ctime;
809  *	case FALSE:
810  *		void;
811  *	};
812  *
813  *	struct SETATTR3args {
814  *		nfs_fh3		object;
815  *		sattr3		new_attributes;
816  *		sattrguard3	guard;
817  *	};
818  */
819 static void encode_sattrguard3(struct xdr_stream *xdr,
820 			       const struct nfs3_sattrargs *args)
821 {
822 	__be32 *p;
823 
824 	if (args->guard) {
825 		p = xdr_reserve_space(xdr, 4 + 8);
826 		*p++ = xdr_one;
827 		xdr_encode_nfstime3(p, &args->guardtime);
828 	} else {
829 		p = xdr_reserve_space(xdr, 4);
830 		*p = xdr_zero;
831 	}
832 }
833 
834 static void nfs3_xdr_enc_setattr3args(struct rpc_rqst *req,
835 				      struct xdr_stream *xdr,
836 				      const void *data)
837 {
838 	const struct nfs3_sattrargs *args = data;
839 	encode_nfs_fh3(xdr, args->fh);
840 	encode_sattr3(xdr, args->sattr);
841 	encode_sattrguard3(xdr, args);
842 }
843 
844 /*
845  * 3.3.3  LOOKUP3args
846  *
847  *	struct LOOKUP3args {
848  *		diropargs3  what;
849  *	};
850  */
851 static void nfs3_xdr_enc_lookup3args(struct rpc_rqst *req,
852 				     struct xdr_stream *xdr,
853 				     const void *data)
854 {
855 	const struct nfs3_diropargs *args = data;
856 
857 	encode_diropargs3(xdr, args->fh, args->name, args->len);
858 }
859 
860 /*
861  * 3.3.4  ACCESS3args
862  *
863  *	struct ACCESS3args {
864  *		nfs_fh3		object;
865  *		uint32		access;
866  *	};
867  */
868 static void encode_access3args(struct xdr_stream *xdr,
869 			       const struct nfs3_accessargs *args)
870 {
871 	encode_nfs_fh3(xdr, args->fh);
872 	encode_uint32(xdr, args->access);
873 }
874 
875 static void nfs3_xdr_enc_access3args(struct rpc_rqst *req,
876 				     struct xdr_stream *xdr,
877 				     const void *data)
878 {
879 	const struct nfs3_accessargs *args = data;
880 
881 	encode_access3args(xdr, args);
882 }
883 
884 /*
885  * 3.3.5  READLINK3args
886  *
887  *	struct READLINK3args {
888  *		nfs_fh3	symlink;
889  *	};
890  */
891 static void nfs3_xdr_enc_readlink3args(struct rpc_rqst *req,
892 				       struct xdr_stream *xdr,
893 				       const void *data)
894 {
895 	const struct nfs3_readlinkargs *args = data;
896 
897 	encode_nfs_fh3(xdr, args->fh);
898 	rpc_prepare_reply_pages(req, args->pages, args->pgbase,
899 				args->pglen, NFS3_readlinkres_sz);
900 }
901 
902 /*
903  * 3.3.6  READ3args
904  *
905  *	struct READ3args {
906  *		nfs_fh3		file;
907  *		offset3		offset;
908  *		count3		count;
909  *	};
910  */
911 static void encode_read3args(struct xdr_stream *xdr,
912 			     const struct nfs_pgio_args *args)
913 {
914 	__be32 *p;
915 
916 	encode_nfs_fh3(xdr, args->fh);
917 
918 	p = xdr_reserve_space(xdr, 8 + 4);
919 	p = xdr_encode_hyper(p, args->offset);
920 	*p = cpu_to_be32(args->count);
921 }
922 
923 static void nfs3_xdr_enc_read3args(struct rpc_rqst *req,
924 				   struct xdr_stream *xdr,
925 				   const void *data)
926 {
927 	const struct nfs_pgio_args *args = data;
928 	unsigned int replen = args->replen ? args->replen : NFS3_readres_sz;
929 
930 	encode_read3args(xdr, args);
931 	rpc_prepare_reply_pages(req, args->pages, args->pgbase,
932 				args->count, replen);
933 	req->rq_rcv_buf.flags |= XDRBUF_READ;
934 }
935 
936 /*
937  * 3.3.7  WRITE3args
938  *
939  *	enum stable_how {
940  *		UNSTABLE  = 0,
941  *		DATA_SYNC = 1,
942  *		FILE_SYNC = 2
943  *	};
944  *
945  *	struct WRITE3args {
946  *		nfs_fh3		file;
947  *		offset3		offset;
948  *		count3		count;
949  *		stable_how	stable;
950  *		opaque		data<>;
951  *	};
952  */
953 static void encode_write3args(struct xdr_stream *xdr,
954 			      const struct nfs_pgio_args *args)
955 {
956 	__be32 *p;
957 
958 	encode_nfs_fh3(xdr, args->fh);
959 
960 	p = xdr_reserve_space(xdr, 8 + 4 + 4 + 4);
961 	p = xdr_encode_hyper(p, args->offset);
962 	*p++ = cpu_to_be32(args->count);
963 	*p++ = cpu_to_be32(args->stable);
964 	*p = cpu_to_be32(args->count);
965 	xdr_write_pages(xdr, args->pages, args->pgbase, args->count);
966 }
967 
968 static void nfs3_xdr_enc_write3args(struct rpc_rqst *req,
969 				    struct xdr_stream *xdr,
970 				    const void *data)
971 {
972 	const struct nfs_pgio_args *args = data;
973 
974 	encode_write3args(xdr, args);
975 	xdr->buf->flags |= XDRBUF_WRITE;
976 }
977 
978 /*
979  * 3.3.8  CREATE3args
980  *
981  *	enum createmode3 {
982  *		UNCHECKED = 0,
983  *		GUARDED   = 1,
984  *		EXCLUSIVE = 2
985  *	};
986  *
987  *	union createhow3 switch (createmode3 mode) {
988  *	case UNCHECKED:
989  *	case GUARDED:
990  *		sattr3       obj_attributes;
991  *	case EXCLUSIVE:
992  *		createverf3  verf;
993  *	};
994  *
995  *	struct CREATE3args {
996  *		diropargs3	where;
997  *		createhow3	how;
998  *	};
999  */
1000 static void encode_createhow3(struct xdr_stream *xdr,
1001 			      const struct nfs3_createargs *args)
1002 {
1003 	encode_uint32(xdr, args->createmode);
1004 	switch (args->createmode) {
1005 	case NFS3_CREATE_UNCHECKED:
1006 	case NFS3_CREATE_GUARDED:
1007 		encode_sattr3(xdr, args->sattr);
1008 		break;
1009 	case NFS3_CREATE_EXCLUSIVE:
1010 		encode_createverf3(xdr, args->verifier);
1011 		break;
1012 	default:
1013 		BUG();
1014 	}
1015 }
1016 
1017 static void nfs3_xdr_enc_create3args(struct rpc_rqst *req,
1018 				     struct xdr_stream *xdr,
1019 				     const void *data)
1020 {
1021 	const struct nfs3_createargs *args = data;
1022 
1023 	encode_diropargs3(xdr, args->fh, args->name, args->len);
1024 	encode_createhow3(xdr, args);
1025 }
1026 
1027 /*
1028  * 3.3.9  MKDIR3args
1029  *
1030  *	struct MKDIR3args {
1031  *		diropargs3	where;
1032  *		sattr3		attributes;
1033  *	};
1034  */
1035 static void nfs3_xdr_enc_mkdir3args(struct rpc_rqst *req,
1036 				    struct xdr_stream *xdr,
1037 				    const void *data)
1038 {
1039 	const struct nfs3_mkdirargs *args = data;
1040 
1041 	encode_diropargs3(xdr, args->fh, args->name, args->len);
1042 	encode_sattr3(xdr, args->sattr);
1043 }
1044 
1045 /*
1046  * 3.3.10  SYMLINK3args
1047  *
1048  *	struct symlinkdata3 {
1049  *		sattr3		symlink_attributes;
1050  *		nfspath3	symlink_data;
1051  *	};
1052  *
1053  *	struct SYMLINK3args {
1054  *		diropargs3	where;
1055  *		symlinkdata3	symlink;
1056  *	};
1057  */
1058 static void encode_symlinkdata3(struct xdr_stream *xdr,
1059 				const void *data)
1060 {
1061 	const struct nfs3_symlinkargs *args = data;
1062 
1063 	encode_sattr3(xdr, args->sattr);
1064 	encode_nfspath3(xdr, args->pages, args->pathlen);
1065 }
1066 
1067 static void nfs3_xdr_enc_symlink3args(struct rpc_rqst *req,
1068 				      struct xdr_stream *xdr,
1069 				      const void *data)
1070 {
1071 	const struct nfs3_symlinkargs *args = data;
1072 
1073 	encode_diropargs3(xdr, args->fromfh, args->fromname, args->fromlen);
1074 	encode_symlinkdata3(xdr, args);
1075 	xdr->buf->flags |= XDRBUF_WRITE;
1076 }
1077 
1078 /*
1079  * 3.3.11  MKNOD3args
1080  *
1081  *	struct devicedata3 {
1082  *		sattr3		dev_attributes;
1083  *		specdata3	spec;
1084  *	};
1085  *
1086  *	union mknoddata3 switch (ftype3 type) {
1087  *	case NF3CHR:
1088  *	case NF3BLK:
1089  *		devicedata3	device;
1090  *	case NF3SOCK:
1091  *	case NF3FIFO:
1092  *		sattr3		pipe_attributes;
1093  *	default:
1094  *		void;
1095  *	};
1096  *
1097  *	struct MKNOD3args {
1098  *		diropargs3	where;
1099  *		mknoddata3	what;
1100  *	};
1101  */
1102 static void encode_devicedata3(struct xdr_stream *xdr,
1103 			       const struct nfs3_mknodargs *args)
1104 {
1105 	encode_sattr3(xdr, args->sattr);
1106 	encode_specdata3(xdr, args->rdev);
1107 }
1108 
1109 static void encode_mknoddata3(struct xdr_stream *xdr,
1110 			      const struct nfs3_mknodargs *args)
1111 {
1112 	encode_ftype3(xdr, args->type);
1113 	switch (args->type) {
1114 	case NF3CHR:
1115 	case NF3BLK:
1116 		encode_devicedata3(xdr, args);
1117 		break;
1118 	case NF3SOCK:
1119 	case NF3FIFO:
1120 		encode_sattr3(xdr, args->sattr);
1121 		break;
1122 	case NF3REG:
1123 	case NF3DIR:
1124 		break;
1125 	default:
1126 		BUG();
1127 	}
1128 }
1129 
1130 static void nfs3_xdr_enc_mknod3args(struct rpc_rqst *req,
1131 				    struct xdr_stream *xdr,
1132 				    const void *data)
1133 {
1134 	const struct nfs3_mknodargs *args = data;
1135 
1136 	encode_diropargs3(xdr, args->fh, args->name, args->len);
1137 	encode_mknoddata3(xdr, args);
1138 }
1139 
1140 /*
1141  * 3.3.12  REMOVE3args
1142  *
1143  *	struct REMOVE3args {
1144  *		diropargs3  object;
1145  *	};
1146  */
1147 static void nfs3_xdr_enc_remove3args(struct rpc_rqst *req,
1148 				     struct xdr_stream *xdr,
1149 				     const void *data)
1150 {
1151 	const struct nfs_removeargs *args = data;
1152 
1153 	encode_diropargs3(xdr, args->fh, args->name.name, args->name.len);
1154 }
1155 
1156 /*
1157  * 3.3.14  RENAME3args
1158  *
1159  *	struct RENAME3args {
1160  *		diropargs3	from;
1161  *		diropargs3	to;
1162  *	};
1163  */
1164 static void nfs3_xdr_enc_rename3args(struct rpc_rqst *req,
1165 				     struct xdr_stream *xdr,
1166 				     const void *data)
1167 {
1168 	const struct nfs_renameargs *args = data;
1169 	const struct qstr *old = args->old_name;
1170 	const struct qstr *new = args->new_name;
1171 
1172 	encode_diropargs3(xdr, args->old_dir, old->name, old->len);
1173 	encode_diropargs3(xdr, args->new_dir, new->name, new->len);
1174 }
1175 
1176 /*
1177  * 3.3.15  LINK3args
1178  *
1179  *	struct LINK3args {
1180  *		nfs_fh3		file;
1181  *		diropargs3	link;
1182  *	};
1183  */
1184 static void nfs3_xdr_enc_link3args(struct rpc_rqst *req,
1185 				   struct xdr_stream *xdr,
1186 				   const void *data)
1187 {
1188 	const struct nfs3_linkargs *args = data;
1189 
1190 	encode_nfs_fh3(xdr, args->fromfh);
1191 	encode_diropargs3(xdr, args->tofh, args->toname, args->tolen);
1192 }
1193 
1194 /*
1195  * 3.3.16  READDIR3args
1196  *
1197  *	struct READDIR3args {
1198  *		nfs_fh3		dir;
1199  *		cookie3		cookie;
1200  *		cookieverf3	cookieverf;
1201  *		count3		count;
1202  *	};
1203  */
1204 static void encode_readdir3args(struct xdr_stream *xdr,
1205 				const struct nfs3_readdirargs *args)
1206 {
1207 	__be32 *p;
1208 
1209 	encode_nfs_fh3(xdr, args->fh);
1210 
1211 	p = xdr_reserve_space(xdr, 8 + NFS3_COOKIEVERFSIZE + 4);
1212 	p = xdr_encode_cookie3(p, args->cookie);
1213 	p = xdr_encode_cookieverf3(p, args->verf);
1214 	*p = cpu_to_be32(args->count);
1215 }
1216 
1217 static void nfs3_xdr_enc_readdir3args(struct rpc_rqst *req,
1218 				      struct xdr_stream *xdr,
1219 				      const void *data)
1220 {
1221 	const struct nfs3_readdirargs *args = data;
1222 
1223 	encode_readdir3args(xdr, args);
1224 	rpc_prepare_reply_pages(req, args->pages, 0,
1225 				args->count, NFS3_readdirres_sz);
1226 }
1227 
1228 /*
1229  * 3.3.17  READDIRPLUS3args
1230  *
1231  *	struct READDIRPLUS3args {
1232  *		nfs_fh3		dir;
1233  *		cookie3		cookie;
1234  *		cookieverf3	cookieverf;
1235  *		count3		dircount;
1236  *		count3		maxcount;
1237  *	};
1238  */
1239 static void encode_readdirplus3args(struct xdr_stream *xdr,
1240 				    const struct nfs3_readdirargs *args)
1241 {
1242 	__be32 *p;
1243 
1244 	encode_nfs_fh3(xdr, args->fh);
1245 
1246 	p = xdr_reserve_space(xdr, 8 + NFS3_COOKIEVERFSIZE + 4 + 4);
1247 	p = xdr_encode_cookie3(p, args->cookie);
1248 	p = xdr_encode_cookieverf3(p, args->verf);
1249 
1250 	/*
1251 	 * readdirplus: need dircount + buffer size.
1252 	 * We just make sure we make dircount big enough
1253 	 */
1254 	*p++ = cpu_to_be32(args->count >> 3);
1255 
1256 	*p = cpu_to_be32(args->count);
1257 }
1258 
1259 static void nfs3_xdr_enc_readdirplus3args(struct rpc_rqst *req,
1260 					  struct xdr_stream *xdr,
1261 					  const void *data)
1262 {
1263 	const struct nfs3_readdirargs *args = data;
1264 
1265 	encode_readdirplus3args(xdr, args);
1266 	rpc_prepare_reply_pages(req, args->pages, 0,
1267 				args->count, NFS3_readdirres_sz);
1268 }
1269 
1270 /*
1271  * 3.3.21  COMMIT3args
1272  *
1273  *	struct COMMIT3args {
1274  *		nfs_fh3		file;
1275  *		offset3		offset;
1276  *		count3		count;
1277  *	};
1278  */
1279 static void encode_commit3args(struct xdr_stream *xdr,
1280 			       const struct nfs_commitargs *args)
1281 {
1282 	__be32 *p;
1283 
1284 	encode_nfs_fh3(xdr, args->fh);
1285 
1286 	p = xdr_reserve_space(xdr, 8 + 4);
1287 	p = xdr_encode_hyper(p, args->offset);
1288 	*p = cpu_to_be32(args->count);
1289 }
1290 
1291 static void nfs3_xdr_enc_commit3args(struct rpc_rqst *req,
1292 				     struct xdr_stream *xdr,
1293 				     const void *data)
1294 {
1295 	const struct nfs_commitargs *args = data;
1296 
1297 	encode_commit3args(xdr, args);
1298 }
1299 
1300 #ifdef CONFIG_NFS_V3_ACL
1301 
1302 static void nfs3_xdr_enc_getacl3args(struct rpc_rqst *req,
1303 				     struct xdr_stream *xdr,
1304 				     const void *data)
1305 {
1306 	const struct nfs3_getaclargs *args = data;
1307 
1308 	encode_nfs_fh3(xdr, args->fh);
1309 	encode_uint32(xdr, args->mask);
1310 	if (args->mask & (NFS_ACL | NFS_DFACL)) {
1311 		rpc_prepare_reply_pages(req, args->pages, 0,
1312 					NFSACL_MAXPAGES << PAGE_SHIFT,
1313 					ACL3_getaclres_sz);
1314 		req->rq_rcv_buf.flags |= XDRBUF_SPARSE_PAGES;
1315 	}
1316 }
1317 
1318 static void nfs3_xdr_enc_setacl3args(struct rpc_rqst *req,
1319 				     struct xdr_stream *xdr,
1320 				     const void *data)
1321 {
1322 	const struct nfs3_setaclargs *args = data;
1323 	unsigned int base;
1324 	int error;
1325 
1326 	encode_nfs_fh3(xdr, NFS_FH(args->inode));
1327 	encode_uint32(xdr, args->mask);
1328 
1329 	base = req->rq_slen;
1330 	if (args->npages != 0)
1331 		xdr_write_pages(xdr, args->pages, 0, args->len);
1332 	else
1333 		xdr_reserve_space(xdr, args->len);
1334 
1335 	error = nfsacl_encode(xdr->buf, base, args->inode,
1336 			    (args->mask & NFS_ACL) ?
1337 			    args->acl_access : NULL, 1, 0);
1338 	/* FIXME: this is just broken */
1339 	BUG_ON(error < 0);
1340 	error = nfsacl_encode(xdr->buf, base + error, args->inode,
1341 			    (args->mask & NFS_DFACL) ?
1342 			    args->acl_default : NULL, 1,
1343 			    NFS_ACL_DEFAULT);
1344 	BUG_ON(error < 0);
1345 }
1346 
1347 #endif  /* CONFIG_NFS_V3_ACL */
1348 
1349 /*
1350  * NFSv3 XDR decode functions
1351  *
1352  * NFSv3 result types are defined in section 3.3 of RFC 1813:
1353  * "NFS Version 3 Protocol Specification".
1354  */
1355 
1356 /*
1357  * 3.3.1  GETATTR3res
1358  *
1359  *	struct GETATTR3resok {
1360  *		fattr3		obj_attributes;
1361  *	};
1362  *
1363  *	union GETATTR3res switch (nfsstat3 status) {
1364  *	case NFS3_OK:
1365  *		GETATTR3resok  resok;
1366  *	default:
1367  *		void;
1368  *	};
1369  */
1370 static int nfs3_xdr_dec_getattr3res(struct rpc_rqst *req,
1371 				    struct xdr_stream *xdr,
1372 				    void *result)
1373 {
1374 	enum nfs_stat status;
1375 	int error;
1376 
1377 	error = decode_nfsstat3(xdr, &status);
1378 	if (unlikely(error))
1379 		goto out;
1380 	if (status != NFS3_OK)
1381 		goto out_default;
1382 	error = decode_fattr3(xdr, result);
1383 out:
1384 	return error;
1385 out_default:
1386 	return nfs3_stat_to_errno(status);
1387 }
1388 
1389 /*
1390  * 3.3.2  SETATTR3res
1391  *
1392  *	struct SETATTR3resok {
1393  *		wcc_data  obj_wcc;
1394  *	};
1395  *
1396  *	struct SETATTR3resfail {
1397  *		wcc_data  obj_wcc;
1398  *	};
1399  *
1400  *	union SETATTR3res switch (nfsstat3 status) {
1401  *	case NFS3_OK:
1402  *		SETATTR3resok   resok;
1403  *	default:
1404  *		SETATTR3resfail resfail;
1405  *	};
1406  */
1407 static int nfs3_xdr_dec_setattr3res(struct rpc_rqst *req,
1408 				    struct xdr_stream *xdr,
1409 				    void *result)
1410 {
1411 	enum nfs_stat status;
1412 	int error;
1413 
1414 	error = decode_nfsstat3(xdr, &status);
1415 	if (unlikely(error))
1416 		goto out;
1417 	error = decode_wcc_data(xdr, result);
1418 	if (unlikely(error))
1419 		goto out;
1420 	if (status != NFS3_OK)
1421 		goto out_status;
1422 out:
1423 	return error;
1424 out_status:
1425 	return nfs3_stat_to_errno(status);
1426 }
1427 
1428 /*
1429  * 3.3.3  LOOKUP3res
1430  *
1431  *	struct LOOKUP3resok {
1432  *		nfs_fh3		object;
1433  *		post_op_attr	obj_attributes;
1434  *		post_op_attr	dir_attributes;
1435  *	};
1436  *
1437  *	struct LOOKUP3resfail {
1438  *		post_op_attr	dir_attributes;
1439  *	};
1440  *
1441  *	union LOOKUP3res switch (nfsstat3 status) {
1442  *	case NFS3_OK:
1443  *		LOOKUP3resok	resok;
1444  *	default:
1445  *		LOOKUP3resfail	resfail;
1446  *	};
1447  */
1448 static int nfs3_xdr_dec_lookup3res(struct rpc_rqst *req,
1449 				   struct xdr_stream *xdr,
1450 				   void *data)
1451 {
1452 	struct nfs3_diropres *result = data;
1453 	enum nfs_stat status;
1454 	int error;
1455 
1456 	error = decode_nfsstat3(xdr, &status);
1457 	if (unlikely(error))
1458 		goto out;
1459 	if (status != NFS3_OK)
1460 		goto out_default;
1461 	error = decode_nfs_fh3(xdr, result->fh);
1462 	if (unlikely(error))
1463 		goto out;
1464 	error = decode_post_op_attr(xdr, result->fattr);
1465 	if (unlikely(error))
1466 		goto out;
1467 	error = decode_post_op_attr(xdr, result->dir_attr);
1468 out:
1469 	return error;
1470 out_default:
1471 	error = decode_post_op_attr(xdr, result->dir_attr);
1472 	if (unlikely(error))
1473 		goto out;
1474 	return nfs3_stat_to_errno(status);
1475 }
1476 
1477 /*
1478  * 3.3.4  ACCESS3res
1479  *
1480  *	struct ACCESS3resok {
1481  *		post_op_attr	obj_attributes;
1482  *		uint32		access;
1483  *	};
1484  *
1485  *	struct ACCESS3resfail {
1486  *		post_op_attr	obj_attributes;
1487  *	};
1488  *
1489  *	union ACCESS3res switch (nfsstat3 status) {
1490  *	case NFS3_OK:
1491  *		ACCESS3resok	resok;
1492  *	default:
1493  *		ACCESS3resfail	resfail;
1494  *	};
1495  */
1496 static int nfs3_xdr_dec_access3res(struct rpc_rqst *req,
1497 				   struct xdr_stream *xdr,
1498 				   void *data)
1499 {
1500 	struct nfs3_accessres *result = data;
1501 	enum nfs_stat status;
1502 	int error;
1503 
1504 	error = decode_nfsstat3(xdr, &status);
1505 	if (unlikely(error))
1506 		goto out;
1507 	error = decode_post_op_attr(xdr, result->fattr);
1508 	if (unlikely(error))
1509 		goto out;
1510 	if (status != NFS3_OK)
1511 		goto out_default;
1512 	error = decode_uint32(xdr, &result->access);
1513 out:
1514 	return error;
1515 out_default:
1516 	return nfs3_stat_to_errno(status);
1517 }
1518 
1519 /*
1520  * 3.3.5  READLINK3res
1521  *
1522  *	struct READLINK3resok {
1523  *		post_op_attr	symlink_attributes;
1524  *		nfspath3	data;
1525  *	};
1526  *
1527  *	struct READLINK3resfail {
1528  *		post_op_attr	symlink_attributes;
1529  *	};
1530  *
1531  *	union READLINK3res switch (nfsstat3 status) {
1532  *	case NFS3_OK:
1533  *		READLINK3resok	resok;
1534  *	default:
1535  *		READLINK3resfail resfail;
1536  *	};
1537  */
1538 static int nfs3_xdr_dec_readlink3res(struct rpc_rqst *req,
1539 				     struct xdr_stream *xdr,
1540 				     void *result)
1541 {
1542 	enum nfs_stat status;
1543 	int error;
1544 
1545 	error = decode_nfsstat3(xdr, &status);
1546 	if (unlikely(error))
1547 		goto out;
1548 	error = decode_post_op_attr(xdr, result);
1549 	if (unlikely(error))
1550 		goto out;
1551 	if (status != NFS3_OK)
1552 		goto out_default;
1553 	error = decode_nfspath3(xdr);
1554 out:
1555 	return error;
1556 out_default:
1557 	return nfs3_stat_to_errno(status);
1558 }
1559 
1560 /*
1561  * 3.3.6  READ3res
1562  *
1563  *	struct READ3resok {
1564  *		post_op_attr	file_attributes;
1565  *		count3		count;
1566  *		bool		eof;
1567  *		opaque		data<>;
1568  *	};
1569  *
1570  *	struct READ3resfail {
1571  *		post_op_attr	file_attributes;
1572  *	};
1573  *
1574  *	union READ3res switch (nfsstat3 status) {
1575  *	case NFS3_OK:
1576  *		READ3resok	resok;
1577  *	default:
1578  *		READ3resfail	resfail;
1579  *	};
1580  */
1581 static int decode_read3resok(struct xdr_stream *xdr,
1582 			     struct nfs_pgio_res *result)
1583 {
1584 	u32 eof, count, ocount, recvd;
1585 	__be32 *p;
1586 
1587 	p = xdr_inline_decode(xdr, 4 + 4 + 4);
1588 	if (unlikely(!p))
1589 		return -EIO;
1590 	count = be32_to_cpup(p++);
1591 	eof = be32_to_cpup(p++);
1592 	ocount = be32_to_cpup(p++);
1593 	if (unlikely(ocount != count))
1594 		goto out_mismatch;
1595 	recvd = xdr_read_pages(xdr, count);
1596 	if (unlikely(count > recvd))
1597 		goto out_cheating;
1598 out:
1599 	result->eof = eof;
1600 	result->count = count;
1601 	return count;
1602 out_mismatch:
1603 	dprintk("NFS: READ count doesn't match length of opaque: "
1604 		"count %u != ocount %u\n", count, ocount);
1605 	return -EIO;
1606 out_cheating:
1607 	dprintk("NFS: server cheating in read result: "
1608 		"count %u > recvd %u\n", count, recvd);
1609 	count = recvd;
1610 	eof = 0;
1611 	goto out;
1612 }
1613 
1614 static int nfs3_xdr_dec_read3res(struct rpc_rqst *req, struct xdr_stream *xdr,
1615 				 void *data)
1616 {
1617 	struct nfs_pgio_res *result = data;
1618 	unsigned int pos;
1619 	enum nfs_stat status;
1620 	int error;
1621 
1622 	pos = xdr_stream_pos(xdr);
1623 	error = decode_nfsstat3(xdr, &status);
1624 	if (unlikely(error))
1625 		goto out;
1626 	error = decode_post_op_attr(xdr, result->fattr);
1627 	if (unlikely(error))
1628 		goto out;
1629 	result->op_status = status;
1630 	if (status != NFS3_OK)
1631 		goto out_status;
1632 	result->replen = 4 + ((xdr_stream_pos(xdr) - pos) >> 2);
1633 	error = decode_read3resok(xdr, result);
1634 out:
1635 	return error;
1636 out_status:
1637 	return nfs3_stat_to_errno(status);
1638 }
1639 
1640 /*
1641  * 3.3.7  WRITE3res
1642  *
1643  *	enum stable_how {
1644  *		UNSTABLE  = 0,
1645  *		DATA_SYNC = 1,
1646  *		FILE_SYNC = 2
1647  *	};
1648  *
1649  *	struct WRITE3resok {
1650  *		wcc_data	file_wcc;
1651  *		count3		count;
1652  *		stable_how	committed;
1653  *		writeverf3	verf;
1654  *	};
1655  *
1656  *	struct WRITE3resfail {
1657  *		wcc_data	file_wcc;
1658  *	};
1659  *
1660  *	union WRITE3res switch (nfsstat3 status) {
1661  *	case NFS3_OK:
1662  *		WRITE3resok	resok;
1663  *	default:
1664  *		WRITE3resfail	resfail;
1665  *	};
1666  */
1667 static int decode_write3resok(struct xdr_stream *xdr,
1668 			      struct nfs_pgio_res *result)
1669 {
1670 	__be32 *p;
1671 
1672 	p = xdr_inline_decode(xdr, 4 + 4);
1673 	if (unlikely(!p))
1674 		return -EIO;
1675 	result->count = be32_to_cpup(p++);
1676 	result->verf->committed = be32_to_cpup(p++);
1677 	if (unlikely(result->verf->committed > NFS_FILE_SYNC))
1678 		goto out_badvalue;
1679 	if (decode_writeverf3(xdr, &result->verf->verifier))
1680 		return -EIO;
1681 	return result->count;
1682 out_badvalue:
1683 	dprintk("NFS: bad stable_how value: %u\n", result->verf->committed);
1684 	return -EIO;
1685 }
1686 
1687 static int nfs3_xdr_dec_write3res(struct rpc_rqst *req, struct xdr_stream *xdr,
1688 				  void *data)
1689 {
1690 	struct nfs_pgio_res *result = data;
1691 	enum nfs_stat status;
1692 	int error;
1693 
1694 	error = decode_nfsstat3(xdr, &status);
1695 	if (unlikely(error))
1696 		goto out;
1697 	error = decode_wcc_data(xdr, result->fattr);
1698 	if (unlikely(error))
1699 		goto out;
1700 	result->op_status = status;
1701 	if (status != NFS3_OK)
1702 		goto out_status;
1703 	error = decode_write3resok(xdr, result);
1704 out:
1705 	return error;
1706 out_status:
1707 	return nfs3_stat_to_errno(status);
1708 }
1709 
1710 /*
1711  * 3.3.8  CREATE3res
1712  *
1713  *	struct CREATE3resok {
1714  *		post_op_fh3	obj;
1715  *		post_op_attr	obj_attributes;
1716  *		wcc_data	dir_wcc;
1717  *	};
1718  *
1719  *	struct CREATE3resfail {
1720  *		wcc_data	dir_wcc;
1721  *	};
1722  *
1723  *	union CREATE3res switch (nfsstat3 status) {
1724  *	case NFS3_OK:
1725  *		CREATE3resok	resok;
1726  *	default:
1727  *		CREATE3resfail	resfail;
1728  *	};
1729  */
1730 static int decode_create3resok(struct xdr_stream *xdr,
1731 			       struct nfs3_diropres *result)
1732 {
1733 	int error;
1734 
1735 	error = decode_post_op_fh3(xdr, result->fh);
1736 	if (unlikely(error))
1737 		goto out;
1738 	error = decode_post_op_attr(xdr, result->fattr);
1739 	if (unlikely(error))
1740 		goto out;
1741 	/* The server isn't required to return a file handle.
1742 	 * If it didn't, force the client to perform a LOOKUP
1743 	 * to determine the correct file handle and attribute
1744 	 * values for the new object. */
1745 	if (result->fh->size == 0)
1746 		result->fattr->valid = 0;
1747 	error = decode_wcc_data(xdr, result->dir_attr);
1748 out:
1749 	return error;
1750 }
1751 
1752 static int nfs3_xdr_dec_create3res(struct rpc_rqst *req,
1753 				   struct xdr_stream *xdr,
1754 				   void *data)
1755 {
1756 	struct nfs3_diropres *result = data;
1757 	enum nfs_stat status;
1758 	int error;
1759 
1760 	error = decode_nfsstat3(xdr, &status);
1761 	if (unlikely(error))
1762 		goto out;
1763 	if (status != NFS3_OK)
1764 		goto out_default;
1765 	error = decode_create3resok(xdr, result);
1766 out:
1767 	return error;
1768 out_default:
1769 	error = decode_wcc_data(xdr, result->dir_attr);
1770 	if (unlikely(error))
1771 		goto out;
1772 	return nfs3_stat_to_errno(status);
1773 }
1774 
1775 /*
1776  * 3.3.12  REMOVE3res
1777  *
1778  *	struct REMOVE3resok {
1779  *		wcc_data    dir_wcc;
1780  *	};
1781  *
1782  *	struct REMOVE3resfail {
1783  *		wcc_data    dir_wcc;
1784  *	};
1785  *
1786  *	union REMOVE3res switch (nfsstat3 status) {
1787  *	case NFS3_OK:
1788  *		REMOVE3resok   resok;
1789  *	default:
1790  *		REMOVE3resfail resfail;
1791  *	};
1792  */
1793 static int nfs3_xdr_dec_remove3res(struct rpc_rqst *req,
1794 				   struct xdr_stream *xdr,
1795 				   void *data)
1796 {
1797 	struct nfs_removeres *result = data;
1798 	enum nfs_stat status;
1799 	int error;
1800 
1801 	error = decode_nfsstat3(xdr, &status);
1802 	if (unlikely(error))
1803 		goto out;
1804 	error = decode_wcc_data(xdr, result->dir_attr);
1805 	if (unlikely(error))
1806 		goto out;
1807 	if (status != NFS3_OK)
1808 		goto out_status;
1809 out:
1810 	return error;
1811 out_status:
1812 	return nfs3_stat_to_errno(status);
1813 }
1814 
1815 /*
1816  * 3.3.14  RENAME3res
1817  *
1818  *	struct RENAME3resok {
1819  *		wcc_data	fromdir_wcc;
1820  *		wcc_data	todir_wcc;
1821  *	};
1822  *
1823  *	struct RENAME3resfail {
1824  *		wcc_data	fromdir_wcc;
1825  *		wcc_data	todir_wcc;
1826  *	};
1827  *
1828  *	union RENAME3res switch (nfsstat3 status) {
1829  *	case NFS3_OK:
1830  *		RENAME3resok   resok;
1831  *	default:
1832  *		RENAME3resfail resfail;
1833  *	};
1834  */
1835 static int nfs3_xdr_dec_rename3res(struct rpc_rqst *req,
1836 				   struct xdr_stream *xdr,
1837 				   void *data)
1838 {
1839 	struct nfs_renameres *result = data;
1840 	enum nfs_stat status;
1841 	int error;
1842 
1843 	error = decode_nfsstat3(xdr, &status);
1844 	if (unlikely(error))
1845 		goto out;
1846 	error = decode_wcc_data(xdr, result->old_fattr);
1847 	if (unlikely(error))
1848 		goto out;
1849 	error = decode_wcc_data(xdr, result->new_fattr);
1850 	if (unlikely(error))
1851 		goto out;
1852 	if (status != NFS3_OK)
1853 		goto out_status;
1854 out:
1855 	return error;
1856 out_status:
1857 	return nfs3_stat_to_errno(status);
1858 }
1859 
1860 /*
1861  * 3.3.15  LINK3res
1862  *
1863  *	struct LINK3resok {
1864  *		post_op_attr	file_attributes;
1865  *		wcc_data	linkdir_wcc;
1866  *	};
1867  *
1868  *	struct LINK3resfail {
1869  *		post_op_attr	file_attributes;
1870  *		wcc_data	linkdir_wcc;
1871  *	};
1872  *
1873  *	union LINK3res switch (nfsstat3 status) {
1874  *	case NFS3_OK:
1875  *		LINK3resok	resok;
1876  *	default:
1877  *		LINK3resfail	resfail;
1878  *	};
1879  */
1880 static int nfs3_xdr_dec_link3res(struct rpc_rqst *req, struct xdr_stream *xdr,
1881 				 void *data)
1882 {
1883 	struct nfs3_linkres *result = data;
1884 	enum nfs_stat status;
1885 	int error;
1886 
1887 	error = decode_nfsstat3(xdr, &status);
1888 	if (unlikely(error))
1889 		goto out;
1890 	error = decode_post_op_attr(xdr, result->fattr);
1891 	if (unlikely(error))
1892 		goto out;
1893 	error = decode_wcc_data(xdr, result->dir_attr);
1894 	if (unlikely(error))
1895 		goto out;
1896 	if (status != NFS3_OK)
1897 		goto out_status;
1898 out:
1899 	return error;
1900 out_status:
1901 	return nfs3_stat_to_errno(status);
1902 }
1903 
1904 /**
1905  * nfs3_decode_dirent - Decode a single NFSv3 directory entry stored in
1906  *			the local page cache
1907  * @xdr: XDR stream where entry resides
1908  * @entry: buffer to fill in with entry data
1909  * @plus: boolean indicating whether this should be a readdirplus entry
1910  *
1911  * Returns zero if successful, otherwise a negative errno value is
1912  * returned.
1913  *
1914  * This function is not invoked during READDIR reply decoding, but
1915  * rather whenever an application invokes the getdents(2) system call
1916  * on a directory already in our cache.
1917  *
1918  * 3.3.16  entry3
1919  *
1920  *	struct entry3 {
1921  *		fileid3		fileid;
1922  *		filename3	name;
1923  *		cookie3		cookie;
1924  *		fhandle3	filehandle;
1925  *		post_op_attr3	attributes;
1926  *		entry3		*nextentry;
1927  *	};
1928  *
1929  * 3.3.17  entryplus3
1930  *	struct entryplus3 {
1931  *		fileid3		fileid;
1932  *		filename3	name;
1933  *		cookie3		cookie;
1934  *		post_op_attr	name_attributes;
1935  *		post_op_fh3	name_handle;
1936  *		entryplus3	*nextentry;
1937  *	};
1938  */
1939 int nfs3_decode_dirent(struct xdr_stream *xdr, struct nfs_entry *entry,
1940 		       bool plus)
1941 {
1942 	struct nfs_entry old = *entry;
1943 	__be32 *p;
1944 	int error;
1945 	u64 new_cookie;
1946 
1947 	p = xdr_inline_decode(xdr, 4);
1948 	if (unlikely(!p))
1949 		return -EAGAIN;
1950 	if (*p == xdr_zero) {
1951 		p = xdr_inline_decode(xdr, 4);
1952 		if (unlikely(!p))
1953 			return -EAGAIN;
1954 		if (*p == xdr_zero)
1955 			return -EAGAIN;
1956 		entry->eof = 1;
1957 		return -EBADCOOKIE;
1958 	}
1959 
1960 	error = decode_fileid3(xdr, &entry->ino);
1961 	if (unlikely(error))
1962 		return error;
1963 
1964 	error = decode_inline_filename3(xdr, &entry->name, &entry->len);
1965 	if (unlikely(error))
1966 		return error;
1967 
1968 	error = decode_cookie3(xdr, &new_cookie);
1969 	if (unlikely(error))
1970 		return error;
1971 
1972 	entry->d_type = DT_UNKNOWN;
1973 
1974 	if (plus) {
1975 		entry->fattr->valid = 0;
1976 		error = decode_post_op_attr(xdr, entry->fattr);
1977 		if (unlikely(error))
1978 			return error;
1979 		if (entry->fattr->valid & NFS_ATTR_FATTR_V3)
1980 			entry->d_type = nfs_umode_to_dtype(entry->fattr->mode);
1981 
1982 		if (entry->fattr->fileid != entry->ino) {
1983 			entry->fattr->mounted_on_fileid = entry->ino;
1984 			entry->fattr->valid |= NFS_ATTR_FATTR_MOUNTED_ON_FILEID;
1985 		}
1986 
1987 		/* In fact, a post_op_fh3: */
1988 		p = xdr_inline_decode(xdr, 4);
1989 		if (unlikely(!p))
1990 			return -EAGAIN;
1991 		if (*p != xdr_zero) {
1992 			error = decode_nfs_fh3(xdr, entry->fh);
1993 			if (unlikely(error)) {
1994 				if (error == -E2BIG)
1995 					goto out_truncated;
1996 				return error;
1997 			}
1998 		} else
1999 			zero_nfs_fh3(entry->fh);
2000 	}
2001 
2002 	entry->prev_cookie = entry->cookie;
2003 	entry->cookie = new_cookie;
2004 
2005 	return 0;
2006 
2007 out_truncated:
2008 	dprintk("NFS: directory entry contains invalid file handle\n");
2009 	*entry = old;
2010 	return -EAGAIN;
2011 }
2012 
2013 /*
2014  * 3.3.16  READDIR3res
2015  *
2016  *	struct dirlist3 {
2017  *		entry3		*entries;
2018  *		bool		eof;
2019  *	};
2020  *
2021  *	struct READDIR3resok {
2022  *		post_op_attr	dir_attributes;
2023  *		cookieverf3	cookieverf;
2024  *		dirlist3	reply;
2025  *	};
2026  *
2027  *	struct READDIR3resfail {
2028  *		post_op_attr	dir_attributes;
2029  *	};
2030  *
2031  *	union READDIR3res switch (nfsstat3 status) {
2032  *	case NFS3_OK:
2033  *		READDIR3resok	resok;
2034  *	default:
2035  *		READDIR3resfail	resfail;
2036  *	};
2037  *
2038  * Read the directory contents into the page cache, but otherwise
2039  * don't touch them.  The actual decoding is done by nfs3_decode_entry()
2040  * during subsequent nfs_readdir() calls.
2041  */
2042 static int decode_dirlist3(struct xdr_stream *xdr)
2043 {
2044 	return xdr_read_pages(xdr, xdr->buf->page_len);
2045 }
2046 
2047 static int decode_readdir3resok(struct xdr_stream *xdr,
2048 				struct nfs3_readdirres *result)
2049 {
2050 	int error;
2051 
2052 	error = decode_post_op_attr(xdr, result->dir_attr);
2053 	if (unlikely(error))
2054 		goto out;
2055 	/* XXX: do we need to check if result->verf != NULL ? */
2056 	error = decode_cookieverf3(xdr, result->verf);
2057 	if (unlikely(error))
2058 		goto out;
2059 	error = decode_dirlist3(xdr);
2060 out:
2061 	return error;
2062 }
2063 
2064 static int nfs3_xdr_dec_readdir3res(struct rpc_rqst *req,
2065 				    struct xdr_stream *xdr,
2066 				    void *data)
2067 {
2068 	struct nfs3_readdirres *result = data;
2069 	enum nfs_stat status;
2070 	int error;
2071 
2072 	error = decode_nfsstat3(xdr, &status);
2073 	if (unlikely(error))
2074 		goto out;
2075 	if (status != NFS3_OK)
2076 		goto out_default;
2077 	error = decode_readdir3resok(xdr, result);
2078 out:
2079 	return error;
2080 out_default:
2081 	error = decode_post_op_attr(xdr, result->dir_attr);
2082 	if (unlikely(error))
2083 		goto out;
2084 	return nfs3_stat_to_errno(status);
2085 }
2086 
2087 /*
2088  * 3.3.18  FSSTAT3res
2089  *
2090  *	struct FSSTAT3resok {
2091  *		post_op_attr	obj_attributes;
2092  *		size3		tbytes;
2093  *		size3		fbytes;
2094  *		size3		abytes;
2095  *		size3		tfiles;
2096  *		size3		ffiles;
2097  *		size3		afiles;
2098  *		uint32		invarsec;
2099  *	};
2100  *
2101  *	struct FSSTAT3resfail {
2102  *		post_op_attr	obj_attributes;
2103  *	};
2104  *
2105  *	union FSSTAT3res switch (nfsstat3 status) {
2106  *	case NFS3_OK:
2107  *		FSSTAT3resok	resok;
2108  *	default:
2109  *		FSSTAT3resfail	resfail;
2110  *	};
2111  */
2112 static int decode_fsstat3resok(struct xdr_stream *xdr,
2113 			       struct nfs_fsstat *result)
2114 {
2115 	__be32 *p;
2116 
2117 	p = xdr_inline_decode(xdr, 8 * 6 + 4);
2118 	if (unlikely(!p))
2119 		return -EIO;
2120 	p = xdr_decode_size3(p, &result->tbytes);
2121 	p = xdr_decode_size3(p, &result->fbytes);
2122 	p = xdr_decode_size3(p, &result->abytes);
2123 	p = xdr_decode_size3(p, &result->tfiles);
2124 	p = xdr_decode_size3(p, &result->ffiles);
2125 	xdr_decode_size3(p, &result->afiles);
2126 	/* ignore invarsec */
2127 	return 0;
2128 }
2129 
2130 static int nfs3_xdr_dec_fsstat3res(struct rpc_rqst *req,
2131 				   struct xdr_stream *xdr,
2132 				   void *data)
2133 {
2134 	struct nfs_fsstat *result = data;
2135 	enum nfs_stat status;
2136 	int error;
2137 
2138 	error = decode_nfsstat3(xdr, &status);
2139 	if (unlikely(error))
2140 		goto out;
2141 	error = decode_post_op_attr(xdr, result->fattr);
2142 	if (unlikely(error))
2143 		goto out;
2144 	if (status != NFS3_OK)
2145 		goto out_status;
2146 	error = decode_fsstat3resok(xdr, result);
2147 out:
2148 	return error;
2149 out_status:
2150 	return nfs3_stat_to_errno(status);
2151 }
2152 
2153 /*
2154  * 3.3.19  FSINFO3res
2155  *
2156  *	struct FSINFO3resok {
2157  *		post_op_attr	obj_attributes;
2158  *		uint32		rtmax;
2159  *		uint32		rtpref;
2160  *		uint32		rtmult;
2161  *		uint32		wtmax;
2162  *		uint32		wtpref;
2163  *		uint32		wtmult;
2164  *		uint32		dtpref;
2165  *		size3		maxfilesize;
2166  *		nfstime3	time_delta;
2167  *		uint32		properties;
2168  *	};
2169  *
2170  *	struct FSINFO3resfail {
2171  *		post_op_attr	obj_attributes;
2172  *	};
2173  *
2174  *	union FSINFO3res switch (nfsstat3 status) {
2175  *	case NFS3_OK:
2176  *		FSINFO3resok	resok;
2177  *	default:
2178  *		FSINFO3resfail	resfail;
2179  *	};
2180  */
2181 static int decode_fsinfo3resok(struct xdr_stream *xdr,
2182 			       struct nfs_fsinfo *result)
2183 {
2184 	__be32 *p;
2185 
2186 	p = xdr_inline_decode(xdr, 4 * 7 + 8 + 8 + 4);
2187 	if (unlikely(!p))
2188 		return -EIO;
2189 	result->rtmax  = be32_to_cpup(p++);
2190 	result->rtpref = be32_to_cpup(p++);
2191 	result->rtmult = be32_to_cpup(p++);
2192 	result->wtmax  = be32_to_cpup(p++);
2193 	result->wtpref = be32_to_cpup(p++);
2194 	result->wtmult = be32_to_cpup(p++);
2195 	result->dtpref = be32_to_cpup(p++);
2196 	p = xdr_decode_size3(p, &result->maxfilesize);
2197 	xdr_decode_nfstime3(p, &result->time_delta);
2198 
2199 	/* ignore properties */
2200 	result->lease_time = 0;
2201 	return 0;
2202 }
2203 
2204 static int nfs3_xdr_dec_fsinfo3res(struct rpc_rqst *req,
2205 				   struct xdr_stream *xdr,
2206 				   void *data)
2207 {
2208 	struct nfs_fsinfo *result = data;
2209 	enum nfs_stat status;
2210 	int error;
2211 
2212 	error = decode_nfsstat3(xdr, &status);
2213 	if (unlikely(error))
2214 		goto out;
2215 	error = decode_post_op_attr(xdr, result->fattr);
2216 	if (unlikely(error))
2217 		goto out;
2218 	if (status != NFS3_OK)
2219 		goto out_status;
2220 	error = decode_fsinfo3resok(xdr, result);
2221 out:
2222 	return error;
2223 out_status:
2224 	return nfs3_stat_to_errno(status);
2225 }
2226 
2227 /*
2228  * 3.3.20  PATHCONF3res
2229  *
2230  *	struct PATHCONF3resok {
2231  *		post_op_attr	obj_attributes;
2232  *		uint32		linkmax;
2233  *		uint32		name_max;
2234  *		bool		no_trunc;
2235  *		bool		chown_restricted;
2236  *		bool		case_insensitive;
2237  *		bool		case_preserving;
2238  *	};
2239  *
2240  *	struct PATHCONF3resfail {
2241  *		post_op_attr	obj_attributes;
2242  *	};
2243  *
2244  *	union PATHCONF3res switch (nfsstat3 status) {
2245  *	case NFS3_OK:
2246  *		PATHCONF3resok	resok;
2247  *	default:
2248  *		PATHCONF3resfail resfail;
2249  *	};
2250  */
2251 static int decode_pathconf3resok(struct xdr_stream *xdr,
2252 				 struct nfs_pathconf *result)
2253 {
2254 	__be32 *p;
2255 
2256 	p = xdr_inline_decode(xdr, 4 * 6);
2257 	if (unlikely(!p))
2258 		return -EIO;
2259 	result->max_link = be32_to_cpup(p++);
2260 	result->max_namelen = be32_to_cpup(p);
2261 	/* ignore remaining fields */
2262 	return 0;
2263 }
2264 
2265 static int nfs3_xdr_dec_pathconf3res(struct rpc_rqst *req,
2266 				     struct xdr_stream *xdr,
2267 				     void *data)
2268 {
2269 	struct nfs_pathconf *result = data;
2270 	enum nfs_stat status;
2271 	int error;
2272 
2273 	error = decode_nfsstat3(xdr, &status);
2274 	if (unlikely(error))
2275 		goto out;
2276 	error = decode_post_op_attr(xdr, result->fattr);
2277 	if (unlikely(error))
2278 		goto out;
2279 	if (status != NFS3_OK)
2280 		goto out_status;
2281 	error = decode_pathconf3resok(xdr, result);
2282 out:
2283 	return error;
2284 out_status:
2285 	return nfs3_stat_to_errno(status);
2286 }
2287 
2288 /*
2289  * 3.3.21  COMMIT3res
2290  *
2291  *	struct COMMIT3resok {
2292  *		wcc_data	file_wcc;
2293  *		writeverf3	verf;
2294  *	};
2295  *
2296  *	struct COMMIT3resfail {
2297  *		wcc_data	file_wcc;
2298  *	};
2299  *
2300  *	union COMMIT3res switch (nfsstat3 status) {
2301  *	case NFS3_OK:
2302  *		COMMIT3resok	resok;
2303  *	default:
2304  *		COMMIT3resfail	resfail;
2305  *	};
2306  */
2307 static int nfs3_xdr_dec_commit3res(struct rpc_rqst *req,
2308 				   struct xdr_stream *xdr,
2309 				   void *data)
2310 {
2311 	struct nfs_commitres *result = data;
2312 	enum nfs_stat status;
2313 	int error;
2314 
2315 	error = decode_nfsstat3(xdr, &status);
2316 	if (unlikely(error))
2317 		goto out;
2318 	error = decode_wcc_data(xdr, result->fattr);
2319 	if (unlikely(error))
2320 		goto out;
2321 	result->op_status = status;
2322 	if (status != NFS3_OK)
2323 		goto out_status;
2324 	error = decode_writeverf3(xdr, &result->verf->verifier);
2325 out:
2326 	return error;
2327 out_status:
2328 	return nfs3_stat_to_errno(status);
2329 }
2330 
2331 #ifdef CONFIG_NFS_V3_ACL
2332 
2333 static inline int decode_getacl3resok(struct xdr_stream *xdr,
2334 				      struct nfs3_getaclres *result)
2335 {
2336 	struct posix_acl **acl;
2337 	unsigned int *aclcnt;
2338 	size_t hdrlen;
2339 	int error;
2340 
2341 	error = decode_post_op_attr(xdr, result->fattr);
2342 	if (unlikely(error))
2343 		goto out;
2344 	error = decode_uint32(xdr, &result->mask);
2345 	if (unlikely(error))
2346 		goto out;
2347 	error = -EINVAL;
2348 	if (result->mask & ~(NFS_ACL|NFS_ACLCNT|NFS_DFACL|NFS_DFACLCNT))
2349 		goto out;
2350 
2351 	hdrlen = xdr_stream_pos(xdr);
2352 
2353 	acl = NULL;
2354 	if (result->mask & NFS_ACL)
2355 		acl = &result->acl_access;
2356 	aclcnt = NULL;
2357 	if (result->mask & NFS_ACLCNT)
2358 		aclcnt = &result->acl_access_count;
2359 	error = nfsacl_decode(xdr->buf, hdrlen, aclcnt, acl);
2360 	if (unlikely(error <= 0))
2361 		goto out;
2362 
2363 	acl = NULL;
2364 	if (result->mask & NFS_DFACL)
2365 		acl = &result->acl_default;
2366 	aclcnt = NULL;
2367 	if (result->mask & NFS_DFACLCNT)
2368 		aclcnt = &result->acl_default_count;
2369 	error = nfsacl_decode(xdr->buf, hdrlen + error, aclcnt, acl);
2370 	if (unlikely(error <= 0))
2371 		return error;
2372 	error = 0;
2373 out:
2374 	return error;
2375 }
2376 
2377 static int nfs3_xdr_dec_getacl3res(struct rpc_rqst *req,
2378 				   struct xdr_stream *xdr,
2379 				   void *result)
2380 {
2381 	enum nfs_stat status;
2382 	int error;
2383 
2384 	error = decode_nfsstat3(xdr, &status);
2385 	if (unlikely(error))
2386 		goto out;
2387 	if (status != NFS3_OK)
2388 		goto out_default;
2389 	error = decode_getacl3resok(xdr, result);
2390 out:
2391 	return error;
2392 out_default:
2393 	return nfs3_stat_to_errno(status);
2394 }
2395 
2396 static int nfs3_xdr_dec_setacl3res(struct rpc_rqst *req,
2397 				   struct xdr_stream *xdr,
2398 				   void *result)
2399 {
2400 	enum nfs_stat status;
2401 	int error;
2402 
2403 	error = decode_nfsstat3(xdr, &status);
2404 	if (unlikely(error))
2405 		goto out;
2406 	if (status != NFS3_OK)
2407 		goto out_default;
2408 	error = decode_post_op_attr(xdr, result);
2409 out:
2410 	return error;
2411 out_default:
2412 	return nfs3_stat_to_errno(status);
2413 }
2414 
2415 #endif  /* CONFIG_NFS_V3_ACL */
2416 
2417 
2418 /*
2419  * We need to translate between nfs status return values and
2420  * the local errno values which may not be the same.
2421  */
2422 static const struct {
2423 	int stat;
2424 	int errno;
2425 } nfs_errtbl[] = {
2426 	{ NFS_OK,		0		},
2427 	{ NFSERR_PERM,		-EPERM		},
2428 	{ NFSERR_NOENT,		-ENOENT		},
2429 	{ NFSERR_IO,		-errno_NFSERR_IO},
2430 	{ NFSERR_NXIO,		-ENXIO		},
2431 /*	{ NFSERR_EAGAIN,	-EAGAIN		}, */
2432 	{ NFSERR_ACCES,		-EACCES		},
2433 	{ NFSERR_EXIST,		-EEXIST		},
2434 	{ NFSERR_XDEV,		-EXDEV		},
2435 	{ NFSERR_NODEV,		-ENODEV		},
2436 	{ NFSERR_NOTDIR,	-ENOTDIR	},
2437 	{ NFSERR_ISDIR,		-EISDIR		},
2438 	{ NFSERR_INVAL,		-EINVAL		},
2439 	{ NFSERR_FBIG,		-EFBIG		},
2440 	{ NFSERR_NOSPC,		-ENOSPC		},
2441 	{ NFSERR_ROFS,		-EROFS		},
2442 	{ NFSERR_MLINK,		-EMLINK		},
2443 	{ NFSERR_NAMETOOLONG,	-ENAMETOOLONG	},
2444 	{ NFSERR_NOTEMPTY,	-ENOTEMPTY	},
2445 	{ NFSERR_DQUOT,		-EDQUOT		},
2446 	{ NFSERR_STALE,		-ESTALE		},
2447 	{ NFSERR_REMOTE,	-EREMOTE	},
2448 #ifdef EWFLUSH
2449 	{ NFSERR_WFLUSH,	-EWFLUSH	},
2450 #endif
2451 	{ NFSERR_BADHANDLE,	-EBADHANDLE	},
2452 	{ NFSERR_NOT_SYNC,	-ENOTSYNC	},
2453 	{ NFSERR_BAD_COOKIE,	-EBADCOOKIE	},
2454 	{ NFSERR_NOTSUPP,	-ENOTSUPP	},
2455 	{ NFSERR_TOOSMALL,	-ETOOSMALL	},
2456 	{ NFSERR_SERVERFAULT,	-EREMOTEIO	},
2457 	{ NFSERR_BADTYPE,	-EBADTYPE	},
2458 	{ NFSERR_JUKEBOX,	-EJUKEBOX	},
2459 	{ -1,			-EIO		}
2460 };
2461 
2462 /**
2463  * nfs3_stat_to_errno - convert an NFS status code to a local errno
2464  * @status: NFS status code to convert
2465  *
2466  * Returns a local errno value, or -EIO if the NFS status code is
2467  * not recognized.  This function is used jointly by NFSv2 and NFSv3.
2468  */
2469 static int nfs3_stat_to_errno(enum nfs_stat status)
2470 {
2471 	int i;
2472 
2473 	for (i = 0; nfs_errtbl[i].stat != -1; i++) {
2474 		if (nfs_errtbl[i].stat == (int)status)
2475 			return nfs_errtbl[i].errno;
2476 	}
2477 	dprintk("NFS: Unrecognized nfs status value: %u\n", status);
2478 	return nfs_errtbl[i].errno;
2479 }
2480 
2481 
2482 #define PROC(proc, argtype, restype, timer)				\
2483 [NFS3PROC_##proc] = {							\
2484 	.p_proc      = NFS3PROC_##proc,					\
2485 	.p_encode    = nfs3_xdr_enc_##argtype##3args,			\
2486 	.p_decode    = nfs3_xdr_dec_##restype##3res,			\
2487 	.p_arglen    = NFS3_##argtype##args_sz,				\
2488 	.p_replen    = NFS3_##restype##res_sz,				\
2489 	.p_timer     = timer,						\
2490 	.p_statidx   = NFS3PROC_##proc,					\
2491 	.p_name      = #proc,						\
2492 	}
2493 
2494 const struct rpc_procinfo nfs3_procedures[] = {
2495 	PROC(GETATTR,		getattr,	getattr,	1),
2496 	PROC(SETATTR,		setattr,	setattr,	0),
2497 	PROC(LOOKUP,		lookup,		lookup,		2),
2498 	PROC(ACCESS,		access,		access,		1),
2499 	PROC(READLINK,		readlink,	readlink,	3),
2500 	PROC(READ,		read,		read,		3),
2501 	PROC(WRITE,		write,		write,		4),
2502 	PROC(CREATE,		create,		create,		0),
2503 	PROC(MKDIR,		mkdir,		create,		0),
2504 	PROC(SYMLINK,		symlink,	create,		0),
2505 	PROC(MKNOD,		mknod,		create,		0),
2506 	PROC(REMOVE,		remove,		remove,		0),
2507 	PROC(RMDIR,		lookup,		setattr,	0),
2508 	PROC(RENAME,		rename,		rename,		0),
2509 	PROC(LINK,		link,		link,		0),
2510 	PROC(READDIR,		readdir,	readdir,	3),
2511 	PROC(READDIRPLUS,	readdirplus,	readdir,	3),
2512 	PROC(FSSTAT,		getattr,	fsstat,		0),
2513 	PROC(FSINFO,		getattr,	fsinfo,		0),
2514 	PROC(PATHCONF,		getattr,	pathconf,	0),
2515 	PROC(COMMIT,		commit,		commit,		5),
2516 };
2517 
2518 static unsigned int nfs_version3_counts[ARRAY_SIZE(nfs3_procedures)];
2519 const struct rpc_version nfs_version3 = {
2520 	.number			= 3,
2521 	.nrprocs		= ARRAY_SIZE(nfs3_procedures),
2522 	.procs			= nfs3_procedures,
2523 	.counts			= nfs_version3_counts,
2524 };
2525 
2526 #ifdef CONFIG_NFS_V3_ACL
2527 static const struct rpc_procinfo nfs3_acl_procedures[] = {
2528 	[ACLPROC3_GETACL] = {
2529 		.p_proc = ACLPROC3_GETACL,
2530 		.p_encode = nfs3_xdr_enc_getacl3args,
2531 		.p_decode = nfs3_xdr_dec_getacl3res,
2532 		.p_arglen = ACL3_getaclargs_sz,
2533 		.p_replen = ACL3_getaclres_sz,
2534 		.p_timer = 1,
2535 		.p_name = "GETACL",
2536 	},
2537 	[ACLPROC3_SETACL] = {
2538 		.p_proc = ACLPROC3_SETACL,
2539 		.p_encode = nfs3_xdr_enc_setacl3args,
2540 		.p_decode = nfs3_xdr_dec_setacl3res,
2541 		.p_arglen = ACL3_setaclargs_sz,
2542 		.p_replen = ACL3_setaclres_sz,
2543 		.p_timer = 0,
2544 		.p_name = "SETACL",
2545 	},
2546 };
2547 
2548 static unsigned int nfs3_acl_counts[ARRAY_SIZE(nfs3_acl_procedures)];
2549 const struct rpc_version nfsacl_version3 = {
2550 	.number			= 3,
2551 	.nrprocs		= ARRAY_SIZE(nfs3_acl_procedures),
2552 	.procs			= nfs3_acl_procedures,
2553 	.counts			= nfs3_acl_counts,
2554 };
2555 #endif  /* CONFIG_NFS_V3_ACL */
2556