// SPDX-License-Identifier: GPL-2.0
/*
 * DFS referral cache routines
 *
 * Copyright (c) 2018-2019 Paulo Alcantara <palcantara@suse.de>
 */

#include <linux/jhash.h>
#include <linux/ktime.h>
#include <linux/slab.h>
#include <linux/proc_fs.h>
#include <linux/nls.h>
#include <linux/workqueue.h>
#include "cifsglob.h"
#include "smb2pdu.h"
#include "smb2proto.h"
#include "cifsproto.h"
#include "cifs_debug.h"
#include "cifs_unicode.h"
#include "smb2glob.h"

#include "dfs_cache.h"

#define CACHE_HTABLE_SIZE 32
#define CACHE_MAX_ENTRIES 64

#define IS_INTERLINK_SET(v) ((v) & (DFSREF_REFERRAL_SERVER | \
				    DFSREF_STORAGE_SERVER))

struct cache_dfs_tgt {
	char *name;
	struct list_head list;
};

struct cache_entry {
	struct hlist_node hlist;
	const char *path;
	int ttl;
	int srvtype;
	int flags;
	struct timespec64 etime;
	int path_consumed;
	int numtgts;
	struct list_head tlist;
	struct cache_dfs_tgt *tgthint;
};

struct vol_info {
	char *fullpath;
	spinlock_t smb_vol_lock;
	struct smb_vol smb_vol;
	char *mntdata;
	struct list_head list;
	struct list_head rlist;
	struct kref refcnt;
};

static struct kmem_cache *cache_slab __read_mostly;
static struct workqueue_struct *dfscache_wq __read_mostly;

static int cache_ttl;
static DEFINE_SPINLOCK(cache_ttl_lock);

static struct nls_table *cache_nlsc;

/*
 * Number of entries in the cache
 */
static atomic_t cache_count;

static struct hlist_head cache_htable[CACHE_HTABLE_SIZE];
static DECLARE_RWSEM(htable_rw_lock);

static LIST_HEAD(vol_list);
static DEFINE_SPINLOCK(vol_list_lock);

static void refresh_cache_worker(struct work_struct *work);

static DECLARE_DELAYED_WORK(refresh_task, refresh_cache_worker);

static int get_normalized_path(const char *path, char **npath)
{
	if (!path || strlen(path) < 3 || (*path != '\\' && *path != '/'))
		return -EINVAL;

	if (*path == '\\') {
		*npath = (char *)path;
	} else {
		*npath = kstrndup(path, strlen(path), GFP_KERNEL);
		if (!*npath)
			return -ENOMEM;
		convert_delimiter(*npath, '\\');
	}
	return 0;
}

static inline void free_normalized_path(const char *path, char *npath)
{
	if (path != npath)
		kfree(npath);
}

static inline bool cache_entry_expired(const struct cache_entry *ce)
{
	struct timespec64 ts;

	ktime_get_coarse_real_ts64(&ts);
	return timespec64_compare(&ts, &ce->etime) >= 0;
}

static inline void free_tgts(struct cache_entry *ce)
{
	struct cache_dfs_tgt *t, *n;

	list_for_each_entry_safe(t, n, &ce->tlist, list) {
		list_del(&t->list);
		kfree(t->name);
		kfree(t);
	}
}

static inline void flush_cache_ent(struct cache_entry *ce)
{
	hlist_del_init(&ce->hlist);
	kfree(ce->path);
	free_tgts(ce);
	atomic_dec(&cache_count);
	kmem_cache_free(cache_slab, ce);
}

static void flush_cache_ents(void)
{
	int i;

	for (i = 0; i < CACHE_HTABLE_SIZE; i++) {
		struct hlist_head *l = &cache_htable[i];
		struct hlist_node *n;
		struct cache_entry *ce;

		hlist_for_each_entry_safe(ce, n, l, hlist) {
			if (!hlist_unhashed(&ce->hlist))
				flush_cache_ent(ce);
		}
	}
}

/*
 * dfs cache /proc file
 */
static int dfscache_proc_show(struct seq_file *m, void *v)
{
	int i;
	struct cache_entry *ce;
	struct cache_dfs_tgt *t;

	seq_puts(m, "DFS cache\n---------\n");

	down_read(&htable_rw_lock);
	for (i = 0; i < CACHE_HTABLE_SIZE; i++) {
		struct hlist_head *l = &cache_htable[i];

		hlist_for_each_entry(ce, l, hlist) {
			if (hlist_unhashed(&ce->hlist))
				continue;

			seq_printf(m,
				   "cache entry: path=%s,type=%s,ttl=%d,etime=%ld,"
				   "interlink=%s,path_consumed=%d,expired=%s\n",
				   ce->path,
				   ce->srvtype == DFS_TYPE_ROOT ? "root" : "link",
				   ce->ttl, ce->etime.tv_nsec,
				   IS_INTERLINK_SET(ce->flags) ? "yes" : "no",
				   ce->path_consumed,
				   cache_entry_expired(ce) ? "yes" : "no");

			list_for_each_entry(t, &ce->tlist, list) {
				seq_printf(m, "  %s%s\n",
					   t->name,
					   ce->tgthint == t ? " (target hint)" : "");
			}
		}
	}
	up_read(&htable_rw_lock);

	return 0;
}

static ssize_t dfscache_proc_write(struct file *file, const char __user *buffer,
				   size_t count, loff_t *ppos)
{
	char c;
	int rc;

	rc = get_user(c, buffer);
	if (rc)
		return rc;

	if (c != '0')
		return -EINVAL;

	cifs_dbg(FYI, "clearing dfs cache");

	down_write(&htable_rw_lock);
	flush_cache_ents();
	up_write(&htable_rw_lock);

	return count;
}

