From 9478e86a5487b7f0b5ce4c4d7f4d7a9283562058 Mon Sep 17 00:00:00 2001 From: Miklos Szeredi Date: Wed, 11 Dec 2002 09:50:26 +0000 Subject: [PATCH] release() changes --- include/fuse.h | 2 +- kernel/file.c | 14 +++++++++++++- lib/fuse.c | 16 ++++++++-------- 3 files changed, 22 insertions(+), 10 deletions(-) diff --git a/include/fuse.h b/include/fuse.h index f92914f..30d5f80 100644 --- a/include/fuse.h +++ b/include/fuse.h @@ -102,7 +102,7 @@ struct fuse_operations { int (*read) (const char *, char *, size_t, off_t); int (*write) (const char *, const char *, size_t, off_t); int (*statfs) (struct fuse_statfs *); - int (*release) (const char *); + int (*release) (const char *, int); }; /** Extra context that may be needed by some filesystems */ diff --git a/kernel/file.c b/kernel/file.c index 0ba4892..f4688f7 100644 --- a/kernel/file.c +++ b/kernel/file.c @@ -44,18 +44,30 @@ static int fuse_release(struct inode *inode, struct file *file) { struct fuse_conn *fc = INO_FC(inode); struct fuse_in *in = NULL; + struct fuse_open_in *inarg = NULL; in = kmalloc(sizeof(struct fuse_in), GFP_NOFS); if(!in) return -ENOMEM; - memset(in, 0, sizeof(struct fuse_in)); + + inarg = kmalloc(sizeof(struct fuse_open_in), GFP_NOFS); + if(!inarg) + goto out_free; + memset(inarg, 0, sizeof(struct fuse_open_in)); + + inarg->flags = file->f_flags & ~O_EXCL; in->h.opcode = FUSE_RELEASE; in->h.ino = inode->i_ino; + in->numargs = 1; + in->args[0].size = sizeof(struct fuse_open_in); + in->args[0].value = inarg; if(!request_send_noreply(fc, in)) return 0; + out_free: + kfree(inarg); kfree(in); return 0; } diff --git a/lib/fuse.c b/lib/fuse.c index 4919965..efe9e97 100644 --- a/lib/fuse.c +++ b/lib/fuse.c @@ -758,19 +758,20 @@ static void do_open(struct fuse *f, struct fuse_in_header *in, if(path != NULL) { /* The open syscall was interrupted, so it must be cancelled */ if(res == 0 && res2 == -ENOENT && f->op.release) - f->op.release(path); + f->op.release(path, arg->flags); free(path); } } -static void do_release(struct fuse *f, struct fuse_in_header *in) +static void do_release(struct fuse *f, struct fuse_in_header *in, + struct fuse_open_in *arg) { char *path; path = get_path(f, in->ino); if(path != NULL) { if(f->op.release) - f->op.release(path); + f->op.release(path, arg->flags); free(path); } } @@ -943,6 +944,10 @@ void __fuse_process_cmd(struct fuse *f, struct fuse_cmd *cmd) do_open(f, in, (struct fuse_open_in *) inarg); break; + case FUSE_RELEASE: + do_release(f, in, (struct fuse_open_in *) inarg); + break; + case FUSE_READ: do_read(f, in, (struct fuse_read_in *) inarg); break; @@ -955,12 +960,7 @@ void __fuse_process_cmd(struct fuse *f, struct fuse_cmd *cmd) do_statfs(f, in); break; - case FUSE_RELEASE: - do_release(f, in); - break; - default: - fprintf(stderr, "Operation %i not implemented\n", in->opcode); send_reply(f, in, -ENOSYS, NULL, 0); } -- 2.30.2