diff options
author | Miklos Szeredi <miklos@szeredi.hu> | 2006-09-30 16:02:25 +0000 |
---|---|---|
committer | Miklos Szeredi <miklos@szeredi.hu> | 2006-09-30 16:02:25 +0000 |
commit | 708b4818f2d0b9a1e277de85a00a0355745a5cd0 (patch) | |
tree | 0e35c2d3906473f9b471eb4029a32e91e32d2480 /kernel/file.c | |
parent | ff5fa7f8de978d56e8c334e746e08195ed25730d (diff) |
bmap support
Diffstat (limited to 'kernel/file.c')
-rw-r--r-- | kernel/file.c | 37 |
1 files changed, 37 insertions, 0 deletions
diff --git a/kernel/file.c b/kernel/file.c index 9e50109..fb381da 100644 --- a/kernel/file.c +++ b/kernel/file.c @@ -805,6 +805,42 @@ static int fuse_file_lock(struct file *file, int cmd, struct file_lock *fl) return err; } +static sector_t fuse_bmap(struct address_space *mapping, sector_t block) +{ + struct inode *inode = mapping->host; + struct fuse_conn *fc = get_fuse_conn(inode); + struct fuse_req *req; + struct fuse_bmap_in inarg; + struct fuse_bmap_out outarg; + int err; + + if (!inode->i_sb->s_bdev || fc->no_bmap) + return 0; + + req = fuse_get_req(fc); + if (IS_ERR(req)) + return 0; + + memset(&inarg, 0, sizeof(inarg)); + inarg.block = block; + inarg.blocksize = inode->i_sb->s_blocksize; + req->in.h.opcode = FUSE_BMAP; + req->in.h.nodeid = get_node_id(inode); + req->in.numargs = 1; + req->in.args[0].size = sizeof(inarg); + req->in.args[0].value = &inarg; + req->out.numargs = 1; + req->out.args[0].size = sizeof(outarg); + req->out.args[0].value = &outarg; + request_send(fc, req); + err = req->out.h.error; + fuse_put_request(fc, req); + if (err == -ENOSYS) + fc->no_bmap = 1; + + return err ? 0 : outarg.block; +} + static struct file_operations fuse_file_operations = { .llseek = generic_file_llseek, .read = generic_file_read, @@ -836,6 +872,7 @@ static struct address_space_operations fuse_file_aops = { .commit_write = fuse_commit_write, .readpages = fuse_readpages, .set_page_dirty = fuse_set_page_dirty, + .bmap = fuse_bmap, }; void fuse_init_file_inode(struct inode *inode) |