mirror of
https://github.com/linux-msm/laptops-kernel.git
synced 2026-08-13 14:19:53 -07:00
9p: convert to the new mount API
Convert 9p to the new mount API. This patch consolidates all parsing into fs/9p/v9fs.c, which stores all results into a filesystem context which can be passed to the various transports as needed. Some of the parsing helper functions such as get_cache_mode() have been eliminated in favor of using the new mount API's enum param type, for simplicity. Signed-off-by: Eric Sandeen <sandeen@redhat.com> Message-ID: <20251010214222.1347785-5-sandeen@redhat.com> [ Dominique: handled source explicitly as per follow-up discussion ] Signed-off-by: Dominique Martinet <asmadeus@codewreck.org>
This commit is contained in:
committed by
Dominique Martinet
parent
075e8bd412
commit
1f3e4142c0
+291
-277
File diff suppressed because it is too large
Load Diff
+6
-1
@@ -10,6 +10,9 @@
|
||||
|
||||
#include <linux/backing-dev.h>
|
||||
#include <linux/netfs.h>
|
||||
#include <linux/fs_parser.h>
|
||||
#include <net/9p/client.h>
|
||||
#include <net/9p/transport.h>
|
||||
|
||||
/**
|
||||
* enum p9_session_flags - option flags for each 9P session
|
||||
@@ -163,11 +166,13 @@ static inline struct fscache_volume *v9fs_session_cache(struct v9fs_session_info
|
||||
#endif
|
||||
}
|
||||
|
||||
extern const struct fs_parameter_spec v9fs_param_spec[];
|
||||
|
||||
extern int v9fs_parse_param(struct fs_context *fc, struct fs_parameter *param);
|
||||
extern int v9fs_show_options(struct seq_file *m, struct dentry *root);
|
||||
|
||||
struct p9_fid *v9fs_session_init(struct v9fs_session_info *v9ses,
|
||||
const char *dev_name, char *data);
|
||||
struct fs_context *fc);
|
||||
extern void v9fs_session_close(struct v9fs_session_info *v9ses);
|
||||
extern void v9fs_session_cancel(struct v9fs_session_info *v9ses);
|
||||
extern void v9fs_session_begin_cancel(struct v9fs_session_info *v9ses);
|
||||
|
||||
+91
-39
@@ -19,6 +19,7 @@
|
||||
#include <linux/statfs.h>
|
||||
#include <linux/magic.h>
|
||||
#include <linux/fscache.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <net/9p/9p.h>
|
||||
#include <net/9p/client.h>
|
||||
|
||||
@@ -30,32 +31,10 @@
|
||||
|
||||
static const struct super_operations v9fs_super_ops, v9fs_super_ops_dotl;
|
||||
|
||||
/**
|
||||
* v9fs_set_super - set the superblock
|
||||
* @s: super block
|
||||
* @data: file system specific data
|
||||
*
|
||||
*/
|
||||
|
||||
static int v9fs_set_super(struct super_block *s, void *data)
|
||||
{
|
||||
s->s_fs_info = data;
|
||||
return set_anon_super(s, data);
|
||||
}
|
||||
|
||||
/**
|
||||
* v9fs_fill_super - populate superblock with info
|
||||
* @sb: superblock
|
||||
* @v9ses: session information
|
||||
* @flags: flags propagated from v9fs_mount()
|
||||
*
|
||||
*/
|
||||
|
||||
static int
|
||||
v9fs_fill_super(struct super_block *sb, struct v9fs_session_info *v9ses,
|
||||
int flags)
|
||||
static int v9fs_fill_super(struct super_block *sb)
|
||||
{
|
||||
int ret;
|
||||
struct v9fs_session_info *v9ses = v9ses = sb->s_fs_info;
|
||||
|
||||
sb->s_maxbytes = MAX_LFS_FILESIZE;
|
||||
sb->s_blocksize_bits = fls(v9ses->maxdata - 1);
|
||||
@@ -95,16 +74,12 @@ v9fs_fill_super(struct super_block *sb, struct v9fs_session_info *v9ses,
|
||||
}
|
||||
|
||||
/**
|
||||
* v9fs_mount - mount a superblock
|
||||
* @fs_type: file system type
|
||||
* @flags: mount flags
|
||||
* @dev_name: device name that was mounted
|
||||
* @data: mount options
|
||||
* v9fs_get_tree - create the mountable root and superblock
|
||||
* @fc: the filesystem context
|
||||
*
|
||||
*/
|
||||
|
||||
static struct dentry *v9fs_mount(struct file_system_type *fs_type, int flags,
|
||||
const char *dev_name, void *data)
|
||||
static int v9fs_get_tree(struct fs_context *fc)
|
||||
{
|
||||
struct super_block *sb = NULL;
|
||||
struct inode *inode = NULL;
|
||||
@@ -117,20 +92,21 @@ static struct dentry *v9fs_mount(struct file_system_type *fs_type, int flags,
|
||||
|
||||
v9ses = kzalloc(sizeof(struct v9fs_session_info), GFP_KERNEL);
|
||||
if (!v9ses)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
return -ENOMEM;
|
||||
|
||||
fid = v9fs_session_init(v9ses, dev_name, data);
|
||||
fid = v9fs_session_init(v9ses, fc);
|
||||
if (IS_ERR(fid)) {
|
||||
retval = PTR_ERR(fid);
|
||||
goto free_session;
|
||||
}
|
||||
|
||||
sb = sget(fs_type, NULL, v9fs_set_super, flags, v9ses);
|
||||
fc->s_fs_info = v9ses;
|
||||
sb = sget_fc(fc, NULL, set_anon_super_fc);
|
||||
if (IS_ERR(sb)) {
|
||||
retval = PTR_ERR(sb);
|
||||
goto clunk_fid;
|
||||
}
|
||||
retval = v9fs_fill_super(sb, v9ses, flags);
|
||||
retval = v9fs_fill_super(sb);
|
||||
if (retval)
|
||||
goto release_sb;
|
||||
|
||||
@@ -159,14 +135,15 @@ static struct dentry *v9fs_mount(struct file_system_type *fs_type, int flags,
|
||||
v9fs_fid_add(root, &fid);
|
||||
|
||||
p9_debug(P9_DEBUG_VFS, " simple set mount, return 0\n");
|
||||
return dget(sb->s_root);
|
||||
fc->root = dget(sb->s_root);
|
||||
return 0;
|
||||
|
||||
clunk_fid:
|
||||
p9_fid_put(fid);
|
||||
v9fs_session_close(v9ses);
|
||||
free_session:
|
||||
kfree(v9ses);
|
||||
return ERR_PTR(retval);
|
||||
return retval;
|
||||
|
||||
release_sb:
|
||||
/*
|
||||
@@ -177,7 +154,7 @@ release_sb:
|
||||
*/
|
||||
p9_fid_put(fid);
|
||||
deactivate_locked_super(sb);
|
||||
return ERR_PTR(retval);
|
||||
return retval;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -303,11 +280,86 @@ static const struct super_operations v9fs_super_ops_dotl = {
|
||||
.write_inode = v9fs_write_inode_dotl,
|
||||
};
|
||||
|
||||
static void v9fs_free_fc(struct fs_context *fc)
|
||||
{
|
||||
struct v9fs_context *ctx = fc->fs_private;
|
||||
|
||||
if (!ctx)
|
||||
return;
|
||||
|
||||
/* These should be NULL by now but guard against leaks */
|
||||
kfree(ctx->session_opts.uname);
|
||||
kfree(ctx->session_opts.aname);
|
||||
#ifdef CONFIG_9P_FSCACHE
|
||||
kfree(ctx->session_opts.cachetag);
|
||||
#endif
|
||||
if (ctx->client_opts.trans_mod)
|
||||
v9fs_put_trans(ctx->client_opts.trans_mod);
|
||||
kfree(ctx);
|
||||
}
|
||||
|
||||
static const struct fs_context_operations v9fs_context_ops = {
|
||||
.parse_param = v9fs_parse_param,
|
||||
.get_tree = v9fs_get_tree,
|
||||
.free = v9fs_free_fc,
|
||||
};
|
||||
|
||||
static int v9fs_init_fs_context(struct fs_context *fc)
|
||||
{
|
||||
struct v9fs_context *ctx;
|
||||
|
||||
ctx = kzalloc(sizeof(*ctx), GFP_KERNEL);
|
||||
if (!ctx)
|
||||
return -ENOMEM;
|
||||
|
||||
/* initialize core options */
|
||||
ctx->session_opts.afid = ~0;
|
||||
ctx->session_opts.cache = CACHE_NONE;
|
||||
ctx->session_opts.session_lock_timeout = P9_LOCK_TIMEOUT;
|
||||
ctx->session_opts.uname = kstrdup(V9FS_DEFUSER, GFP_KERNEL);
|
||||
if (!ctx->session_opts.uname)
|
||||
goto error;
|
||||
|
||||
ctx->session_opts.aname = kstrdup(V9FS_DEFANAME, GFP_KERNEL);
|
||||
if (!ctx->session_opts.aname)
|
||||
goto error;
|
||||
|
||||
ctx->session_opts.uid = INVALID_UID;
|
||||
ctx->session_opts.dfltuid = V9FS_DEFUID;
|
||||
ctx->session_opts.dfltgid = V9FS_DEFGID;
|
||||
|
||||
/* initialize client options */
|
||||
ctx->client_opts.proto_version = p9_proto_2000L;
|
||||
ctx->client_opts.msize = DEFAULT_MSIZE;
|
||||
|
||||
/* initialize fd transport options */
|
||||
ctx->fd_opts.port = P9_FD_PORT;
|
||||
ctx->fd_opts.rfd = ~0;
|
||||
ctx->fd_opts.wfd = ~0;
|
||||
ctx->fd_opts.privport = false;
|
||||
|
||||
/* initialize rdma transport options */
|
||||
ctx->rdma_opts.port = P9_RDMA_PORT;
|
||||
ctx->rdma_opts.sq_depth = P9_RDMA_SQ_DEPTH;
|
||||
ctx->rdma_opts.rq_depth = P9_RDMA_RQ_DEPTH;
|
||||
ctx->rdma_opts.timeout = P9_RDMA_TIMEOUT;
|
||||
ctx->rdma_opts.privport = false;
|
||||
|
||||
fc->ops = &v9fs_context_ops;
|
||||
fc->fs_private = ctx;
|
||||
|
||||
return 0;
|
||||
error:
|
||||
fc->need_free = 1;
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
struct file_system_type v9fs_fs_type = {
|
||||
.name = "9p",
|
||||
.mount = v9fs_mount,
|
||||
.kill_sb = v9fs_kill_super,
|
||||
.owner = THIS_MODULE,
|
||||
.fs_flags = FS_RENAME_DOES_D_MOVE,
|
||||
.init_fs_context = v9fs_init_fs_context,
|
||||
.parameters = v9fs_param_spec,
|
||||
};
|
||||
MODULE_ALIAS_FS("9p");
|
||||
|
||||
@@ -279,7 +279,7 @@ int p9_client_rename(struct p9_fid *fid, struct p9_fid *newdirfid,
|
||||
const char *name);
|
||||
int p9_client_renameat(struct p9_fid *olddirfid, const char *old_name,
|
||||
struct p9_fid *newdirfid, const char *new_name);
|
||||
struct p9_client *p9_client_create(const char *dev_name, char *options);
|
||||
struct p9_client *p9_client_create(struct fs_context *fc);
|
||||
void p9_client_destroy(struct p9_client *clnt);
|
||||
void p9_client_disconnect(struct p9_client *clnt);
|
||||
void p9_client_begin_disconnect(struct p9_client *clnt);
|
||||
|
||||
@@ -57,7 +57,7 @@ struct p9_trans_module {
|
||||
bool supports_vmalloc; /* can work with vmalloc'd buffers */
|
||||
struct module *owner;
|
||||
int (*create)(struct p9_client *client,
|
||||
const char *devname, char *args);
|
||||
struct fs_context *fc);
|
||||
void (*close)(struct p9_client *client);
|
||||
int (*request)(struct p9_client *client, struct p9_req_t *req);
|
||||
int (*cancel)(struct p9_client *client, struct p9_req_t *req);
|
||||
|
||||
+12
-136
@@ -20,8 +20,8 @@
|
||||
#include <linux/uio.h>
|
||||
#include <linux/netfs.h>
|
||||
#include <net/9p/9p.h>
|
||||
#include <linux/parser.h>
|
||||
#include <linux/seq_file.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <net/9p/client.h>
|
||||
#include <net/9p/transport.h>
|
||||
#include "protocol.h"
|
||||
@@ -33,22 +33,6 @@
|
||||
* - a little lazy - parse all client options
|
||||
*/
|
||||
|
||||
enum {
|
||||
Opt_msize,
|
||||
Opt_trans,
|
||||
Opt_legacy,
|
||||
Opt_version,
|
||||
Opt_err,
|
||||
};
|
||||
|
||||
static const match_table_t tokens = {
|
||||
{Opt_msize, "msize=%u"},
|
||||
{Opt_legacy, "noextend"},
|
||||
{Opt_trans, "trans=%s"},
|
||||
{Opt_version, "version=%s"},
|
||||
{Opt_err, NULL},
|
||||
};
|
||||
|
||||
inline int p9_is_proto_dotl(struct p9_client *clnt)
|
||||
{
|
||||
return clnt->proto_version == p9_proto_2000L;
|
||||
@@ -97,124 +81,16 @@ static int safe_errno(int err)
|
||||
return err;
|
||||
}
|
||||
|
||||
/* Interpret mount option for protocol version */
|
||||
static int get_protocol_version(char *s)
|
||||
static int apply_client_options(struct p9_client *clnt, struct fs_context *fc)
|
||||
{
|
||||
int version = -EINVAL;
|
||||
struct v9fs_context *ctx = fc->fs_private;
|
||||
|
||||
if (!strcmp(s, "9p2000")) {
|
||||
version = p9_proto_legacy;
|
||||
p9_debug(P9_DEBUG_9P, "Protocol version: Legacy\n");
|
||||
} else if (!strcmp(s, "9p2000.u")) {
|
||||
version = p9_proto_2000u;
|
||||
p9_debug(P9_DEBUG_9P, "Protocol version: 9P2000.u\n");
|
||||
} else if (!strcmp(s, "9p2000.L")) {
|
||||
version = p9_proto_2000L;
|
||||
p9_debug(P9_DEBUG_9P, "Protocol version: 9P2000.L\n");
|
||||
} else {
|
||||
pr_info("Unknown protocol version %s\n", s);
|
||||
}
|
||||
clnt->msize = ctx->client_opts.msize;
|
||||
clnt->trans_mod = ctx->client_opts.trans_mod;
|
||||
ctx->client_opts.trans_mod = NULL;
|
||||
clnt->proto_version = ctx->client_opts.proto_version;
|
||||
|
||||
return version;
|
||||
}
|
||||
|
||||
/**
|
||||
* parse_opts - parse mount options into client structure
|
||||
* @opts: options string passed from mount
|
||||
* @clnt: existing v9fs client information
|
||||
*
|
||||
* Return 0 upon success, -ERRNO upon failure
|
||||
*/
|
||||
|
||||
static int parse_opts(char *opts, struct p9_client *clnt)
|
||||
{
|
||||
char *options, *tmp_options;
|
||||
char *p;
|
||||
substring_t args[MAX_OPT_ARGS];
|
||||
int option;
|
||||
char *s;
|
||||
int ret = 0;
|
||||
|
||||
clnt->proto_version = p9_proto_2000L;
|
||||
clnt->msize = DEFAULT_MSIZE;
|
||||
|
||||
if (!opts)
|
||||
return 0;
|
||||
|
||||
tmp_options = kstrdup(opts, GFP_KERNEL);
|
||||
if (!tmp_options)
|
||||
return -ENOMEM;
|
||||
options = tmp_options;
|
||||
|
||||
while ((p = strsep(&options, ",")) != NULL) {
|
||||
int token, r;
|
||||
|
||||
if (!*p)
|
||||
continue;
|
||||
token = match_token(p, tokens, args);
|
||||
switch (token) {
|
||||
case Opt_msize:
|
||||
r = match_int(&args[0], &option);
|
||||
if (r < 0) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"integer field, but no integer?\n");
|
||||
ret = r;
|
||||
continue;
|
||||
}
|
||||
if (option < 4096) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"msize should be at least 4k\n");
|
||||
ret = -EINVAL;
|
||||
continue;
|
||||
}
|
||||
clnt->msize = option;
|
||||
break;
|
||||
case Opt_trans:
|
||||
s = match_strdup(&args[0]);
|
||||
if (!s) {
|
||||
ret = -ENOMEM;
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"problem allocating copy of trans arg\n");
|
||||
goto free_and_return;
|
||||
}
|
||||
|
||||
v9fs_put_trans(clnt->trans_mod);
|
||||
clnt->trans_mod = v9fs_get_trans_by_name(s);
|
||||
if (!clnt->trans_mod) {
|
||||
pr_info("Could not find request transport: %s\n",
|
||||
s);
|
||||
ret = -EINVAL;
|
||||
}
|
||||
kfree(s);
|
||||
break;
|
||||
case Opt_legacy:
|
||||
clnt->proto_version = p9_proto_legacy;
|
||||
break;
|
||||
case Opt_version:
|
||||
s = match_strdup(&args[0]);
|
||||
if (!s) {
|
||||
ret = -ENOMEM;
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"problem allocating copy of version arg\n");
|
||||
goto free_and_return;
|
||||
}
|
||||
r = get_protocol_version(s);
|
||||
if (r < 0)
|
||||
ret = r;
|
||||
else
|
||||
clnt->proto_version = r;
|
||||
kfree(s);
|
||||
break;
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
free_and_return:
|
||||
if (ret)
|
||||
v9fs_put_trans(clnt->trans_mod);
|
||||
kfree(tmp_options);
|
||||
return ret;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int p9_fcall_init(struct p9_client *c, struct p9_fcall *fc,
|
||||
@@ -975,7 +851,7 @@ error:
|
||||
return err;
|
||||
}
|
||||
|
||||
struct p9_client *p9_client_create(const char *dev_name, char *options)
|
||||
struct p9_client *p9_client_create(struct fs_context *fc)
|
||||
{
|
||||
int err;
|
||||
static atomic_t seqno = ATOMIC_INIT(0);
|
||||
@@ -998,8 +874,8 @@ struct p9_client *p9_client_create(const char *dev_name, char *options)
|
||||
idr_init(&clnt->fids);
|
||||
idr_init(&clnt->reqs);
|
||||
|
||||
err = parse_opts(options, clnt);
|
||||
if (err < 0)
|
||||
err = apply_client_options(clnt, fc);
|
||||
if (err)
|
||||
goto free_client;
|
||||
|
||||
if (!clnt->trans_mod)
|
||||
@@ -1015,7 +891,7 @@ struct p9_client *p9_client_create(const char *dev_name, char *options)
|
||||
p9_debug(P9_DEBUG_MUX, "clnt %p trans %p msize %d protocol %d\n",
|
||||
clnt, clnt->trans_mod, clnt->msize, clnt->proto_version);
|
||||
|
||||
err = clnt->trans_mod->create(clnt, dev_name, options);
|
||||
err = clnt->trans_mod->create(clnt, fc);
|
||||
if (err)
|
||||
goto put_trans;
|
||||
|
||||
|
||||
+1
-1
@@ -16,7 +16,6 @@
|
||||
#include <linux/moduleparam.h>
|
||||
#include <net/9p/9p.h>
|
||||
#include <linux/fs.h>
|
||||
#include <linux/parser.h>
|
||||
#include <net/9p/client.h>
|
||||
#include <net/9p/transport.h>
|
||||
#include <linux/list.h>
|
||||
@@ -171,6 +170,7 @@ void v9fs_put_trans(struct p9_trans_module *m)
|
||||
if (m)
|
||||
module_put(m->owner);
|
||||
}
|
||||
EXPORT_SYMBOL(v9fs_put_trans);
|
||||
|
||||
/**
|
||||
* init_p9 - Initialize module
|
||||
|
||||
+11
-98
@@ -22,7 +22,7 @@
|
||||
#include <linux/uaccess.h>
|
||||
#include <linux/inet.h>
|
||||
#include <linux/file.h>
|
||||
#include <linux/parser.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/seq_file.h>
|
||||
#include <net/9p/9p.h>
|
||||
@@ -37,26 +37,6 @@
|
||||
static struct p9_trans_module p9_tcp_trans;
|
||||
static struct p9_trans_module p9_fd_trans;
|
||||
|
||||
/*
|
||||
* Option Parsing (code inspired by NFS code)
|
||||
* - a little lazy - parse all fd-transport options
|
||||
*/
|
||||
|
||||
enum {
|
||||
/* Options that take integer arguments */
|
||||
Opt_port, Opt_rfdno, Opt_wfdno, Opt_err,
|
||||
/* Options that take no arguments */
|
||||
Opt_privport,
|
||||
};
|
||||
|
||||
static const match_table_t tokens = {
|
||||
{Opt_port, "port=%u"},
|
||||
{Opt_rfdno, "rfdno=%u"},
|
||||
{Opt_wfdno, "wfdno=%u"},
|
||||
{Opt_privport, "privport"},
|
||||
{Opt_err, NULL},
|
||||
};
|
||||
|
||||
enum {
|
||||
Rworksched = 1, /* read work scheduled or running */
|
||||
Rpending = 2, /* can read */
|
||||
@@ -737,73 +717,6 @@ static int p9_fd_show_options(struct seq_file *m, struct p9_client *clnt)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* parse_opts - parse mount options into p9_fd_opts structure
|
||||
* @params: options string passed from mount
|
||||
* @opts: fd transport-specific structure to parse options into
|
||||
*
|
||||
* Returns 0 upon success, -ERRNO upon failure
|
||||
*/
|
||||
|
||||
static int parse_opts(char *params, struct p9_fd_opts *opts)
|
||||
{
|
||||
char *p;
|
||||
substring_t args[MAX_OPT_ARGS];
|
||||
int option;
|
||||
char *options, *tmp_options;
|
||||
|
||||
opts->port = P9_FD_PORT;
|
||||
opts->rfd = ~0;
|
||||
opts->wfd = ~0;
|
||||
opts->privport = false;
|
||||
|
||||
if (!params)
|
||||
return 0;
|
||||
|
||||
tmp_options = kstrdup(params, GFP_KERNEL);
|
||||
if (!tmp_options) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"failed to allocate copy of option string\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
options = tmp_options;
|
||||
|
||||
while ((p = strsep(&options, ",")) != NULL) {
|
||||
int token;
|
||||
int r;
|
||||
if (!*p)
|
||||
continue;
|
||||
token = match_token(p, tokens, args);
|
||||
if ((token != Opt_err) && (token != Opt_privport)) {
|
||||
r = match_int(&args[0], &option);
|
||||
if (r < 0) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"integer field, but no integer?\n");
|
||||
continue;
|
||||
}
|
||||
}
|
||||
switch (token) {
|
||||
case Opt_port:
|
||||
opts->port = option;
|
||||
break;
|
||||
case Opt_rfdno:
|
||||
opts->rfd = option;
|
||||
break;
|
||||
case Opt_wfdno:
|
||||
opts->wfd = option;
|
||||
break;
|
||||
case Opt_privport:
|
||||
opts->privport = true;
|
||||
break;
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
kfree(tmp_options);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int p9_fd_open(struct p9_client *client, int rfd, int wfd)
|
||||
{
|
||||
struct p9_trans_fd *ts = kzalloc(sizeof(struct p9_trans_fd),
|
||||
@@ -958,17 +871,18 @@ static int p9_bind_privport(struct socket *sock)
|
||||
}
|
||||
|
||||
static int
|
||||
p9_fd_create_tcp(struct p9_client *client, const char *addr, char *args)
|
||||
p9_fd_create_tcp(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *addr = fc->source;
|
||||
struct v9fs_context *ctx = fc->fs_private;
|
||||
int err;
|
||||
char port_str[6];
|
||||
struct socket *csocket;
|
||||
struct sockaddr_storage stor = { 0 };
|
||||
struct p9_fd_opts opts;
|
||||
|
||||
err = parse_opts(args, &opts);
|
||||
if (err < 0)
|
||||
return err;
|
||||
/* opts are already parsed in context */
|
||||
opts = ctx->fd_opts;
|
||||
|
||||
if (!addr)
|
||||
return -EINVAL;
|
||||
@@ -1015,8 +929,9 @@ p9_fd_create_tcp(struct p9_client *client, const char *addr, char *args)
|
||||
}
|
||||
|
||||
static int
|
||||
p9_fd_create_unix(struct p9_client *client, const char *addr, char *args)
|
||||
p9_fd_create_unix(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *addr = fc->source;
|
||||
int err;
|
||||
struct socket *csocket;
|
||||
struct sockaddr_un sun_server;
|
||||
@@ -1055,14 +970,12 @@ p9_fd_create_unix(struct p9_client *client, const char *addr, char *args)
|
||||
}
|
||||
|
||||
static int
|
||||
p9_fd_create(struct p9_client *client, const char *addr, char *args)
|
||||
p9_fd_create(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
struct v9fs_context *ctx = fc->fs_private;
|
||||
struct p9_fd_opts opts = ctx->fd_opts;
|
||||
int err;
|
||||
struct p9_fd_opts opts;
|
||||
|
||||
err = parse_opts(args, &opts);
|
||||
if (err < 0)
|
||||
return err;
|
||||
client->trans_opts.fd.rfd = opts.rfd;
|
||||
client->trans_opts.fd.wfd = opts.wfd;
|
||||
|
||||
|
||||
+8
-100
@@ -22,7 +22,7 @@
|
||||
#include <linux/uaccess.h>
|
||||
#include <linux/inet.h>
|
||||
#include <linux/file.h>
|
||||
#include <linux/parser.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <linux/semaphore.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/seq_file.h>
|
||||
@@ -106,26 +106,6 @@ struct p9_rdma_context {
|
||||
};
|
||||
};
|
||||
|
||||
/*
|
||||
* Option Parsing (code inspired by NFS code)
|
||||
*/
|
||||
enum {
|
||||
/* Options that take integer arguments */
|
||||
Opt_port, Opt_rq_depth, Opt_sq_depth, Opt_timeout,
|
||||
/* Options that take no argument */
|
||||
Opt_privport,
|
||||
Opt_err,
|
||||
};
|
||||
|
||||
static match_table_t tokens = {
|
||||
{Opt_port, "port=%u"},
|
||||
{Opt_sq_depth, "sq=%u"},
|
||||
{Opt_rq_depth, "rq=%u"},
|
||||
{Opt_timeout, "timeout=%u"},
|
||||
{Opt_privport, "privport"},
|
||||
{Opt_err, NULL},
|
||||
};
|
||||
|
||||
static int p9_rdma_show_options(struct seq_file *m, struct p9_client *clnt)
|
||||
{
|
||||
struct p9_trans_rdma *rdma = clnt->trans;
|
||||
@@ -143,77 +123,6 @@ static int p9_rdma_show_options(struct seq_file *m, struct p9_client *clnt)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* parse_opts - parse mount options into rdma options structure
|
||||
* @params: options string passed from mount
|
||||
* @opts: rdma transport-specific structure to parse options into
|
||||
*
|
||||
* Returns 0 upon success, -ERRNO upon failure
|
||||
*/
|
||||
static int parse_opts(char *params, struct p9_rdma_opts *opts)
|
||||
{
|
||||
char *p;
|
||||
substring_t args[MAX_OPT_ARGS];
|
||||
int option;
|
||||
char *options, *tmp_options;
|
||||
|
||||
opts->port = P9_RDMA_PORT;
|
||||
opts->sq_depth = P9_RDMA_SQ_DEPTH;
|
||||
opts->rq_depth = P9_RDMA_RQ_DEPTH;
|
||||
opts->timeout = P9_RDMA_TIMEOUT;
|
||||
opts->privport = false;
|
||||
|
||||
if (!params)
|
||||
return 0;
|
||||
|
||||
tmp_options = kstrdup(params, GFP_KERNEL);
|
||||
if (!tmp_options) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"failed to allocate copy of option string\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
options = tmp_options;
|
||||
|
||||
while ((p = strsep(&options, ",")) != NULL) {
|
||||
int token;
|
||||
int r;
|
||||
if (!*p)
|
||||
continue;
|
||||
token = match_token(p, tokens, args);
|
||||
if ((token != Opt_err) && (token != Opt_privport)) {
|
||||
r = match_int(&args[0], &option);
|
||||
if (r < 0) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"integer field, but no integer?\n");
|
||||
continue;
|
||||
}
|
||||
}
|
||||
switch (token) {
|
||||
case Opt_port:
|
||||
opts->port = option;
|
||||
break;
|
||||
case Opt_sq_depth:
|
||||
opts->sq_depth = option;
|
||||
break;
|
||||
case Opt_rq_depth:
|
||||
opts->rq_depth = option;
|
||||
break;
|
||||
case Opt_timeout:
|
||||
opts->timeout = option;
|
||||
break;
|
||||
case Opt_privport:
|
||||
opts->privport = true;
|
||||
break;
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
}
|
||||
/* RQ must be at least as large as the SQ */
|
||||
opts->rq_depth = max(opts->rq_depth, opts->sq_depth);
|
||||
kfree(tmp_options);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
p9_cm_event_handler(struct rdma_cm_id *id, struct rdma_cm_event *event)
|
||||
{
|
||||
@@ -607,14 +516,15 @@ static int p9_rdma_bind_privport(struct p9_trans_rdma *rdma)
|
||||
/**
|
||||
* rdma_create_trans - Transport method for creating a transport instance
|
||||
* @client: client instance
|
||||
* @addr: IP address string
|
||||
* @args: Mount options string
|
||||
* @fc: The filesystem context
|
||||
*/
|
||||
static int
|
||||
rdma_create_trans(struct p9_client *client, const char *addr, char *args)
|
||||
rdma_create_trans(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *addr = fc->source;
|
||||
struct v9fs_context *ctx = fc->fs_private;
|
||||
struct p9_rdma_opts opts = ctx->rdma_opts;
|
||||
int err;
|
||||
struct p9_rdma_opts opts;
|
||||
struct p9_trans_rdma *rdma;
|
||||
struct rdma_conn_param conn_param;
|
||||
struct ib_qp_init_attr qp_attr;
|
||||
@@ -622,10 +532,8 @@ rdma_create_trans(struct p9_client *client, const char *addr, char *args)
|
||||
if (addr == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
/* Parse the transport specific mount options */
|
||||
err = parse_opts(args, &opts);
|
||||
if (err < 0)
|
||||
return err;
|
||||
/* options are already parsed, in the fs context */
|
||||
opts = ctx->rdma_opts;
|
||||
|
||||
/* Create and initialize the RDMA transport structure */
|
||||
rdma = alloc_rdma(&opts);
|
||||
|
||||
+3
-1
@@ -27,6 +27,7 @@
|
||||
#include <linux/cleanup.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <linux/usb/composite.h>
|
||||
#include <linux/usb/func_utils.h>
|
||||
|
||||
@@ -376,8 +377,9 @@ out:
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int p9_usbg_create(struct p9_client *client, const char *devname, char *args)
|
||||
static int p9_usbg_create(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *devname = fc->source;
|
||||
struct f_usb9pfs_dev *dev;
|
||||
struct f_usb9pfs *usb9pfs;
|
||||
int ret = -ENOENT;
|
||||
|
||||
@@ -26,7 +26,7 @@
|
||||
#include <linux/highmem.h>
|
||||
#include <linux/slab.h>
|
||||
#include <net/9p/9p.h>
|
||||
#include <linux/parser.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <net/9p/client.h>
|
||||
#include <net/9p/transport.h>
|
||||
#include <linux/scatterlist.h>
|
||||
@@ -679,8 +679,7 @@ fail:
|
||||
/**
|
||||
* p9_virtio_create - allocate a new virtio channel
|
||||
* @client: client instance invoking this transport
|
||||
* @devname: string identifying the channel to connect to (unused)
|
||||
* @args: args passed from sys_mount() for per-transport options (unused)
|
||||
* @fc: the filesystem context
|
||||
*
|
||||
* This sets up a transport channel for 9p communication. Right now
|
||||
* we only match the first available channel, but eventually we could look up
|
||||
@@ -691,8 +690,9 @@ fail:
|
||||
*/
|
||||
|
||||
static int
|
||||
p9_virtio_create(struct p9_client *client, const char *devname, char *args)
|
||||
p9_virtio_create(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *devname = fc->source;
|
||||
struct virtio_chan *chan;
|
||||
int ret = -ENOENT;
|
||||
int found = 0;
|
||||
|
||||
+3
-1
@@ -15,6 +15,7 @@
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/spinlock.h>
|
||||
#include <linux/fs_context.h>
|
||||
#include <net/9p/9p.h>
|
||||
#include <net/9p/client.h>
|
||||
#include <net/9p/transport.h>
|
||||
@@ -66,8 +67,9 @@ static int p9_xen_cancel(struct p9_client *client, struct p9_req_t *req)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int p9_xen_create(struct p9_client *client, const char *addr, char *args)
|
||||
static int p9_xen_create(struct p9_client *client, struct fs_context *fc)
|
||||
{
|
||||
const char *addr = fc->source;
|
||||
struct xen_9pfs_front_priv *priv;
|
||||
|
||||
if (addr == NULL)
|
||||
|
||||
Reference in New Issue
Block a user