Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit bc74b4f5 authored by Trond Myklebust's avatar Trond Myklebust
Browse files

SUNRPC: Allow the cache_detail to specify alternative upcall mechanisms



For events that are rare, such as referral DNS lookups, it makes limited
sense to have a daemon constantly listening for upcalls on a channel. An
alternative in those cases might simply be to run the app that fills the
cache using call_usermodehelper_exec() and friends.

The following patch allows the cache_detail to specify alternative upcall
mechanisms for these particular cases.

Signed-off-by: default avatarTrond Myklebust <Trond.Myklebust@netapp.com>
parent da77005f
Loading
Loading
Loading
Loading
+12 −2
Original line number Diff line number Diff line
@@ -85,6 +85,11 @@ static void expkey_request(struct cache_detail *cd,
	(*bpp)[-1] = '\n';
}

static int expkey_upcall(struct cache_detail *cd, struct cache_head *h)
{
	return sunrpc_cache_pipe_upcall(cd, h, expkey_request);
}

static struct svc_expkey *svc_expkey_update(struct svc_expkey *new, struct svc_expkey *old);
static struct svc_expkey *svc_expkey_lookup(struct svc_expkey *);
static struct cache_detail svc_expkey_cache;
@@ -259,7 +264,7 @@ static struct cache_detail svc_expkey_cache = {
	.hash_table	= expkey_table,
	.name		= "nfsd.fh",
	.cache_put	= expkey_put,
	.cache_request	= expkey_request,
	.cache_upcall	= expkey_upcall,
	.cache_parse	= expkey_parse,
	.cache_show	= expkey_show,
	.match		= expkey_match,
@@ -355,6 +360,11 @@ static void svc_export_request(struct cache_detail *cd,
	(*bpp)[-1] = '\n';
}

static int svc_export_upcall(struct cache_detail *cd, struct cache_head *h)
{
	return sunrpc_cache_pipe_upcall(cd, h, svc_export_request);
}

static struct svc_export *svc_export_update(struct svc_export *new,
					    struct svc_export *old);
static struct svc_export *svc_export_lookup(struct svc_export *);
@@ -724,7 +734,7 @@ struct cache_detail svc_export_cache = {
	.hash_table	= export_table,
	.name		= "nfsd.export",
	.cache_put	= svc_export_put,
	.cache_request	= svc_export_request,
	.cache_upcall	= svc_export_upcall,
	.cache_parse	= svc_export_parse,
	.cache_show	= svc_export_show,
	.match		= svc_export_match,
+14 −2
Original line number Diff line number Diff line
@@ -145,6 +145,12 @@ idtoname_request(struct cache_detail *cd, struct cache_head *ch, char **bpp,
	(*bpp)[-1] = '\n';
}

static int
idtoname_upcall(struct cache_detail *cd, struct cache_head *ch)
{
	return sunrpc_cache_pipe_upcall(cd, ch, idtoname_request);
}

static int
idtoname_match(struct cache_head *ca, struct cache_head *cb)
{
@@ -192,7 +198,7 @@ static struct cache_detail idtoname_cache = {
	.hash_table	= idtoname_table,
	.name		= "nfs4.idtoname",
	.cache_put	= ent_put,
	.cache_request	= idtoname_request,
	.cache_upcall	= idtoname_upcall,
	.cache_parse	= idtoname_parse,
	.cache_show	= idtoname_show,
	.warn_no_listener = warn_no_idmapd,
@@ -324,6 +330,12 @@ nametoid_request(struct cache_detail *cd, struct cache_head *ch, char **bpp,
	(*bpp)[-1] = '\n';
}

static int
nametoid_upcall(struct cache_detail *cd, struct cache_head *ch)
{
	return sunrpc_cache_pipe_upcall(cd, ch, nametoid_request);
}

static int
nametoid_match(struct cache_head *ca, struct cache_head *cb)
{
@@ -363,7 +375,7 @@ static struct cache_detail nametoid_cache = {
	.hash_table	= nametoid_table,
	.name		= "nfs4.nametoid",
	.cache_put	= ent_put,
	.cache_request	= nametoid_request,
	.cache_upcall	= nametoid_upcall,
	.cache_parse	= nametoid_parse,
	.cache_show	= nametoid_show,
	.warn_no_listener = warn_no_idmapd,
+10 −3
Original line number Diff line number Diff line
@@ -70,9 +70,9 @@ struct cache_detail {
	char			*name;
	void			(*cache_put)(struct kref *);

	void			(*cache_request)(struct cache_detail *cd,
						 struct cache_head *h,
						 char **bpp, int *blen);
	int			(*cache_upcall)(struct cache_detail *,
						struct cache_head *);

	int			(*cache_parse)(struct cache_detail *,
					       char *buf, int len);

@@ -135,6 +135,13 @@ extern struct cache_head *
sunrpc_cache_update(struct cache_detail *detail,
		    struct cache_head *new, struct cache_head *old, int hash);

extern int
sunrpc_cache_pipe_upcall(struct cache_detail *detail, struct cache_head *h,
		void (*cache_request)(struct cache_detail *,
				      struct cache_head *,
				      char **,
				      int *));


extern void cache_clean_deferred(void *owner);

+6 −1
Original line number Diff line number Diff line
@@ -181,6 +181,11 @@ static void rsi_request(struct cache_detail *cd,
	(*bpp)[-1] = '\n';
}

static int rsi_upcall(struct cache_detail *cd, struct cache_head *h)
{
	return sunrpc_cache_pipe_upcall(cd, h, rsi_request);
}


static int rsi_parse(struct cache_detail *cd,
		    char *mesg, int mlen)
@@ -270,7 +275,7 @@ static struct cache_detail rsi_cache = {
	.hash_table     = rsi_table,
	.name           = "auth.rpcsec.init",
	.cache_put      = rsi_put,
	.cache_request  = rsi_request,
	.cache_upcall   = rsi_upcall,
	.cache_parse    = rsi_parse,
	.match		= rsi_match,
	.init		= rsi_init,
+18 −8
Original line number Diff line number Diff line
@@ -176,7 +176,13 @@ struct cache_head *sunrpc_cache_update(struct cache_detail *detail,
}
EXPORT_SYMBOL_GPL(sunrpc_cache_update);

static int cache_make_upcall(struct cache_detail *detail, struct cache_head *h);
static int cache_make_upcall(struct cache_detail *cd, struct cache_head *h)
{
	if (!cd->cache_upcall)
		return -EINVAL;
	return cd->cache_upcall(cd, h);
}

/*
 * This is the generic cache management routine for all
 * the authentication caches.
@@ -322,7 +328,7 @@ static int create_cache_proc_entries(struct cache_detail *cd)
	if (p == NULL)
		goto out_nomem;

	if (cd->cache_request || cd->cache_parse) {
	if (cd->cache_upcall || cd->cache_parse) {
		p = proc_create_data("channel", S_IFREG|S_IRUSR|S_IWUSR,
				     cd->proc_ent, &cache_file_operations, cd);
		cd->channel_ent = p;
@@ -1080,10 +1086,16 @@ static void warn_no_listener(struct cache_detail *detail)
}

/*
 * register an upcall request to user-space.
 * register an upcall request to user-space and queue it up for read() by the
 * upcall daemon.
 *
 * Each request is at most one page long.
 */
static int cache_make_upcall(struct cache_detail *detail, struct cache_head *h)
int sunrpc_cache_pipe_upcall(struct cache_detail *detail, struct cache_head *h,
		void (*cache_request)(struct cache_detail *,
				      struct cache_head *,
				      char **,
				      int *))
{

	char *buf;
@@ -1091,9 +1103,6 @@ static int cache_make_upcall(struct cache_detail *detail, struct cache_head *h)
	char *bp;
	int len;

	if (detail->cache_request == NULL)
		return -EINVAL;

	if (atomic_read(&detail->readers) == 0 &&
	    detail->last_close < get_seconds() - 30) {
			warn_no_listener(detail);
@@ -1112,7 +1121,7 @@ static int cache_make_upcall(struct cache_detail *detail, struct cache_head *h)

	bp = buf; len = PAGE_SIZE;

	detail->cache_request(detail, h, &bp, &len);
	cache_request(detail, h, &bp, &len);

	if (len < 0) {
		kfree(buf);
@@ -1130,6 +1139,7 @@ static int cache_make_upcall(struct cache_detail *detail, struct cache_head *h)
	wake_up(&queue_wait);
	return 0;
}
EXPORT_SYMBOL_GPL(sunrpc_cache_pipe_upcall);

/*
 * parse a message from user-space and pass it
Loading