aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/block/xen-blkback/xenbus.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/block/xen-blkback/xenbus.c')
-rw-r--r--drivers/block/xen-blkback/xenbus.c26
1 files changed, 26 insertions, 0 deletions
diff --git a/drivers/block/xen-blkback/xenbus.c b/drivers/block/xen-blkback/xenbus.c
index e0fd92a2a4cd..1f1ade6d6e09 100644
--- a/drivers/block/xen-blkback/xenbus.c
+++ b/drivers/block/xen-blkback/xenbus.c
@@ -105,6 +105,7 @@ static void xen_update_blkif_status(struct xen_blkif *blkif)
105static struct xen_blkif *xen_blkif_alloc(domid_t domid) 105static struct xen_blkif *xen_blkif_alloc(domid_t domid)
106{ 106{
107 struct xen_blkif *blkif; 107 struct xen_blkif *blkif;
108 int i;
108 109
109 blkif = kmem_cache_zalloc(xen_blkif_cachep, GFP_KERNEL); 110 blkif = kmem_cache_zalloc(xen_blkif_cachep, GFP_KERNEL);
110 if (!blkif) 111 if (!blkif)
@@ -124,6 +125,21 @@ static struct xen_blkif *xen_blkif_alloc(domid_t domid)
124 blkif->free_pages_num = 0; 125 blkif->free_pages_num = 0;
125 atomic_set(&blkif->persistent_gnt_in_use, 0); 126 atomic_set(&blkif->persistent_gnt_in_use, 0);
126 127
128 blkif->pending_reqs = kcalloc(XEN_BLKIF_REQS,
129 sizeof(blkif->pending_reqs[0]),
130 GFP_KERNEL);
131 if (!blkif->pending_reqs) {
132 kmem_cache_free(xen_blkif_cachep, blkif);
133 return ERR_PTR(-ENOMEM);
134 }
135 INIT_LIST_HEAD(&blkif->pending_free);
136 spin_lock_init(&blkif->pending_free_lock);
137 init_waitqueue_head(&blkif->pending_free_wq);
138
139 for (i = 0; i < XEN_BLKIF_REQS; i++)
140 list_add_tail(&blkif->pending_reqs[i].free_list,
141 &blkif->pending_free);
142
127 return blkif; 143 return blkif;
128} 144}
129 145
@@ -203,8 +219,18 @@ static void xen_blkif_disconnect(struct xen_blkif *blkif)
203 219
204static void xen_blkif_free(struct xen_blkif *blkif) 220static void xen_blkif_free(struct xen_blkif *blkif)
205{ 221{
222 struct pending_req *req;
223 int i = 0;
224
206 if (!atomic_dec_and_test(&blkif->refcnt)) 225 if (!atomic_dec_and_test(&blkif->refcnt))
207 BUG(); 226 BUG();
227
228 /* Check that there is no request in use */
229 list_for_each_entry(req, &blkif->pending_free, free_list)
230 i++;
231 BUG_ON(i != XEN_BLKIF_REQS);
232
233 kfree(blkif->pending_reqs);
208 kmem_cache_free(xen_blkif_cachep, blkif); 234 kmem_cache_free(xen_blkif_cachep, blkif);
209} 235}
210 236