ceph: add a dedicated private data for netfs rreq
[linux-2.6-microblaze.git] / fs / ceph / addr.c
index 6bb251a..19c4f08 100644 (file)
@@ -362,18 +362,28 @@ static int ceph_init_request(struct netfs_io_request *rreq, struct file *file)
 {
        struct inode *inode = rreq->inode;
        int got = 0, want = CEPH_CAP_FILE_CACHE;
+       struct ceph_netfs_request_data *priv;
        int ret = 0;
 
        if (rreq->origin != NETFS_READAHEAD)
                return 0;
 
+       priv = kzalloc(sizeof(*priv), GFP_NOFS);
+       if (!priv)
+               return -ENOMEM;
+
        if (file) {
                struct ceph_rw_context *rw_ctx;
                struct ceph_file_info *fi = file->private_data;
 
+               priv->file_ra_pages = file->f_ra.ra_pages;
+               priv->file_ra_disabled = file->f_mode & FMODE_RANDOM;
+
                rw_ctx = ceph_find_rw_context(fi);
-               if (rw_ctx)
+               if (rw_ctx) {
+                       rreq->netfs_priv = priv;
                        return 0;
+               }
        }
 
        /*
@@ -383,27 +393,40 @@ static int ceph_init_request(struct netfs_io_request *rreq, struct file *file)
        ret = ceph_try_get_caps(inode, CEPH_CAP_FILE_RD, want, true, &got);
        if (ret < 0) {
                dout("start_read %p, error getting cap\n", inode);
-               return ret;
+               goto out;
        }
 
        if (!(got & want)) {
                dout("start_read %p, no cache cap\n", inode);
-               return -EACCES;
+               ret = -EACCES;
+               goto out;
+       }
+       if (ret == 0) {
+               ret = -EACCES;
+               goto out;
        }
-       if (ret == 0)
-               return -EACCES;
 
-       rreq->netfs_priv = (void *)(uintptr_t)got;
-       return 0;
+       priv->caps = got;
+       rreq->netfs_priv = priv;
+
+out:
+       if (ret < 0)
+               kfree(priv);
+
+       return ret;
 }
 
 static void ceph_netfs_free_request(struct netfs_io_request *rreq)
 {
-       struct ceph_inode_info *ci = ceph_inode(rreq->inode);
-       int got = (uintptr_t)rreq->netfs_priv;
+       struct ceph_netfs_request_data *priv = rreq->netfs_priv;
+
+       if (!priv)
+               return;
 
-       if (got)
-               ceph_put_cap_refs(ci, got);
+       if (priv->caps)
+               ceph_put_cap_refs(ceph_inode(rreq->inode), priv->caps);
+       kfree(priv);
+       rreq->netfs_priv = NULL;
 }
 
 const struct netfs_request_ops ceph_netfs_ops = {