static int dfscache_proc_open(struct inode *inode, struct file *file)
{
	return single_open(file, dfscache_proc_show, NULL);
}

const struct proc_ops dfscache_proc_ops = {
	.proc_open	= dfscache_proc_open,
	.proc_read	= seq_read,
	.proc_lseek	= seq_lseek,
	.proc_release	= single_release,
	.proc_write	= dfscache_proc_write,
};

#ifdef CONFIG_CIFS_DEBUG2
static inline void dump_tgts(const struct cache_entry *ce)
{
	struct cache_dfs_tgt *t;

	cifs_dbg(FYI, "target list:\n");
	list_for_each_entry(t, &ce->tlist, list) {
		cifs_dbg(FYI, "  %s%s\n", t->name,
			 ce->tgthint == t ? " (target hint)" : "");
	}
}

static inline void dump_ce(const struct cache_entry *ce)
{
	cifs_dbg(FYI, "cache entry: path=%s,type=%s,ttl=%d,etime=%ld,"
		 "interlink=%s,path_consumed=%d,expired=%s\n", ce->path,
		 ce->srvtype == DFS_TYPE_ROOT ? "root" : "link", ce->ttl,
		 ce->etime.tv_nsec,
		 IS_INTERLINK_SET(ce->flags) ? "yes" : "no",
		 ce->path_consumed,
		 cache_entry_expired(ce) ? "yes" : "no");
	dump_tgts(ce);
}

static inline void dump_refs(const struct dfs_info3_param *refs, int numrefs)
{
	int i;

	cifs_dbg(FYI, "DFS referrals returned by the server:\n");
	for (i = 0; i < numrefs; i++) {
		const struct dfs_info3_param *ref = &refs[i];

		cifs_dbg(FYI,
			 "\n"
			 "flags:         0x%x\n"
			 "path_consumed: %d\n"
			 "server_type:   0x%x\n"
			 "ref_flag:      0x%x\n"
			 "path_name:     %s\n"
			 "node_name:     %s\n"
			 "ttl:           %d (%dm)\n",
			 ref->flags, ref->path_consumed, ref->server_type,
			 ref->ref_flag, ref->path_name, ref->node_name,
			 ref->ttl, ref->ttl / 60);
	}
}
#else
#define dump_tgts(e)
#define dump_ce(e)
#define dump_refs(r, n)
#endif

/**
 * dfs_cache_init - Initialize DFS referral cache.
 *
 * Return zero if initialized successfully, otherwise non-zero.
 */
int dfs_cache_init(void)
{
	int rc;
	int i;

	dfscache_wq = alloc_workqueue("cifs-dfscache",
				      WQ_FREEZABLE | WQ_MEM_RECLAIM, 1);
	if (!dfscache_wq)
		return -ENOMEM;

	cache_slab = kmem_cache_create("cifs_dfs_cache",
				       sizeof(struct cache_entry), 0,
				       SLAB_HWCACHE_ALIGN, NULL);
	if (!cache_slab) {
		rc = -ENOMEM;
		goto out_destroy_wq;
	}

	for (i = 0; i < CACHE_HTABLE_SIZE; i++)
		INIT_HLIST_HEAD(&cache_htable[i]);

	atomic_set(&cache_count, 0);
	cache_nlsc = load_nls_default();

	cifs_dbg(FYI, "%s: initialized DFS referral cache\n", __func__);
	return 0;

out_destroy_wq:
	destroy_workqueue(dfscache_wq);
	return rc;
}

static inline unsigned int cache_entry_hash(const void *data, int size)
{
	unsigned int h;

	h = jhash(data, size, 0);
	return h & (CACHE_HTABLE_SIZE - 1);
}

/* Check whether second path component of @path is SYSVOL or NETLOGON */
static inline bool is_sysvol_or_netlogon(const char *path)
{
	const char *s;
	char sep = path[0];

	s = strchr(path + 1, sep) + 1;
	return !strncasecmp(s, "sysvol", strlen("sysvol")) ||
		!strncasecmp(s, "netlogon", strlen("netlogon"));
}

/* Return target hint of a DFS cache entry */
static inline char *get_tgt_name(const struct cache_entry *ce)
{
	struct cache_dfs_tgt *t = ce->tgthint;

	return t ? t->name : ERR_PTR(-ENOENT);
}

/* Return expire time out of a new entry's TTL */
static inline struct timespec64 get_expire_time(int ttl)
{
	struct timespec64 ts = {
		.tv_sec = ttl,
		.tv_nsec = 0,
	};
	struct timespec64 now;

	ktime_get_coarse_real_ts64(&now);
	return timespec64_add(now, ts);
}

/* Allocate a new DFS target */
static struct cache_dfs_tgt *alloc_target(const char *name)
{
	struct cache_dfs_tgt *t;

	t = kmalloc(sizeof(*t), GFP_ATOMIC);
	if (!t)
		return ERR_PTR(-ENOMEM);
	t->name = kstrndup(name, strlen(name), GFP_ATOMIC);
	if (!t->name) {
		kfree(t);
		return ERR_PTR(-ENOMEM);
	}
	INIT_LIST_HEAD(&t->list);
	return t;
}

/*
 * Copy DFS referral information to a cache entry and conditionally update
 * target hint.
 */
