[prev in list] [next in list] [prev in thread] [next in thread] 

List:       linux-nfsv4
Subject:    [PATCH 1/3] : mount.nfs: Try v4 mounts first (Release 4)
From:       Steve Dickson <SteveD () redhat ! com>
Date:       2009-09-28 19:13:30
Message-ID: 4AC10ADA.4020606 () RedHat ! com
[Download RAW message or body]

commit ccca5e1577407997c4cb53483f287c73fd15bc89
Author: Steve Dickson <steved@redhat.com>
Date:   Thu Sep 24 12:43:49 2009 -0400

    Changed mount.nfs to start the protocol negotiation
    with version 4 when the version is not supplied on the
    command line.
    
    Also moved the setting of the protocol specific mandatory
    mount options to nfs_try_mount() so they can be changed
    if the the protocol version changes due to negotiations
    with the server.
    
    Signed-off-by: Steve Dickson <steved@redhat.com>

diff --git a/utils/mount/stropts.c b/utils/mount/stropts.c
index 3eb661e..9598f47 100644
--- a/utils/mount/stropts.c
+++ b/utils/mount/stropts.c
@@ -278,28 +278,12 @@ static int nfs_validate_options(struct nfsmount_info *mi)
 	if (strncmp(mi->type, "nfs4", 4) == 0)
 		mi->version = 4;
 
-	if (mi->version == 4) {
-		if (!nfs_append_clientaddr_option(sap, salen, mi->options))
-			return 0;
-	} else {
-		if (!nfs_fix_mounthost_option(mi->options))
-			return 0;
-		if (!mi->fake && !nfs_verify_lock_option(mi->options))
-			return 0;
-	}
-
 	if (!nfs_append_sloppy_option(mi->options))
 		return 0;
 
 	if (!nfs_append_addr_option(sap, salen, mi->options))
 		return 0;
 
-	/*
-	 * Update option string to be recorded in /etc/mnttab
-	 */
-	if (po_join(mi->options, mi->extra_opts) == PO_FAILED)
-		return 0;
-
 	return 1;
 }
 
@@ -422,7 +406,7 @@ static int nfs_construct_new_options(struct mount_options *options,
  * FALSE is returned if some failure occurred.
  */
 static int
-nfs_rewrite_pmap_mount_options(struct mount_options *options)
+nfs_rewrite_pmap_mount_options(struct nfsmount_info *mi)
 {
 	struct sockaddr_storage nfs_address;
 	struct sockaddr *nfs_saddr = (struct sockaddr *)&nfs_address;
@@ -432,6 +416,7 @@ nfs_rewrite_pmap_mount_options(struct mount_options *options)
 	struct sockaddr *mnt_saddr = (struct sockaddr *)&mnt_address;
 	socklen_t mnt_salen = sizeof(mnt_address);
 	struct pmap mnt_pmap;
+	struct mount_options *options = mi->options;
 	char *option;
 
 	/*
@@ -478,12 +463,79 @@ nfs_rewrite_pmap_mount_options(struct mount_options *options)
 		return 0;
 	}
 
+	mi->version = nfs_pmap.pm_vers;
+
 out:
 	errno = 0;
 	return 1;
 }
 
 /*
+ * Add the mandatory mount options which are
+ * determined by the protocol version
+ */
+static inline int nfs_mandatory_opts(struct nfsmount_info *mi)
+{
+	struct sockaddr_storage dummy;
+	struct sockaddr *sa = (struct sockaddr *)&dummy;
+	socklen_t salen = sizeof(dummy);
+
+	switch(mi->version) {
+	case 2:
+	case 3:
+		if (!nfs_fix_mounthost_option(mi->options))
+			return 0;
+		if (!mi->fake && !nfs_verify_lock_option(mi->options))
+			return 0;
+		break;
+	case 4:
+		if (!nfs_name_to_address(mi->hostname, sa, &salen))
+			return 0;
+
+		if (!nfs_append_clientaddr_option(sa, salen, mi->options))
+			return 0;
+		break;
+	default:
+		break;
+	}
+
+	return 1;
+}
+
+/*
+ * If the version has not already been set, start
+ * the server negotiation with version 4 
+ */
+static inline void nfs_set_version(struct nfsmount_info *mi)
+{
+	char new_option[512];
+	int len;
+
+	/* The version is already chosen */
+	if (mi->version)
+		return;
+
+	/* Start with version 4 */
+	mi->version = 4;
+	len = snprintf(new_option, sizeof(new_option), "v%ld", mi->version);
+	if (len < 0 || (size_t)len >= sizeof(new_option)) {
+		nfs_error(_("%s: failed to construct v4 option"), progname);
+		goto out_err;
+	}
+	if (po_append(mi->options, new_option) != PO_SUCCEEDED) {
+		nfs_error(_("%s: malloc failed during construction v4 option"),
+			progname);
+		goto out_err;
+	}
+
+	return;
+
+out_err:
+	mi->version = 0;
+	return;
+}
+
+/*
  * Do the mount(2) system call.
  *
  * Returns TRUE if successful, otherwise FALSE.
@@ -494,11 +546,23 @@ static int nfs_try_mount(struct nfsmount_info *mi)
 	char *options = NULL;
 	int result;
 
+	/* 
+	 * Set protocol version if its not already set
+	 */
+	nfs_set_version(mi);
+
 	if (mi->version != 4) {
-		if (!nfs_rewrite_pmap_mount_options(mi->options))
+		if (!nfs_rewrite_pmap_mount_options(mi))
 			return 0;
 	}
 
+	/*
+	 * Now, set the mandatory mount options that are 
+	 * version specific
+	 */
+	if (!nfs_mandatory_opts(mi))
+		return 0;
+
 	if (po_join(mi->options, &options) == PO_FAILED) {
 		errno = EIO;
 		return 0;
@@ -518,6 +582,18 @@ static int nfs_try_mount(struct nfsmount_info *mi)
 		nfs_error(_("%s: mount(2): %s"), progname, strerror(save));
 		errno = save;
 	}
+
+	/*
+	 * If the mount succeeded update option string to be 
+	 * recorded in /etc/mnttab
+	 */
+	if (!result) {
+		if (po_join(mi->options, mi->extra_opts) == PO_FAILED) {
+			errno = ENOMEM;
+			return 0;
+		}
+	}
+
 	return !result;
 }
 

_______________________________________________
NFSv4 mailing list
NFSv4@linux-nfs.org
http://linux-nfs.org/cgi-bin/mailman/listinfo/nfsv4
[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic