aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/nfs/super.c43
-rw-r--r--include/linux/nfs4_mount.h3
-rw-r--r--include/linux/nfs_mount.h1
3 files changed, 41 insertions, 6 deletions
diff --git a/fs/nfs/super.c b/fs/nfs/super.c
index 064e69d2fdde..1b555cd41e3b 100644
--- a/fs/nfs/super.c
+++ b/fs/nfs/super.c
@@ -100,6 +100,7 @@ enum {
100 Opt_udp, Opt_tcp, 100 Opt_udp, Opt_tcp,
101 Opt_acl, Opt_noacl, 101 Opt_acl, Opt_noacl,
102 Opt_rdirplus, Opt_nordirplus, 102 Opt_rdirplus, Opt_nordirplus,
103 Opt_sharecache, Opt_nosharecache,
103 104
104 /* Mount options that take integer arguments */ 105 /* Mount options that take integer arguments */
105 Opt_port, 106 Opt_port,
@@ -146,6 +147,8 @@ static match_table_t nfs_mount_option_tokens = {
146 { Opt_noacl, "noacl" }, 147 { Opt_noacl, "noacl" },
147 { Opt_rdirplus, "rdirplus" }, 148 { Opt_rdirplus, "rdirplus" },
148 { Opt_nordirplus, "nordirplus" }, 149 { Opt_nordirplus, "nordirplus" },
150 { Opt_sharecache, "sharecache" },
151 { Opt_nosharecache, "nosharecache" },
149 152
150 { Opt_port, "port=%u" }, 153 { Opt_port, "port=%u" },
151 { Opt_rsize, "rsize=%u" }, 154 { Opt_rsize, "rsize=%u" },
@@ -450,6 +453,7 @@ static void nfs_show_mount_options(struct seq_file *m, struct nfs_server *nfss,
450 { NFS_MOUNT_NONLM, ",nolock", "" }, 453 { NFS_MOUNT_NONLM, ",nolock", "" },
451 { NFS_MOUNT_NOACL, ",noacl", "" }, 454 { NFS_MOUNT_NOACL, ",noacl", "" },
452 { NFS_MOUNT_NORDIRPLUS, ",nordirplus", "" }, 455 { NFS_MOUNT_NORDIRPLUS, ",nordirplus", "" },
456 { NFS_MOUNT_UNSHARED, ",nosharecache", ""},
453 { 0, NULL, NULL } 457 { 0, NULL, NULL }
454 }; 458 };
455 const struct proc_nfs_info *nfs_infop; 459 const struct proc_nfs_info *nfs_infop;
@@ -714,6 +718,12 @@ static int nfs_parse_mount_options(char *raw,
714 case Opt_nordirplus: 718 case Opt_nordirplus:
715 mnt->flags |= NFS_MOUNT_NORDIRPLUS; 719 mnt->flags |= NFS_MOUNT_NORDIRPLUS;
716 break; 720 break;
721 case Opt_sharecache:
722 mnt->flags &= ~NFS_MOUNT_UNSHARED;
723 break;
724 case Opt_nosharecache:
725 mnt->flags |= NFS_MOUNT_UNSHARED;
726 break;
717 727
718 case Opt_port: 728 case Opt_port:
719 if (match_int(args, &option)) 729 if (match_int(args, &option))
@@ -1309,6 +1319,9 @@ static int nfs_compare_super(struct super_block *sb, void *data)
1309 1319
1310 if (old->nfs_client != server->nfs_client) 1320 if (old->nfs_client != server->nfs_client)
1311 return 0; 1321 return 0;
1322 /* Note: NFS_MOUNT_UNSHARED == NFS4_MOUNT_UNSHARED */
1323 if (old->flags & NFS_MOUNT_UNSHARED)
1324 return 0;
1312 if (memcmp(&old->fsid, &server->fsid, sizeof(old->fsid)) != 0) 1325 if (memcmp(&old->fsid, &server->fsid, sizeof(old->fsid)) != 0)
1313 return 0; 1326 return 0;
1314 return 1; 1327 return 1;
@@ -1322,6 +1335,7 @@ static int nfs_get_sb(struct file_system_type *fs_type,
1322 struct nfs_fh mntfh; 1335 struct nfs_fh mntfh;
1323 struct nfs_mount_data *data = raw_data; 1336 struct nfs_mount_data *data = raw_data;
1324 struct dentry *mntroot; 1337 struct dentry *mntroot;
1338 int (*compare_super)(struct super_block *, void *) = nfs_compare_super;
1325 int error; 1339 int error;
1326 1340
1327 /* Validate the mount data */ 1341 /* Validate the mount data */
@@ -1336,8 +1350,11 @@ static int nfs_get_sb(struct file_system_type *fs_type,
1336 goto out; 1350 goto out;
1337 } 1351 }
1338 1352
1353 if (server->flags & NFS_MOUNT_UNSHARED)
1354 compare_super = NULL;
1355
1339 /* Get a superblock - note that we may end up sharing one that already exists */ 1356 /* Get a superblock - note that we may end up sharing one that already exists */
1340 s = sget(fs_type, nfs_compare_super, nfs_set_super, server); 1357 s = sget(fs_type, compare_super, nfs_set_super, server);
1341 if (IS_ERR(s)) { 1358 if (IS_ERR(s)) {
1342 error = PTR_ERR(s); 1359 error = PTR_ERR(s);
1343 goto out_err_nosb; 1360 goto out_err_nosb;
@@ -1402,6 +1419,7 @@ static int nfs_xdev_get_sb(struct file_system_type *fs_type, int flags,
1402 struct super_block *s; 1419 struct super_block *s;
1403 struct nfs_server *server; 1420 struct nfs_server *server;
1404 struct dentry *mntroot; 1421 struct dentry *mntroot;
1422 int (*compare_super)(struct super_block *, void *) = nfs_compare_super;
1405 int error; 1423 int error;
1406 1424
1407 dprintk("--> nfs_xdev_get_sb()\n"); 1425 dprintk("--> nfs_xdev_get_sb()\n");
@@ -1413,8 +1431,11 @@ static int nfs_xdev_get_sb(struct file_system_type *fs_type, int flags,
1413 goto out_err_noserver; 1431 goto out_err_noserver;
1414 } 1432 }
1415 1433
1434 if (server->flags & NFS_MOUNT_UNSHARED)
1435 compare_super = NULL;
1436
1416 /* Get a superblock - note that we may end up sharing one that already exists */ 1437 /* Get a superblock - note that we may end up sharing one that already exists */
1417 s = sget(&nfs_fs_type, nfs_compare_super, nfs_set_super, server); 1438 s = sget(&nfs_fs_type, compare_super, nfs_set_super, server);
1418 if (IS_ERR(s)) { 1439 if (IS_ERR(s)) {
1419 error = PTR_ERR(s); 1440 error = PTR_ERR(s);
1420 goto out_err_nosb; 1441 goto out_err_nosb;
@@ -1657,6 +1678,7 @@ static int nfs4_get_sb(struct file_system_type *fs_type,
1657 struct nfs_fh mntfh; 1678 struct nfs_fh mntfh;
1658 struct dentry *mntroot; 1679 struct dentry *mntroot;
1659 char *mntpath = NULL, *hostname = NULL, *ip_addr = NULL; 1680 char *mntpath = NULL, *hostname = NULL, *ip_addr = NULL;
1681 int (*compare_super)(struct super_block *, void *) = nfs_compare_super;
1660 int error; 1682 int error;
1661 1683
1662 /* Validate the mount data */ 1684 /* Validate the mount data */
@@ -1673,8 +1695,11 @@ static int nfs4_get_sb(struct file_system_type *fs_type,
1673 goto out; 1695 goto out;
1674 } 1696 }
1675 1697
1698 if (server->flags & NFS4_MOUNT_UNSHARED)
1699 compare_super = NULL;
1700
1676 /* Get a superblock - note that we may end up sharing one that already exists */ 1701 /* Get a superblock - note that we may end up sharing one that already exists */
1677 s = sget(fs_type, nfs_compare_super, nfs_set_super, server); 1702 s = sget(fs_type, compare_super, nfs_set_super, server);
1678 if (IS_ERR(s)) { 1703 if (IS_ERR(s)) {
1679 error = PTR_ERR(s); 1704 error = PTR_ERR(s);
1680 goto out_free; 1705 goto out_free;
@@ -1740,6 +1765,7 @@ static int nfs4_xdev_get_sb(struct file_system_type *fs_type, int flags,
1740 struct super_block *s; 1765 struct super_block *s;
1741 struct nfs_server *server; 1766 struct nfs_server *server;
1742 struct dentry *mntroot; 1767 struct dentry *mntroot;
1768 int (*compare_super)(struct super_block *, void *) = nfs_compare_super;
1743 int error; 1769 int error;
1744 1770
1745 dprintk("--> nfs4_xdev_get_sb()\n"); 1771 dprintk("--> nfs4_xdev_get_sb()\n");
@@ -1751,8 +1777,11 @@ static int nfs4_xdev_get_sb(struct file_system_type *fs_type, int flags,
1751 goto out_err_noserver; 1777 goto out_err_noserver;
1752 } 1778 }
1753 1779
1780 if (server->flags & NFS4_MOUNT_UNSHARED)
1781 compare_super = NULL;
1782
1754 /* Get a superblock - note that we may end up sharing one that already exists */ 1783 /* Get a superblock - note that we may end up sharing one that already exists */
1755 s = sget(&nfs_fs_type, nfs_compare_super, nfs_set_super, server); 1784 s = sget(&nfs_fs_type, compare_super, nfs_set_super, server);
1756 if (IS_ERR(s)) { 1785 if (IS_ERR(s)) {
1757 error = PTR_ERR(s); 1786 error = PTR_ERR(s);
1758 goto out_err_nosb; 1787 goto out_err_nosb;
@@ -1807,6 +1836,7 @@ static int nfs4_referral_get_sb(struct file_system_type *fs_type, int flags,
1807 struct nfs_server *server; 1836 struct nfs_server *server;
1808 struct dentry *mntroot; 1837 struct dentry *mntroot;
1809 struct nfs_fh mntfh; 1838 struct nfs_fh mntfh;
1839 int (*compare_super)(struct super_block *, void *) = nfs_compare_super;
1810 int error; 1840 int error;
1811 1841
1812 dprintk("--> nfs4_referral_get_sb()\n"); 1842 dprintk("--> nfs4_referral_get_sb()\n");
@@ -1818,8 +1848,11 @@ static int nfs4_referral_get_sb(struct file_system_type *fs_type, int flags,
1818 goto out_err_noserver; 1848 goto out_err_noserver;
1819 } 1849 }
1820 1850
1851 if (server->flags & NFS4_MOUNT_UNSHARED)
1852 compare_super = NULL;
1853
1821 /* Get a superblock - note that we may end up sharing one that already exists */ 1854 /* Get a superblock - note that we may end up sharing one that already exists */
1822 s = sget(&nfs_fs_type, nfs_compare_super, nfs_set_super, server); 1855 s = sget(&nfs_fs_type, compare_super, nfs_set_super, server);
1823 if (IS_ERR(s)) { 1856 if (IS_ERR(s)) {
1824 error = PTR_ERR(s); 1857 error = PTR_ERR(s);
1825 goto out_err_nosb; 1858 goto out_err_nosb;
diff --git a/include/linux/nfs4_mount.h b/include/linux/nfs4_mount.h
index d8d7480e5a47..a0dcf6655657 100644
--- a/include/linux/nfs4_mount.h
+++ b/include/linux/nfs4_mount.h
@@ -65,6 +65,7 @@ struct nfs4_mount_data {
65#define NFS4_MOUNT_NOCTO 0x0010 /* 1 */ 65#define NFS4_MOUNT_NOCTO 0x0010 /* 1 */
66#define NFS4_MOUNT_NOAC 0x0020 /* 1 */ 66#define NFS4_MOUNT_NOAC 0x0020 /* 1 */
67#define NFS4_MOUNT_STRICTLOCK 0x1000 /* 1 */ 67#define NFS4_MOUNT_STRICTLOCK 0x1000 /* 1 */
68#define NFS4_MOUNT_FLAGMASK 0x1033 68#define NFS4_MOUNT_UNSHARED 0x8000 /* 1 */
69#define NFS4_MOUNT_FLAGMASK 0x9033
69 70
70#endif 71#endif
diff --git a/include/linux/nfs_mount.h b/include/linux/nfs_mount.h
index 0b82a17c705b..a3ade89a64d2 100644
--- a/include/linux/nfs_mount.h
+++ b/include/linux/nfs_mount.h
@@ -62,6 +62,7 @@ struct nfs_mount_data {
62#define NFS_MOUNT_STRICTLOCK 0x1000 /* reserved for NFSv4 */ 62#define NFS_MOUNT_STRICTLOCK 0x1000 /* reserved for NFSv4 */
63#define NFS_MOUNT_SECFLAVOUR 0x2000 /* 5 */ 63#define NFS_MOUNT_SECFLAVOUR 0x2000 /* 5 */
64#define NFS_MOUNT_NORDIRPLUS 0x4000 /* 5 */ 64#define NFS_MOUNT_NORDIRPLUS 0x4000 /* 5 */
65#define NFS_MOUNT_UNSHARED 0x8000 /* 5 */
65#define NFS_MOUNT_FLAGMASK 0xFFFF 66#define NFS_MOUNT_FLAGMASK 0xFFFF
66 67
67#endif 68#endif