static int copy_ref_data(const struct dfs_info3_param *refs, int numrefs,
			 struct cache_entry *ce, const char *tgthint)
{
	int i;

	ce->ttl = refs[0].ttl;
	ce->etime = get_expire_time(ce->ttl);
	ce->srvtype = refs[0].server_type;
	ce->flags = refs[0].ref_flag;
	ce->path_consumed = refs[0].path_consumed;

	for (i = 0; i < numrefs; i++) {
		struct cache_dfs_tgt *t;

		t = alloc_target(refs[i].node_name);
		if (IS_ERR(t)) {
			free_tgts(ce);
			return PTR_ERR(t);
		}
		if (tgthint && !strcasecmp(t->name, tgthint)) {
			list_add(&t->list, &ce->tlist);
			tgthint = NULL;
		} else {
			list_add_tail(&t->list, &ce->tlist);
		}
		ce->numtgts++;
	}

	ce->tgthint = list_first_entry_or_null(&ce->tlist,
					       struct cache_dfs_tgt, list);

	return 0;
}

/* Allocate a new cache entry */
static struct cache_entry *alloc_cache_entry(const char *path,
					     const struct dfs_info3_param *refs,
					     int numrefs)
{
	struct cache_entry *ce;
	int rc;

	ce = kmem_cache_zalloc(cache_slab, GFP_KERNEL);
	if (!ce)
		return ERR_PTR(-ENOMEM);

	ce->path = kstrndup(path, strlen(path), GFP_KERNEL);
	if (!ce->path) {
		kmem_cache_free(cache_slab, ce);
		return ERR_PTR(-ENOMEM);
	}
	INIT_HLIST_NODE(&ce->hlist);
	INIT_LIST_HEAD(&ce->tlist);

	rc = copy_ref_data(refs, numrefs, ce, NULL);
	if (rc) {
		kfree(ce->path);
		kmem_cache_free(cache_slab, ce);
		ce = ERR_PTR(rc);
	}
	return ce;
}

/* Must be called with htable_rw_lock held */
static void remove_oldest_entry(void)
{
	int i;
	struct cache_entry *ce;
	struct cache_entry *to_del = NULL;

	for (i = 0; i < CACHE_HTABLE_SIZE; i++) {
		struct hlist_head *l = &cache_htable[i];

		hlist_for_each_entry(ce, l, hlist) {
			if (hlist_unhashed(&ce->hlist))
				continue;
			if (!to_del || timespec64_compare(&ce->etime,
							  &to_del->etime) < 0)
				to_del = ce;
		}
	}

	if (!to_del) {
		cifs_dbg(FYI, "%s: no entry to remove", __func__);
		return;
	}

	cifs_dbg(FYI, "%s: removing entry", __func__);
	dump_ce(to_del);
	flush_cache_ent(to_del);
}

/* Add a new DFS cache entry */
static int add_cache_entry(const char *path, unsigned int hash,
			   struct dfs_info3_param *refs, int numrefs)
{
	struct cache_entry *ce;

	ce = alloc_cache_entry(path, refs, numrefs);
	if (IS_ERR(ce))
		return PTR_ERR(ce);

	spin_lock(&cache_ttl_lock);
	if (!cache_ttl) {
		cache_ttl = ce->ttl;
		queue_delayed_work(dfscache_wq, &refresh_task, cache_ttl * HZ);
	} else {
		cache_ttl = min_t(int, cache_ttl, ce->ttl);
		mod_delayed_work(dfscache_wq, &refresh_task, cache_ttl * HZ);
	}
	spin_unlock(&cache_ttl_lock);

	down_write(&htable_rw_lock);
	hlist_add_head(&ce->hlist, &cache_htable[hash]);
	dump_ce(ce);
	up_write(&htable_rw_lock);

	return 0;
}

/*
 * Find a DFS cache entry in hash table and optionally check prefix path against
 * @path.
 * Use whole path components in the match.
 * Must be called with htable_rw_lock held.
 *
 * Return ERR_PTR(-ENOENT) if the entry is not found.
 */
static struct cache_entry *lookup_cache_entry(const char *path,
					      unsigned int *hash)
{
	struct cache_entry *ce;
	unsigned int h;
	bool found = false;

	h = cache_entry_hash(path, strlen(path));

	hlist_for_each_entry(ce, &cache_htable[h], hlist) {
		if (!strcasecmp(path, ce->path)) {
			found = true;
			dump_ce(ce);
			break;
		}
	}

	if (!found)
		ce = ERR_PTR(-ENOENT);
	if (hash)
		*hash = h;

	return ce;
}

static void __vol_release(struct vol_info *vi)
{
	kfree(vi->fullpath);
	kfree(vi->mntdata);
	cifs_cleanup_volume_info_contents(&vi->smb_vol);
	kfree(vi);
}

static void vol_release(struct kref *kref)
{
	struct vol_info *vi = container_of(kref, struct vol_info, refcnt);

	spin_lock(&vol_list_lock);
	list_del(&vi->list);
	spin_unlock(&vol_list_lock);
	__vol_release(vi);
}

static inline void free_vol_list(void)
{
	struct vol_info *vi, *nvi;

	list_for_each_entry_safe(vi, nvi, &vol_list, list) {
		list_del_init(&vi->list);
		__vol_release(vi);
	}
}

/**
 * dfs_cache_destroy - destroy DFS referral cache
 */
