hc
2024-02-20 102a0743326a03cd1a1202ceda21e175b7d3575c
kernel/fs/nfs/nfs2xdr.c
....@@ -22,6 +22,7 @@
2222 #include <linux/nfs.h>
2323 #include <linux/nfs2.h>
2424 #include <linux/nfs_fs.h>
25
+#include "nfstrace.h"
2526 #include "internal.h"
2627
2728 #define NFSDBG_FACILITY NFSDBG_XDR
....@@ -55,40 +56,14 @@
5556
5657 #define NFS_attrstat_sz (1+NFS_fattr_sz)
5758 #define NFS_diropres_sz (1+NFS_fhandle_sz+NFS_fattr_sz)
58
-#define NFS_readlinkres_sz (2)
59
-#define NFS_readres_sz (1+NFS_fattr_sz+1)
59
+#define NFS_readlinkres_sz (2+1)
60
+#define NFS_readres_sz (1+NFS_fattr_sz+1+1)
6061 #define NFS_writeres_sz (NFS_attrstat_sz)
6162 #define NFS_stat_sz (1)
62
-#define NFS_readdirres_sz (1)
63
+#define NFS_readdirres_sz (1+1)
6364 #define NFS_statfsres_sz (1+NFS_info_sz)
6465
6566 static int nfs_stat_to_errno(enum nfs_stat);
66
-
67
-/*
68
- * While encoding arguments, set up the reply buffer in advance to
69
- * receive reply data directly into the page cache.
70
- */
71
-static void prepare_reply_buffer(struct rpc_rqst *req, struct page **pages,
72
- unsigned int base, unsigned int len,
73
- unsigned int bufsize)
74
-{
75
- struct rpc_auth *auth = req->rq_cred->cr_auth;
76
- unsigned int replen;
77
-
78
- replen = RPC_REPHDRSIZE + auth->au_rslack + bufsize;
79
- xdr_inline_pages(&req->rq_rcv_buf, replen << 2, pages, base, len);
80
-}
81
-
82
-/*
83
- * Handle decode buffer overflows out-of-line.
84
- */
85
-static void print_overflow_msg(const char *func, const struct xdr_stream *xdr)
86
-{
87
- dprintk("NFS: %s prematurely hit the end of our receive buffer. "
88
- "Remaining buffer length is %tu words.\n",
89
- func, xdr->end - xdr->p);
90
-}
91
-
9267
9368 /*
9469 * Encode/decode NFSv2 basic data types
....@@ -101,6 +76,20 @@
10176 * or decoded inline.
10277 */
10378
79
+static struct user_namespace *rpc_userns(const struct rpc_clnt *clnt)
80
+{
81
+ if (clnt && clnt->cl_cred)
82
+ return clnt->cl_cred->user_ns;
83
+ return &init_user_ns;
84
+}
85
+
86
+static struct user_namespace *rpc_rqst_userns(const struct rpc_rqst *rqstp)
87
+{
88
+ if (rqstp->rq_task)
89
+ return rpc_userns(rqstp->rq_task->tk_client);
90
+ return &init_user_ns;
91
+}
92
+
10493 /*
10594 * typedef opaque nfsdata<>;
10695 */
....@@ -110,8 +99,8 @@
11099 __be32 *p;
111100
112101 p = xdr_inline_decode(xdr, 4);
113
- if (unlikely(p == NULL))
114
- goto out_overflow;
102
+ if (unlikely(!p))
103
+ return -EIO;
115104 count = be32_to_cpup(p);
116105 recvd = xdr_read_pages(xdr, count);
117106 if (unlikely(count > recvd))
....@@ -125,9 +114,6 @@
125114 "count %u > recvd %u\n", count, recvd);
126115 count = recvd;
127116 goto out;
128
-out_overflow:
129
- print_overflow_msg(__func__, xdr);
130
- return -EIO;
131117 }
132118
133119 /*
....@@ -157,13 +143,16 @@
157143 __be32 *p;
158144
159145 p = xdr_inline_decode(xdr, 4);
160
- if (unlikely(p == NULL))
161
- goto out_overflow;
162
- *status = be32_to_cpup(p);
146
+ if (unlikely(!p))
147
+ return -EIO;
148
+ if (unlikely(*p != cpu_to_be32(NFS_OK)))
149
+ goto out_status;
150
+ *status = 0;
163151 return 0;
164
-out_overflow:
165
- print_overflow_msg(__func__, xdr);
166
- return -EIO;
152
+out_status:
153
+ *status = be32_to_cpup(p);
154
+ trace_nfs_xdr_status(xdr, (int)*status);
155
+ return 0;
167156 }
168157
169158 /*
....@@ -205,14 +194,11 @@
205194 __be32 *p;
206195
207196 p = xdr_inline_decode(xdr, NFS2_FHSIZE);
208
- if (unlikely(p == NULL))
209
- goto out_overflow;
197
+ if (unlikely(!p))
198
+ return -EIO;
210199 fh->size = NFS2_FHSIZE;
211200 memcpy(fh->data, p, NFS2_FHSIZE);
212201 return 0;
213
-out_overflow:
214
- print_overflow_msg(__func__, xdr);
215
- return -EIO;
216202 }
217203
218204 /*
....@@ -223,9 +209,9 @@
223209 * unsigned int useconds;
224210 * };
225211 */
226
-static __be32 *xdr_encode_time(__be32 *p, const struct timespec *timep)
212
+static __be32 *xdr_encode_time(__be32 *p, const struct timespec64 *timep)
227213 {
228
- *p++ = cpu_to_be32(timep->tv_sec);
214
+ *p++ = cpu_to_be32((u32)timep->tv_sec);
229215 if (timep->tv_nsec != 0)
230216 *p++ = cpu_to_be32(timep->tv_nsec / NSEC_PER_USEC);
231217 else
....@@ -241,14 +227,14 @@
241227 * Illustrated" by Brent Callaghan, Addison-Wesley, ISBN 0-201-32750-5.
242228 */
243229 static __be32 *xdr_encode_current_server_time(__be32 *p,
244
- const struct timespec *timep)
230
+ const struct timespec64 *timep)
245231 {
246232 *p++ = cpu_to_be32(timep->tv_sec);
247233 *p++ = cpu_to_be32(1000000);
248234 return p;
249235 }
250236
251
-static __be32 *xdr_decode_time(__be32 *p, struct timespec *timep)
237
+static __be32 *xdr_decode_time(__be32 *p, struct timespec64 *timep)
252238 {
253239 timep->tv_sec = be32_to_cpup(p++);
254240 timep->tv_nsec = be32_to_cpup(p++) * NSEC_PER_USEC;
....@@ -276,14 +262,15 @@
276262 * };
277263 *
278264 */
279
-static int decode_fattr(struct xdr_stream *xdr, struct nfs_fattr *fattr)
265
+static int decode_fattr(struct xdr_stream *xdr, struct nfs_fattr *fattr,
266
+ struct user_namespace *userns)
280267 {
281268 u32 rdev, type;
282269 __be32 *p;
283270
284271 p = xdr_inline_decode(xdr, NFS_fattr_sz << 2);
285
- if (unlikely(p == NULL))
286
- goto out_overflow;
272
+ if (unlikely(!p))
273
+ return -EIO;
287274
288275 fattr->valid |= NFS_ATTR_FATTR_V2;
289276
....@@ -291,10 +278,10 @@
291278
292279 fattr->mode = be32_to_cpup(p++);
293280 fattr->nlink = be32_to_cpup(p++);
294
- fattr->uid = make_kuid(&init_user_ns, be32_to_cpup(p++));
281
+ fattr->uid = make_kuid(userns, be32_to_cpup(p++));
295282 if (!uid_valid(fattr->uid))
296283 goto out_uid;
297
- fattr->gid = make_kgid(&init_user_ns, be32_to_cpup(p++));
284
+ fattr->gid = make_kgid(userns, be32_to_cpup(p++));
298285 if (!gid_valid(fattr->gid))
299286 goto out_gid;
300287
....@@ -325,9 +312,6 @@
325312 out_gid:
326313 dprintk("NFS: returned invalid gid\n");
327314 return -EINVAL;
328
-out_overflow:
329
- print_overflow_msg(__func__, xdr);
330
- return -EIO;
331315 }
332316
333317 /*
....@@ -352,9 +336,9 @@
352336 return p;
353337 }
354338
355
-static void encode_sattr(struct xdr_stream *xdr, const struct iattr *attr)
339
+static void encode_sattr(struct xdr_stream *xdr, const struct iattr *attr,
340
+ struct user_namespace *userns)
356341 {
357
- struct timespec ts;
358342 __be32 *p;
359343
360344 p = xdr_reserve_space(xdr, NFS_sattr_sz << 2);
....@@ -364,11 +348,11 @@
364348 else
365349 *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
366350 if (attr->ia_valid & ATTR_UID)
367
- *p++ = cpu_to_be32(from_kuid(&init_user_ns, attr->ia_uid));
351
+ *p++ = cpu_to_be32(from_kuid_munged(userns, attr->ia_uid));
368352 else
369353 *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
370354 if (attr->ia_valid & ATTR_GID)
371
- *p++ = cpu_to_be32(from_kgid(&init_user_ns, attr->ia_gid));
355
+ *p++ = cpu_to_be32(from_kgid_munged(userns, attr->ia_gid));
372356 else
373357 *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
374358 if (attr->ia_valid & ATTR_SIZE)
....@@ -376,21 +360,17 @@
376360 else
377361 *p++ = cpu_to_be32(NFS2_SATTR_NOT_SET);
378362
379
- if (attr->ia_valid & ATTR_ATIME_SET) {
380
- ts = timespec64_to_timespec(attr->ia_atime);
381
- p = xdr_encode_time(p, &ts);
382
- } else if (attr->ia_valid & ATTR_ATIME) {
383
- ts = timespec64_to_timespec(attr->ia_atime);
384
- p = xdr_encode_current_server_time(p, &ts);
385
- } else
363
+ if (attr->ia_valid & ATTR_ATIME_SET)
364
+ p = xdr_encode_time(p, &attr->ia_atime);
365
+ else if (attr->ia_valid & ATTR_ATIME)
366
+ p = xdr_encode_current_server_time(p, &attr->ia_atime);
367
+ else
386368 p = xdr_time_not_set(p);
387
- if (attr->ia_valid & ATTR_MTIME_SET) {
388
- ts = timespec64_to_timespec(attr->ia_mtime);
389
- xdr_encode_time(p, &ts);
390
- } else if (attr->ia_valid & ATTR_MTIME) {
391
- ts = timespec64_to_timespec(attr->ia_mtime);
392
- xdr_encode_current_server_time(p, &ts);
393
- } else
369
+ if (attr->ia_valid & ATTR_MTIME_SET)
370
+ xdr_encode_time(p, &attr->ia_mtime);
371
+ else if (attr->ia_valid & ATTR_MTIME)
372
+ xdr_encode_current_server_time(p, &attr->ia_mtime);
373
+ else
394374 xdr_time_not_set(p);
395375 }
396376
....@@ -416,23 +396,20 @@
416396 u32 count;
417397
418398 p = xdr_inline_decode(xdr, 4);
419
- if (unlikely(p == NULL))
420
- goto out_overflow;
399
+ if (unlikely(!p))
400
+ return -EIO;
421401 count = be32_to_cpup(p);
422402 if (count > NFS3_MAXNAMLEN)
423403 goto out_nametoolong;
424404 p = xdr_inline_decode(xdr, count);
425
- if (unlikely(p == NULL))
426
- goto out_overflow;
405
+ if (unlikely(!p))
406
+ return -EIO;
427407 *name = (const char *)p;
428408 *length = count;
429409 return 0;
430410 out_nametoolong:
431411 dprintk("NFS: returned filename too long: %u\n", count);
432412 return -ENAMETOOLONG;
433
-out_overflow:
434
- print_overflow_msg(__func__, xdr);
435
- return -EIO;
436413 }
437414
438415 /*
....@@ -455,8 +432,8 @@
455432 __be32 *p;
456433
457434 p = xdr_inline_decode(xdr, 4);
458
- if (unlikely(p == NULL))
459
- goto out_overflow;
435
+ if (unlikely(!p))
436
+ return -EIO;
460437 length = be32_to_cpup(p);
461438 if (unlikely(length >= xdr->buf->page_len || length > NFS_MAXPATHLEN))
462439 goto out_size;
....@@ -472,9 +449,6 @@
472449 dprintk("NFS: server cheating in pathname result: "
473450 "length %u > received %u\n", length, recvd);
474451 return -EIO;
475
-out_overflow:
476
- print_overflow_msg(__func__, xdr);
477
- return -EIO;
478452 }
479453
480454 /*
....@@ -488,7 +462,8 @@
488462 * };
489463 */
490464 static int decode_attrstat(struct xdr_stream *xdr, struct nfs_fattr *result,
491
- __u32 *op_status)
465
+ __u32 *op_status,
466
+ struct user_namespace *userns)
492467 {
493468 enum nfs_stat status;
494469 int error;
....@@ -500,7 +475,7 @@
500475 *op_status = status;
501476 if (status != NFS_OK)
502477 goto out_default;
503
- error = decode_fattr(xdr, result);
478
+ error = decode_fattr(xdr, result, userns);
504479 out:
505480 return error;
506481 out_default:
....@@ -535,19 +510,21 @@
535510 * void;
536511 * };
537512 */
538
-static int decode_diropok(struct xdr_stream *xdr, struct nfs_diropok *result)
513
+static int decode_diropok(struct xdr_stream *xdr, struct nfs_diropok *result,
514
+ struct user_namespace *userns)
539515 {
540516 int error;
541517
542518 error = decode_fhandle(xdr, result->fh);
543519 if (unlikely(error))
544520 goto out;
545
- error = decode_fattr(xdr, result->fattr);
521
+ error = decode_fattr(xdr, result->fattr, userns);
546522 out:
547523 return error;
548524 }
549525
550
-static int decode_diropres(struct xdr_stream *xdr, struct nfs_diropok *result)
526
+static int decode_diropres(struct xdr_stream *xdr, struct nfs_diropok *result,
527
+ struct user_namespace *userns)
551528 {
552529 enum nfs_stat status;
553530 int error;
....@@ -557,7 +534,7 @@
557534 goto out;
558535 if (status != NFS_OK)
559536 goto out_default;
560
- error = decode_diropok(xdr, result);
537
+ error = decode_diropok(xdr, result, userns);
561538 out:
562539 return error;
563540 out_default:
....@@ -596,7 +573,7 @@
596573 const struct nfs_sattrargs *args = data;
597574
598575 encode_fhandle(xdr, args->fh);
599
- encode_sattr(xdr, args->sattr);
576
+ encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
600577 }
601578
602579 static void nfs2_xdr_enc_diropargs(struct rpc_rqst *req,
....@@ -615,8 +592,8 @@
615592 const struct nfs_readlinkargs *args = data;
616593
617594 encode_fhandle(xdr, args->fh);
618
- prepare_reply_buffer(req, args->pages, args->pgbase,
619
- args->pglen, NFS_readlinkres_sz);
595
+ rpc_prepare_reply_pages(req, args->pages, args->pgbase,
596
+ args->pglen, NFS_readlinkres_sz);
620597 }
621598
622599 /*
....@@ -651,8 +628,8 @@
651628 const struct nfs_pgio_args *args = data;
652629
653630 encode_readargs(xdr, args);
654
- prepare_reply_buffer(req, args->pages, args->pgbase,
655
- args->count, NFS_readres_sz);
631
+ rpc_prepare_reply_pages(req, args->pages, args->pgbase,
632
+ args->count, NFS_readres_sz);
656633 req->rq_rcv_buf.flags |= XDRBUF_READ;
657634 }
658635
....@@ -711,7 +688,7 @@
711688 const struct nfs_createargs *args = data;
712689
713690 encode_diropargs(xdr, args->fh, args->name, args->len);
714
- encode_sattr(xdr, args->sattr);
691
+ encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
715692 }
716693
717694 static void nfs2_xdr_enc_removeargs(struct rpc_rqst *req,
....@@ -778,7 +755,7 @@
778755
779756 encode_diropargs(xdr, args->fromfh, args->fromname, args->fromlen);
780757 encode_path(xdr, args->pages, args->pathlen);
781
- encode_sattr(xdr, args->sattr);
758
+ encode_sattr(xdr, args->sattr, rpc_rqst_userns(req));
782759 }
783760
784761 /*
....@@ -809,8 +786,8 @@
809786 const struct nfs_readdirargs *args = data;
810787
811788 encode_readdirargs(xdr, args);
812
- prepare_reply_buffer(req, args->pages, 0,
813
- args->count, NFS_readdirres_sz);
789
+ rpc_prepare_reply_pages(req, args->pages, 0,
790
+ args->count, NFS_readdirres_sz);
814791 }
815792
816793 /*
....@@ -840,13 +817,13 @@
840817 static int nfs2_xdr_dec_attrstat(struct rpc_rqst *req, struct xdr_stream *xdr,
841818 void *result)
842819 {
843
- return decode_attrstat(xdr, result, NULL);
820
+ return decode_attrstat(xdr, result, NULL, rpc_rqst_userns(req));
844821 }
845822
846823 static int nfs2_xdr_dec_diropres(struct rpc_rqst *req, struct xdr_stream *xdr,
847824 void *result)
848825 {
849
- return decode_diropres(xdr, result);
826
+ return decode_diropres(xdr, result, rpc_rqst_userns(req));
850827 }
851828
852829 /*
....@@ -901,7 +878,7 @@
901878 result->op_status = status;
902879 if (status != NFS_OK)
903880 goto out_default;
904
- error = decode_fattr(xdr, result->fattr);
881
+ error = decode_fattr(xdr, result->fattr, rpc_rqst_userns(req));
905882 if (unlikely(error))
906883 goto out;
907884 error = decode_nfsdata(xdr, result);
....@@ -918,7 +895,8 @@
918895
919896 /* All NFSv2 writes are "file sync" writes */
920897 result->verf->committed = NFS_FILE_SYNC;
921
- return decode_attrstat(xdr, result->fattr, &result->op_status);
898
+ return decode_attrstat(xdr, result->fattr, &result->op_status,
899
+ rpc_rqst_userns(req));
922900 }
923901
924902 /**
....@@ -951,12 +929,12 @@
951929 int error;
952930
953931 p = xdr_inline_decode(xdr, 4);
954
- if (unlikely(p == NULL))
955
- goto out_overflow;
932
+ if (unlikely(!p))
933
+ return -EAGAIN;
956934 if (*p++ == xdr_zero) {
957935 p = xdr_inline_decode(xdr, 4);
958
- if (unlikely(p == NULL))
959
- goto out_overflow;
936
+ if (unlikely(!p))
937
+ return -EAGAIN;
960938 if (*p++ == xdr_zero)
961939 return -EAGAIN;
962940 entry->eof = 1;
....@@ -964,13 +942,13 @@
964942 }
965943
966944 p = xdr_inline_decode(xdr, 4);
967
- if (unlikely(p == NULL))
968
- goto out_overflow;
945
+ if (unlikely(!p))
946
+ return -EAGAIN;
969947 entry->ino = be32_to_cpup(p);
970948
971949 error = decode_filename_inline(xdr, &entry->name, &entry->len);
972950 if (unlikely(error))
973
- return error;
951
+ return error == -ENAMETOOLONG ? -ENAMETOOLONG : -EAGAIN;
974952
975953 /*
976954 * The type (size and byte order) of nfscookie isn't defined in
....@@ -978,17 +956,13 @@
978956 */
979957 entry->prev_cookie = entry->cookie;
980958 p = xdr_inline_decode(xdr, 4);
981
- if (unlikely(p == NULL))
982
- goto out_overflow;
959
+ if (unlikely(!p))
960
+ return -EAGAIN;
983961 entry->cookie = be32_to_cpup(p);
984962
985963 entry->d_type = DT_UNKNOWN;
986964
987965 return 0;
988
-
989
-out_overflow:
990
- print_overflow_msg(__func__, xdr);
991
- return -EAGAIN;
992966 }
993967
994968 /*
....@@ -1052,17 +1026,14 @@
10521026 __be32 *p;
10531027
10541028 p = xdr_inline_decode(xdr, NFS_info_sz << 2);
1055
- if (unlikely(p == NULL))
1056
- goto out_overflow;
1029
+ if (unlikely(!p))
1030
+ return -EIO;
10571031 result->tsize = be32_to_cpup(p++);
10581032 result->bsize = be32_to_cpup(p++);
10591033 result->blocks = be32_to_cpup(p++);
10601034 result->bfree = be32_to_cpup(p++);
10611035 result->bavail = be32_to_cpup(p);
10621036 return 0;
1063
-out_overflow:
1064
- print_overflow_msg(__func__, xdr);
1065
- return -EIO;
10661037 }
10671038
10681039 static int nfs2_xdr_dec_statfsres(struct rpc_rqst *req, struct xdr_stream *xdr,