1 // SPDX-License-Identifier: GPL-2.0-only 1 2 /* 3 * linux/fs/nfs/fs_context.c 4 * 5 * Copyright (C) 1992 Rick Sladkey 6 * Conversion to new mount api Copyright (C) D 7 * 8 * NFS mount handling. 9 * 10 * Split from fs/nfs/super.c by David Howells 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 22 #include <net/handshake.h> 23 24 #include "nfs.h" 25 #include "internal.h" 26 27 #include "nfstrace.h" 28 29 #define NFSDBG_FACILITY NFSDBG_MOUNT 30 31 #if IS_ENABLED(CONFIG_NFS_V3) 32 #define NFS_DEFAULT_VERSION 3 33 #else 34 #define NFS_DEFAULT_VERSION 2 35 #endif 36 37 #define NFS_MAX_CONNECTIONS 16 38 39 enum nfs_param { 40 Opt_ac, 41 Opt_acdirmax, 42 Opt_acdirmin, 43 Opt_acl, 44 Opt_acregmax, 45 Opt_acregmin, 46 Opt_actimeo, 47 Opt_addr, 48 Opt_bg, 49 Opt_bsize, 50 Opt_clientaddr, 51 Opt_cto, 52 Opt_alignwrite, 53 Opt_fg, 54 Opt_fscache, 55 Opt_fscache_flag, 56 Opt_hard, 57 Opt_intr, 58 Opt_local_lock, 59 Opt_lock, 60 Opt_lookupcache, 61 Opt_migration, 62 Opt_minorversion, 63 Opt_mountaddr, 64 Opt_mounthost, 65 Opt_mountport, 66 Opt_mountproto, 67 Opt_mountvers, 68 Opt_namelen, 69 Opt_nconnect, 70 Opt_max_connect, 71 Opt_port, 72 Opt_posix, 73 Opt_proto, 74 Opt_rdirplus, 75 Opt_rdma, 76 Opt_resvport, 77 Opt_retrans, 78 Opt_retry, 79 Opt_rsize, 80 Opt_sec, 81 Opt_sharecache, 82 Opt_sloppy, 83 Opt_soft, 84 Opt_softerr, 85 Opt_softreval, 86 Opt_source, 87 Opt_tcp, 88 Opt_timeo, 89 Opt_trunkdiscovery, 90 Opt_udp, 91 Opt_v, 92 Opt_vers, 93 Opt_wsize, 94 Opt_write, 95 Opt_xprtsec, 96 }; 97 98 enum { 99 Opt_local_lock_all, 100 Opt_local_lock_flock, 101 Opt_local_lock_none, 102 Opt_local_lock_posix, 103 }; 104 105 static const struct constant_table nfs_param_e 106 { "all", Opt_local_lock 107 { "flock", Opt_local_lock_flock } 108 { "posix", Opt_local_lock_posix } 109 { "none", Opt_local_lock 110 {} 111 }; 112 113 enum { 114 Opt_lookupcache_all, 115 Opt_lookupcache_none, 116 Opt_lookupcache_positive, 117 }; 118 119 static const struct constant_table nfs_param_e 120 { "all", Opt_lookupcach 121 { "none", Opt_lookupcach 122 { "pos", Opt_lookupcach 123 { "positive", Opt_lookupcach 124 {} 125 }; 126 127 enum { 128 Opt_write_lazy, 129 Opt_write_eager, 130 Opt_write_wait, 131 }; 132 133 static const struct constant_table nfs_param_e 134 { "lazy", Opt_write_lazy 135 { "eager", Opt_write_eage 136 { "wait", Opt_write_wait 137 {} 138 }; 139 140 static const struct fs_parameter_spec nfs_fs_p 141 fsparam_flag_no("ac", Opt_ac 142 fsparam_u32 ("acdirmax", Opt_ac 143 fsparam_u32 ("acdirmin", Opt_ac 144 fsparam_flag_no("acl", Opt_ac 145 fsparam_u32 ("acregmax", Opt_ac 146 fsparam_u32 ("acregmin", Opt_ac 147 fsparam_u32 ("actimeo", Opt_ac 148 fsparam_string("addr", Opt_ad 149 fsparam_flag ("bg", Opt_bg 150 fsparam_u32 ("bsize", Opt_bs 151 fsparam_string("clientaddr", Opt_cl 152 fsparam_flag_no("cto", Opt_ct 153 fsparam_flag_no("alignwrite", Opt_al 154 fsparam_flag ("fg", Opt_fg 155 fsparam_flag_no("fsc", Opt_fs 156 fsparam_string("fsc", Opt_fs 157 fsparam_flag ("hard", Opt_ha 158 __fsparam(NULL, "intr", Opt_in 159 fs_param_neg_with_no|fs_para 160 fsparam_enum ("local_lock", Opt_lo 161 fsparam_flag_no("lock", Opt_lo 162 fsparam_enum ("lookupcache", Opt_lo 163 fsparam_flag_no("migration", Opt_mi 164 fsparam_u32 ("minorversion", Opt_mi 165 fsparam_string("mountaddr", Opt_mo 166 fsparam_string("mounthost", Opt_mo 167 fsparam_u32 ("mountport", Opt_mo 168 fsparam_string("mountproto", Opt_mo 169 fsparam_u32 ("mountvers", Opt_mo 170 fsparam_u32 ("namlen", Opt_na 171 fsparam_u32 ("nconnect", Opt_nc 172 fsparam_u32 ("max_connect", Opt_ma 173 fsparam_string("nfsvers", Opt_ve 174 fsparam_u32 ("port", Opt_po 175 fsparam_flag_no("posix", Opt_po 176 fsparam_string("proto", Opt_pr 177 fsparam_flag_no("rdirplus", Opt_rd 178 fsparam_flag ("rdma", Opt_rd 179 fsparam_flag_no("resvport", Opt_re 180 fsparam_u32 ("retrans", Opt_re 181 fsparam_string("retry", Opt_re 182 fsparam_u32 ("rsize", Opt_rs 183 fsparam_string("sec", Opt_se 184 fsparam_flag_no("sharecache", Opt_sh 185 fsparam_flag ("sloppy", Opt_sl 186 fsparam_flag ("soft", Opt_so 187 fsparam_flag ("softerr", Opt_so 188 fsparam_flag ("softreval", Opt_so 189 fsparam_string("source", Opt_so 190 fsparam_flag ("tcp", Opt_tc 191 fsparam_u32 ("timeo", Opt_ti 192 fsparam_flag_no("trunkdiscovery", Opt_ 193 fsparam_flag ("udp", Opt_ud 194 fsparam_flag ("v2", Opt_v) 195 fsparam_flag ("v3", Opt_v) 196 fsparam_flag ("v4", Opt_v) 197 fsparam_flag ("v4.0", Opt_v) 198 fsparam_flag ("v4.1", Opt_v) 199 fsparam_flag ("v4.2", Opt_v) 200 fsparam_string("vers", Opt_ve 201 fsparam_enum ("write", Opt_wr 202 fsparam_u32 ("wsize", Opt_ws 203 fsparam_string("xprtsec", Opt_xp 204 {} 205 }; 206 207 enum { 208 Opt_vers_2, 209 Opt_vers_3, 210 Opt_vers_4, 211 Opt_vers_4_0, 212 Opt_vers_4_1, 213 Opt_vers_4_2, 214 }; 215 216 static const struct constant_table nfs_vers_to 217 { "2", Opt_vers_2 }, 218 { "3", Opt_vers_3 }, 219 { "4", Opt_vers_4 }, 220 { "4.0", Opt_vers_4_0 }, 221 { "4.1", Opt_vers_4_1 }, 222 { "4.2", Opt_vers_4_2 }, 223 {} 224 }; 225 226 enum { 227 Opt_xprt_rdma, 228 Opt_xprt_rdma6, 229 Opt_xprt_tcp, 230 Opt_xprt_tcp6, 231 Opt_xprt_udp, 232 Opt_xprt_udp6, 233 nr__Opt_xprt 234 }; 235 236 static const struct constant_table nfs_xprt_pr 237 { "rdma", Opt_xprt_rdma }, 238 { "rdma6", Opt_xprt_rdma6 }, 239 { "tcp", Opt_xprt_tcp }, 240 { "tcp6", Opt_xprt_tcp6 }, 241 { "udp", Opt_xprt_udp }, 242 { "udp6", Opt_xprt_udp6 }, 243 {} 244 }; 245 246 enum { 247 Opt_sec_krb5, 248 Opt_sec_krb5i, 249 Opt_sec_krb5p, 250 Opt_sec_lkey, 251 Opt_sec_lkeyi, 252 Opt_sec_lkeyp, 253 Opt_sec_none, 254 Opt_sec_spkm, 255 Opt_sec_spkmi, 256 Opt_sec_spkmp, 257 Opt_sec_sys, 258 nr__Opt_sec 259 }; 260 261 static const struct constant_table nfs_secflav 262 { "krb5", Opt_sec_krb5 }, 263 { "krb5i", Opt_sec_krb5i }, 264 { "krb5p", Opt_sec_krb5p }, 265 { "lkey", Opt_sec_lkey }, 266 { "lkeyi", Opt_sec_lkeyi }, 267 { "lkeyp", Opt_sec_lkeyp }, 268 { "none", Opt_sec_none }, 269 { "null", Opt_sec_none }, 270 { "spkm3", Opt_sec_spkm }, 271 { "spkm3i", Opt_sec_spkmi }, 272 { "spkm3p", Opt_sec_spkmp }, 273 { "sys", Opt_sec_sys }, 274 {} 275 }; 276 277 enum { 278 Opt_xprtsec_none, 279 Opt_xprtsec_tls, 280 Opt_xprtsec_mtls, 281 nr__Opt_xprtsec 282 }; 283 284 static const struct constant_table nfs_xprtsec 285 { "none", Opt_xprtsec_none }, 286 { "tls", Opt_xprtsec_tls }, 287 { "mtls", Opt_xprtsec_mtls }, 288 {} 289 }; 290 291 /* 292 * Sanity-check a server address provided by t 293 * 294 * Address family must be initialized, and add 295 * the ANY address for that family. 296 */ 297 static int nfs_verify_server_address(struct so 298 { 299 switch (addr->ss_family) { 300 case AF_INET: { 301 struct sockaddr_in *sa = (stru 302 return sa->sin_addr.s_addr != 303 } 304 case AF_INET6: { 305 struct in6_addr *sa = &((struc 306 return !ipv6_addr_any(sa); 307 } 308 } 309 310 return 0; 311 } 312 313 #ifdef CONFIG_NFS_DISABLE_UDP_SUPPORT 314 static bool nfs_server_transport_udp_invalid(c 315 { 316 return true; 317 } 318 #else 319 static bool nfs_server_transport_udp_invalid(c 320 { 321 if (ctx->version == 4) 322 return true; 323 return false; 324 } 325 #endif 326 327 /* 328 * Sanity check the NFS transport protocol. 329 */ 330 static int nfs_validate_transport_protocol(str 331 str 332 { 333 switch (ctx->nfs_server.protocol) { 334 case XPRT_TRANSPORT_UDP: 335 if (nfs_server_transport_udp_i 336 goto out_invalid_trans 337 break; 338 case XPRT_TRANSPORT_TCP: 339 case XPRT_TRANSPORT_RDMA: 340 break; 341 default: 342 ctx->nfs_server.protocol = XPR 343 } 344 345 if (ctx->xprtsec.policy != RPC_XPRTSEC 346 switch (ctx->nfs_server.protoc 347 case XPRT_TRANSPORT_TCP: 348 ctx->nfs_server.protoc 349 break; 350 default: 351 goto out_invalid_xprts 352 } 353 354 return 0; 355 out_invalid_transport_udp: 356 return nfs_invalf(fc, "NFS: Unsupporte 357 out_invalid_xprtsec_policy: 358 return nfs_invalf(fc, "NFS: Transport 359 } 360 361 /* 362 * For text based NFSv2/v3 mounts, the mount p 363 * settings should depend upon the specified N 364 */ 365 static void nfs_set_mount_transport_protocol(s 366 { 367 if (ctx->mount_server.protocol == XPRT 368 ctx->mount_server.protocol == XPRT 369 return; 370 switch (ctx->nfs_server.protocol) { 371 case XPRT_TRANSPORT_UDP: 372 ctx->mount_server.protocol = X 373 break; 374 case XPRT_TRANSPORT_TCP: 375 case XPRT_TRANSPORT_RDMA: 376 ctx->mount_server.protocol = X 377 } 378 } 379 380 /* 381 * Add 'flavor' to 'auth_info' if not already 382 * Returns true if 'flavor' ends up in the lis 383 */ 384 static int nfs_auth_info_add(struct fs_context 385 struct nfs_auth_i 386 rpc_authflavor_t 387 { 388 unsigned int i; 389 unsigned int max_flavor_len = ARRAY_SI 390 391 /* make sure this flavor isn't already 392 for (i = 0; i < auth_info->flavor_len; 393 if (flavor == auth_info->flavo 394 return 0; 395 } 396 397 if (auth_info->flavor_len + 1 >= max_f 398 return nfs_invalf(fc, "NFS: to 399 400 auth_info->flavors[auth_info->flavor_l 401 return 0; 402 } 403 404 /* 405 * Parse the value of the 'sec=' option. 406 */ 407 static int nfs_parse_security_flavors(struct f 408 struct f 409 { 410 struct nfs_fs_context *ctx = nfs_fc2co 411 rpc_authflavor_t pseudoflavor; 412 char *string = param->string, *p; 413 int ret; 414 415 trace_nfs_mount_assign(param->key, str 416 417 while ((p = strsep(&string, ":")) != N 418 if (!*p) 419 continue; 420 switch (lookup_constant(nfs_se 421 case Opt_sec_none: 422 pseudoflavor = RPC_AUT 423 break; 424 case Opt_sec_sys: 425 pseudoflavor = RPC_AUT 426 break; 427 case Opt_sec_krb5: 428 pseudoflavor = RPC_AUT 429 break; 430 case Opt_sec_krb5i: 431 pseudoflavor = RPC_AUT 432 break; 433 case Opt_sec_krb5p: 434 pseudoflavor = RPC_AUT 435 break; 436 case Opt_sec_lkey: 437 pseudoflavor = RPC_AUT 438 break; 439 case Opt_sec_lkeyi: 440 pseudoflavor = RPC_AUT 441 break; 442 case Opt_sec_lkeyp: 443 pseudoflavor = RPC_AUT 444 break; 445 case Opt_sec_spkm: 446 pseudoflavor = RPC_AUT 447 break; 448 case Opt_sec_spkmi: 449 pseudoflavor = RPC_AUT 450 break; 451 case Opt_sec_spkmp: 452 pseudoflavor = RPC_AUT 453 break; 454 default: 455 return nfs_invalf(fc, 456 } 457 458 ret = nfs_auth_info_add(fc, &c 459 if (ret < 0) 460 return ret; 461 } 462 463 return 0; 464 } 465 466 static int nfs_parse_xprtsec_policy(struct fs_ 467 struct fs_ 468 { 469 struct nfs_fs_context *ctx = nfs_fc2co 470 471 trace_nfs_mount_assign(param->key, par 472 473 switch (lookup_constant(nfs_xprtsec_po 474 case Opt_xprtsec_none: 475 ctx->xprtsec.policy = RPC_XPRT 476 break; 477 case Opt_xprtsec_tls: 478 ctx->xprtsec.policy = RPC_XPRT 479 break; 480 case Opt_xprtsec_mtls: 481 ctx->xprtsec.policy = RPC_XPRT 482 break; 483 default: 484 return nfs_invalf(fc, "NFS: Un 485 } 486 return 0; 487 } 488 489 static int nfs_parse_version_string(struct fs_ 490 const char 491 { 492 struct nfs_fs_context *ctx = nfs_fc2co 493 494 ctx->flags &= ~NFS_MOUNT_VER3; 495 switch (lookup_constant(nfs_vers_token 496 case Opt_vers_2: 497 ctx->version = 2; 498 break; 499 case Opt_vers_3: 500 ctx->flags |= NFS_MOUNT_VER3; 501 ctx->version = 3; 502 break; 503 case Opt_vers_4: 504 /* Backward compatibility opti 505 * the mount program should al 506 * a NFSv4 minor version numbe 507 */ 508 ctx->version = 4; 509 break; 510 case Opt_vers_4_0: 511 ctx->version = 4; 512 ctx->minorversion = 0; 513 break; 514 case Opt_vers_4_1: 515 ctx->version = 4; 516 ctx->minorversion = 1; 517 break; 518 case Opt_vers_4_2: 519 ctx->version = 4; 520 ctx->minorversion = 2; 521 break; 522 default: 523 return nfs_invalf(fc, "NFS: Un 524 } 525 return 0; 526 } 527 528 /* 529 * Parse a single mount parameter. 530 */ 531 static int nfs_fs_context_parse_param(struct f 532 struct f 533 { 534 struct fs_parse_result result; 535 struct nfs_fs_context *ctx = nfs_fc2co 536 unsigned short protofamily, mountfamil 537 unsigned int len; 538 int ret, opt; 539 540 trace_nfs_mount_option(param); 541 542 opt = fs_parse(fc, nfs_fs_parameters, 543 if (opt < 0) 544 return (opt == -ENOPARAM && ct 545 546 if (fc->security) 547 ctx->has_sec_mnt_opts = 1; 548 549 switch (opt) { 550 case Opt_source: 551 if (fc->source) 552 return nfs_invalf(fc, 553 fc->source = param->string; 554 param->string = NULL; 555 break; 556 557 /* 558 * boolean options: foo/nofoo 559 */ 560 case Opt_soft: 561 ctx->flags |= NFS_MOUNT_SOFT; 562 ctx->flags &= ~NFS_MOUNT_SOFTE 563 break; 564 case Opt_softerr: 565 ctx->flags |= NFS_MOUNT_SOFTER 566 ctx->flags &= ~NFS_MOUNT_SOFT; 567 break; 568 case Opt_hard: 569 ctx->flags &= ~(NFS_MOUNT_SOFT 570 NFS_MOUNT_SOFT 571 NFS_MOUNT_SOFT 572 break; 573 case Opt_softreval: 574 if (result.negated) 575 ctx->flags &= ~NFS_MOU 576 else 577 ctx->flags |= NFS_MOUN 578 break; 579 case Opt_posix: 580 if (result.negated) 581 ctx->flags &= ~NFS_MOU 582 else 583 ctx->flags |= NFS_MOUN 584 break; 585 case Opt_cto: 586 if (result.negated) 587 ctx->flags |= NFS_MOUN 588 else 589 ctx->flags &= ~NFS_MOU 590 break; 591 case Opt_trunkdiscovery: 592 if (result.negated) 593 ctx->flags &= ~NFS_MOU 594 else 595 ctx->flags |= NFS_MOUN 596 break; 597 case Opt_alignwrite: 598 if (result.negated) 599 ctx->flags |= NFS_MOUN 600 else 601 ctx->flags &= ~NFS_MOU 602 break; 603 case Opt_ac: 604 if (result.negated) 605 ctx->flags |= NFS_MOUN 606 else 607 ctx->flags &= ~NFS_MOU 608 break; 609 case Opt_lock: 610 if (result.negated) { 611 ctx->lock_status = NFS 612 ctx->flags |= NFS_MOUN 613 ctx->flags |= (NFS_MOU 614 } else { 615 ctx->lock_status = NFS 616 ctx->flags &= ~NFS_MOU 617 ctx->flags &= ~(NFS_MO 618 } 619 break; 620 case Opt_udp: 621 ctx->flags &= ~NFS_MOUNT_TCP; 622 ctx->nfs_server.protocol = XPR 623 break; 624 case Opt_tcp: 625 case Opt_rdma: 626 ctx->flags |= NFS_MOUNT_TCP; / 627 ret = xprt_find_transport_iden 628 if (ret < 0) 629 goto out_bad_transport 630 ctx->nfs_server.protocol = ret 631 break; 632 case Opt_acl: 633 if (result.negated) 634 ctx->flags |= NFS_MOUN 635 else 636 ctx->flags &= ~NFS_MOU 637 break; 638 case Opt_rdirplus: 639 if (result.negated) 640 ctx->flags |= NFS_MOUN 641 else 642 ctx->flags &= ~NFS_MOU 643 break; 644 case Opt_sharecache: 645 if (result.negated) 646 ctx->flags |= NFS_MOUN 647 else 648 ctx->flags &= ~NFS_MOU 649 break; 650 case Opt_resvport: 651 if (result.negated) 652 ctx->flags |= NFS_MOUN 653 else 654 ctx->flags &= ~NFS_MOU 655 break; 656 case Opt_fscache_flag: 657 if (result.negated) 658 ctx->options &= ~NFS_O 659 else 660 ctx->options |= NFS_OP 661 kfree(ctx->fscache_uniq); 662 ctx->fscache_uniq = NULL; 663 break; 664 case Opt_fscache: 665 trace_nfs_mount_assign(param-> 666 ctx->options |= NFS_OPTION_FSC 667 kfree(ctx->fscache_uniq); 668 ctx->fscache_uniq = param->str 669 param->string = NULL; 670 break; 671 case Opt_migration: 672 if (result.negated) 673 ctx->options &= ~NFS_O 674 else 675 ctx->options |= NFS_OP 676 break; 677 678 /* 679 * options that take numeric v 680 */ 681 case Opt_port: 682 if (result.uint_32 > USHRT_MAX 683 goto out_of_bounds; 684 ctx->nfs_server.port = result. 685 break; 686 case Opt_rsize: 687 ctx->rsize = result.uint_32; 688 break; 689 case Opt_wsize: 690 ctx->wsize = result.uint_32; 691 break; 692 case Opt_bsize: 693 ctx->bsize = result.uint_32; 694 break; 695 case Opt_timeo: 696 if (result.uint_32 < 1 || resu 697 goto out_of_bounds; 698 ctx->timeo = result.uint_32; 699 break; 700 case Opt_retrans: 701 if (result.uint_32 > INT_MAX) 702 goto out_of_bounds; 703 ctx->retrans = result.uint_32; 704 break; 705 case Opt_acregmin: 706 ctx->acregmin = result.uint_32 707 break; 708 case Opt_acregmax: 709 ctx->acregmax = result.uint_32 710 break; 711 case Opt_acdirmin: 712 ctx->acdirmin = result.uint_32 713 break; 714 case Opt_acdirmax: 715 ctx->acdirmax = result.uint_32 716 break; 717 case Opt_actimeo: 718 ctx->acregmin = result.uint_32 719 ctx->acregmax = result.uint_32 720 ctx->acdirmin = result.uint_32 721 ctx->acdirmax = result.uint_32 722 break; 723 case Opt_namelen: 724 ctx->namlen = result.uint_32; 725 break; 726 case Opt_mountport: 727 if (result.uint_32 > USHRT_MAX 728 goto out_of_bounds; 729 ctx->mount_server.port = resul 730 break; 731 case Opt_mountvers: 732 if (result.uint_32 < NFS_MNT_V 733 result.uint_32 > NFS_MNT3_ 734 goto out_of_bounds; 735 ctx->mount_server.version = re 736 break; 737 case Opt_minorversion: 738 if (result.uint_32 > NFS4_MAX_ 739 goto out_of_bounds; 740 ctx->minorversion = result.uin 741 break; 742 743 /* 744 * options that take text valu 745 */ 746 case Opt_v: 747 ret = nfs_parse_version_string 748 if (ret < 0) 749 return ret; 750 break; 751 case Opt_vers: 752 if (!param->string) 753 goto out_invalid_value 754 trace_nfs_mount_assign(param-> 755 ret = nfs_parse_version_string 756 if (ret < 0) 757 return ret; 758 break; 759 case Opt_sec: 760 ret = nfs_parse_security_flavo 761 if (ret < 0) 762 return ret; 763 break; 764 case Opt_xprtsec: 765 ret = nfs_parse_xprtsec_policy 766 if (ret < 0) 767 return ret; 768 break; 769 770 case Opt_proto: 771 if (!param->string) 772 goto out_invalid_value 773 trace_nfs_mount_assign(param-> 774 protofamily = AF_INET; 775 switch (lookup_constant(nfs_xp 776 case Opt_xprt_udp6: 777 protofamily = AF_INET6 778 fallthrough; 779 case Opt_xprt_udp: 780 ctx->flags &= ~NFS_MOU 781 ctx->nfs_server.protoc 782 break; 783 case Opt_xprt_tcp6: 784 protofamily = AF_INET6 785 fallthrough; 786 case Opt_xprt_tcp: 787 ctx->flags |= NFS_MOUN 788 ctx->nfs_server.protoc 789 break; 790 case Opt_xprt_rdma6: 791 protofamily = AF_INET6 792 fallthrough; 793 case Opt_xprt_rdma: 794 /* vector side protoco 795 ctx->flags |= NFS_MOUN 796 ret = xprt_find_transp 797 if (ret < 0) 798 goto out_bad_t 799 ctx->nfs_server.protoc 800 break; 801 default: 802 goto out_bad_transport 803 } 804 805 ctx->protofamily = protofamily 806 break; 807 808 case Opt_mountproto: 809 if (!param->string) 810 goto out_invalid_value 811 trace_nfs_mount_assign(param-> 812 mountfamily = AF_INET; 813 switch (lookup_constant(nfs_xp 814 case Opt_xprt_udp6: 815 mountfamily = AF_INET6 816 fallthrough; 817 case Opt_xprt_udp: 818 ctx->mount_server.prot 819 break; 820 case Opt_xprt_tcp6: 821 mountfamily = AF_INET6 822 fallthrough; 823 case Opt_xprt_tcp: 824 ctx->mount_server.prot 825 break; 826 case Opt_xprt_rdma: /* not use 827 default: 828 goto out_bad_transport 829 } 830 ctx->mountfamily = mountfamily 831 break; 832 833 case Opt_addr: 834 trace_nfs_mount_assign(param-> 835 len = rpc_pton(fc->net_ns, par 836 &ctx->nfs_serve 837 sizeof(ctx->nfs 838 if (len == 0) 839 goto out_invalid_addre 840 ctx->nfs_server.addrlen = len; 841 break; 842 case Opt_clientaddr: 843 trace_nfs_mount_assign(param-> 844 kfree(ctx->client_address); 845 ctx->client_address = param->s 846 param->string = NULL; 847 break; 848 case Opt_mounthost: 849 trace_nfs_mount_assign(param-> 850 kfree(ctx->mount_server.hostna 851 ctx->mount_server.hostname = p 852 param->string = NULL; 853 break; 854 case Opt_mountaddr: 855 trace_nfs_mount_assign(param-> 856 len = rpc_pton(fc->net_ns, par 857 &ctx->mount_ser 858 sizeof(ctx->mou 859 if (len == 0) 860 goto out_invalid_addre 861 ctx->mount_server.addrlen = le 862 break; 863 case Opt_nconnect: 864 trace_nfs_mount_assign(param-> 865 if (result.uint_32 < 1 || resu 866 goto out_of_bounds; 867 ctx->nfs_server.nconnect = res 868 break; 869 case Opt_max_connect: 870 trace_nfs_mount_assign(param-> 871 if (result.uint_32 < 1 || resu 872 goto out_of_bounds; 873 ctx->nfs_server.max_connect = 874 break; 875 case Opt_lookupcache: 876 trace_nfs_mount_assign(param-> 877 switch (result.uint_32) { 878 case Opt_lookupcache_all: 879 ctx->flags &= ~(NFS_MO 880 break; 881 case Opt_lookupcache_positive: 882 ctx->flags &= ~NFS_MOU 883 ctx->flags |= NFS_MOUN 884 break; 885 case Opt_lookupcache_none: 886 ctx->flags |= NFS_MOUN 887 break; 888 default: 889 goto out_invalid_value 890 } 891 break; 892 case Opt_local_lock: 893 trace_nfs_mount_assign(param-> 894 switch (result.uint_32) { 895 case Opt_local_lock_all: 896 ctx->flags |= (NFS_MOU 897 NFS_MOU 898 break; 899 case Opt_local_lock_flock: 900 ctx->flags |= NFS_MOUN 901 break; 902 case Opt_local_lock_posix: 903 ctx->flags |= NFS_MOUN 904 break; 905 case Opt_local_lock_none: 906 ctx->flags &= ~(NFS_MO 907 NFS_MO 908 break; 909 default: 910 goto out_invalid_value 911 } 912 break; 913 case Opt_write: 914 trace_nfs_mount_assign(param-> 915 switch (result.uint_32) { 916 case Opt_write_lazy: 917 ctx->flags &= 918 ~(NFS_MOUNT_WR 919 break; 920 case Opt_write_eager: 921 ctx->flags |= NFS_MOUN 922 ctx->flags &= ~NFS_MOU 923 break; 924 case Opt_write_wait: 925 ctx->flags |= 926 NFS_MOUNT_WRIT 927 break; 928 default: 929 goto out_invalid_value 930 } 931 break; 932 933 /* 934 * Special options 935 */ 936 case Opt_sloppy: 937 ctx->sloppy = true; 938 break; 939 } 940 941 return 0; 942 943 out_invalid_value: 944 return nfs_invalf(fc, "NFS: Bad mount 945 out_invalid_address: 946 return nfs_invalf(fc, "NFS: Bad IP add 947 out_of_bounds: 948 return nfs_invalf(fc, "NFS: Value for 949 out_bad_transport: 950 return nfs_invalf(fc, "NFS: Unrecogniz 951 } 952 953 /* 954 * Split fc->source into "hostname:export_path 955 * 956 * The leftmost colon demarks the split betwee 957 * and the export path. If the hostname start 958 * bracket, then it may contain colons. 959 * 960 * Note: caller frees hostname and export path 961 */ 962 static int nfs_parse_source(struct fs_context 963 size_t maxnamlen, 964 { 965 struct nfs_fs_context *ctx = nfs_fc2co 966 const char *dev_name = fc->source; 967 size_t len; 968 const char *end; 969 970 if (unlikely(!dev_name || !*dev_name)) 971 return -EINVAL; 972 973 /* Is the host name protected with squ 974 if (*dev_name == '[') { 975 end = strchr(++dev_name, ']'); 976 if (end == NULL || end[1] != ' 977 goto out_bad_devname; 978 979 len = end - dev_name; 980 end++; 981 } else { 982 const char *comma; 983 984 end = strchr(dev_name, ':'); 985 if (end == NULL) 986 goto out_bad_devname; 987 len = end - dev_name; 988 989 /* kill possible hostname list 990 comma = memchr(dev_name, ',', 991 if (comma) 992 len = comma - dev_name 993 } 994 995 if (len > maxnamlen) 996 goto out_hostname; 997 998 kfree(ctx->nfs_server.hostname); 999 1000 /* N.B. caller will free nfs_server.h 1001 ctx->nfs_server.hostname = kmemdup_nu 1002 if (!ctx->nfs_server.hostname) 1003 goto out_nomem; 1004 len = strlen(++end); 1005 if (len > maxpathlen) 1006 goto out_path; 1007 ctx->nfs_server.export_path = kmemdup 1008 if (!ctx->nfs_server.export_path) 1009 goto out_nomem; 1010 1011 trace_nfs_mount_path(ctx->nfs_server. 1012 return 0; 1013 1014 out_bad_devname: 1015 return nfs_invalf(fc, "NFS: device na 1016 out_nomem: 1017 nfs_errorf(fc, "NFS: not enough memor 1018 return -ENOMEM; 1019 out_hostname: 1020 nfs_errorf(fc, "NFS: server hostname 1021 return -ENAMETOOLONG; 1022 out_path: 1023 nfs_errorf(fc, "NFS: export pathname 1024 return -ENAMETOOLONG; 1025 } 1026 1027 static inline bool is_remount_fc(struct fs_co 1028 { 1029 return fc->root != NULL; 1030 } 1031 1032 /* 1033 * Parse monolithic NFS2/NFS3 mount data 1034 * - fills in the mount root filehandle 1035 * 1036 * For option strings, user space handles the 1037 * 1038 * + DNS: mapping server host name to IP addr 1039 * 1040 * + failure mode: how to behave if a mount r 1041 * immediately ("fg/bg" option) 1042 * 1043 * + retry: how often to retry a mount reques 1044 * 1045 * + breaking back: trying proto=udp after pr 1046 * mountproto=tcp after mountproto=udp, and 1047 */ 1048 static int nfs23_parse_monolithic(struct fs_c 1049 struct nfs_ 1050 { 1051 struct nfs_fs_context *ctx = nfs_fc2c 1052 struct nfs_fh *mntfh = ctx->mntfh; 1053 struct sockaddr_storage *sap = &ctx-> 1054 int extra_flags = NFS_MOUNT_LEGACY_IN 1055 int ret; 1056 1057 if (data == NULL) 1058 goto out_no_data; 1059 1060 ctx->version = NFS_DEFAULT_VERSION; 1061 switch (data->version) { 1062 case 1: 1063 data->namlen = 0; 1064 fallthrough; 1065 case 2: 1066 data->bsize = 0; 1067 fallthrough; 1068 case 3: 1069 if (data->flags & NFS_MOUNT_V 1070 goto out_no_v3; 1071 data->root.size = NFS2_FHSIZE 1072 memcpy(data->root.data, data- 1073 /* Turn off security negotiat 1074 extra_flags |= NFS_MOUNT_SECF 1075 fallthrough; 1076 case 4: 1077 if (data->flags & NFS_MOUNT_S 1078 goto out_no_sec; 1079 fallthrough; 1080 case 5: 1081 memset(data->context, 0, size 1082 fallthrough; 1083 case 6: 1084 if (data->flags & NFS_MOUNT_V 1085 if (data->root.size > 1086 goto out_inva 1087 mntfh->size = data->r 1088 ctx->version = 3; 1089 } else { 1090 mntfh->size = NFS2_FH 1091 ctx->version = 2; 1092 } 1093 1094 1095 memcpy(mntfh->data, data->roo 1096 if (mntfh->size < sizeof(mntf 1097 memset(mntfh->data + 1098 sizeof(mntfh-> 1099 1100 /* 1101 * for proto == XPRT_TRANSPOR 1102 * to_exponential, implying s 1103 * to BITS_PER_LONG (majortim 1104 */ 1105 if (!(data->flags & NFS_MOUNT 1106 if (data->retrans >= 1107 goto out_inva 1108 1109 /* 1110 * Translate to nfs_fs_contex 1111 * can deal with. 1112 */ 1113 ctx->flags = data->flags 1114 ctx->flags |= extra_flag 1115 ctx->rsize = data->rsize 1116 ctx->wsize = data->wsize 1117 ctx->timeo = data->timeo 1118 ctx->retrans = data->retra 1119 ctx->acregmin = data->acreg 1120 ctx->acregmax = data->acreg 1121 ctx->acdirmin = data->acdir 1122 ctx->acdirmax = data->acdir 1123 ctx->need_mount = false; 1124 1125 if (!is_remount_fc(fc)) { 1126 memcpy(sap, &data->ad 1127 ctx->nfs_server.addrl 1128 ctx->nfs_server.port 1129 } 1130 1131 if (sap->ss_family != AF_INET 1132 !nfs_verify_server_addres 1133 goto out_no_address; 1134 1135 if (!(data->flags & NFS_MOUNT 1136 ctx->nfs_server.proto 1137 /* N.B. caller will free nfs_ 1138 ctx->nfs_server.hostname = ks 1139 if (!ctx->nfs_server.hostname 1140 goto out_nomem; 1141 1142 ctx->namlen = dat 1143 ctx->bsize = dat 1144 1145 if (data->flags & NFS_MOUNT_S 1146 ctx->selected_flavor 1147 else 1148 ctx->selected_flavor 1149 1150 if (!(data->flags & NFS_MOUNT 1151 ctx->flags &= ~(NFS_M 1152 NFS_ 1153 else 1154 ctx->flags |= (NFS_MO 1155 NFS_M 1156 1157 /* 1158 * The legacy version 6 binar 1159 * field used only to transpo 1160 * kernel. To continue to su 1161 * have a touch of selinux kn 1162 * userspace code converted c 1163 * converting back to the ful 1164 */ 1165 if (data->context[0]){ 1166 #ifdef CONFIG_SECURITY_SELINUX 1167 int ret; 1168 1169 data->context[NFS_MAX 1170 ret = vfs_parse_fs_st 1171 1172 if (ret < 0) 1173 return ret; 1174 #else 1175 return -EINVAL; 1176 #endif 1177 } 1178 1179 break; 1180 default: 1181 goto generic; 1182 } 1183 1184 ret = nfs_validate_transport_protocol 1185 if (ret) 1186 return ret; 1187 1188 ctx->skip_reconfig_option_check = tru 1189 return 0; 1190 1191 generic: 1192 return generic_parse_monolithic(fc, d 1193 1194 out_no_data: 1195 if (is_remount_fc(fc)) { 1196 ctx->skip_reconfig_option_che 1197 return 0; 1198 } 1199 return nfs_invalf(fc, "NFS: mount pro 1200 1201 out_no_v3: 1202 return nfs_invalf(fc, "NFS: nfs_mount 1203 1204 out_no_sec: 1205 return nfs_invalf(fc, "NFS: nfs_mount 1206 1207 out_nomem: 1208 return -ENOMEM; 1209 1210 out_no_address: 1211 return nfs_invalf(fc, "NFS: mount pro 1212 1213 out_invalid_fh: 1214 return nfs_invalf(fc, "NFS: invalid r 1215 1216 out_invalid_data: 1217 return nfs_invalf(fc, "NFS: invalid b 1218 } 1219 1220 #if IS_ENABLED(CONFIG_NFS_V4) 1221 struct compat_nfs_string { 1222 compat_uint_t len; 1223 compat_uptr_t data; 1224 }; 1225 1226 static inline void compat_nfs_string(struct n 1227 struct c 1228 { 1229 dst->data = compat_ptr(src->data); 1230 dst->len = src->len; 1231 } 1232 1233 struct compat_nfs4_mount_data_v1 { 1234 compat_int_t version; 1235 compat_int_t flags; 1236 compat_int_t rsize; 1237 compat_int_t wsize; 1238 compat_int_t timeo; 1239 compat_int_t retrans; 1240 compat_int_t acregmin; 1241 compat_int_t acregmax; 1242 compat_int_t acdirmin; 1243 compat_int_t acdirmax; 1244 struct compat_nfs_string client_addr; 1245 struct compat_nfs_string mnt_path; 1246 struct compat_nfs_string hostname; 1247 compat_uint_t host_addrlen; 1248 compat_uptr_t host_addr; 1249 compat_int_t proto; 1250 compat_int_t auth_flavourlen; 1251 compat_uptr_t auth_flavours; 1252 }; 1253 1254 static void nfs4_compat_mount_data_conv(struc 1255 { 1256 struct compat_nfs4_mount_data_v1 *com 1257 (struct compat_nfs4_m 1258 1259 /* copy the fields backwards */ 1260 data->auth_flavours = compat_ptr(comp 1261 data->auth_flavourlen = compat->auth_ 1262 data->proto = compat->proto; 1263 data->host_addr = compat_ptr(compat-> 1264 data->host_addrlen = compat->host_add 1265 compat_nfs_string(&data->hostname, &c 1266 compat_nfs_string(&data->mnt_path, &c 1267 compat_nfs_string(&data->client_addr, 1268 data->acdirmax = compat->acdirmax; 1269 data->acdirmin = compat->acdirmin; 1270 data->acregmax = compat->acregmax; 1271 data->acregmin = compat->acregmin; 1272 data->retrans = compat->retrans; 1273 data->timeo = compat->timeo; 1274 data->wsize = compat->wsize; 1275 data->rsize = compat->rsize; 1276 data->flags = compat->flags; 1277 data->version = compat->version; 1278 } 1279 1280 /* 1281 * Validate NFSv4 mount options 1282 */ 1283 static int nfs4_parse_monolithic(struct fs_co 1284 struct nfs4_ 1285 { 1286 struct nfs_fs_context *ctx = nfs_fc2c 1287 struct sockaddr_storage *sap = &ctx-> 1288 int ret; 1289 char *c; 1290 1291 if (!data) { 1292 if (is_remount_fc(fc)) 1293 goto done; 1294 return nfs_invalf(fc, 1295 "NFS4: mount program 1296 } 1297 1298 ctx->version = 4; 1299 1300 if (data->version != 1) 1301 return generic_parse_monolith 1302 1303 if (in_compat_syscall()) 1304 nfs4_compat_mount_data_conv(d 1305 1306 if (data->host_addrlen > sizeof(ctx-> 1307 goto out_no_address; 1308 if (data->host_addrlen == 0) 1309 goto out_no_address; 1310 ctx->nfs_server.addrlen = data->host_ 1311 if (copy_from_user(sap, data->host_ad 1312 return -EFAULT; 1313 if (!nfs_verify_server_address(sap)) 1314 goto out_no_address; 1315 ctx->nfs_server.port = ntohs(((struct 1316 1317 if (data->auth_flavourlen) { 1318 rpc_authflavor_t pseudoflavor 1319 1320 if (data->auth_flavourlen > 1 1321 goto out_inval_auth; 1322 if (copy_from_user(&pseudofla 1323 sizeof(pse 1324 return -EFAULT; 1325 ctx->selected_flavor = pseudo 1326 } else { 1327 ctx->selected_flavor = RPC_AU 1328 } 1329 1330 c = strndup_user(data->hostname.data, 1331 if (IS_ERR(c)) 1332 return PTR_ERR(c); 1333 ctx->nfs_server.hostname = c; 1334 1335 c = strndup_user(data->mnt_path.data, 1336 if (IS_ERR(c)) 1337 return PTR_ERR(c); 1338 ctx->nfs_server.export_path = c; 1339 trace_nfs_mount_path(c); 1340 1341 c = strndup_user(data->client_addr.da 1342 if (IS_ERR(c)) 1343 return PTR_ERR(c); 1344 ctx->client_address = c; 1345 1346 /* 1347 * Translate to nfs_fs_context, which 1348 * can deal with. 1349 */ 1350 1351 ctx->flags = data->flags & NFS4_ 1352 ctx->rsize = data->rsize; 1353 ctx->wsize = data->wsize; 1354 ctx->timeo = data->timeo; 1355 ctx->retrans = data->retrans; 1356 ctx->acregmin = data->acregmin; 1357 ctx->acregmax = data->acregmax; 1358 ctx->acdirmin = data->acdirmin; 1359 ctx->acdirmax = data->acdirmax; 1360 ctx->nfs_server.protocol = data->prot 1361 ret = nfs_validate_transport_protocol 1362 if (ret) 1363 return ret; 1364 done: 1365 ctx->skip_reconfig_option_check = tru 1366 return 0; 1367 1368 out_inval_auth: 1369 return nfs_invalf(fc, "NFS4: Invalid 1370 data->auth_flavourlen); 1371 1372 out_no_address: 1373 return nfs_invalf(fc, "NFS4: mount pr 1374 } 1375 #endif 1376 1377 /* 1378 * Parse a monolithic block of data from sys_ 1379 */ 1380 static int nfs_fs_context_parse_monolithic(st 1381 vo 1382 { 1383 if (fc->fs_type == &nfs_fs_type) 1384 return nfs23_parse_monolithic 1385 1386 #if IS_ENABLED(CONFIG_NFS_V4) 1387 if (fc->fs_type == &nfs4_fs_type) 1388 return nfs4_parse_monolithic( 1389 #endif 1390 1391 return nfs_invalf(fc, "NFS: Unsupport 1392 } 1393 1394 /* 1395 * Validate the preparsed information in the 1396 */ 1397 static int nfs_fs_context_validate(struct fs_ 1398 { 1399 struct nfs_fs_context *ctx = nfs_fc2c 1400 struct nfs_subversion *nfs_mod; 1401 struct sockaddr_storage *sap = &ctx-> 1402 int max_namelen = PAGE_SIZE; 1403 int max_pathlen = NFS_MAXPATHLEN; 1404 int port = 0; 1405 int ret; 1406 1407 if (!fc->source) 1408 goto out_no_device_name; 1409 1410 /* Check for sanity first. */ 1411 if (ctx->minorversion && ctx->version 1412 goto out_minorversion_mismatc 1413 1414 if (ctx->options & NFS_OPTION_MIGRATI 1415 (ctx->version != 4 || ctx->minorv 1416 goto out_migration_misuse; 1417 1418 /* Verify that any proto=/mountproto= 1419 * families in the addr=/mountaddr= o 1420 */ 1421 if (ctx->protofamily != AF_UNSPEC && 1422 ctx->protofamily != ctx->nfs_serv 1423 goto out_proto_mismatch; 1424 1425 if (ctx->mountfamily != AF_UNSPEC) { 1426 if (ctx->mount_server.addrlen 1427 if (ctx->mountfamily 1428 goto out_moun 1429 } else { 1430 if (ctx->mountfamily 1431 goto out_moun 1432 } 1433 } 1434 1435 if (!nfs_verify_server_address(sap)) 1436 goto out_no_address; 1437 1438 ret = nfs_validate_transport_protocol 1439 if (ret) 1440 return ret; 1441 1442 if (ctx->version == 4) { 1443 if (IS_ENABLED(CONFIG_NFS_V4) 1444 if (ctx->nfs_server.p 1445 port = NFS_RD 1446 else 1447 port = NFS_PO 1448 max_namelen = NFS4_MA 1449 max_pathlen = NFS4_MA 1450 ctx->flags &= ~(NFS_M 1451 NFS_M 1452 NFS_M 1453 } else { 1454 goto out_v4_not_compi 1455 } 1456 } else { 1457 nfs_set_mount_transport_proto 1458 if (ctx->nfs_server.protocol 1459 port = NFS_RDMA_PORT; 1460 } 1461 1462 nfs_set_port(sap, &ctx->nfs_server.po 1463 1464 ret = nfs_parse_source(fc, max_namele 1465 if (ret < 0) 1466 return ret; 1467 1468 /* Load the NFS protocol module if we 1469 if (!ctx->nfs_mod) { 1470 nfs_mod = get_nfs_version(ctx 1471 if (IS_ERR(nfs_mod)) { 1472 ret = PTR_ERR(nfs_mod 1473 goto out_version_unav 1474 } 1475 ctx->nfs_mod = nfs_mod; 1476 } 1477 1478 /* Ensure the filesystem context has 1479 if (fc->fs_type != ctx->nfs_mod->nfs_ 1480 module_put(fc->fs_type->owner 1481 __module_get(ctx->nfs_mod->nf 1482 fc->fs_type = ctx->nfs_mod->n 1483 } 1484 return 0; 1485 1486 out_no_device_name: 1487 return nfs_invalf(fc, "NFS: Device na 1488 out_v4_not_compiled: 1489 nfs_errorf(fc, "NFS: NFSv4 is not com 1490 return -EPROTONOSUPPORT; 1491 out_no_address: 1492 return nfs_invalf(fc, "NFS: mount pro 1493 out_mountproto_mismatch: 1494 return nfs_invalf(fc, "NFS: Mount ser 1495 out_proto_mismatch: 1496 return nfs_invalf(fc, "NFS: Server ad 1497 out_minorversion_mismatch: 1498 return nfs_invalf(fc, "NFS: Mount opt 1499 ctx->version, ctx-> 1500 out_migration_misuse: 1501 return nfs_invalf(fc, "NFS: 'Migratio 1502 out_version_unavailable: 1503 nfs_errorf(fc, "NFS: Version unavaila 1504 return ret; 1505 } 1506 1507 /* 1508 * Create an NFS superblock by the appropriat 1509 */ 1510 static int nfs_get_tree(struct fs_context *fc 1511 { 1512 struct nfs_fs_context *ctx = nfs_fc2c 1513 int err = nfs_fs_context_validate(fc) 1514 1515 if (err) 1516 return err; 1517 if (!ctx->internal) 1518 return ctx->nfs_mod->rpc_ops- 1519 else 1520 return nfs_get_tree_common(fc 1521 } 1522 1523 /* 1524 * Handle duplication of a configuration. Th 1525 * it can't deal with resource pointers in th 1526 * to do that. We need to clear pointers, co 1527 * appropriate. 1528 */ 1529 static int nfs_fs_context_dup(struct fs_conte 1530 { 1531 struct nfs_fs_context *src = nfs_fc2c 1532 1533 ctx = kmemdup(src, sizeof(struct nfs_ 1534 if (!ctx) 1535 return -ENOMEM; 1536 1537 ctx->mntfh = nfs_alloc_fhandle(); 1538 if (!ctx->mntfh) { 1539 kfree(ctx); 1540 return -ENOMEM; 1541 } 1542 nfs_copy_fh(ctx->mntfh, src->mntfh); 1543 1544 __module_get(ctx->nfs_mod->owner); 1545 ctx->client_address = NUL 1546 ctx->mount_server.hostname = NUL 1547 ctx->nfs_server.export_path = NUL 1548 ctx->nfs_server.hostname = NUL 1549 ctx->fscache_uniq = NUL 1550 ctx->clone_data.fattr = NUL 1551 fc->fs_private = ctx; 1552 return 0; 1553 } 1554 1555 static void nfs_fs_context_free(struct fs_con 1556 { 1557 struct nfs_fs_context *ctx = nfs_fc2c 1558 1559 if (ctx) { 1560 if (ctx->server) 1561 nfs_free_server(ctx-> 1562 if (ctx->nfs_mod) 1563 put_nfs_version(ctx-> 1564 kfree(ctx->client_address); 1565 kfree(ctx->mount_server.hostn 1566 kfree(ctx->nfs_server.export_ 1567 kfree(ctx->nfs_server.hostnam 1568 kfree(ctx->fscache_uniq); 1569 nfs_free_fhandle(ctx->mntfh); 1570 nfs_free_fattr(ctx->clone_dat 1571 kfree(ctx); 1572 } 1573 } 1574 1575 static const struct fs_context_operations nfs 1576 .free = nfs_fs_cont 1577 .dup = nfs_fs_cont 1578 .parse_param = nfs_fs_cont 1579 .parse_monolithic = nfs_fs_cont 1580 .get_tree = nfs_get_tre 1581 .reconfigure = nfs_reconfi 1582 }; 1583 1584 /* 1585 * Prepare superblock configuration. We use 1586 * context. This may be the current process' 1587 * container's namespaces. 1588 */ 1589 static int nfs_init_fs_context(struct fs_cont 1590 { 1591 struct nfs_fs_context *ctx; 1592 1593 ctx = kzalloc(sizeof(struct nfs_fs_co 1594 if (unlikely(!ctx)) 1595 return -ENOMEM; 1596 1597 ctx->mntfh = nfs_alloc_fhandle(); 1598 if (unlikely(!ctx->mntfh)) { 1599 kfree(ctx); 1600 return -ENOMEM; 1601 } 1602 1603 ctx->protofamily = AF_UNSPEC; 1604 ctx->mountfamily = AF_UNSPEC; 1605 ctx->mount_server.port = NFS_UNSPEC_ 1606 1607 if (fc->root) { 1608 /* reconfigure, start with th 1609 struct nfs_server *nfss = fc- 1610 struct net *net = nfss->nfs_c 1611 1612 ctx->flags = nfs 1613 ctx->rsize = nfs 1614 ctx->wsize = nfs 1615 ctx->retrans = nfs 1616 ctx->selected_flavor = nfs 1617 ctx->acregmin = nfs 1618 ctx->acregmax = nfs 1619 ctx->acdirmin = nfs 1620 ctx->acdirmax = nfs 1621 ctx->timeo = 10U 1622 ctx->nfs_server.port = nfs 1623 ctx->nfs_server.addrlen = nfs 1624 ctx->version = nfs 1625 ctx->minorversion = nfs 1626 1627 memcpy(&ctx->nfs_server._addr 1628 ctx->nfs_server.addrl 1629 1630 if (fc->net_ns != net) { 1631 put_net(fc->net_ns); 1632 fc->net_ns = get_net( 1633 } 1634 1635 ctx->nfs_mod = nfss->nfs_clie 1636 __module_get(ctx->nfs_mod->ow 1637 } else { 1638 /* defaults */ 1639 ctx->timeo = NFS 1640 ctx->retrans = NFS 1641 ctx->acregmin = NFS 1642 ctx->acregmax = NFS 1643 ctx->acdirmin = NFS 1644 ctx->acdirmax = NFS 1645 ctx->nfs_server.port = NFS 1646 ctx->nfs_server.protocol = XP 1647 ctx->selected_flavor = RPC 1648 ctx->minorversion = 0; 1649 ctx->need_mount = tru 1650 ctx->xprtsec.policy = RPC 1651 ctx->xprtsec.cert_serial 1652 ctx->xprtsec.privkey_serial 1653 1654 fc->s_iflags |= SB 1655 } 1656 fc->fs_private = ctx; 1657 fc->ops = &nfs_fs_context_ops; 1658 return 0; 1659 } 1660 1661 struct file_system_type nfs_fs_type = { 1662 .owner = THIS_MODULE 1663 .name = "nfs", 1664 .init_fs_context = nfs_init_fs 1665 .parameters = nfs_fs_para 1666 .kill_sb = nfs_kill_su 1667 .fs_flags = FS_RENAME_D 1668 }; 1669 MODULE_ALIAS_FS("nfs"); 1670 EXPORT_SYMBOL_GPL(nfs_fs_type); 1671 1672 #if IS_ENABLED(CONFIG_NFS_V4) 1673 struct file_system_type nfs4_fs_type = { 1674 .owner = THIS_MODULE 1675 .name = "nfs4", 1676 .init_fs_context = nfs_init_fs 1677 .parameters = nfs_fs_para 1678 .kill_sb = nfs_kill_su 1679 .fs_flags = FS_RENAME_D 1680 }; 1681 MODULE_ALIAS_FS("nfs4"); 1682 MODULE_ALIAS("nfs4"); 1683 EXPORT_SYMBOL_GPL(nfs4_fs_type); 1684 #endif /* CONFIG_NFS_V4 */ 1685
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.