void dfs_cache_destroy(void)
{
	cancel_delayed_work_sync(&refresh_task);
	unload_nls(cache_nlsc);
	free_vol_list();
	flush_cache_ents();
	kmem_cache_destroy(cache_slab);
	destroy_workqueue(dfscache_wq);

	cifs_dbg(FYI, "%s: destroyed DFS referral cache\n", __func__);
}

/* Must be called with htable_rw_lock held */
static int __update_cache_entry(const char *path,
				const struct dfs_info3_param *refs,
				int numrefs)
{
	int rc;
	struct cache_entry *ce;
	char *s, *th = NULL;

	ce = lookup_cache_entry(path, NULL);
	if (IS_ERR(ce))
		return PTR_ERR(ce);

	if (ce->tgthint) {
		s = ce->tgthint->name;
		th = kstrndup(s, strlen(s), GFP_ATOMIC);
		if (!th)
			return -ENOMEM;
	}

	free_tgts(ce);
	ce->numtgts = 0;

	rc = copy_ref_data(refs, numrefs, ce, th);

	kfree(th);

	return rc;
}

static int get_dfs_referral(const unsigned int xid, struct cifs_ses *ses,
			    const struct nls_table *nls_codepage, int remap,
			    const char *path,  struct dfs_info3_param **refs,
			    int *numrefs)
{
	cifs_dbg(FYI, "%s: get an DFS referral for %s\n", __func__, path);

	if (!ses || !ses->server || !ses->server->ops->get_dfs_refer)
		return -EOPNOTSUPP;
	if (unlikely(!nls_codepage))
		return -EINVAL;

	*refs = NULL;
	*numrefs = 0;

	return ses->server->ops->get_dfs_refer(xid, ses, path, refs, numrefs,
					       nls_codepage, remap);
}

/* Update an expired cache entry by getting a new DFS referral from server */
static int update_cache_entry(const char *path,
			      const struct dfs_info3_param *refs,
			      int numrefs)
{

	int rc;

	down_write(&htable_rw_lock);
	rc = __update_cache_entry(path, refs, numrefs);
	up_write(&htable_rw_lock);

	return rc;
}

/*
 * Find, create or update a DFS cache entry.
 *
 * If the entry wasn't found, it will create a new one. Or if it was found but
 * expired, then it will update the entry accordingly.
 *
 * For interlinks, __cifs_dfs_mount() and expand_dfs_referral() are supposed to
 * handle them properly.
 */
static int __dfs_cache_find(const unsigned int xid, struct cifs_ses *ses,
			    const struct nls_table *nls_codepage, int remap,
			    const char *path, bool noreq)
{
	int rc;
	unsigned int hash;
	struct cache_entry *ce;
	struct dfs_info3_param *refs = NULL;
	int numrefs = 0;
	bool newent = false;

	cifs_dbg(FYI, "%s: search path: %s\n", __func__, path);

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(path, &hash);

	/*
	 * If @noreq is set, no requests will be sent to the server. Just return
	 * the cache entry.
	 */
	if (noreq) {
		up_read(&htable_rw_lock);
		return PTR_ERR_OR_ZERO(ce);
	}

	if (!IS_ERR(ce)) {
		if (!cache_entry_expired(ce)) {
			dump_ce(ce);
			up_read(&htable_rw_lock);
			return 0;
		}
	} else {
		newent = true;
	}

	up_read(&htable_rw_lock);

	/*
	 * No entry was found.
	 *
	 * Request a new DFS referral in order to create a new cache entry, or
	 * updating an existing one.
	 */
	rc = get_dfs_referral(xid, ses, nls_codepage, remap, path,
			      &refs, &numrefs);
	if (rc)
		return rc;

	dump_refs(refs, numrefs);

	if (!newent) {
		rc = update_cache_entry(path, refs, numrefs);
		goto out_free_refs;
	}

	if (atomic_read(&cache_count) >= CACHE_MAX_ENTRIES) {
		cifs_dbg(FYI, "%s: reached max cache size (%d)", __func__,
			 CACHE_MAX_ENTRIES);
		down_write(&htable_rw_lock);
		remove_oldest_entry();
		up_write(&htable_rw_lock);
	}

	rc = add_cache_entry(path, hash, refs, numrefs);
	if (!rc)
		atomic_inc(&cache_count);

out_free_refs:
	free_dfs_info_array(refs, numrefs);
	return rc;
}

/*
 * Set up a DFS referral from a given cache entry.
 *
 * Must be called with htable_rw_lock held.
 */
static int setup_referral(const char *path, struct cache_entry *ce,
			  struct dfs_info3_param *ref, const char *target)
{
	int rc;

	cifs_dbg(FYI, "%s: set up new ref\n", __func__);

	memset(ref, 0, sizeof(*ref));

	ref->path_name = kstrndup(path, strlen(path), GFP_ATOMIC);
	if (!ref->path_name)
		return -ENOMEM;

	ref->node_name = kstrndup(target, strlen(target), GFP_ATOMIC);
	if (!ref->node_name) {
		rc = -ENOMEM;
		goto err_free_path;
	}

	ref->path_consumed = ce->path_consumed;
	ref->ttl = ce->ttl;
	ref->server_type = ce->srvtype;
	ref->ref_flag = ce->flags;

	return 0;

err_free_path:
	kfree(ref->path_name);
	ref->path_name = NULL;
	return rc;
}

/* Return target list of a DFS cache entry */
static int get_targets(struct cache_entry *ce, struct dfs_cache_tgt_list *tl)
{
	int rc;
	struct list_head *head = &tl->tl_list;
	struct cache_dfs_tgt *t;
	struct dfs_cache_tgt_iterator *it, *nit;

	memset(tl, 0, sizeof(*tl));
	INIT_LIST_HEAD(head);

	list_for_each_entry(t, &ce->tlist, list) {
		it = kzalloc(sizeof(*it), GFP_ATOMIC);
		if (!it) {
			rc = -ENOMEM;
			goto err_free_it;
		}

		it->it_name = kstrndup(t->name, strlen(t->name), GFP_ATOMIC);
		if (!it->it_name) {
			kfree(it);
			rc = -ENOMEM;
			goto err_free_it;
		}

		if (ce->tgthint == t)
			list_add(&it->it_list, head);
		else
			list_add_tail(&it->it_list, head);
	}

	tl->tl_numtgts = ce->numtgts;

	return 0;

err_free_it:
	list_for_each_entry_safe(it, nit, head, it_list) {
		kfree(it->it_name);
		kfree(it);
	}
	return rc;
}

/**
 * dfs_cache_find - find a DFS cache entry
 *
 * If it doesn't find the cache entry, then it will get a DFS referral
 * for @path and create a new entry.
 *
 * In case the cache entry exists but expired, it will get a DFS referral
 * for @path and then update the respective cache entry.
 *
 * These parameters are passed down to the get_dfs_refer() call if it
 * needs to be issued:
 * @xid: syscall xid
 * @ses: smb session to issue the request on
 * @nls_codepage: charset conversion
 * @remap: path character remapping type
 * @path: path to lookup in DFS referral cache.
 *
 * @ref: when non-NULL, store single DFS referral result in it.
 * @tgt_list: when non-NULL, store complete DFS target list in it.
 *
 * Return zero if the target was found, otherwise non-zero.
 */
int dfs_cache_find(const unsigned int xid, struct cifs_ses *ses,
		   const struct nls_table *nls_codepage, int remap,
		   const char *path, struct dfs_info3_param *ref,
		   struct dfs_cache_tgt_list *tgt_list)
{
	int rc;
	char *npath;
	struct cache_entry *ce;

	rc = get_normalized_path(path, &npath);
	if (rc)
		return rc;

	rc = __dfs_cache_find(xid, ses, nls_codepage, remap, npath, false);
	if (rc)
		goto out_free_path;

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		up_read(&htable_rw_lock);
		rc = PTR_ERR(ce);
		goto out_free_path;
	}

	if (ref)
		rc = setup_referral(path, ce, ref, get_tgt_name(ce));
	else
		rc = 0;
	if (!rc && tgt_list)
		rc = get_targets(ce, tgt_list);

	up_read(&htable_rw_lock);

out_free_path:
	free_normalized_path(path, npath);
	return rc;
}

/**
 * dfs_cache_noreq_find - find a DFS cache entry without sending any requests to
 * the currently connected server.
 *
 * NOTE: This function will neither update a cache entry in case it was
 * expired, nor create a new cache entry if @path hasn't been found. It heavily
 * relies on an existing cache entry.
 *
 * @path: path to lookup in the DFS referral cache.
 * @ref: when non-NULL, store single DFS referral result in it.
 * @tgt_list: when non-NULL, store complete DFS target list in it.
 *
 * Return 0 if successful.
 * Return -ENOENT if the entry was not found.
 * Return non-zero for other errors.
 */
int dfs_cache_noreq_find(const char *path, struct dfs_info3_param *ref,
			 struct dfs_cache_tgt_list *tgt_list)
{
	int rc;
	char *npath;
	struct cache_entry *ce;

	rc = get_normalized_path(path, &npath);
	if (rc)
		return rc;

	cifs_dbg(FYI, "%s: path: %s\n", __func__, npath);

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		rc = PTR_ERR(ce);
		goto out_unlock;
	}

	if (ref)
		rc = setup_referral(path, ce, ref, get_tgt_name(ce));
	else
		rc = 0;
	if (!rc && tgt_list)
		rc = get_targets(ce, tgt_list);

out_unlock:
	up_read(&htable_rw_lock);
	free_normalized_path(path, npath);

	return rc;
}

/**
 * dfs_cache_update_tgthint - update target hint of a DFS cache entry
 *
 * If it doesn't find the cache entry, then it will get a DFS referral for @path
 * and create a new entry.
 *
 * In case the cache entry exists but expired, it will get a DFS referral
 * for @path and then update the respective cache entry.
 *
 * @xid: syscall id
 * @ses: smb session
 * @nls_codepage: charset conversion
 * @remap: type of character remapping for paths
 * @path: path to lookup in DFS referral cache.
 * @it: DFS target iterator
 *
 * Return zero if the target hint was updated successfully, otherwise non-zero.
 */
int dfs_cache_update_tgthint(const unsigned int xid, struct cifs_ses *ses,
			     const struct nls_table *nls_codepage, int remap,
			     const char *path,
			     const struct dfs_cache_tgt_iterator *it)
{
	int rc;
	char *npath;
	struct cache_entry *ce;
	struct cache_dfs_tgt *t;

	rc = get_normalized_path(path, &npath);
	if (rc)
		return rc;

	cifs_dbg(FYI, "%s: update target hint - path: %s\n", __func__, npath);

	rc = __dfs_cache_find(xid, ses, nls_codepage, remap, npath, false);
	if (rc)
		goto out_free_path;

	down_write(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		rc = PTR_ERR(ce);
		goto out_unlock;
	}

	t = ce->tgthint;

	if (likely(!strcasecmp(it->it_name, t->name)))
		goto out_unlock;

	list_for_each_entry(t, &ce->tlist, list) {
		if (!strcasecmp(t->name, it->it_name)) {
			ce->tgthint = t;
			cifs_dbg(FYI, "%s: new target hint: %s\n", __func__,
				 it->it_name);
			break;
		}
	}

out_unlock:
	up_write(&htable_rw_lock);
out_free_path:
	free_normalized_path(path, npath);

	return rc;
}

