SOURCES: kernel-desktop-CITI_NFS4_ALL.patch (NEW), kernel-desktop-...

czarny czarny at pld-linux.org
Thu Aug 23 14:10:40 CEST 2007


Author: czarny                       Date: Thu Aug 23 12:10:40 2007 GMT
Module: SOURCES                       Tag: HEAD
---- Log message:
- wholla lotta patches from kernel.spec into desktop version
- unionfs upped to 2.1.2_for_2.6.22.4

---- Files affected:
SOURCES:
   kernel-desktop-CITI_NFS4_ALL.patch (NONE -> 1.1)  (NEW), kernel-desktop-forcedeth-WON.patch (NONE -> 1.1)  (NEW), kernel-desktop-hostap.patch (NONE -> 1.1)  (NEW), kernel-desktop-NFS_ALL.patch (NONE -> 1.1)  (NEW), kernel-desktop-PF_RING.patch (NONE -> 1.1)  (NEW), kernel-desktop-routes.patch (NONE -> 1.1)  (NEW), kernel-desktop-toshiba-acpi.patch (NONE -> 1.1)  (NEW), kernel-desktop-ueagle-atm-freezer.patch (NONE -> 1.1)  (NEW), kernel-desktop-unionfs.patch (NONE -> 1.1)  (NEW)

---- Diffs:

================================================================
Index: SOURCES/kernel-desktop-CITI_NFS4_ALL.patch
diff -u /dev/null SOURCES/kernel-desktop-CITI_NFS4_ALL.patch:1.1
--- /dev/null	Thu Aug 23 14:10:40 2007
+++ SOURCES/kernel-desktop-CITI_NFS4_ALL.patch	Thu Aug 23 14:10:35 2007
@@ -0,0 +1,1999 @@
+Changes since 2.6.22-rc1-CITI_NFS4_ALL-1
+	- update to 2.6.22-rc5
+	- allow id-squashing options to vary per pseudoflavor
+	- enforce requirement that flags other than ro/rw and
+	  id-squashing flags not vary per pseudoflavor
+	- meelap: vary maximum delegation limit by RAM size
+	- meelap: don't grant delegations on files that saw conflicts
+	- silence a compiler warning in ACL code
+	- bhalevy: fix enc_stateid_sz for nfsd callbacks
+	- fix mishandling of acl errors that could cause an oops
+	- make all export finding function return -errno's on err
+	- show flavor info in /proc/net/rpc/nfsd.export/content
+	- miscellaneous cleanup
+
+---
+
+ b/fs/Kconfig                            |    1 
+ b/fs/lockd/svc.c                        |   31 ++-
+ b/fs/locks.c                            |   23 +-
+ b/fs/nfs/file.c                         |    4 
+ b/fs/nfsd/auth.c                        |   18 +-
+ b/fs/nfsd/export.c                      |  284 ++++++++++++++++++++++++++------
+ b/fs/nfsd/lockd.c                       |    1 
+ b/fs/nfsd/nfs4acl.c                     |   12 +
+ b/fs/nfsd/nfs4callback.c                |    2 
+ b/fs/nfsd/nfs4idmap.c                   |   13 +
+ b/fs/nfsd/nfs4proc.c                    |   34 +++
+ b/fs/nfsd/nfs4state.c                   |   28 ++-
+ b/fs/nfsd/nfs4xdr.c                     |   99 +++++++++++
+ b/fs/nfsd/nfsctl.c                      |    1 
+ b/fs/nfsd/nfsfh.c                       |   32 ++-
+ b/fs/nfsd/nfsproc.c                     |    3 
+ b/fs/nfsd/nfssvc.c                      |   10 +
+ b/fs/nfsd/vfs.c                         |  110 ++++++------
+ b/fs/open.c                             |   16 +
+ b/include/linux/fs.h                    |    2 
+ b/include/linux/lockd/bind.h            |    9 +
+ b/include/linux/nfsd/export.h           |   41 ++++
+ b/include/linux/nfsd/nfsd.h             |    9 -
+ b/include/linux/nfsd/state.h            |    3 
+ b/include/linux/nfsd/xdr4.h             |    7 
+ b/include/linux/sunrpc/gss_api.h        |    1 
+ b/include/linux/sunrpc/svc.h            |    2 
+ b/include/linux/sunrpc/svcauth.h        |    1 
+ b/include/linux/sunrpc/svcauth_gss.h    |    2 
+ b/net/sunrpc/auth_gss/gss_krb5_mech.c   |    1 
+ b/net/sunrpc/auth_gss/gss_mech_switch.c |   15 +
+ b/net/sunrpc/auth_gss/gss_spkm3_mech.c  |    1 
+ b/net/sunrpc/auth_gss/svcauth_gss.c     |   32 +++
+ b/net/sunrpc/svcauth_unix.c             |    7 
+ include/linux/nfsd/interface.h          |   13 -
+ 36 files changed, 693 insertions(+), 177 deletions(-)
+
+diff --git a/fs/Kconfig b/fs/Kconfig
+index 0fa0c11..76cf825 100644
+--- a/fs/Kconfig
++++ b/fs/Kconfig
+@@ -1675,6 +1675,7 @@ config NFSD_V3_ACL
+ config NFSD_V4
+ 	bool "Provide NFSv4 server support (EXPERIMENTAL)"
+ 	depends on NFSD_V3 && EXPERIMENTAL
++	select RPCSEC_GSS_KRB5
+ 	help
+ 	  If you would like to include the NFSv4 server as well as the NFSv2
+ 	  and NFSv3 servers, say Y here.  This feature is experimental, and
+diff --git a/fs/lockd/svc.c b/fs/lockd/svc.c
+index 126b1bf..6378572 100644
+--- a/fs/lockd/svc.c
++++ b/fs/lockd/svc.c
+@@ -75,18 +75,35 @@ static const int		nlm_port_min = 0, nlm_port_max = 65535;
+ 
+ static struct ctl_table_header * nlm_sysctl_table;
+ 
+-static unsigned long set_grace_period(void)
++static time_t get_lockd_grace_period(void)
+ {
+-	unsigned long grace_period;
+-
+ 	/* Note: nlm_timeout should always be nonzero */
+ 	if (nlm_grace_period)
+-		grace_period = ((nlm_grace_period + nlm_timeout - 1)
+-				/ nlm_timeout) * nlm_timeout * HZ;
++		return ((nlm_grace_period + nlm_timeout - 1)
++				/ nlm_timeout) * nlm_timeout;
+ 	else
+-		grace_period = nlm_timeout * 5 * HZ;
++		return nlm_timeout * 5;
++}
++
++time_t get_nfs_grace_period(void)
++{
++	time_t lockdgrace = get_lockd_grace_period();
++	time_t nfsdgrace = 0;
++
++	if (nlmsvc_ops)
++		nfsdgrace = nlmsvc_ops->get_grace_period();
++
++	return max(lockdgrace, nfsdgrace);
++}
++EXPORT_SYMBOL(get_nfs_grace_period);
++
++static unsigned long set_grace_period(void)
++{
++	time_t grace_period;
++
++	grace_period = get_nfs_grace_period();
+ 	nlmsvc_grace_period = 1;
+-	return grace_period + jiffies;
++	return grace_period * HZ + jiffies;
+ }
+ 
+ static inline void clear_grace_period(void)
+diff --git a/fs/locks.c b/fs/locks.c
+index 431a8b8..bcc37b9 100644
+--- a/fs/locks.c
++++ b/fs/locks.c
+@@ -661,7 +661,7 @@ static int locks_block_on_timeout(struct file_lock *blocker, struct file_lock *w
+ 	return result;
+ }
+ 
+-int
++void
+ posix_test_lock(struct file *filp, struct file_lock *fl)
+ {
+ 	struct file_lock *cfl;
+@@ -670,17 +670,15 @@ posix_test_lock(struct file *filp, struct file_lock *fl)
+ 	for (cfl = filp->f_path.dentry->d_inode->i_flock; cfl; cfl = cfl->fl_next) {
+ 		if (!IS_POSIX(cfl))
+ 			continue;
+-		if (posix_locks_conflict(cfl, fl))
++		if (posix_locks_conflict(fl, cfl))
+ 			break;
+ 	}
+-	if (cfl) {
++	if (cfl)
+ 		__locks_copy_lock(fl, cfl);
+-		unlock_kernel();
+-		return 1;
+-	} else
++	else
+ 		fl->fl_type = F_UNLCK;
+ 	unlock_kernel();
+-	return 0;
++	return;
+ }
+ 
+ EXPORT_SYMBOL(posix_test_lock);
+@@ -823,7 +821,7 @@ static int __posix_lock_file(struct inode *inode, struct file_lock *request, str
+ 	lock_kernel();
+ 	if (request->fl_type != F_UNLCK) {
+ 		for_each_lock(inode, before) {
+-			struct file_lock *fl = *before;
++			fl = *before;
+ 			if (!IS_POSIX(fl))
+ 				continue;
+ 			if (!posix_locks_conflict(request, fl))
+@@ -1169,9 +1167,9 @@ static void time_out_leases(struct inode *inode)
+  *	@inode: the inode of the file to return
+  *	@mode: the open mode (read or write)
+  *
+- *	break_lease (inlined for speed) has checked there already
+- *	is a lease on this file.  Leases are broken on a call to open()
+- *	or truncate().  This function can sleep unless you
++ *	break_lease (inlined for speed) has checked there already is at least
++ *	some kind of lock (maybe a lease) on this file.  Leases are broken on
++ *	a call to open() or truncate().  This function can sleep unless you
+  *	specified %O_NONBLOCK to your open().
+  */
+ int __break_lease(struct inode *inode, unsigned int mode)
+@@ -1597,8 +1595,7 @@ asmlinkage long sys_flock(unsigned int fd, unsigned int cmd)
+ /**
+  * vfs_test_lock - test file byte range lock
+  * @filp: The file to test lock for
+- * @fl: The lock to test
+- * @conf: Place to return a copy of the conflicting lock, if found
++ * @fl: The lock to test; also used to hold result
+  *
+  * Returns -ERRNO on failure.  Indicates presence of conflicting lock by
+  * setting conf->fl_type to something other than F_UNLCK.
+diff --git a/fs/nfs/file.c b/fs/nfs/file.c
+index 9eb8eb4..5b24e88 100644
+--- a/fs/nfs/file.c
++++ b/fs/nfs/file.c
+@@ -397,7 +397,9 @@ static int do_getlk(struct file *filp, int cmd, struct file_lock *fl)
+ 
+ 	lock_kernel();
+ 	/* Try local locking first */
+-	if (posix_test_lock(filp, fl)) {
++	posix_test_lock(filp, fl);
++	if (fl->fl_type != F_UNLCK) {
++		/* found a conflict */
+ 		goto out;
+ 	}
+ 
+diff --git a/fs/nfsd/auth.c b/fs/nfsd/auth.c
+index 6e92b0f..cf61dc8 100644
+--- a/fs/nfsd/auth.c
++++ b/fs/nfsd/auth.c
+@@ -12,17 +12,31 @@
+ 
+ #define	CAP_NFSD_MASK (CAP_FS_MASK|CAP_TO_MASK(CAP_SYS_RESOURCE))
+ 
++static int nfsexp_flags(struct svc_rqst *rqstp, struct svc_export *exp)
++{
++	struct exp_flavor_info *f;
++	struct exp_flavor_info *end = exp->ex_flavors + exp->ex_nflavors;
++
++	for (f = exp->ex_flavors; f < end; f++) {
++		if (f->pseudoflavor == rqstp->rq_flavor)
++			return f->flags;
++	}
++	return exp->ex_flags;
++
++}
++
+ int nfsd_setuser(struct svc_rqst *rqstp, struct svc_export *exp)
+ {
+ 	struct svc_cred	cred = rqstp->rq_cred;
+ 	int i;
++	int flags = nfsexp_flags(rqstp, exp);
+ 	int ret;
+ 
+-	if (exp->ex_flags & NFSEXP_ALLSQUASH) {
++	if (flags & NFSEXP_ALLSQUASH) {
+ 		cred.cr_uid = exp->ex_anon_uid;
+ 		cred.cr_gid = exp->ex_anon_gid;
+ 		cred.cr_group_info = groups_alloc(0);
+-	} else if (exp->ex_flags & NFSEXP_ROOTSQUASH) {
++	} else if (flags & NFSEXP_ROOTSQUASH) {
+ 		struct group_info *gi;
+ 		if (!cred.cr_uid)
+ 			cred.cr_uid = exp->ex_anon_uid;
+diff --git a/fs/nfsd/export.c b/fs/nfsd/export.c
+index 79bd03b..d9ed7f1 100644
+--- a/fs/nfsd/export.c
++++ b/fs/nfsd/export.c
+@@ -32,6 +32,8 @@
+ #include <linux/nfsd/nfsfh.h>
+ #include <linux/nfsd/syscall.h>
+ #include <linux/lockd/bind.h>
++#include <linux/sunrpc/msg_prot.h>
++#include <linux/sunrpc/gss_api.h>
+ 
+ #define NFSDDBG_FACILITY	NFSDDBG_EXPORT
+ 
+@@ -451,8 +453,46 @@ out_free_all:
+ 	return err;
+ }
+ 
++static int secinfo_parse(char **mesg, char *buf, struct svc_export *exp)
++{
++	int listsize, err;
++	struct exp_flavor_info *f;
++
++	err = get_int(mesg, &listsize);
++	if (err)
++		return err;
++	if (listsize < 0 || listsize > MAX_SECINFO_LIST)
++		return -EINVAL;
++
++	for (f=exp->ex_flavors; f < exp->ex_flavors + listsize; f++) {
++		err = get_int(mesg, &f->pseudoflavor);
++		if (err)
++			return err;
++		/*
++		 * Just a quick sanity check; we could also try to check
++		 * whether this pseudoflavor is supported, but at worst
++		 * an unsupported pseudoflavor on the export would just
++		 * be a pseudoflavor that won't match the flavor of any
++		 * authenticated request.  The administrator will
++		 * probably discover the problem when someone fails to
++		 * authenticate.
++		 */
++		if (f->pseudoflavor < 0)
++			return -EINVAL;
++		err = get_int(mesg, &f->flags);
++		if (err)
++			return err;
++		/* Only some flags are allowed to differ between flavors: */
++		if (~NFSEXP_SECINFO_FLAGS & (f->flags ^ exp->ex_flags))
++			return -EINVAL;
++	}
++	exp->ex_nflavors = listsize;
++	return 0;
++}
++
+ #else /* CONFIG_NFSD_V4 */
+ static inline int fsloc_parse(char **mesg, char *buf, struct nfsd4_fs_locations *fsloc) { return 0; }
++static inline int secinfo_parse(char **mesg, char *buf, struct svc_export *exp) { return 0; }
+ #endif
+ 
+ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
+@@ -476,6 +516,9 @@ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
+ 
+ 	exp.ex_uuid = NULL;
+ 
++	/* secinfo */
++	exp.ex_nflavors = 0;
++
+ 	if (mesg[mlen-1] != '\n')
+ 		return -EINVAL;
+ 	mesg[mlen-1] = 0;
+@@ -553,7 +596,9 @@ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
+ 					if (exp.ex_uuid == NULL)
+ 						err = -ENOMEM;
+ 				}
+-			} else
++			} else if (strcmp(buf, "secinfo") == 0)
++				err = secinfo_parse(&mesg, buf, &exp);
++			else
+ 				/* quietly ignore unknown words and anything
+ 				 * following. Newer user-space can try to set
+ 				 * new values, then see what the result was.
+@@ -593,6 +638,7 @@ static int svc_export_parse(struct cache_detail *cd, char *mesg, int mlen)
+ 
+ static void exp_flags(struct seq_file *m, int flag, int fsid,
+ 		uid_t anonu, uid_t anong, struct nfsd4_fs_locations *fslocs);
++static void show_secinfo(struct seq_file *m, struct svc_export *exp);
+ 
+ static int svc_export_show(struct seq_file *m,
+ 			   struct cache_detail *cd,
+@@ -622,6 +668,7 @@ static int svc_export_show(struct seq_file *m,
+ 				seq_printf(m, "%02x", exp->ex_uuid[i]);
+ 			}
+ 		}
++		show_secinfo(m, exp);
+ 	}
+ 	seq_puts(m, ")\n");
+ 	return 0;
+@@ -654,6 +701,7 @@ static void export_update(struct cache_head *cnew, struct cache_head *citem)
+ {
+ 	struct svc_export *new = container_of(cnew, struct svc_export, h);
+ 	struct svc_export *item = container_of(citem, struct svc_export, h);
++	int i;
+ 
+ 	new->ex_flags = item->ex_flags;
+ 	new->ex_anon_uid = item->ex_anon_uid;
+@@ -669,6 +717,10 @@ static void export_update(struct cache_head *cnew, struct cache_head *citem)
+ 	item->ex_fslocs.locations_count = 0;
+ 	new->ex_fslocs.migrated = item->ex_fslocs.migrated;
+ 	item->ex_fslocs.migrated = 0;
++	new->ex_nflavors = item->ex_nflavors;
++	for (i = 0; i < MAX_SECINFO_LIST; i++){
++		new->ex_flavors[i] = item->ex_flavors[i];
++	}
+ }
+ 
+ static struct cache_head *svc_export_alloc(void)
+@@ -738,16 +790,18 @@ exp_find_key(svc_client *clp, int fsid_type, u32 *fsidv, struct cache_req *reqp)
+ 	int err;
+ 	
+ 	if (!clp)
+-		return NULL;
++		return ERR_PTR(-ENOENT);
+ 
+ 	key.ek_client = clp;
+ 	key.ek_fsidtype = fsid_type;
+ 	memcpy(key.ek_fsid, fsidv, key_len(fsid_type));
+ 
+ 	ek = svc_expkey_lookup(&key);
+-	if (ek != NULL)
+-		if ((err = cache_check(&svc_expkey_cache, &ek->h, reqp)))
+-			ek = ERR_PTR(err);
++	if (ek == NULL)
++		return ERR_PTR(-ENOMEM);
++	err = cache_check(&svc_expkey_cache, &ek->h, reqp);
++	if (err)
++		return ERR_PTR(err);
+ 	return ek;
+ }
+ 
+@@ -808,30 +862,21 @@ exp_get_by_name(svc_client *clp, struct vfsmount *mnt, struct dentry *dentry,
+ 		struct cache_req *reqp)
+ {
+ 	struct svc_export *exp, key;
++	int err;
+ 	
+ 	if (!clp)
+-		return NULL;
++		return ERR_PTR(-ENOENT);
+ 
+ 	key.ex_client = clp;
+ 	key.ex_mnt = mnt;
+ 	key.ex_dentry = dentry;
+ 
+ 	exp = svc_export_lookup(&key);
+-	if (exp != NULL)  {
+-		int err;
+-
+-		err = cache_check(&svc_export_cache, &exp->h, reqp);
+-		switch (err) {
+-		case 0: break;
+-		case -EAGAIN:
+-		case -ETIMEDOUT:
+-			exp = ERR_PTR(err);
+-			break;
+-		default:
+-			exp = NULL;
+-		}
+-	}
+-
++	if (exp == NULL)
++		return ERR_PTR(-ENOMEM);
++	err = cache_check(&svc_export_cache, &exp->h, reqp);
++	if (err)
++		return ERR_PTR(err);
+ 	return exp;
+ }
+ 
+@@ -847,7 +892,7 @@ exp_parent(svc_client *clp, struct vfsmount *mnt, struct dentry *dentry,
+ 	dget(dentry);
+ 	exp = exp_get_by_name(clp, mnt, dentry, reqp);
+ 
+-	while (exp == NULL && !IS_ROOT(dentry)) {
++	while (PTR_ERR(exp) == -ENOENT && !IS_ROOT(dentry)) {
+ 		struct dentry *parent;
+ 
+ 		parent = dget_parent(dentry);
+@@ -900,7 +945,7 @@ static void exp_fsid_unhash(struct svc_export *exp)
+ 		return;
+ 
+ 	ek = exp_get_fsid_key(exp->ex_client, exp->ex_fsid);
+-	if (ek && !IS_ERR(ek)) {
++	if (!IS_ERR(ek)) {
+ 		ek->h.expiry_time = get_seconds()-1;
+ 		cache_put(&ek->h, &svc_expkey_cache);
+ 	}
+@@ -938,7 +983,7 @@ static void exp_unhash(struct svc_export *exp)
+ 	struct inode *inode = exp->ex_dentry->d_inode;
+ 
+ 	ek = exp_get_key(exp->ex_client, inode->i_sb->s_dev, inode->i_ino);
+-	if (ek && !IS_ERR(ek)) {
++	if (!IS_ERR(ek)) {
+ 		ek->h.expiry_time = get_seconds()-1;
+ 		cache_put(&ek->h, &svc_expkey_cache);
+ 	}
+@@ -989,13 +1034,12 @@ exp_export(struct nfsctl_export *nxp)
+ 
+ 	/* must make sure there won't be an ex_fsid clash */
+ 	if ((nxp->ex_flags & NFSEXP_FSID) &&
+-	    (fsid_key = exp_get_fsid_key(clp, nxp->ex_dev)) &&
+-	    !IS_ERR(fsid_key) &&
++	    (!IS_ERR(fsid_key = exp_get_fsid_key(clp, nxp->ex_dev))) &&
+ 	    fsid_key->ek_mnt &&
+ 	    (fsid_key->ek_mnt != nd.mnt || fsid_key->ek_dentry != nd.dentry) )
+ 		goto finish;
+ 
+-	if (exp) {
++	if (!IS_ERR(exp)) {
+ 		/* just a flags/id/fsid update */
+ 
+ 		exp_fsid_unhash(exp);
+@@ -1104,7 +1148,7 @@ exp_unexport(struct nfsctl_export *nxp)
+ 	err = -EINVAL;
+ 	exp = exp_get_by_name(dom, nd.mnt, nd.dentry, NULL);
+ 	path_release(&nd);
+-	if (!exp)
++	if (IS_ERR(exp))
+ 		goto out_domain;
+ 
+ 	exp_do_unexport(exp);
+@@ -1149,10 +1193,6 @@ exp_rootfh(svc_client *clp, char *path, struct knfsd_fh *f, int maxsize)
+ 		err = PTR_ERR(exp);
+ 		goto out;
+ 	}
+-	if (!exp) {
+-		dprintk("nfsd: exp_rootfh export not found.\n");
+-		goto out;
+-	}
+ 
+ 	/*
+ 	 * fh must be initialized before calling fh_compose
+@@ -1176,17 +1216,130 @@ exp_find(struct auth_domain *clp, int fsid_type, u32 *fsidv,
+ {
+ 	struct svc_export *exp;
+ 	struct svc_expkey *ek = exp_find_key(clp, fsid_type, fsidv, reqp);
+-	if (!ek || IS_ERR(ek))
++	if (IS_ERR(ek))
+ 		return ERR_PTR(PTR_ERR(ek));
+ 
+ 	exp = exp_get_by_name(clp, ek->ek_mnt, ek->ek_dentry, reqp);
+ 	cache_put(&ek->h, &svc_expkey_cache);
+ 
+-	if (!exp || IS_ERR(exp))
++	if (IS_ERR(exp))
+ 		return ERR_PTR(PTR_ERR(exp));
+ 	return exp;
+ }
+ 
++__be32 check_nfsd_access(struct svc_export *exp, struct svc_rqst *rqstp)
++{
++	struct exp_flavor_info *f;
++	struct exp_flavor_info *end = exp->ex_flavors + exp->ex_nflavors;
++
++	/* legacy gss-only clients are always OK: */
++	if (exp->ex_client == rqstp->rq_gssclient)
++		return 0;
++	/* ip-address based client; check sec= export option: */
++	for (f = exp->ex_flavors; f < end; f++) {
++		if (f->pseudoflavor == rqstp->rq_flavor)
++			return 0;
++	}
++	/* defaults in absence of sec= options: */
++	if (exp->ex_nflavors == 0) {
++		if (rqstp->rq_flavor == RPC_AUTH_NULL ||
++		    rqstp->rq_flavor == RPC_AUTH_UNIX)
++			return 0;
++	}
++	return nfserr_wrongsec;
++}
++
++/*
++ * Uses rq_client and rq_gssclient to find an export; uses rq_client (an
++ * auth_unix client) if it's available and has secinfo information;
++ * otherwise, will try to use rq_gssclient.
++ *
++ * Called from functions that handle requests; functions that do work on
++ * behalf of mountd are passed a single client name to use, and should
++ * use exp_get_by_name() or exp_find().
++ */
++struct svc_export *
++rqst_exp_get_by_name(struct svc_rqst *rqstp, struct vfsmount *mnt,
++		struct dentry *dentry)
++{
++	struct svc_export *gssexp, *exp = NULL;
++
++	if (rqstp->rq_client == NULL)
++		goto gss;
++
++	/* First try the auth_unix client: */
++	exp = exp_get_by_name(rqstp->rq_client, mnt, dentry,
++						&rqstp->rq_chandle);
++	if (PTR_ERR(exp) == -ENOENT)
++		goto gss;
++	if (IS_ERR(exp))
++		return exp;
++	/* If it has secinfo, assume there are no gss/... clients */
++	if (exp->ex_nflavors > 0)
++		return exp;
++gss:
++	/* Otherwise, try falling back on gss client */
++	if (rqstp->rq_gssclient == NULL)
++		return exp;
++	gssexp = exp_get_by_name(rqstp->rq_gssclient, mnt, dentry,
++						&rqstp->rq_chandle);
++	if (PTR_ERR(gssexp) == -ENOENT)
++		return exp;
++	if (exp)
++		exp_put(exp);
++	return gssexp;
++}
++
++struct svc_export *
++rqst_exp_find(struct svc_rqst *rqstp, int fsid_type, u32 *fsidv)
++{
++	struct svc_export *gssexp, *exp = NULL;
++
++	if (rqstp->rq_client == NULL)
++		goto gss;
++
++	/* First try the auth_unix client: */
++	exp = exp_find(rqstp->rq_client, fsid_type, fsidv, &rqstp->rq_chandle);
++	if (PTR_ERR(exp) == -ENOENT)
++		goto gss;
++	if (IS_ERR(exp))
++		return exp;
++	/* If it has secinfo, assume there are no gss/... clients */
++	if (exp->ex_nflavors > 0)
++		return exp;
++gss:
++	/* Otherwise, try falling back on gss client */
++	if (rqstp->rq_gssclient == NULL)
++		return exp;
++	gssexp = exp_find(rqstp->rq_gssclient, fsid_type, fsidv,
++						&rqstp->rq_chandle);
++	if (PTR_ERR(gssexp) == -ENOENT)
++		return exp;
++	if (exp)
++		exp_put(exp);
++	return gssexp;
++}
++
++struct svc_export *
++rqst_exp_parent(struct svc_rqst *rqstp, struct vfsmount *mnt,
++		struct dentry *dentry)
++{
++	struct svc_export *exp;
++
++	dget(dentry);
++	exp = rqst_exp_get_by_name(rqstp, mnt, dentry);
++
<<Diff was trimmed, longer than 597 lines>>


More information about the pld-cvs-commit mailing list