Skip to content

Commit

Permalink
9p: Make sure we are able to clunk the cached fid on umount
Browse files Browse the repository at this point in the history
dcache prune happen on umount. So we cannot mark the client
satus disconnect. That will prevent a 9p call to the server

Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
Signed-off-by: Eric Van Hensbergen <ericvh@gmail.com>
  • Loading branch information
Aneesh Kumar K.V authored and Eric Van Hensbergen committed Apr 5, 2010
1 parent d994f40 commit 6d96d3a
Show file tree
Hide file tree
Showing 5 changed files with 34 additions and 3 deletions.
13 changes: 13 additions & 0 deletions fs/9p/v9fs.c
Original file line number Diff line number Diff line change
Expand Up @@ -342,6 +342,19 @@ void v9fs_session_cancel(struct v9fs_session_info *v9ses) {
p9_client_disconnect(v9ses->clnt);
}

/**
* v9fs_session_begin_cancel - Begin terminate of a session
* @v9ses: session to terminate
*
* After this call we don't allow any request other than clunk.
*/

void v9fs_session_begin_cancel(struct v9fs_session_info *v9ses)
{
P9_DPRINTK(P9_DEBUG_ERROR, "begin cancel session %p\n", v9ses);
p9_client_begin_disconnect(v9ses->clnt);
}

extern int v9fs_error_init(void);

static struct kobject *v9fs_kobj;
Expand Down
1 change: 1 addition & 0 deletions fs/9p/v9fs.h
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@ struct p9_fid *v9fs_session_init(struct v9fs_session_info *, const char *,
char *);
void v9fs_session_close(struct v9fs_session_info *v9ses);
void v9fs_session_cancel(struct v9fs_session_info *v9ses);
void v9fs_session_begin_cancel(struct v9fs_session_info *v9ses);

#define V9FS_MAGIC 0x01021997

Expand Down
3 changes: 2 additions & 1 deletion fs/9p/vfs_super.c
Original file line number Diff line number Diff line change
Expand Up @@ -193,6 +193,7 @@ static void v9fs_kill_super(struct super_block *s)

kill_anon_super(s);

v9fs_session_cancel(v9ses);
v9fs_session_close(v9ses);
kfree(v9ses);
s->s_fs_info = NULL;
Expand All @@ -205,7 +206,7 @@ v9fs_umount_begin(struct super_block *sb)
struct v9fs_session_info *v9ses;

v9ses = sb->s_fs_info;
v9fs_session_cancel(v9ses);
v9fs_session_begin_cancel(v9ses);
}

static const struct super_operations v9fs_super_ops = {
Expand Down
2 changes: 2 additions & 0 deletions include/net/9p/client.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ enum p9_proto_versions{

enum p9_trans_status {
Connected,
BeginDisconnect,
Disconnected,
Hung,
};
Expand Down Expand Up @@ -198,6 +199,7 @@ int p9_client_version(struct p9_client *);
struct p9_client *p9_client_create(const char *dev_name, char *options);
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);
struct p9_fid *p9_client_attach(struct p9_client *clnt, struct p9_fid *afid,
char *uname, u32 n_uname, char *aname);
struct p9_fid *p9_client_auth(struct p9_client *clnt, char *uname,
Expand Down
18 changes: 16 additions & 2 deletions net/9p/client.c
Original file line number Diff line number Diff line change
Expand Up @@ -533,7 +533,12 @@ p9_client_rpc(struct p9_client *c, int8_t type, const char *fmt, ...)

P9_DPRINTK(P9_DEBUG_MUX, "client %p op %d\n", c, type);

if (c->status != Connected)
/* we allow for any status other than disconnected */
if (c->status == Disconnected)
return ERR_PTR(-EIO);

/* if status is begin_disconnected we allow only clunk request */
if ((c->status == BeginDisconnect) && (type != P9_TCLUNK))
return ERR_PTR(-EIO);

if (signal_pending(current)) {
Expand Down Expand Up @@ -799,8 +804,10 @@ void p9_client_destroy(struct p9_client *clnt)

v9fs_put_trans(clnt->trans_mod);

list_for_each_entry_safe(fid, fidptr, &clnt->fidlist, flist)
list_for_each_entry_safe(fid, fidptr, &clnt->fidlist, flist) {
printk(KERN_INFO "Found fid %d not clunked\n", fid->fid);
p9_fid_destroy(fid);
}

if (clnt->fidpool)
p9_idpool_destroy(clnt->fidpool);
Expand All @@ -818,6 +825,13 @@ void p9_client_disconnect(struct p9_client *clnt)
}
EXPORT_SYMBOL(p9_client_disconnect);

void p9_client_begin_disconnect(struct p9_client *clnt)
{
P9_DPRINTK(P9_DEBUG_9P, "clnt %p\n", clnt);
clnt->status = BeginDisconnect;
}
EXPORT_SYMBOL(p9_client_begin_disconnect);

struct p9_fid *p9_client_attach(struct p9_client *clnt, struct p9_fid *afid,
char *uname, u32 n_uname, char *aname)
{
Expand Down

0 comments on commit 6d96d3a

Please sign in to comment.