/**
 * dfs_cache_noreq_update_tgthint - update target hint of a DFS cache entry
 * without sending any requests to the currently connected server.
 *
 * NOTE: This function will neither update a cache entry in case it was
 * expired, nor create a new cache entry if @path hasn't been found. It heavily
 * relies on an existing cache entry.
 *
 * @path: path to lookup in DFS referral cache.
 * @it: target iterator which contains the target hint to update the cache
 * entry with.
 *
 * Return zero if the target hint was updated successfully, otherwise non-zero.
 */
int dfs_cache_noreq_update_tgthint(const char *path,
				   const struct dfs_cache_tgt_iterator *it)
{
	int rc;
	char *npath;
	struct cache_entry *ce;
	struct cache_dfs_tgt *t;

	if (!it)
		return -EINVAL;

	rc = get_normalized_path(path, &npath);
	if (rc)
		return rc;

	cifs_dbg(FYI, "%s: path: %s\n", __func__, npath);

	down_write(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		rc = PTR_ERR(ce);
		goto out_unlock;
	}

	rc = 0;
	t = ce->tgthint;

	if (unlikely(!strcasecmp(it->it_name, t->name)))
		goto out_unlock;

	list_for_each_entry(t, &ce->tlist, list) {
		if (!strcasecmp(t->name, it->it_name)) {
			ce->tgthint = t;
			cifs_dbg(FYI, "%s: new target hint: %s\n", __func__,
				 it->it_name);
			break;
		}
	}

out_unlock:
	up_write(&htable_rw_lock);
	free_normalized_path(path, npath);

	return rc;
}

/**
 * dfs_cache_get_tgt_referral - returns a DFS referral (@ref) from a given
 * target iterator (@it).
 *
 * @path: path to lookup in DFS referral cache.
 * @it: DFS target iterator.
 * @ref: DFS referral pointer to set up the gathered information.
 *
 * Return zero if the DFS referral was set up correctly, otherwise non-zero.
 */
int dfs_cache_get_tgt_referral(const char *path,
			       const struct dfs_cache_tgt_iterator *it,
			       struct dfs_info3_param *ref)
{
	int rc;
	char *npath;
	struct cache_entry *ce;

	if (!it || !ref)
		return -EINVAL;

	rc = get_normalized_path(path, &npath);
	if (rc)
		return rc;

	cifs_dbg(FYI, "%s: path: %s\n", __func__, npath);

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		rc = PTR_ERR(ce);
		goto out_unlock;
	}

	cifs_dbg(FYI, "%s: target name: %s\n", __func__, it->it_name);

	rc = setup_referral(path, ce, ref, it->it_name);

out_unlock:
	up_read(&htable_rw_lock);
	free_normalized_path(path, npath);

	return rc;
}

static int dup_vol(struct smb_vol *vol, struct smb_vol *new)
{
	memcpy(new, vol, sizeof(*new));

	if (vol->username) {
		new->username = kstrndup(vol->username, strlen(vol->username),
					 GFP_KERNEL);
		if (!new->username)
			return -ENOMEM;
	}
	if (vol->password) {
		new->password = kstrndup(vol->password, strlen(vol->password),
					 GFP_KERNEL);
		if (!new->password)
			goto err_free_username;
	}
	if (vol->UNC) {
		cifs_dbg(FYI, "%s: vol->UNC: %s\n", __func__, vol->UNC);
		new->UNC = kstrndup(vol->UNC, strlen(vol->UNC), GFP_KERNEL);
		if (!new->UNC)
			goto err_free_password;
	}
	if (vol->domainname) {
		new->domainname = kstrndup(vol->domainname,
					   strlen(vol->domainname), GFP_KERNEL);
		if (!new->domainname)
			goto err_free_unc;
	}
	if (vol->iocharset) {
		new->iocharset = kstrndup(vol->iocharset,
					  strlen(vol->iocharset), GFP_KERNEL);
		if (!new->iocharset)
			goto err_free_domainname;
	}
	if (vol->prepath) {
		cifs_dbg(FYI, "%s: vol->prepath: %s\n", __func__, vol->prepath);
		new->prepath = kstrndup(vol->prepath, strlen(vol->prepath),
					GFP_KERNEL);
		if (!new->prepath)
			goto err_free_iocharset;
	}

	return 0;

err_free_iocharset:
	kfree(new->iocharset);
err_free_domainname:
	kfree(new->domainname);
err_free_unc:
	kfree(new->UNC);
err_free_password:
	kzfree(new->password);
err_free_username:
	kfree(new->username);
	kfree(new);
	return -ENOMEM;
}

/**
 * dfs_cache_add_vol - add a cifs volume during mount() that will be handled by
 * DFS cache refresh worker.
 *
 * @mntdata: mount data.
 * @vol: cifs volume.
 * @fullpath: origin full path.
 *
 * Return zero if volume was set up correctly, otherwise non-zero.
 */
