|
@@ -917,7 +917,7 @@ static struct nfs_parsed_mount_data *nfs_alloc_parsed_mount_data(void)
|
|
|
data->mount_server.port = NFS_UNSPEC_PORT;
|
|
|
data->nfs_server.port = NFS_UNSPEC_PORT;
|
|
|
data->nfs_server.protocol = XPRT_TRANSPORT_TCP;
|
|
|
- data->auth_flavors[0] = RPC_AUTH_UNIX;
|
|
|
+ data->auth_flavors[0] = RPC_AUTH_MAXFLAVOR;
|
|
|
data->auth_flavor_len = 1;
|
|
|
data->minorversion = 0;
|
|
|
data->need_mount = true;
|
|
@@ -1605,49 +1605,57 @@ out_security_failure:
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
- * Match the requested auth flavors with the list returned by
|
|
|
- * the server. Returns zero and sets the mount's authentication
|
|
|
- * flavor on success; returns -EACCES if server does not support
|
|
|
- * the requested flavor.
|
|
|
+ * Select a security flavor for this mount. The selected flavor
|
|
|
+ * is planted in args->auth_flavors[0].
|
|
|
*/
|
|
|
-static int nfs_walk_authlist(struct nfs_parsed_mount_data *args,
|
|
|
- struct nfs_mount_request *request)
|
|
|
+static void nfs_select_flavor(struct nfs_parsed_mount_data *args,
|
|
|
+ struct nfs_mount_request *request)
|
|
|
{
|
|
|
- unsigned int i, j, server_authlist_len = *(request->auth_flav_len);
|
|
|
+ unsigned int i, count = *(request->auth_flav_len);
|
|
|
+ rpc_authflavor_t flavor;
|
|
|
+
|
|
|
+ if (args->auth_flavors[0] != RPC_AUTH_MAXFLAVOR)
|
|
|
+ goto out;
|
|
|
+
|
|
|
+ /*
|
|
|
+ * The NFSv2 MNT operation does not return a flavor list.
|
|
|
+ */
|
|
|
+ if (args->mount_server.version != NFS_MNT3_VERSION)
|
|
|
+ goto out_default;
|
|
|
|
|
|
/*
|
|
|
* Certain releases of Linux's mountd return an empty
|
|
|
- * flavor list. To prevent behavioral regression with
|
|
|
- * these servers (ie. rejecting mounts that used to
|
|
|
- * succeed), revert to pre-2.6.32 behavior (no checking)
|
|
|
- * if the returned flavor list is empty.
|
|
|
+ * flavor list in some cases.
|
|
|
*/
|
|
|
- if (server_authlist_len == 0)
|
|
|
- return 0;
|
|
|
+ if (count == 0)
|
|
|
+ goto out_default;
|
|
|
|
|
|
/*
|
|
|
- * We avoid sophisticated negotiating here, as there are
|
|
|
- * plenty of cases where we can get it wrong, providing
|
|
|
- * either too little or too much security.
|
|
|
- *
|
|
|
* RFC 2623, section 2.7 suggests we SHOULD prefer the
|
|
|
* flavor listed first. However, some servers list
|
|
|
- * AUTH_NULL first. Our caller plants AUTH_SYS, the
|
|
|
- * preferred default, in args->auth_flavors[0] if user
|
|
|
- * didn't specify sec= mount option.
|
|
|
+ * AUTH_NULL first. Avoid ever choosing AUTH_NULL.
|
|
|
*/
|
|
|
- for (i = 0; i < args->auth_flavor_len; i++)
|
|
|
- for (j = 0; j < server_authlist_len; j++)
|
|
|
- if (args->auth_flavors[i] == request->auth_flavs[j]) {
|
|
|
- dfprintk(MOUNT, "NFS: using auth flavor %d\n",
|
|
|
- request->auth_flavs[j]);
|
|
|
- args->auth_flavors[0] = request->auth_flavs[j];
|
|
|
- return 0;
|
|
|
- }
|
|
|
+ for (i = 0; i < count; i++) {
|
|
|
+ struct rpcsec_gss_info info;
|
|
|
+
|
|
|
+ flavor = request->auth_flavs[i];
|
|
|
+ switch (flavor) {
|
|
|
+ case RPC_AUTH_UNIX:
|
|
|
+ goto out_set;
|
|
|
+ case RPC_AUTH_NULL:
|
|
|
+ continue;
|
|
|
+ default:
|
|
|
+ if (rpcauth_get_gssinfo(flavor, &info) == 0)
|
|
|
+ goto out_set;
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
- dfprintk(MOUNT, "NFS: server does not support requested auth flavor\n");
|
|
|
- nfs_umount(request);
|
|
|
- return -EACCES;
|
|
|
+out_default:
|
|
|
+ flavor = RPC_AUTH_UNIX;
|
|
|
+out_set:
|
|
|
+ args->auth_flavors[0] = flavor;
|
|
|
+out:
|
|
|
+ dfprintk(MOUNT, "NFS: using auth flavor %d\n", args->auth_flavors[0]);
|
|
|
}
|
|
|
|
|
|
/*
|
|
@@ -1710,12 +1718,8 @@ static int nfs_request_mount(struct nfs_parsed_mount_data *args,
|
|
|
return status;
|
|
|
}
|
|
|
|
|
|
- /*
|
|
|
- * MNTv1 (NFSv2) does not support auth flavor negotiation.
|
|
|
- */
|
|
|
- if (args->mount_server.version != NFS_MNT3_VERSION)
|
|
|
- return 0;
|
|
|
- return nfs_walk_authlist(args, &request);
|
|
|
+ nfs_select_flavor(args, &request);
|
|
|
+ return 0;
|
|
|
}
|
|
|
|
|
|
struct dentry *nfs_try_mount(int flags, const char *dev_name,
|