Browse Source

nfs4: fix referrals on mounts that use IPv6 addrs

All referrals (IPv4 addr, IPv6 addr, and DNS) are broken on mounts of
IPv6 addresses, because validation code uses a path that is parsed
from the dev_name ("<server>:<path>") by splitting on the first colon and
colons are used in IPv6 addrs.
This patch ignores colons within IPv6 addresses that are escaped by '[' and ']'.

Signed-off-by: Weston Andros Adamson <dros@netapp.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Weston Andros Adamson 13 years ago
parent
commit
1aba156763
1 changed files with 27 additions and 3 deletions
  1. 27 3
      fs/nfs/nfs4namespace.c

+ 27 - 3
fs/nfs/nfs4namespace.c

@@ -51,6 +51,30 @@ Elong:
 	return ERR_PTR(-ENAMETOOLONG);
 	return ERR_PTR(-ENAMETOOLONG);
 }
 }
 
 
+/*
+ * return the path component of "<server>:<path>"
+ *  nfspath - the "<server>:<path>" string
+ *  end - one past the last char that could contain "<server>:"
+ * returns NULL on failure
+ */
+static char *nfs_path_component(const char *nfspath, const char *end)
+{
+	char *p;
+
+	if (*nfspath == '[') {
+		/* parse [] escaped IPv6 addrs */
+		p = strchr(nfspath, ']');
+		if (p != NULL && ++p < end && *p == ':')
+			return p + 1;
+	} else {
+		/* otherwise split on first colon */
+		p = strchr(nfspath, ':');
+		if (p != NULL && p < end)
+			return p + 1;
+	}
+	return NULL;
+}
+
 /*
 /*
  * Determine the mount path as a string
  * Determine the mount path as a string
  */
  */
@@ -59,9 +83,9 @@ static char *nfs4_path(struct dentry *dentry, char *buffer, ssize_t buflen)
 	char *limit;
 	char *limit;
 	char *path = nfs_path(&limit, dentry, buffer, buflen);
 	char *path = nfs_path(&limit, dentry, buffer, buflen);
 	if (!IS_ERR(path)) {
 	if (!IS_ERR(path)) {
-		char *colon = strchr(path, ':');
-		if (colon && colon < limit)
-			path = colon + 1;
+		char *path_component = nfs_path_component(path, limit);
+		if (path_component)
+			return path_component;
 	}
 	}
 	return path;
 	return path;
 }
 }