int dfs_cache_add_vol(char *mntdata, struct smb_vol *vol, const char *fullpath)
{
	int rc;
	struct vol_info *vi;

	if (!vol || !fullpath || !mntdata)
		return -EINVAL;

	cifs_dbg(FYI, "%s: fullpath: %s\n", __func__, fullpath);

	vi = kzalloc(sizeof(*vi), GFP_KERNEL);
	if (!vi)
		return -ENOMEM;

	vi->fullpath = kstrndup(fullpath, strlen(fullpath), GFP_KERNEL);
	if (!vi->fullpath) {
		rc = -ENOMEM;
		goto err_free_vi;
	}

	rc = dup_vol(vol, &vi->smb_vol);
	if (rc)
		goto err_free_fullpath;

	vi->mntdata = mntdata;
	spin_lock_init(&vi->smb_vol_lock);
	kref_init(&vi->refcnt);

	spin_lock(&vol_list_lock);
	list_add_tail(&vi->list, &vol_list);
	spin_unlock(&vol_list_lock);

	return 0;

err_free_fullpath:
	kfree(vi->fullpath);
err_free_vi:
	kfree(vi);
	return rc;
}

/* Must be called with vol_list_lock held */
static struct vol_info *find_vol(const char *fullpath)
{
	struct vol_info *vi;

	list_for_each_entry(vi, &vol_list, list) {
		cifs_dbg(FYI, "%s: vi->fullpath: %s\n", __func__, vi->fullpath);
		if (!strcasecmp(vi->fullpath, fullpath))
			return vi;
	}
	return ERR_PTR(-ENOENT);
}

/**
 * dfs_cache_update_vol - update vol info in DFS cache after failover
 *
 * @fullpath: fullpath to look up in volume list.
 * @server: TCP ses pointer.
 *
 * Return zero if volume was updated, otherwise non-zero.
 */
int dfs_cache_update_vol(const char *fullpath, struct TCP_Server_Info *server)
{
	struct vol_info *vi;

	if (!fullpath || !server)
		return -EINVAL;

	cifs_dbg(FYI, "%s: fullpath: %s\n", __func__, fullpath);

	spin_lock(&vol_list_lock);
	vi = find_vol(fullpath);
	if (IS_ERR(vi)) {
		spin_unlock(&vol_list_lock);
		return PTR_ERR(vi);
	}
	kref_get(&vi->refcnt);
	spin_unlock(&vol_list_lock);

	cifs_dbg(FYI, "%s: updating volume info\n", __func__);
	spin_lock(&vi->smb_vol_lock);
	memcpy(&vi->smb_vol.dstaddr, &server->dstaddr,
	       sizeof(vi->smb_vol.dstaddr));
	spin_unlock(&vi->smb_vol_lock);

	kref_put(&vi->refcnt, vol_release);

	return 0;
}

/**
 * dfs_cache_del_vol - remove volume info in DFS cache during umount()
 *
 * @fullpath: fullpath to look up in volume list.
 */
void dfs_cache_del_vol(const char *fullpath)
{
	struct vol_info *vi;

	if (!fullpath || !*fullpath)
		return;

	cifs_dbg(FYI, "%s: fullpath: %s\n", __func__, fullpath);

	spin_lock(&vol_list_lock);
	vi = find_vol(fullpath);
	spin_unlock(&vol_list_lock);

	kref_put(&vi->refcnt, vol_release);
}

/* Get all tcons that are within a DFS namespace and can be refreshed */
static void get_tcons(struct TCP_Server_Info *server, struct list_head *head)
{
	struct cifs_ses *ses;
	struct cifs_tcon *tcon;

	INIT_LIST_HEAD(head);

	spin_lock(&cifs_tcp_ses_lock);
	list_for_each_entry(ses, &server->smb_ses_list, smb_ses_list) {
		list_for_each_entry(tcon, &ses->tcon_list, tcon_list) {
			if (!tcon->need_reconnect && !tcon->need_reopen_files &&
			    tcon->dfs_path) {
				tcon->tc_count++;
				list_add_tail(&tcon->ulist, head);
			}
		}
		if (ses->tcon_ipc && !ses->tcon_ipc->need_reconnect &&
		    ses->tcon_ipc->dfs_path) {
			list_add_tail(&ses->tcon_ipc->ulist, head);
		}
	}
	spin_unlock(&cifs_tcp_ses_lock);
}

static bool is_dfs_link(const char *path)
{
	char *s;

	s = strchr(path + 1, '\\');
	if (!s)
		return false;
	return !!strchr(s + 1, '\\');
}

static char *get_dfs_root(const char *path)
{
	char *s, *npath;

	s = strchr(path + 1, '\\');
	if (!s)
		return ERR_PTR(-EINVAL);

	s = strchr(s + 1, '\\');
	if (!s)
		return ERR_PTR(-EINVAL);

	npath = kstrndup(path, s - path, GFP_KERNEL);
	if (!npath)
		return ERR_PTR(-ENOMEM);

	return npath;
}

static inline void put_tcp_server(struct TCP_Server_Info *server)
{
	cifs_put_tcp_session(server, 0);
}

static struct TCP_Server_Info *get_tcp_server(struct smb_vol *vol)
{
	struct TCP_Server_Info *server;

	server = cifs_find_tcp_session(vol);
	if (IS_ERR_OR_NULL(server))
		return NULL;

	spin_lock(&GlobalMid_Lock);
	if (server->tcpStatus != CifsGood) {
		spin_unlock(&GlobalMid_Lock);
		put_tcp_server(server);
		return NULL;
	}
	spin_unlock(&GlobalMid_Lock);

	return server;
}

