Linux kernel mirror (for testing)
git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel
os
linux
1// SPDX-License-Identifier: GPL-2.0-only
2/*
3 * linux/fs/nfs/fs_context.c
4 *
5 * Copyright (C) 1992 Rick Sladkey
6 * Conversion to new mount api Copyright (C) David Howells
7 *
8 * NFS mount handling.
9 *
10 * Split from fs/nfs/super.c by David Howells <dhowells@redhat.com>
11 */
12
13#include <linux/compat.h>
14#include <linux/module.h>
15#include <linux/fs.h>
16#include <linux/fs_context.h>
17#include <linux/fs_parser.h>
18#include <linux/nfs_fs.h>
19#include <linux/nfs_mount.h>
20#include <linux/nfs4_mount.h>
21#include "nfs.h"
22#include "internal.h"
23
24#define NFSDBG_FACILITY NFSDBG_MOUNT
25
26#if IS_ENABLED(CONFIG_NFS_V3)
27#define NFS_DEFAULT_VERSION 3
28#else
29#define NFS_DEFAULT_VERSION 2
30#endif
31
32#define NFS_MAX_CONNECTIONS 16
33
34enum nfs_param {
35 Opt_ac,
36 Opt_acdirmax,
37 Opt_acdirmin,
38 Opt_acl,
39 Opt_acregmax,
40 Opt_acregmin,
41 Opt_actimeo,
42 Opt_addr,
43 Opt_bg,
44 Opt_bsize,
45 Opt_clientaddr,
46 Opt_cto,
47 Opt_fg,
48 Opt_fscache,
49 Opt_fscache_flag,
50 Opt_hard,
51 Opt_intr,
52 Opt_local_lock,
53 Opt_lock,
54 Opt_lookupcache,
55 Opt_migration,
56 Opt_minorversion,
57 Opt_mountaddr,
58 Opt_mounthost,
59 Opt_mountport,
60 Opt_mountproto,
61 Opt_mountvers,
62 Opt_namelen,
63 Opt_nconnect,
64 Opt_max_connect,
65 Opt_port,
66 Opt_posix,
67 Opt_proto,
68 Opt_rdirplus,
69 Opt_rdma,
70 Opt_resvport,
71 Opt_retrans,
72 Opt_retry,
73 Opt_rsize,
74 Opt_sec,
75 Opt_sharecache,
76 Opt_sloppy,
77 Opt_soft,
78 Opt_softerr,
79 Opt_softreval,
80 Opt_source,
81 Opt_tcp,
82 Opt_timeo,
83 Opt_udp,
84 Opt_v,
85 Opt_vers,
86 Opt_wsize,
87 Opt_write,
88};
89
90enum {
91 Opt_local_lock_all,
92 Opt_local_lock_flock,
93 Opt_local_lock_none,
94 Opt_local_lock_posix,
95};
96
97static const struct constant_table nfs_param_enums_local_lock[] = {
98 { "all", Opt_local_lock_all },
99 { "flock", Opt_local_lock_flock },
100 { "posix", Opt_local_lock_posix },
101 { "none", Opt_local_lock_none },
102 {}
103};
104
105enum {
106 Opt_lookupcache_all,
107 Opt_lookupcache_none,
108 Opt_lookupcache_positive,
109};
110
111static const struct constant_table nfs_param_enums_lookupcache[] = {
112 { "all", Opt_lookupcache_all },
113 { "none", Opt_lookupcache_none },
114 { "pos", Opt_lookupcache_positive },
115 { "positive", Opt_lookupcache_positive },
116 {}
117};
118
119enum {
120 Opt_write_lazy,
121 Opt_write_eager,
122 Opt_write_wait,
123};
124
125static const struct constant_table nfs_param_enums_write[] = {
126 { "lazy", Opt_write_lazy },
127 { "eager", Opt_write_eager },
128 { "wait", Opt_write_wait },
129 {}
130};
131
132static const struct fs_parameter_spec nfs_fs_parameters[] = {
133 fsparam_flag_no("ac", Opt_ac),
134 fsparam_u32 ("acdirmax", Opt_acdirmax),
135 fsparam_u32 ("acdirmin", Opt_acdirmin),
136 fsparam_flag_no("acl", Opt_acl),
137 fsparam_u32 ("acregmax", Opt_acregmax),
138 fsparam_u32 ("acregmin", Opt_acregmin),
139 fsparam_u32 ("actimeo", Opt_actimeo),
140 fsparam_string("addr", Opt_addr),
141 fsparam_flag ("bg", Opt_bg),
142 fsparam_u32 ("bsize", Opt_bsize),
143 fsparam_string("clientaddr", Opt_clientaddr),
144 fsparam_flag_no("cto", Opt_cto),
145 fsparam_flag ("fg", Opt_fg),
146 fsparam_flag_no("fsc", Opt_fscache_flag),
147 fsparam_string("fsc", Opt_fscache),
148 fsparam_flag ("hard", Opt_hard),
149 __fsparam(NULL, "intr", Opt_intr,
150 fs_param_neg_with_no|fs_param_deprecated, NULL),
151 fsparam_enum ("local_lock", Opt_local_lock, nfs_param_enums_local_lock),
152 fsparam_flag_no("lock", Opt_lock),
153 fsparam_enum ("lookupcache", Opt_lookupcache, nfs_param_enums_lookupcache),
154 fsparam_flag_no("migration", Opt_migration),
155 fsparam_u32 ("minorversion", Opt_minorversion),
156 fsparam_string("mountaddr", Opt_mountaddr),
157 fsparam_string("mounthost", Opt_mounthost),
158 fsparam_u32 ("mountport", Opt_mountport),
159 fsparam_string("mountproto", Opt_mountproto),
160 fsparam_u32 ("mountvers", Opt_mountvers),
161 fsparam_u32 ("namlen", Opt_namelen),
162 fsparam_u32 ("nconnect", Opt_nconnect),
163 fsparam_u32 ("max_connect", Opt_max_connect),
164 fsparam_string("nfsvers", Opt_vers),
165 fsparam_u32 ("port", Opt_port),
166 fsparam_flag_no("posix", Opt_posix),
167 fsparam_string("proto", Opt_proto),
168 fsparam_flag_no("rdirplus", Opt_rdirplus),
169 fsparam_flag ("rdma", Opt_rdma),
170 fsparam_flag_no("resvport", Opt_resvport),
171 fsparam_u32 ("retrans", Opt_retrans),
172 fsparam_string("retry", Opt_retry),
173 fsparam_u32 ("rsize", Opt_rsize),
174 fsparam_string("sec", Opt_sec),
175 fsparam_flag_no("sharecache", Opt_sharecache),
176 fsparam_flag ("sloppy", Opt_sloppy),
177 fsparam_flag ("soft", Opt_soft),
178 fsparam_flag ("softerr", Opt_softerr),
179 fsparam_flag ("softreval", Opt_softreval),
180 fsparam_string("source", Opt_source),
181 fsparam_flag ("tcp", Opt_tcp),
182 fsparam_u32 ("timeo", Opt_timeo),
183 fsparam_flag ("udp", Opt_udp),
184 fsparam_flag ("v2", Opt_v),
185 fsparam_flag ("v3", Opt_v),
186 fsparam_flag ("v4", Opt_v),
187 fsparam_flag ("v4.0", Opt_v),
188 fsparam_flag ("v4.1", Opt_v),
189 fsparam_flag ("v4.2", Opt_v),
190 fsparam_string("vers", Opt_vers),
191 fsparam_enum ("write", Opt_write, nfs_param_enums_write),
192 fsparam_u32 ("wsize", Opt_wsize),
193 {}
194};
195
196enum {
197 Opt_vers_2,
198 Opt_vers_3,
199 Opt_vers_4,
200 Opt_vers_4_0,
201 Opt_vers_4_1,
202 Opt_vers_4_2,
203};
204
205static const struct constant_table nfs_vers_tokens[] = {
206 { "2", Opt_vers_2 },
207 { "3", Opt_vers_3 },
208 { "4", Opt_vers_4 },
209 { "4.0", Opt_vers_4_0 },
210 { "4.1", Opt_vers_4_1 },
211 { "4.2", Opt_vers_4_2 },
212 {}
213};
214
215enum {
216 Opt_xprt_rdma,
217 Opt_xprt_rdma6,
218 Opt_xprt_tcp,
219 Opt_xprt_tcp6,
220 Opt_xprt_udp,
221 Opt_xprt_udp6,
222 nr__Opt_xprt
223};
224
225static const struct constant_table nfs_xprt_protocol_tokens[] = {
226 { "rdma", Opt_xprt_rdma },
227 { "rdma6", Opt_xprt_rdma6 },
228 { "tcp", Opt_xprt_tcp },
229 { "tcp6", Opt_xprt_tcp6 },
230 { "udp", Opt_xprt_udp },
231 { "udp6", Opt_xprt_udp6 },
232 {}
233};
234
235enum {
236 Opt_sec_krb5,
237 Opt_sec_krb5i,
238 Opt_sec_krb5p,
239 Opt_sec_lkey,
240 Opt_sec_lkeyi,
241 Opt_sec_lkeyp,
242 Opt_sec_none,
243 Opt_sec_spkm,
244 Opt_sec_spkmi,
245 Opt_sec_spkmp,
246 Opt_sec_sys,
247 nr__Opt_sec
248};
249
250static const struct constant_table nfs_secflavor_tokens[] = {
251 { "krb5", Opt_sec_krb5 },
252 { "krb5i", Opt_sec_krb5i },
253 { "krb5p", Opt_sec_krb5p },
254 { "lkey", Opt_sec_lkey },
255 { "lkeyi", Opt_sec_lkeyi },
256 { "lkeyp", Opt_sec_lkeyp },
257 { "none", Opt_sec_none },
258 { "null", Opt_sec_none },
259 { "spkm3", Opt_sec_spkm },
260 { "spkm3i", Opt_sec_spkmi },
261 { "spkm3p", Opt_sec_spkmp },
262 { "sys", Opt_sec_sys },
263 {}
264};
265
266/*
267 * Sanity-check a server address provided by the mount command.
268 *
269 * Address family must be initialized, and address must not be
270 * the ANY address for that family.
271 */
272static int nfs_verify_server_address(struct sockaddr *addr)
273{
274 switch (addr->sa_family) {
275 case AF_INET: {
276 struct sockaddr_in *sa = (struct sockaddr_in *)addr;
277 return sa->sin_addr.s_addr != htonl(INADDR_ANY);
278 }
279 case AF_INET6: {
280 struct in6_addr *sa = &((struct sockaddr_in6 *)addr)->sin6_addr;
281 return !ipv6_addr_any(sa);
282 }
283 }
284
285 dfprintk(MOUNT, "NFS: Invalid IP address specified\n");
286 return 0;
287}
288
289#ifdef CONFIG_NFS_DISABLE_UDP_SUPPORT
290static bool nfs_server_transport_udp_invalid(const struct nfs_fs_context *ctx)
291{
292 return true;
293}
294#else
295static bool nfs_server_transport_udp_invalid(const struct nfs_fs_context *ctx)
296{
297 if (ctx->version == 4)
298 return true;
299 return false;
300}
301#endif
302
303/*
304 * Sanity check the NFS transport protocol.
305 */
306static int nfs_validate_transport_protocol(struct fs_context *fc,
307 struct nfs_fs_context *ctx)
308{
309 switch (ctx->nfs_server.protocol) {
310 case XPRT_TRANSPORT_UDP:
311 if (nfs_server_transport_udp_invalid(ctx))
312 goto out_invalid_transport_udp;
313 break;
314 case XPRT_TRANSPORT_TCP:
315 case XPRT_TRANSPORT_RDMA:
316 break;
317 default:
318 ctx->nfs_server.protocol = XPRT_TRANSPORT_TCP;
319 }
320 return 0;
321out_invalid_transport_udp:
322 return nfs_invalf(fc, "NFS: Unsupported transport protocol udp");
323}
324
325/*
326 * For text based NFSv2/v3 mounts, the mount protocol transport default
327 * settings should depend upon the specified NFS transport.
328 */
329static void nfs_set_mount_transport_protocol(struct nfs_fs_context *ctx)
330{
331 if (ctx->mount_server.protocol == XPRT_TRANSPORT_UDP ||
332 ctx->mount_server.protocol == XPRT_TRANSPORT_TCP)
333 return;
334 switch (ctx->nfs_server.protocol) {
335 case XPRT_TRANSPORT_UDP:
336 ctx->mount_server.protocol = XPRT_TRANSPORT_UDP;
337 break;
338 case XPRT_TRANSPORT_TCP:
339 case XPRT_TRANSPORT_RDMA:
340 ctx->mount_server.protocol = XPRT_TRANSPORT_TCP;
341 }
342}
343
344/*
345 * Add 'flavor' to 'auth_info' if not already present.
346 * Returns true if 'flavor' ends up in the list, false otherwise
347 */
348static int nfs_auth_info_add(struct fs_context *fc,
349 struct nfs_auth_info *auth_info,
350 rpc_authflavor_t flavor)
351{
352 unsigned int i;
353 unsigned int max_flavor_len = ARRAY_SIZE(auth_info->flavors);
354
355 /* make sure this flavor isn't already in the list */
356 for (i = 0; i < auth_info->flavor_len; i++) {
357 if (flavor == auth_info->flavors[i])
358 return 0;
359 }
360
361 if (auth_info->flavor_len + 1 >= max_flavor_len)
362 return nfs_invalf(fc, "NFS: too many sec= flavors");
363
364 auth_info->flavors[auth_info->flavor_len++] = flavor;
365 return 0;
366}
367
368/*
369 * Parse the value of the 'sec=' option.
370 */
371static int nfs_parse_security_flavors(struct fs_context *fc,
372 struct fs_parameter *param)
373{
374 struct nfs_fs_context *ctx = nfs_fc2context(fc);
375 rpc_authflavor_t pseudoflavor;
376 char *string = param->string, *p;
377 int ret;
378
379 dfprintk(MOUNT, "NFS: parsing %s=%s option\n", param->key, param->string);
380
381 while ((p = strsep(&string, ":")) != NULL) {
382 if (!*p)
383 continue;
384 switch (lookup_constant(nfs_secflavor_tokens, p, -1)) {
385 case Opt_sec_none:
386 pseudoflavor = RPC_AUTH_NULL;
387 break;
388 case Opt_sec_sys:
389 pseudoflavor = RPC_AUTH_UNIX;
390 break;
391 case Opt_sec_krb5:
392 pseudoflavor = RPC_AUTH_GSS_KRB5;
393 break;
394 case Opt_sec_krb5i:
395 pseudoflavor = RPC_AUTH_GSS_KRB5I;
396 break;
397 case Opt_sec_krb5p:
398 pseudoflavor = RPC_AUTH_GSS_KRB5P;
399 break;
400 case Opt_sec_lkey:
401 pseudoflavor = RPC_AUTH_GSS_LKEY;
402 break;
403 case Opt_sec_lkeyi:
404 pseudoflavor = RPC_AUTH_GSS_LKEYI;
405 break;
406 case Opt_sec_lkeyp:
407 pseudoflavor = RPC_AUTH_GSS_LKEYP;
408 break;
409 case Opt_sec_spkm:
410 pseudoflavor = RPC_AUTH_GSS_SPKM;
411 break;
412 case Opt_sec_spkmi:
413 pseudoflavor = RPC_AUTH_GSS_SPKMI;
414 break;
415 case Opt_sec_spkmp:
416 pseudoflavor = RPC_AUTH_GSS_SPKMP;
417 break;
418 default:
419 return nfs_invalf(fc, "NFS: sec=%s option not recognized", p);
420 }
421
422 ret = nfs_auth_info_add(fc, &ctx->auth_info, pseudoflavor);
423 if (ret < 0)
424 return ret;
425 }
426
427 return 0;
428}
429
430static int nfs_parse_version_string(struct fs_context *fc,
431 const char *string)
432{
433 struct nfs_fs_context *ctx = nfs_fc2context(fc);
434
435 ctx->flags &= ~NFS_MOUNT_VER3;
436 switch (lookup_constant(nfs_vers_tokens, string, -1)) {
437 case Opt_vers_2:
438 ctx->version = 2;
439 break;
440 case Opt_vers_3:
441 ctx->flags |= NFS_MOUNT_VER3;
442 ctx->version = 3;
443 break;
444 case Opt_vers_4:
445 /* Backward compatibility option. In future,
446 * the mount program should always supply
447 * a NFSv4 minor version number.
448 */
449 ctx->version = 4;
450 break;
451 case Opt_vers_4_0:
452 ctx->version = 4;
453 ctx->minorversion = 0;
454 break;
455 case Opt_vers_4_1:
456 ctx->version = 4;
457 ctx->minorversion = 1;
458 break;
459 case Opt_vers_4_2:
460 ctx->version = 4;
461 ctx->minorversion = 2;
462 break;
463 default:
464 return nfs_invalf(fc, "NFS: Unsupported NFS version");
465 }
466 return 0;
467}
468
469/*
470 * Parse a single mount parameter.
471 */
472static int nfs_fs_context_parse_param(struct fs_context *fc,
473 struct fs_parameter *param)
474{
475 struct fs_parse_result result;
476 struct nfs_fs_context *ctx = nfs_fc2context(fc);
477 unsigned short protofamily, mountfamily;
478 unsigned int len;
479 int ret, opt;
480
481 dfprintk(MOUNT, "NFS: parsing nfs mount option '%s'\n", param->key);
482
483 opt = fs_parse(fc, nfs_fs_parameters, param, &result);
484 if (opt < 0)
485 return ctx->sloppy ? 1 : opt;
486
487 if (fc->security)
488 ctx->has_sec_mnt_opts = 1;
489
490 switch (opt) {
491 case Opt_source:
492 if (fc->source)
493 return nfs_invalf(fc, "NFS: Multiple sources not supported");
494 fc->source = param->string;
495 param->string = NULL;
496 break;
497
498 /*
499 * boolean options: foo/nofoo
500 */
501 case Opt_soft:
502 ctx->flags |= NFS_MOUNT_SOFT;
503 ctx->flags &= ~NFS_MOUNT_SOFTERR;
504 break;
505 case Opt_softerr:
506 ctx->flags |= NFS_MOUNT_SOFTERR | NFS_MOUNT_SOFTREVAL;
507 ctx->flags &= ~NFS_MOUNT_SOFT;
508 break;
509 case Opt_hard:
510 ctx->flags &= ~(NFS_MOUNT_SOFT |
511 NFS_MOUNT_SOFTERR |
512 NFS_MOUNT_SOFTREVAL);
513 break;
514 case Opt_softreval:
515 if (result.negated)
516 ctx->flags &= ~NFS_MOUNT_SOFTREVAL;
517 else
518 ctx->flags &= NFS_MOUNT_SOFTREVAL;
519 break;
520 case Opt_posix:
521 if (result.negated)
522 ctx->flags &= ~NFS_MOUNT_POSIX;
523 else
524 ctx->flags |= NFS_MOUNT_POSIX;
525 break;
526 case Opt_cto:
527 if (result.negated)
528 ctx->flags |= NFS_MOUNT_NOCTO;
529 else
530 ctx->flags &= ~NFS_MOUNT_NOCTO;
531 break;
532 case Opt_ac:
533 if (result.negated)
534 ctx->flags |= NFS_MOUNT_NOAC;
535 else
536 ctx->flags &= ~NFS_MOUNT_NOAC;
537 break;
538 case Opt_lock:
539 if (result.negated) {
540 ctx->flags |= NFS_MOUNT_NONLM;
541 ctx->flags |= (NFS_MOUNT_LOCAL_FLOCK | NFS_MOUNT_LOCAL_FCNTL);
542 } else {
543 ctx->flags &= ~NFS_MOUNT_NONLM;
544 ctx->flags &= ~(NFS_MOUNT_LOCAL_FLOCK | NFS_MOUNT_LOCAL_FCNTL);
545 }
546 break;
547 case Opt_udp:
548 ctx->flags &= ~NFS_MOUNT_TCP;
549 ctx->nfs_server.protocol = XPRT_TRANSPORT_UDP;
550 break;
551 case Opt_tcp:
552 case Opt_rdma:
553 ctx->flags |= NFS_MOUNT_TCP; /* for side protocols */
554 ret = xprt_find_transport_ident(param->key);
555 if (ret < 0)
556 goto out_bad_transport;
557 ctx->nfs_server.protocol = ret;
558 break;
559 case Opt_acl:
560 if (result.negated)
561 ctx->flags |= NFS_MOUNT_NOACL;
562 else
563 ctx->flags &= ~NFS_MOUNT_NOACL;
564 break;
565 case Opt_rdirplus:
566 if (result.negated)
567 ctx->flags |= NFS_MOUNT_NORDIRPLUS;
568 else
569 ctx->flags &= ~NFS_MOUNT_NORDIRPLUS;
570 break;
571 case Opt_sharecache:
572 if (result.negated)
573 ctx->flags |= NFS_MOUNT_UNSHARED;
574 else
575 ctx->flags &= ~NFS_MOUNT_UNSHARED;
576 break;
577 case Opt_resvport:
578 if (result.negated)
579 ctx->flags |= NFS_MOUNT_NORESVPORT;
580 else
581 ctx->flags &= ~NFS_MOUNT_NORESVPORT;
582 break;
583 case Opt_fscache_flag:
584 if (result.negated)
585 ctx->options &= ~NFS_OPTION_FSCACHE;
586 else
587 ctx->options |= NFS_OPTION_FSCACHE;
588 kfree(ctx->fscache_uniq);
589 ctx->fscache_uniq = NULL;
590 break;
591 case Opt_fscache:
592 ctx->options |= NFS_OPTION_FSCACHE;
593 kfree(ctx->fscache_uniq);
594 ctx->fscache_uniq = param->string;
595 param->string = NULL;
596 break;
597 case Opt_migration:
598 if (result.negated)
599 ctx->options &= ~NFS_OPTION_MIGRATION;
600 else
601 ctx->options |= NFS_OPTION_MIGRATION;
602 break;
603
604 /*
605 * options that take numeric values
606 */
607 case Opt_port:
608 if (result.uint_32 > USHRT_MAX)
609 goto out_of_bounds;
610 ctx->nfs_server.port = result.uint_32;
611 break;
612 case Opt_rsize:
613 ctx->rsize = result.uint_32;
614 break;
615 case Opt_wsize:
616 ctx->wsize = result.uint_32;
617 break;
618 case Opt_bsize:
619 ctx->bsize = result.uint_32;
620 break;
621 case Opt_timeo:
622 if (result.uint_32 < 1 || result.uint_32 > INT_MAX)
623 goto out_of_bounds;
624 ctx->timeo = result.uint_32;
625 break;
626 case Opt_retrans:
627 if (result.uint_32 > INT_MAX)
628 goto out_of_bounds;
629 ctx->retrans = result.uint_32;
630 break;
631 case Opt_acregmin:
632 ctx->acregmin = result.uint_32;
633 break;
634 case Opt_acregmax:
635 ctx->acregmax = result.uint_32;
636 break;
637 case Opt_acdirmin:
638 ctx->acdirmin = result.uint_32;
639 break;
640 case Opt_acdirmax:
641 ctx->acdirmax = result.uint_32;
642 break;
643 case Opt_actimeo:
644 ctx->acregmin = result.uint_32;
645 ctx->acregmax = result.uint_32;
646 ctx->acdirmin = result.uint_32;
647 ctx->acdirmax = result.uint_32;
648 break;
649 case Opt_namelen:
650 ctx->namlen = result.uint_32;
651 break;
652 case Opt_mountport:
653 if (result.uint_32 > USHRT_MAX)
654 goto out_of_bounds;
655 ctx->mount_server.port = result.uint_32;
656 break;
657 case Opt_mountvers:
658 if (result.uint_32 < NFS_MNT_VERSION ||
659 result.uint_32 > NFS_MNT3_VERSION)
660 goto out_of_bounds;
661 ctx->mount_server.version = result.uint_32;
662 break;
663 case Opt_minorversion:
664 if (result.uint_32 > NFS4_MAX_MINOR_VERSION)
665 goto out_of_bounds;
666 ctx->minorversion = result.uint_32;
667 break;
668
669 /*
670 * options that take text values
671 */
672 case Opt_v:
673 ret = nfs_parse_version_string(fc, param->key + 1);
674 if (ret < 0)
675 return ret;
676 break;
677 case Opt_vers:
678 ret = nfs_parse_version_string(fc, param->string);
679 if (ret < 0)
680 return ret;
681 break;
682 case Opt_sec:
683 ret = nfs_parse_security_flavors(fc, param);
684 if (ret < 0)
685 return ret;
686 break;
687
688 case Opt_proto:
689 protofamily = AF_INET;
690 switch (lookup_constant(nfs_xprt_protocol_tokens, param->string, -1)) {
691 case Opt_xprt_udp6:
692 protofamily = AF_INET6;
693 fallthrough;
694 case Opt_xprt_udp:
695 ctx->flags &= ~NFS_MOUNT_TCP;
696 ctx->nfs_server.protocol = XPRT_TRANSPORT_UDP;
697 break;
698 case Opt_xprt_tcp6:
699 protofamily = AF_INET6;
700 fallthrough;
701 case Opt_xprt_tcp:
702 ctx->flags |= NFS_MOUNT_TCP;
703 ctx->nfs_server.protocol = XPRT_TRANSPORT_TCP;
704 break;
705 case Opt_xprt_rdma6:
706 protofamily = AF_INET6;
707 fallthrough;
708 case Opt_xprt_rdma:
709 /* vector side protocols to TCP */
710 ctx->flags |= NFS_MOUNT_TCP;
711 ret = xprt_find_transport_ident(param->string);
712 if (ret < 0)
713 goto out_bad_transport;
714 ctx->nfs_server.protocol = ret;
715 break;
716 default:
717 goto out_bad_transport;
718 }
719
720 ctx->protofamily = protofamily;
721 break;
722
723 case Opt_mountproto:
724 mountfamily = AF_INET;
725 switch (lookup_constant(nfs_xprt_protocol_tokens, param->string, -1)) {
726 case Opt_xprt_udp6:
727 mountfamily = AF_INET6;
728 fallthrough;
729 case Opt_xprt_udp:
730 ctx->mount_server.protocol = XPRT_TRANSPORT_UDP;
731 break;
732 case Opt_xprt_tcp6:
733 mountfamily = AF_INET6;
734 fallthrough;
735 case Opt_xprt_tcp:
736 ctx->mount_server.protocol = XPRT_TRANSPORT_TCP;
737 break;
738 case Opt_xprt_rdma: /* not used for side protocols */
739 default:
740 goto out_bad_transport;
741 }
742 ctx->mountfamily = mountfamily;
743 break;
744
745 case Opt_addr:
746 len = rpc_pton(fc->net_ns, param->string, param->size,
747 &ctx->nfs_server.address,
748 sizeof(ctx->nfs_server._address));
749 if (len == 0)
750 goto out_invalid_address;
751 ctx->nfs_server.addrlen = len;
752 break;
753 case Opt_clientaddr:
754 kfree(ctx->client_address);
755 ctx->client_address = param->string;
756 param->string = NULL;
757 break;
758 case Opt_mounthost:
759 kfree(ctx->mount_server.hostname);
760 ctx->mount_server.hostname = param->string;
761 param->string = NULL;
762 break;
763 case Opt_mountaddr:
764 len = rpc_pton(fc->net_ns, param->string, param->size,
765 &ctx->mount_server.address,
766 sizeof(ctx->mount_server._address));
767 if (len == 0)
768 goto out_invalid_address;
769 ctx->mount_server.addrlen = len;
770 break;
771 case Opt_nconnect:
772 if (result.uint_32 < 1 || result.uint_32 > NFS_MAX_CONNECTIONS)
773 goto out_of_bounds;
774 ctx->nfs_server.nconnect = result.uint_32;
775 break;
776 case Opt_max_connect:
777 if (result.uint_32 < 1 || result.uint_32 > NFS_MAX_TRANSPORTS)
778 goto out_of_bounds;
779 ctx->nfs_server.max_connect = result.uint_32;
780 break;
781 case Opt_lookupcache:
782 switch (result.uint_32) {
783 case Opt_lookupcache_all:
784 ctx->flags &= ~(NFS_MOUNT_LOOKUP_CACHE_NONEG|NFS_MOUNT_LOOKUP_CACHE_NONE);
785 break;
786 case Opt_lookupcache_positive:
787 ctx->flags &= ~NFS_MOUNT_LOOKUP_CACHE_NONE;
788 ctx->flags |= NFS_MOUNT_LOOKUP_CACHE_NONEG;
789 break;
790 case Opt_lookupcache_none:
791 ctx->flags |= NFS_MOUNT_LOOKUP_CACHE_NONEG|NFS_MOUNT_LOOKUP_CACHE_NONE;
792 break;
793 default:
794 goto out_invalid_value;
795 }
796 break;
797 case Opt_local_lock:
798 switch (result.uint_32) {
799 case Opt_local_lock_all:
800 ctx->flags |= (NFS_MOUNT_LOCAL_FLOCK |
801 NFS_MOUNT_LOCAL_FCNTL);
802 break;
803 case Opt_local_lock_flock:
804 ctx->flags |= NFS_MOUNT_LOCAL_FLOCK;
805 break;
806 case Opt_local_lock_posix:
807 ctx->flags |= NFS_MOUNT_LOCAL_FCNTL;
808 break;
809 case Opt_local_lock_none:
810 ctx->flags &= ~(NFS_MOUNT_LOCAL_FLOCK |
811 NFS_MOUNT_LOCAL_FCNTL);
812 break;
813 default:
814 goto out_invalid_value;
815 }
816 break;
817 case Opt_write:
818 switch (result.uint_32) {
819 case Opt_write_lazy:
820 ctx->flags &=
821 ~(NFS_MOUNT_WRITE_EAGER | NFS_MOUNT_WRITE_WAIT);
822 break;
823 case Opt_write_eager:
824 ctx->flags |= NFS_MOUNT_WRITE_EAGER;
825 ctx->flags &= ~NFS_MOUNT_WRITE_WAIT;
826 break;
827 case Opt_write_wait:
828 ctx->flags |=
829 NFS_MOUNT_WRITE_EAGER | NFS_MOUNT_WRITE_WAIT;
830 break;
831 default:
832 goto out_invalid_value;
833 }
834 break;
835
836 /*
837 * Special options
838 */
839 case Opt_sloppy:
840 ctx->sloppy = true;
841 dfprintk(MOUNT, "NFS: relaxing parsing rules\n");
842 break;
843 }
844
845 return 0;
846
847out_invalid_value:
848 return nfs_invalf(fc, "NFS: Bad mount option value specified");
849out_invalid_address:
850 return nfs_invalf(fc, "NFS: Bad IP address specified");
851out_of_bounds:
852 return nfs_invalf(fc, "NFS: Value for '%s' out of range", param->key);
853out_bad_transport:
854 return nfs_invalf(fc, "NFS: Unrecognized transport protocol");
855}
856
857/*
858 * Split fc->source into "hostname:export_path".
859 *
860 * The leftmost colon demarks the split between the server's hostname
861 * and the export path. If the hostname starts with a left square
862 * bracket, then it may contain colons.
863 *
864 * Note: caller frees hostname and export path, even on error.
865 */
866static int nfs_parse_source(struct fs_context *fc,
867 size_t maxnamlen, size_t maxpathlen)
868{
869 struct nfs_fs_context *ctx = nfs_fc2context(fc);
870 const char *dev_name = fc->source;
871 size_t len;
872 const char *end;
873
874 if (unlikely(!dev_name || !*dev_name)) {
875 dfprintk(MOUNT, "NFS: device name not specified\n");
876 return -EINVAL;
877 }
878
879 /* Is the host name protected with square brakcets? */
880 if (*dev_name == '[') {
881 end = strchr(++dev_name, ']');
882 if (end == NULL || end[1] != ':')
883 goto out_bad_devname;
884
885 len = end - dev_name;
886 end++;
887 } else {
888 const char *comma;
889
890 end = strchr(dev_name, ':');
891 if (end == NULL)
892 goto out_bad_devname;
893 len = end - dev_name;
894
895 /* kill possible hostname list: not supported */
896 comma = memchr(dev_name, ',', len);
897 if (comma)
898 len = comma - dev_name;
899 }
900
901 if (len > maxnamlen)
902 goto out_hostname;
903
904 kfree(ctx->nfs_server.hostname);
905
906 /* N.B. caller will free nfs_server.hostname in all cases */
907 ctx->nfs_server.hostname = kmemdup_nul(dev_name, len, GFP_KERNEL);
908 if (!ctx->nfs_server.hostname)
909 goto out_nomem;
910 len = strlen(++end);
911 if (len > maxpathlen)
912 goto out_path;
913 ctx->nfs_server.export_path = kmemdup_nul(end, len, GFP_KERNEL);
914 if (!ctx->nfs_server.export_path)
915 goto out_nomem;
916
917 dfprintk(MOUNT, "NFS: MNTPATH: '%s'\n", ctx->nfs_server.export_path);
918 return 0;
919
920out_bad_devname:
921 return nfs_invalf(fc, "NFS: device name not in host:path format");
922out_nomem:
923 nfs_errorf(fc, "NFS: not enough memory to parse device name");
924 return -ENOMEM;
925out_hostname:
926 nfs_errorf(fc, "NFS: server hostname too long");
927 return -ENAMETOOLONG;
928out_path:
929 nfs_errorf(fc, "NFS: export pathname too long");
930 return -ENAMETOOLONG;
931}
932
933static inline bool is_remount_fc(struct fs_context *fc)
934{
935 return fc->root != NULL;
936}
937
938/*
939 * Parse monolithic NFS2/NFS3 mount data
940 * - fills in the mount root filehandle
941 *
942 * For option strings, user space handles the following behaviors:
943 *
944 * + DNS: mapping server host name to IP address ("addr=" option)
945 *
946 * + failure mode: how to behave if a mount request can't be handled
947 * immediately ("fg/bg" option)
948 *
949 * + retry: how often to retry a mount request ("retry=" option)
950 *
951 * + breaking back: trying proto=udp after proto=tcp, v2 after v3,
952 * mountproto=tcp after mountproto=udp, and so on
953 */
954static int nfs23_parse_monolithic(struct fs_context *fc,
955 struct nfs_mount_data *data)
956{
957 struct nfs_fs_context *ctx = nfs_fc2context(fc);
958 struct nfs_fh *mntfh = ctx->mntfh;
959 struct sockaddr *sap = (struct sockaddr *)&ctx->nfs_server.address;
960 int extra_flags = NFS_MOUNT_LEGACY_INTERFACE;
961 int ret;
962
963 if (data == NULL)
964 goto out_no_data;
965
966 ctx->version = NFS_DEFAULT_VERSION;
967 switch (data->version) {
968 case 1:
969 data->namlen = 0;
970 fallthrough;
971 case 2:
972 data->bsize = 0;
973 fallthrough;
974 case 3:
975 if (data->flags & NFS_MOUNT_VER3)
976 goto out_no_v3;
977 data->root.size = NFS2_FHSIZE;
978 memcpy(data->root.data, data->old_root.data, NFS2_FHSIZE);
979 /* Turn off security negotiation */
980 extra_flags |= NFS_MOUNT_SECFLAVOUR;
981 fallthrough;
982 case 4:
983 if (data->flags & NFS_MOUNT_SECFLAVOUR)
984 goto out_no_sec;
985 fallthrough;
986 case 5:
987 memset(data->context, 0, sizeof(data->context));
988 fallthrough;
989 case 6:
990 if (data->flags & NFS_MOUNT_VER3) {
991 if (data->root.size > NFS3_FHSIZE || data->root.size == 0)
992 goto out_invalid_fh;
993 mntfh->size = data->root.size;
994 ctx->version = 3;
995 } else {
996 mntfh->size = NFS2_FHSIZE;
997 ctx->version = 2;
998 }
999
1000
1001 memcpy(mntfh->data, data->root.data, mntfh->size);
1002 if (mntfh->size < sizeof(mntfh->data))
1003 memset(mntfh->data + mntfh->size, 0,
1004 sizeof(mntfh->data) - mntfh->size);
1005
1006 /*
1007 * for proto == XPRT_TRANSPORT_UDP, which is what uses
1008 * to_exponential, implying shift: limit the shift value
1009 * to BITS_PER_LONG (majortimeo is unsigned long)
1010 */
1011 if (!(data->flags & NFS_MOUNT_TCP)) /* this will be UDP */
1012 if (data->retrans >= 64) /* shift value is too large */
1013 goto out_invalid_data;
1014
1015 /*
1016 * Translate to nfs_fs_context, which nfs_fill_super
1017 * can deal with.
1018 */
1019 ctx->flags = data->flags & NFS_MOUNT_FLAGMASK;
1020 ctx->flags |= extra_flags;
1021 ctx->rsize = data->rsize;
1022 ctx->wsize = data->wsize;
1023 ctx->timeo = data->timeo;
1024 ctx->retrans = data->retrans;
1025 ctx->acregmin = data->acregmin;
1026 ctx->acregmax = data->acregmax;
1027 ctx->acdirmin = data->acdirmin;
1028 ctx->acdirmax = data->acdirmax;
1029 ctx->need_mount = false;
1030
1031 memcpy(sap, &data->addr, sizeof(data->addr));
1032 ctx->nfs_server.addrlen = sizeof(data->addr);
1033 ctx->nfs_server.port = ntohs(data->addr.sin_port);
1034 if (sap->sa_family != AF_INET ||
1035 !nfs_verify_server_address(sap))
1036 goto out_no_address;
1037
1038 if (!(data->flags & NFS_MOUNT_TCP))
1039 ctx->nfs_server.protocol = XPRT_TRANSPORT_UDP;
1040 /* N.B. caller will free nfs_server.hostname in all cases */
1041 ctx->nfs_server.hostname = kstrdup(data->hostname, GFP_KERNEL);
1042 if (!ctx->nfs_server.hostname)
1043 goto out_nomem;
1044
1045 ctx->namlen = data->namlen;
1046 ctx->bsize = data->bsize;
1047
1048 if (data->flags & NFS_MOUNT_SECFLAVOUR)
1049 ctx->selected_flavor = data->pseudoflavor;
1050 else
1051 ctx->selected_flavor = RPC_AUTH_UNIX;
1052
1053 if (!(data->flags & NFS_MOUNT_NONLM))
1054 ctx->flags &= ~(NFS_MOUNT_LOCAL_FLOCK|
1055 NFS_MOUNT_LOCAL_FCNTL);
1056 else
1057 ctx->flags |= (NFS_MOUNT_LOCAL_FLOCK|
1058 NFS_MOUNT_LOCAL_FCNTL);
1059
1060 /*
1061 * The legacy version 6 binary mount data from userspace has a
1062 * field used only to transport selinux information into the
1063 * kernel. To continue to support that functionality we
1064 * have a touch of selinux knowledge here in the NFS code. The
1065 * userspace code converted context=blah to just blah so we are
1066 * converting back to the full string selinux understands.
1067 */
1068 if (data->context[0]){
1069#ifdef CONFIG_SECURITY_SELINUX
1070 int ret;
1071
1072 data->context[NFS_MAX_CONTEXT_LEN] = '\0';
1073 ret = vfs_parse_fs_string(fc, "context",
1074 data->context, strlen(data->context));
1075 if (ret < 0)
1076 return ret;
1077#else
1078 return -EINVAL;
1079#endif
1080 }
1081
1082 break;
1083 default:
1084 goto generic;
1085 }
1086
1087 ret = nfs_validate_transport_protocol(fc, ctx);
1088 if (ret)
1089 return ret;
1090
1091 ctx->skip_reconfig_option_check = true;
1092 return 0;
1093
1094generic:
1095 return generic_parse_monolithic(fc, data);
1096
1097out_no_data:
1098 if (is_remount_fc(fc)) {
1099 ctx->skip_reconfig_option_check = true;
1100 return 0;
1101 }
1102 return nfs_invalf(fc, "NFS: mount program didn't pass any mount data");
1103
1104out_no_v3:
1105 return nfs_invalf(fc, "NFS: nfs_mount_data version does not support v3");
1106
1107out_no_sec:
1108 return nfs_invalf(fc, "NFS: nfs_mount_data version supports only AUTH_SYS");
1109
1110out_nomem:
1111 dfprintk(MOUNT, "NFS: not enough memory to handle mount options");
1112 return -ENOMEM;
1113
1114out_no_address:
1115 return nfs_invalf(fc, "NFS: mount program didn't pass remote address");
1116
1117out_invalid_fh:
1118 return nfs_invalf(fc, "NFS: invalid root filehandle");
1119
1120out_invalid_data:
1121 return nfs_invalf(fc, "NFS: invalid binary mount data");
1122}
1123
1124#if IS_ENABLED(CONFIG_NFS_V4)
1125struct compat_nfs_string {
1126 compat_uint_t len;
1127 compat_uptr_t data;
1128};
1129
1130static inline void compat_nfs_string(struct nfs_string *dst,
1131 struct compat_nfs_string *src)
1132{
1133 dst->data = compat_ptr(src->data);
1134 dst->len = src->len;
1135}
1136
1137struct compat_nfs4_mount_data_v1 {
1138 compat_int_t version;
1139 compat_int_t flags;
1140 compat_int_t rsize;
1141 compat_int_t wsize;
1142 compat_int_t timeo;
1143 compat_int_t retrans;
1144 compat_int_t acregmin;
1145 compat_int_t acregmax;
1146 compat_int_t acdirmin;
1147 compat_int_t acdirmax;
1148 struct compat_nfs_string client_addr;
1149 struct compat_nfs_string mnt_path;
1150 struct compat_nfs_string hostname;
1151 compat_uint_t host_addrlen;
1152 compat_uptr_t host_addr;
1153 compat_int_t proto;
1154 compat_int_t auth_flavourlen;
1155 compat_uptr_t auth_flavours;
1156};
1157
1158static void nfs4_compat_mount_data_conv(struct nfs4_mount_data *data)
1159{
1160 struct compat_nfs4_mount_data_v1 *compat =
1161 (struct compat_nfs4_mount_data_v1 *)data;
1162
1163 /* copy the fields backwards */
1164 data->auth_flavours = compat_ptr(compat->auth_flavours);
1165 data->auth_flavourlen = compat->auth_flavourlen;
1166 data->proto = compat->proto;
1167 data->host_addr = compat_ptr(compat->host_addr);
1168 data->host_addrlen = compat->host_addrlen;
1169 compat_nfs_string(&data->hostname, &compat->hostname);
1170 compat_nfs_string(&data->mnt_path, &compat->mnt_path);
1171 compat_nfs_string(&data->client_addr, &compat->client_addr);
1172 data->acdirmax = compat->acdirmax;
1173 data->acdirmin = compat->acdirmin;
1174 data->acregmax = compat->acregmax;
1175 data->acregmin = compat->acregmin;
1176 data->retrans = compat->retrans;
1177 data->timeo = compat->timeo;
1178 data->wsize = compat->wsize;
1179 data->rsize = compat->rsize;
1180 data->flags = compat->flags;
1181 data->version = compat->version;
1182}
1183
1184/*
1185 * Validate NFSv4 mount options
1186 */
1187static int nfs4_parse_monolithic(struct fs_context *fc,
1188 struct nfs4_mount_data *data)
1189{
1190 struct nfs_fs_context *ctx = nfs_fc2context(fc);
1191 struct sockaddr *sap = (struct sockaddr *)&ctx->nfs_server.address;
1192 int ret;
1193 char *c;
1194
1195 if (!data) {
1196 if (is_remount_fc(fc))
1197 goto done;
1198 return nfs_invalf(fc,
1199 "NFS4: mount program didn't pass any mount data");
1200 }
1201
1202 ctx->version = 4;
1203
1204 if (data->version != 1)
1205 return generic_parse_monolithic(fc, data);
1206
1207 if (in_compat_syscall())
1208 nfs4_compat_mount_data_conv(data);
1209
1210 if (data->host_addrlen > sizeof(ctx->nfs_server.address))
1211 goto out_no_address;
1212 if (data->host_addrlen == 0)
1213 goto out_no_address;
1214 ctx->nfs_server.addrlen = data->host_addrlen;
1215 if (copy_from_user(sap, data->host_addr, data->host_addrlen))
1216 return -EFAULT;
1217 if (!nfs_verify_server_address(sap))
1218 goto out_no_address;
1219 ctx->nfs_server.port = ntohs(((struct sockaddr_in *)sap)->sin_port);
1220
1221 if (data->auth_flavourlen) {
1222 rpc_authflavor_t pseudoflavor;
1223
1224 if (data->auth_flavourlen > 1)
1225 goto out_inval_auth;
1226 if (copy_from_user(&pseudoflavor, data->auth_flavours,
1227 sizeof(pseudoflavor)))
1228 return -EFAULT;
1229 ctx->selected_flavor = pseudoflavor;
1230 } else {
1231 ctx->selected_flavor = RPC_AUTH_UNIX;
1232 }
1233
1234 c = strndup_user(data->hostname.data, NFS4_MAXNAMLEN);
1235 if (IS_ERR(c))
1236 return PTR_ERR(c);
1237 ctx->nfs_server.hostname = c;
1238
1239 c = strndup_user(data->mnt_path.data, NFS4_MAXPATHLEN);
1240 if (IS_ERR(c))
1241 return PTR_ERR(c);
1242 ctx->nfs_server.export_path = c;
1243 dfprintk(MOUNT, "NFS: MNTPATH: '%s'\n", c);
1244
1245 c = strndup_user(data->client_addr.data, 16);
1246 if (IS_ERR(c))
1247 return PTR_ERR(c);
1248 ctx->client_address = c;
1249
1250 /*
1251 * Translate to nfs_fs_context, which nfs_fill_super
1252 * can deal with.
1253 */
1254
1255 ctx->flags = data->flags & NFS4_MOUNT_FLAGMASK;
1256 ctx->rsize = data->rsize;
1257 ctx->wsize = data->wsize;
1258 ctx->timeo = data->timeo;
1259 ctx->retrans = data->retrans;
1260 ctx->acregmin = data->acregmin;
1261 ctx->acregmax = data->acregmax;
1262 ctx->acdirmin = data->acdirmin;
1263 ctx->acdirmax = data->acdirmax;
1264 ctx->nfs_server.protocol = data->proto;
1265 ret = nfs_validate_transport_protocol(fc, ctx);
1266 if (ret)
1267 return ret;
1268done:
1269 ctx->skip_reconfig_option_check = true;
1270 return 0;
1271
1272out_inval_auth:
1273 return nfs_invalf(fc, "NFS4: Invalid number of RPC auth flavours %d",
1274 data->auth_flavourlen);
1275
1276out_no_address:
1277 return nfs_invalf(fc, "NFS4: mount program didn't pass remote address");
1278}
1279#endif
1280
1281/*
1282 * Parse a monolithic block of data from sys_mount().
1283 */
1284static int nfs_fs_context_parse_monolithic(struct fs_context *fc,
1285 void *data)
1286{
1287 if (fc->fs_type == &nfs_fs_type)
1288 return nfs23_parse_monolithic(fc, data);
1289
1290#if IS_ENABLED(CONFIG_NFS_V4)
1291 if (fc->fs_type == &nfs4_fs_type)
1292 return nfs4_parse_monolithic(fc, data);
1293#endif
1294
1295 return nfs_invalf(fc, "NFS: Unsupported monolithic data version");
1296}
1297
1298/*
1299 * Validate the preparsed information in the config.
1300 */
1301static int nfs_fs_context_validate(struct fs_context *fc)
1302{
1303 struct nfs_fs_context *ctx = nfs_fc2context(fc);
1304 struct nfs_subversion *nfs_mod;
1305 struct sockaddr *sap = (struct sockaddr *)&ctx->nfs_server.address;
1306 int max_namelen = PAGE_SIZE;
1307 int max_pathlen = NFS_MAXPATHLEN;
1308 int port = 0;
1309 int ret;
1310
1311 if (!fc->source)
1312 goto out_no_device_name;
1313
1314 /* Check for sanity first. */
1315 if (ctx->minorversion && ctx->version != 4)
1316 goto out_minorversion_mismatch;
1317
1318 if (ctx->options & NFS_OPTION_MIGRATION &&
1319 (ctx->version != 4 || ctx->minorversion != 0))
1320 goto out_migration_misuse;
1321
1322 /* Verify that any proto=/mountproto= options match the address
1323 * families in the addr=/mountaddr= options.
1324 */
1325 if (ctx->protofamily != AF_UNSPEC &&
1326 ctx->protofamily != ctx->nfs_server.address.sa_family)
1327 goto out_proto_mismatch;
1328
1329 if (ctx->mountfamily != AF_UNSPEC) {
1330 if (ctx->mount_server.addrlen) {
1331 if (ctx->mountfamily != ctx->mount_server.address.sa_family)
1332 goto out_mountproto_mismatch;
1333 } else {
1334 if (ctx->mountfamily != ctx->nfs_server.address.sa_family)
1335 goto out_mountproto_mismatch;
1336 }
1337 }
1338
1339 if (!nfs_verify_server_address(sap))
1340 goto out_no_address;
1341
1342 ret = nfs_validate_transport_protocol(fc, ctx);
1343 if (ret)
1344 return ret;
1345
1346 if (ctx->version == 4) {
1347 if (IS_ENABLED(CONFIG_NFS_V4)) {
1348 if (ctx->nfs_server.protocol == XPRT_TRANSPORT_RDMA)
1349 port = NFS_RDMA_PORT;
1350 else
1351 port = NFS_PORT;
1352 max_namelen = NFS4_MAXNAMLEN;
1353 max_pathlen = NFS4_MAXPATHLEN;
1354 ctx->flags &= ~(NFS_MOUNT_NONLM | NFS_MOUNT_NOACL |
1355 NFS_MOUNT_VER3 | NFS_MOUNT_LOCAL_FLOCK |
1356 NFS_MOUNT_LOCAL_FCNTL);
1357 } else {
1358 goto out_v4_not_compiled;
1359 }
1360 } else {
1361 nfs_set_mount_transport_protocol(ctx);
1362 if (ctx->nfs_server.protocol == XPRT_TRANSPORT_RDMA)
1363 port = NFS_RDMA_PORT;
1364 }
1365
1366 nfs_set_port(sap, &ctx->nfs_server.port, port);
1367
1368 ret = nfs_parse_source(fc, max_namelen, max_pathlen);
1369 if (ret < 0)
1370 return ret;
1371
1372 /* Load the NFS protocol module if we haven't done so yet */
1373 if (!ctx->nfs_mod) {
1374 nfs_mod = get_nfs_version(ctx->version);
1375 if (IS_ERR(nfs_mod)) {
1376 ret = PTR_ERR(nfs_mod);
1377 goto out_version_unavailable;
1378 }
1379 ctx->nfs_mod = nfs_mod;
1380 }
1381
1382 /* Ensure the filesystem context has the correct fs_type */
1383 if (fc->fs_type != ctx->nfs_mod->nfs_fs) {
1384 module_put(fc->fs_type->owner);
1385 __module_get(ctx->nfs_mod->nfs_fs->owner);
1386 fc->fs_type = ctx->nfs_mod->nfs_fs;
1387 }
1388 return 0;
1389
1390out_no_device_name:
1391 return nfs_invalf(fc, "NFS: Device name not specified");
1392out_v4_not_compiled:
1393 nfs_errorf(fc, "NFS: NFSv4 is not compiled into kernel");
1394 return -EPROTONOSUPPORT;
1395out_no_address:
1396 return nfs_invalf(fc, "NFS: mount program didn't pass remote address");
1397out_mountproto_mismatch:
1398 return nfs_invalf(fc, "NFS: Mount server address does not match mountproto= option");
1399out_proto_mismatch:
1400 return nfs_invalf(fc, "NFS: Server address does not match proto= option");
1401out_minorversion_mismatch:
1402 return nfs_invalf(fc, "NFS: Mount option vers=%u does not support minorversion=%u",
1403 ctx->version, ctx->minorversion);
1404out_migration_misuse:
1405 return nfs_invalf(fc, "NFS: 'Migration' not supported for this NFS version");
1406out_version_unavailable:
1407 nfs_errorf(fc, "NFS: Version unavailable");
1408 return ret;
1409}
1410
1411/*
1412 * Create an NFS superblock by the appropriate method.
1413 */
1414static int nfs_get_tree(struct fs_context *fc)
1415{
1416 struct nfs_fs_context *ctx = nfs_fc2context(fc);
1417 int err = nfs_fs_context_validate(fc);
1418
1419 if (err)
1420 return err;
1421 if (!ctx->internal)
1422 return ctx->nfs_mod->rpc_ops->try_get_tree(fc);
1423 else
1424 return nfs_get_tree_common(fc);
1425}
1426
1427/*
1428 * Handle duplication of a configuration. The caller copied *src into *sc, but
1429 * it can't deal with resource pointers in the filesystem context, so we have
1430 * to do that. We need to clear pointers, copy data or get extra refs as
1431 * appropriate.
1432 */
1433static int nfs_fs_context_dup(struct fs_context *fc, struct fs_context *src_fc)
1434{
1435 struct nfs_fs_context *src = nfs_fc2context(src_fc), *ctx;
1436
1437 ctx = kmemdup(src, sizeof(struct nfs_fs_context), GFP_KERNEL);
1438 if (!ctx)
1439 return -ENOMEM;
1440
1441 ctx->mntfh = nfs_alloc_fhandle();
1442 if (!ctx->mntfh) {
1443 kfree(ctx);
1444 return -ENOMEM;
1445 }
1446 nfs_copy_fh(ctx->mntfh, src->mntfh);
1447
1448 __module_get(ctx->nfs_mod->owner);
1449 ctx->client_address = NULL;
1450 ctx->mount_server.hostname = NULL;
1451 ctx->nfs_server.export_path = NULL;
1452 ctx->nfs_server.hostname = NULL;
1453 ctx->fscache_uniq = NULL;
1454 ctx->clone_data.fattr = NULL;
1455 fc->fs_private = ctx;
1456 return 0;
1457}
1458
1459static void nfs_fs_context_free(struct fs_context *fc)
1460{
1461 struct nfs_fs_context *ctx = nfs_fc2context(fc);
1462
1463 if (ctx) {
1464 if (ctx->server)
1465 nfs_free_server(ctx->server);
1466 if (ctx->nfs_mod)
1467 put_nfs_version(ctx->nfs_mod);
1468 kfree(ctx->client_address);
1469 kfree(ctx->mount_server.hostname);
1470 kfree(ctx->nfs_server.export_path);
1471 kfree(ctx->nfs_server.hostname);
1472 kfree(ctx->fscache_uniq);
1473 nfs_free_fhandle(ctx->mntfh);
1474 nfs_free_fattr(ctx->clone_data.fattr);
1475 kfree(ctx);
1476 }
1477}
1478
1479static const struct fs_context_operations nfs_fs_context_ops = {
1480 .free = nfs_fs_context_free,
1481 .dup = nfs_fs_context_dup,
1482 .parse_param = nfs_fs_context_parse_param,
1483 .parse_monolithic = nfs_fs_context_parse_monolithic,
1484 .get_tree = nfs_get_tree,
1485 .reconfigure = nfs_reconfigure,
1486};
1487
1488/*
1489 * Prepare superblock configuration. We use the namespaces attached to the
1490 * context. This may be the current process's namespaces, or it may be a
1491 * container's namespaces.
1492 */
1493static int nfs_init_fs_context(struct fs_context *fc)
1494{
1495 struct nfs_fs_context *ctx;
1496
1497 ctx = kzalloc(sizeof(struct nfs_fs_context), GFP_KERNEL);
1498 if (unlikely(!ctx))
1499 return -ENOMEM;
1500
1501 ctx->mntfh = nfs_alloc_fhandle();
1502 if (unlikely(!ctx->mntfh)) {
1503 kfree(ctx);
1504 return -ENOMEM;
1505 }
1506
1507 ctx->protofamily = AF_UNSPEC;
1508 ctx->mountfamily = AF_UNSPEC;
1509 ctx->mount_server.port = NFS_UNSPEC_PORT;
1510
1511 if (fc->root) {
1512 /* reconfigure, start with the current config */
1513 struct nfs_server *nfss = fc->root->d_sb->s_fs_info;
1514 struct net *net = nfss->nfs_client->cl_net;
1515
1516 ctx->flags = nfss->flags;
1517 ctx->rsize = nfss->rsize;
1518 ctx->wsize = nfss->wsize;
1519 ctx->retrans = nfss->client->cl_timeout->to_retries;
1520 ctx->selected_flavor = nfss->client->cl_auth->au_flavor;
1521 ctx->acregmin = nfss->acregmin / HZ;
1522 ctx->acregmax = nfss->acregmax / HZ;
1523 ctx->acdirmin = nfss->acdirmin / HZ;
1524 ctx->acdirmax = nfss->acdirmax / HZ;
1525 ctx->timeo = 10U * nfss->client->cl_timeout->to_initval / HZ;
1526 ctx->nfs_server.port = nfss->port;
1527 ctx->nfs_server.addrlen = nfss->nfs_client->cl_addrlen;
1528 ctx->version = nfss->nfs_client->rpc_ops->version;
1529 ctx->minorversion = nfss->nfs_client->cl_minorversion;
1530
1531 memcpy(&ctx->nfs_server.address, &nfss->nfs_client->cl_addr,
1532 ctx->nfs_server.addrlen);
1533
1534 if (fc->net_ns != net) {
1535 put_net(fc->net_ns);
1536 fc->net_ns = get_net(net);
1537 }
1538
1539 ctx->nfs_mod = nfss->nfs_client->cl_nfs_mod;
1540 __module_get(ctx->nfs_mod->owner);
1541 } else {
1542 /* defaults */
1543 ctx->timeo = NFS_UNSPEC_TIMEO;
1544 ctx->retrans = NFS_UNSPEC_RETRANS;
1545 ctx->acregmin = NFS_DEF_ACREGMIN;
1546 ctx->acregmax = NFS_DEF_ACREGMAX;
1547 ctx->acdirmin = NFS_DEF_ACDIRMIN;
1548 ctx->acdirmax = NFS_DEF_ACDIRMAX;
1549 ctx->nfs_server.port = NFS_UNSPEC_PORT;
1550 ctx->nfs_server.protocol = XPRT_TRANSPORT_TCP;
1551 ctx->selected_flavor = RPC_AUTH_MAXFLAVOR;
1552 ctx->minorversion = 0;
1553 ctx->need_mount = true;
1554
1555 fc->s_iflags |= SB_I_STABLE_WRITES;
1556 }
1557 fc->fs_private = ctx;
1558 fc->ops = &nfs_fs_context_ops;
1559 return 0;
1560}
1561
1562struct file_system_type nfs_fs_type = {
1563 .owner = THIS_MODULE,
1564 .name = "nfs",
1565 .init_fs_context = nfs_init_fs_context,
1566 .parameters = nfs_fs_parameters,
1567 .kill_sb = nfs_kill_super,
1568 .fs_flags = FS_RENAME_DOES_D_MOVE|FS_BINARY_MOUNTDATA,
1569};
1570MODULE_ALIAS_FS("nfs");
1571EXPORT_SYMBOL_GPL(nfs_fs_type);
1572
1573#if IS_ENABLED(CONFIG_NFS_V4)
1574struct file_system_type nfs4_fs_type = {
1575 .owner = THIS_MODULE,
1576 .name = "nfs4",
1577 .init_fs_context = nfs_init_fs_context,
1578 .parameters = nfs_fs_parameters,
1579 .kill_sb = nfs_kill_super,
1580 .fs_flags = FS_RENAME_DOES_D_MOVE|FS_BINARY_MOUNTDATA,
1581};
1582MODULE_ALIAS_FS("nfs4");
1583MODULE_ALIAS("nfs4");
1584EXPORT_SYMBOL_GPL(nfs4_fs_type);
1585#endif /* CONFIG_NFS_V4 */