/* Find root SMB session out of a DFS link path */
static struct cifs_ses *find_root_ses(struct vol_info *vi,
				      struct cifs_tcon *tcon,
				      const char *path)
{
	char *rpath;
	int rc;
	struct cache_entry *ce;
	struct dfs_info3_param ref = {0};
	char *mdata = NULL, *devname = NULL;
	struct TCP_Server_Info *server;
	struct cifs_ses *ses;
	struct smb_vol vol = {NULL};

	rpath = get_dfs_root(path);
	if (IS_ERR(rpath))
		return ERR_CAST(rpath);

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(rpath, NULL);
	if (IS_ERR(ce)) {
		up_read(&htable_rw_lock);
		ses = ERR_CAST(ce);
		goto out;
	}

	rc = setup_referral(path, ce, &ref, get_tgt_name(ce));
	if (rc) {
		up_read(&htable_rw_lock);
		ses = ERR_PTR(rc);
		goto out;
	}

	up_read(&htable_rw_lock);

	mdata = cifs_compose_mount_options(vi->mntdata, rpath, &ref,
					   &devname);
	free_dfs_info_param(&ref);

	if (IS_ERR(mdata)) {
		ses = ERR_CAST(mdata);
		mdata = NULL;
		goto out;
	}

	rc = cifs_setup_volume_info(&vol, mdata, devname, false);
	kfree(devname);

	if (rc) {
		ses = ERR_PTR(rc);
		goto out;
	}

	server = get_tcp_server(&vol);
	if (!server) {
		ses = ERR_PTR(-EHOSTDOWN);
		goto out;
	}

	ses = cifs_get_smb_ses(server, &vol);

out:
	cifs_cleanup_volume_info_contents(&vol);
	kfree(mdata);
	kfree(rpath);

	return ses;
}

/* Refresh DFS cache entry from a given tcon */
static int refresh_tcon(struct vol_info *vi, struct cifs_tcon *tcon)
{
	int rc = 0;
	unsigned int xid;
	char *path, *npath;
	struct cache_entry *ce;
	struct cifs_ses *root_ses = NULL, *ses;
	struct dfs_info3_param *refs = NULL;
	int numrefs = 0;

	xid = get_xid();

	path = tcon->dfs_path + 1;

	rc = get_normalized_path(path, &npath);
	if (rc)
		goto out_free_xid;

	down_read(&htable_rw_lock);

	ce = lookup_cache_entry(npath, NULL);
	if (IS_ERR(ce)) {
		rc = PTR_ERR(ce);
		up_read(&htable_rw_lock);
		goto out_free_path;
	}

	if (!cache_entry_expired(ce)) {
		up_read(&htable_rw_lock);
		goto out_free_path;
	}

	up_read(&htable_rw_lock);

	/* If it's a DFS Link, then use root SMB session for refreshing it */
	if (is_dfs_link(npath)) {
		ses = root_ses = find_root_ses(vi, tcon, npath);
		if (IS_ERR(ses)) {
			rc = PTR_ERR(ses);
			root_ses = NULL;
			goto out_free_path;
		}
	} else {
		ses = tcon->ses;
	}

	rc = get_dfs_referral(xid, ses, cache_nlsc, tcon->remap, npath, &refs,
			      &numrefs);
	if (!rc) {
		dump_refs(refs, numrefs);
		rc = update_cache_entry(npath, refs, numrefs);
		free_dfs_info_array(refs, numrefs);
	}

	if (root_ses)
		cifs_put_smb_ses(root_ses);

out_free_path:
	free_normalized_path(path, npath);

out_free_xid:
	free_xid(xid);
	return rc;
}

/*
 * Worker that will refresh DFS cache based on lowest TTL value from a DFS
 * referral.
 */
static void refresh_cache_worker(struct work_struct *work)
{
	struct vol_info *vi, *nvi;
	struct TCP_Server_Info *server;
	LIST_HEAD(vols);
	LIST_HEAD(tcons);
	struct cifs_tcon *tcon, *ntcon;
	int rc;

	/*
	 * Find SMB volumes that are eligible (server->tcpStatus == CifsGood)
	 * for refreshing.
	 */
	spin_lock(&vol_list_lock);
	list_for_each_entry(vi, &vol_list, list) {
		server = get_tcp_server(&vi->smb_vol);
		if (!server)
			continue;

		kref_get(&vi->refcnt);
		list_add_tail(&vi->rlist, &vols);
		put_tcp_server(server);
	}
	spin_unlock(&vol_list_lock);

	/* Walk through all TCONs and refresh any expired cache entry */
	list_for_each_entry_safe(vi, nvi, &vols, rlist) {
		spin_lock(&vi->smb_vol_lock);
		server = get_tcp_server(&vi->smb_vol);
		spin_unlock(&vi->smb_vol_lock);

		if (!server)
			goto next_vol;

		get_tcons(server, &tcons);
		rc = 0;

		list_for_each_entry_safe(tcon, ntcon, &tcons, ulist) {
			/*
			 * Skip tcp server if any of its tcons failed to refresh
			 * (possibily due to reconnects).
			 */
			if (!rc)
				rc = refresh_tcon(vi, tcon);

			list_del_init(&tcon->ulist);
			cifs_put_tcon(tcon);
		}

		put_tcp_server(server);

next_vol:
		list_del_init(&vi->rlist);
		kref_put(&vi->refcnt, vol_release);
	}

	spin_lock(&cache_ttl_lock);
	queue_delayed_work(dfscache_wq, &refresh_task, cache_ttl * HZ);
	spin_unlock(&cache_ttl_lock);
}
