aboutsummaryrefslogtreecommitdiffstats
path: root/fs/fscache
diff options
context:
space:
mode:
authorDavid Howells <dhowells@redhat.com>2013-05-10 14:50:26 -0400
committerDavid Howells <dhowells@redhat.com>2013-06-19 09:16:47 -0400
commit1362729b169b7903c7e739dbe7904994b0d8c47f (patch)
tree31c6d2a831b94a1ed0b4efe2d3ff3d1a21c654e2 /fs/fscache
parentcaaef6900befb45689b1d1831ce3c7e7fb5b504f (diff)
FS-Cache: Simplify cookie retention for fscache_objects, fixing oops
Simplify the way fscache cache objects retain their cookie. The way I implemented the cookie storage handling made synchronisation a pain (ie. the object state machine can't rely on the cookie actually still being there). Instead of the the object being detached from the cookie and the cookie being freed in __fscache_relinquish_cookie(), we defer both operations: (*) The detachment of the object from the list in the cookie now takes place in fscache_drop_object() and is thus governed by the object state machine (fscache_detach_from_cookie() has been removed). (*) The release of the cookie is now in fscache_object_destroy() - which is called by the cache backend just before it frees the object. This means that the fscache_cookie struct is now available to the cache all the way through from ->alloc_object() to ->drop_object() and ->put_object() - meaning that it's no longer necessary to take object->lock to guarantee access. However, __fscache_relinquish_cookie() doesn't wait for the object to go all the way through to destruction before letting the netfs proceed. That would massively slow down the netfs. Since __fscache_relinquish_cookie() leaves the cookie around, in must therefore break all attachments to the netfs - which includes ->def, ->netfs_data and any outstanding page read/writes. To handle this, struct fscache_cookie now has an n_active counter: (1) This starts off initialised to 1. (2) Any time the cache needs to get at the netfs data, it calls fscache_use_cookie() to increment it - if it is not zero. If it was zero, then access is not permitted. (3) When the cache has finished with the data, it calls fscache_unuse_cookie() to decrement it. This does a wake-up on it if it reaches 0. (4) __fscache_relinquish_cookie() decrements n_active and then waits for it to reach 0. The initialisation to 1 in step (1) ensures that we only get wake ups when we're trying to get rid of the cookie. This leaves __fscache_relinquish_cookie() a lot simpler. *** This fixes a problem in the current code whereby if fscache_invalidate() is followed sufficiently quickly by fscache_relinquish_cookie() then it is possible for __fscache_relinquish_cookie() to have detached the cookie from the object and cleared the pointer before a thread is dispatched to process the invalidation state in the object state machine. Since the pending write clearance was deferred to the invalidation state to make it asynchronous, we need to either wait in relinquishment for the stores tree to be cleared in the invalidation state or we need to handle the clearance in relinquishment. Further, if the relinquishment code does clear the tree, then the invalidation state need to make the clearance contingent on still having the cookie to hand (since that's where the tree is rooted) and we have to prevent the cookie from disappearing for the duration. This can lead to an oops like the following: BUG: unable to handle kernel NULL pointer dereference at 000000000000000c ... RIP: 0010:[<ffffffff8151023e>] _spin_lock+0xe/0x30 ... CR2: 000000000000000c ... ... Process kslowd002 (...) .... Call Trace: [<ffffffffa01c3278>] fscache_invalidate_writes+0x38/0xd0 [fscache] [<ffffffff810096f0>] ? __switch_to+0xd0/0x320 [<ffffffff8105e759>] ? find_busiest_queue+0x69/0x150 [<ffffffff8110ddd4>] ? slow_work_enqueue+0x104/0x180 [<ffffffffa01c1303>] fscache_object_slow_work_execute+0x5e3/0x9d0 [fscache] [<ffffffff81096b67>] ? bit_waitqueue+0x17/0xd0 [<ffffffff8110e233>] slow_work_execute+0x233/0x310 [<ffffffff8110e515>] slow_work_thread+0x205/0x360 [<ffffffff81096ca0>] ? autoremove_wake_function+0x0/0x40 [<ffffffff8110e310>] ? slow_work_thread+0x0/0x360 [<ffffffff81096936>] kthread+0x96/0xa0 [<ffffffff8100c0ca>] child_rip+0xa/0x20 [<ffffffff810968a0>] ? kthread+0x0/0xa0 [<ffffffff8100c0c0>] ? child_rip+0x0/0x20 The parameter to fscache_invalidate_writes() was object->cookie which is NULL. Signed-off-by: David Howells <dhowells@redhat.com> Tested-By: Milosz Tanski <milosz@adfin.com> Acked-by: Jeff Layton <jlayton@redhat.com>
Diffstat (limited to 'fs/fscache')
-rw-r--r--fs/fscache/cookie.c80
-rw-r--r--fs/fscache/fsdef.c1
-rw-r--r--fs/fscache/internal.h3
-rw-r--r--fs/fscache/main.c11
-rw-r--r--fs/fscache/netfs.c1
-rw-r--r--fs/fscache/object-list.c93
-rw-r--r--fs/fscache/object.c188
-rw-r--r--fs/fscache/operation.c12
-rw-r--r--fs/fscache/page.c26
9 files changed, 179 insertions, 236 deletions
diff --git a/fs/fscache/cookie.c b/fs/fscache/cookie.c
index eee436646989..0e91a3c9fdb2 100644
--- a/fs/fscache/cookie.c
+++ b/fs/fscache/cookie.c
@@ -95,6 +95,11 @@ struct fscache_cookie *__fscache_acquire_cookie(
95 atomic_set(&cookie->usage, 1); 95 atomic_set(&cookie->usage, 1);
96 atomic_set(&cookie->n_children, 0); 96 atomic_set(&cookie->n_children, 0);
97 97
98 /* We keep the active count elevated until relinquishment to prevent an
99 * attempt to wake up every time the object operations queue quiesces.
100 */
101 atomic_set(&cookie->n_active, 1);
102
98 atomic_inc(&parent->usage); 103 atomic_inc(&parent->usage);
99 atomic_inc(&parent->n_children); 104 atomic_inc(&parent->n_children);
100 105
@@ -177,7 +182,6 @@ static int fscache_acquire_non_index_cookie(struct fscache_cookie *cookie)
177 182
178 cookie->flags = 183 cookie->flags =
179 (1 << FSCACHE_COOKIE_LOOKING_UP) | 184 (1 << FSCACHE_COOKIE_LOOKING_UP) |
180 (1 << FSCACHE_COOKIE_CREATING) |
181 (1 << FSCACHE_COOKIE_NO_DATA_YET); 185 (1 << FSCACHE_COOKIE_NO_DATA_YET);
182 186
183 /* ask the cache to allocate objects for this cookie and its parent 187 /* ask the cache to allocate objects for this cookie and its parent
@@ -467,7 +471,6 @@ EXPORT_SYMBOL(__fscache_update_cookie);
467 */ 471 */
468void __fscache_relinquish_cookie(struct fscache_cookie *cookie, int retire) 472void __fscache_relinquish_cookie(struct fscache_cookie *cookie, int retire)
469{ 473{
470 struct fscache_cache *cache;
471 struct fscache_object *object; 474 struct fscache_object *object;
472 475
473 fscache_stat(&fscache_n_relinquishes); 476 fscache_stat(&fscache_n_relinquishes);
@@ -480,8 +483,11 @@ void __fscache_relinquish_cookie(struct fscache_cookie *cookie, int retire)
480 return; 483 return;
481 } 484 }
482 485
483 _enter("%p{%s,%p},%d", 486 _enter("%p{%s,%p,%d},%d",
484 cookie, cookie->def->name, cookie->netfs_data, retire); 487 cookie, cookie->def->name, cookie->netfs_data,
488 atomic_read(&cookie->n_active), retire);
489
490 ASSERTCMP(atomic_read(&cookie->n_active), >, 0);
485 491
486 if (atomic_read(&cookie->n_children) != 0) { 492 if (atomic_read(&cookie->n_children) != 0) {
487 printk(KERN_ERR "FS-Cache: Cookie '%s' still has children\n", 493 printk(KERN_ERR "FS-Cache: Cookie '%s' still has children\n",
@@ -489,62 +495,28 @@ void __fscache_relinquish_cookie(struct fscache_cookie *cookie, int retire)
489 BUG(); 495 BUG();
490 } 496 }
491 497
492 /* wait for the cookie to finish being instantiated (or to fail) */ 498 /* No further netfs-accessing operations on this cookie permitted */
493 if (test_bit(FSCACHE_COOKIE_CREATING, &cookie->flags)) { 499 set_bit(FSCACHE_COOKIE_RELINQUISHED, &cookie->flags);
494 fscache_stat(&fscache_n_relinquishes_waitcrt); 500 if (retire)
495 wait_on_bit(&cookie->flags, FSCACHE_COOKIE_CREATING, 501 set_bit(FSCACHE_COOKIE_RETIRED, &cookie->flags);
496 fscache_wait_bit, TASK_UNINTERRUPTIBLE);
497 }
498 502
499try_again:
500 spin_lock(&cookie->lock); 503 spin_lock(&cookie->lock);
501 504 hlist_for_each_entry(object, &cookie->backing_objects, cookie_link) {
502 /* break links with all the active objects */
503 while (!hlist_empty(&cookie->backing_objects)) {
504 int n_reads;
505 object = hlist_entry(cookie->backing_objects.first,
506 struct fscache_object,
507 cookie_link);
508
509 _debug("RELEASE OBJ%x", object->debug_id);
510
511 set_bit(FSCACHE_COOKIE_WAITING_ON_READS, &cookie->flags);
512 n_reads = atomic_read(&object->n_reads);
513 if (n_reads) {
514 int n_ops = object->n_ops;
515 int n_in_progress = object->n_in_progress;
516 spin_unlock(&cookie->lock);
517 printk(KERN_ERR "FS-Cache:"
518 " Cookie '%s' still has %d outstanding reads (%d,%d)\n",
519 cookie->def->name,
520 n_reads, n_ops, n_in_progress);
521 wait_on_bit(&cookie->flags, FSCACHE_COOKIE_WAITING_ON_READS,
522 fscache_wait_bit, TASK_UNINTERRUPTIBLE);
523 printk("Wait finished\n");
524 goto try_again;
525 }
526
527 /* detach each cache object from the object cookie */
528 spin_lock(&object->lock);
529 hlist_del_init(&object->cookie_link);
530
531 cache = object->cache;
532 object->cookie = NULL;
533 if (retire)
534 set_bit(FSCACHE_OBJECT_RETIRE, &object->flags);
535 fscache_raise_event(object, FSCACHE_OBJECT_EV_KILL); 505 fscache_raise_event(object, FSCACHE_OBJECT_EV_KILL);
536 spin_unlock(&object->lock);
537
538 if (atomic_dec_and_test(&cookie->usage))
539 /* the cookie refcount shouldn't be reduced to 0 yet */
540 BUG();
541 } 506 }
507 spin_unlock(&cookie->lock);
542 508
543 /* detach pointers back to the netfs */ 509 /* Wait for cessation of activity requiring access to the netfs (when
510 * n_active reaches 0).
511 */
512 if (!atomic_dec_and_test(&cookie->n_active))
513 wait_on_atomic_t(&cookie->n_active, fscache_wait_atomic_t,
514 TASK_UNINTERRUPTIBLE);
515
516 /* Clear pointers back to the netfs */
544 cookie->netfs_data = NULL; 517 cookie->netfs_data = NULL;
545 cookie->def = NULL; 518 cookie->def = NULL;
546 519 BUG_ON(cookie->stores.rnode);
547 spin_unlock(&cookie->lock);
548 520
549 if (cookie->parent) { 521 if (cookie->parent) {
550 ASSERTCMP(atomic_read(&cookie->parent->usage), >, 0); 522 ASSERTCMP(atomic_read(&cookie->parent->usage), >, 0);
@@ -552,7 +524,7 @@ try_again:
552 atomic_dec(&cookie->parent->n_children); 524 atomic_dec(&cookie->parent->n_children);
553 } 525 }
554 526
555 /* finally dispose of the cookie */ 527 /* Dispose of the netfs's link to the cookie */
556 ASSERTCMP(atomic_read(&cookie->usage), >, 0); 528 ASSERTCMP(atomic_read(&cookie->usage), >, 0);
557 fscache_cookie_put(cookie); 529 fscache_cookie_put(cookie);
558 530
diff --git a/fs/fscache/fsdef.c b/fs/fscache/fsdef.c
index f5b4baee7352..10a2ade0bdf8 100644
--- a/fs/fscache/fsdef.c
+++ b/fs/fscache/fsdef.c
@@ -55,6 +55,7 @@ static struct fscache_cookie_def fscache_fsdef_index_def = {
55 55
56struct fscache_cookie fscache_fsdef_index = { 56struct fscache_cookie fscache_fsdef_index = {
57 .usage = ATOMIC_INIT(1), 57 .usage = ATOMIC_INIT(1),
58 .n_active = ATOMIC_INIT(1),
58 .lock = __SPIN_LOCK_UNLOCKED(fscache_fsdef_index.lock), 59 .lock = __SPIN_LOCK_UNLOCKED(fscache_fsdef_index.lock),
59 .backing_objects = HLIST_HEAD_INIT, 60 .backing_objects = HLIST_HEAD_INIT,
60 .def = &fscache_fsdef_index_def, 61 .def = &fscache_fsdef_index_def,
diff --git a/fs/fscache/internal.h b/fs/fscache/internal.h
index 3322d3c42ba8..12d505bedb5c 100644
--- a/fs/fscache/internal.h
+++ b/fs/fscache/internal.h
@@ -93,6 +93,7 @@ static inline bool fscache_object_congested(void)
93 93
94extern int fscache_wait_bit(void *); 94extern int fscache_wait_bit(void *);
95extern int fscache_wait_bit_interruptible(void *); 95extern int fscache_wait_bit_interruptible(void *);
96extern int fscache_wait_atomic_t(atomic_t *);
96 97
97/* 98/*
98 * object.c 99 * object.c
@@ -106,8 +107,10 @@ extern void fscache_enqueue_object(struct fscache_object *);
106extern const struct file_operations fscache_objlist_fops; 107extern const struct file_operations fscache_objlist_fops;
107 108
108extern void fscache_objlist_add(struct fscache_object *); 109extern void fscache_objlist_add(struct fscache_object *);
110extern void fscache_objlist_remove(struct fscache_object *);
109#else 111#else
110#define fscache_objlist_add(object) do {} while(0) 112#define fscache_objlist_add(object) do {} while(0)
113#define fscache_objlist_remove(object) do {} while(0)
111#endif 114#endif
112 115
113/* 116/*
diff --git a/fs/fscache/main.c b/fs/fscache/main.c
index f9d856773f79..7c27907e650c 100644
--- a/fs/fscache/main.c
+++ b/fs/fscache/main.c
@@ -205,7 +205,6 @@ int fscache_wait_bit(void *flags)
205 schedule(); 205 schedule();
206 return 0; 206 return 0;
207} 207}
208EXPORT_SYMBOL(fscache_wait_bit);
209 208
210/* 209/*
211 * wait_on_bit() sleep function for interruptible waiting 210 * wait_on_bit() sleep function for interruptible waiting
@@ -215,4 +214,12 @@ int fscache_wait_bit_interruptible(void *flags)
215 schedule(); 214 schedule();
216 return signal_pending(current); 215 return signal_pending(current);
217} 216}
218EXPORT_SYMBOL(fscache_wait_bit_interruptible); 217
218/*
219 * wait_on_atomic_t() sleep function for uninterruptible waiting
220 */
221int fscache_wait_atomic_t(atomic_t *p)
222{
223 schedule();
224 return 0;
225}
diff --git a/fs/fscache/netfs.c b/fs/fscache/netfs.c
index e028b8eb1c40..b1bb6117473a 100644
--- a/fs/fscache/netfs.c
+++ b/fs/fscache/netfs.c
@@ -40,6 +40,7 @@ int __fscache_register_netfs(struct fscache_netfs *netfs)
40 /* initialise the primary index cookie */ 40 /* initialise the primary index cookie */
41 atomic_set(&netfs->primary_index->usage, 1); 41 atomic_set(&netfs->primary_index->usage, 1);
42 atomic_set(&netfs->primary_index->n_children, 0); 42 atomic_set(&netfs->primary_index->n_children, 0);
43 atomic_set(&netfs->primary_index->n_active, 1);
43 44
44 netfs->primary_index->def = &fscache_fsdef_netfs_def; 45 netfs->primary_index->def = &fscache_fsdef_netfs_def;
45 netfs->primary_index->parent = &fscache_fsdef_index; 46 netfs->primary_index->parent = &fscache_fsdef_index;
diff --git a/fs/fscache/object-list.c b/fs/fscache/object-list.c
index 4a386b080e03..e1959efad64f 100644
--- a/fs/fscache/object-list.c
+++ b/fs/fscache/object-list.c
@@ -70,13 +70,10 @@ void fscache_objlist_add(struct fscache_object *obj)
70 write_unlock(&fscache_object_list_lock); 70 write_unlock(&fscache_object_list_lock);
71} 71}
72 72
73/** 73/*
74 * fscache_object_destroy - Note that a cache object is about to be destroyed 74 * Remove an object from the object list.
75 * @object: The object to be destroyed
76 *
77 * Note the imminent destruction and deallocation of a cache object record.
78 */ 75 */
79void fscache_object_destroy(struct fscache_object *obj) 76void fscache_objlist_remove(struct fscache_object *obj)
80{ 77{
81 write_lock(&fscache_object_list_lock); 78 write_lock(&fscache_object_list_lock);
82 79
@@ -85,7 +82,6 @@ void fscache_object_destroy(struct fscache_object *obj)
85 82
86 write_unlock(&fscache_object_list_lock); 83 write_unlock(&fscache_object_list_lock);
87} 84}
88EXPORT_SYMBOL(fscache_object_destroy);
89 85
90/* 86/*
91 * find the object in the tree on or after the specified index 87 * find the object in the tree on or after the specified index
@@ -166,10 +162,9 @@ static int fscache_objlist_show(struct seq_file *m, void *v)
166{ 162{
167 struct fscache_objlist_data *data = m->private; 163 struct fscache_objlist_data *data = m->private;
168 struct fscache_object *obj = v; 164 struct fscache_object *obj = v;
165 struct fscache_cookie *cookie;
169 unsigned long config = data->config; 166 unsigned long config = data->config;
170 uint16_t keylen, auxlen;
171 char _type[3], *type; 167 char _type[3], *type;
172 bool no_cookie;
173 u8 *buf = data->buf, *p; 168 u8 *buf = data->buf, *p;
174 169
175 if ((unsigned long) v == 1) { 170 if ((unsigned long) v == 1) {
@@ -216,8 +211,9 @@ static int fscache_objlist_show(struct seq_file *m, void *v)
216 } \ 211 } \
217 } while(0) 212 } while(0)
218 213
214 cookie = obj->cookie;
219 if (~config) { 215 if (~config) {
220 FILTER(obj->cookie, 216 FILTER(cookie->def,
221 COOKIE, NOCOOKIE); 217 COOKIE, NOCOOKIE);
222 FILTER(fscache_object_is_active(obj) || 218 FILTER(fscache_object_is_active(obj) ||
223 obj->n_ops != 0 || 219 obj->n_ops != 0 ||
@@ -250,48 +246,40 @@ static int fscache_objlist_show(struct seq_file *m, void *v)
250 obj->flags, 246 obj->flags,
251 work_busy(&obj->work)); 247 work_busy(&obj->work));
252 248
253 no_cookie = true; 249 if (fscache_use_cookie(obj)) {
254 keylen = auxlen = 0; 250 uint16_t keylen = 0, auxlen = 0;
255 if (obj->cookie) {
256 spin_lock(&obj->lock);
257 if (obj->cookie) {
258 switch (obj->cookie->def->type) {
259 case 0:
260 type = "IX";
261 break;
262 case 1:
263 type = "DT";
264 break;
265 default:
266 sprintf(_type, "%02u",
267 obj->cookie->def->type);
268 type = _type;
269 break;
270 }
271 251
272 seq_printf(m, "%-16s %s %2lx %16p", 252 switch (cookie->def->type) {
273 obj->cookie->def->name, 253 case 0:
274 type, 254 type = "IX";
275 obj->cookie->flags, 255 break;
276 obj->cookie->netfs_data); 256 case 1:
277 257 type = "DT";
278 if (obj->cookie->def->get_key && 258 break;
279 config & FSCACHE_OBJLIST_CONFIG_KEY) 259 default:
280 keylen = obj->cookie->def->get_key( 260 sprintf(_type, "%02u", cookie->def->type);
281 obj->cookie->netfs_data, 261 type = _type;
282 buf, 400); 262 break;
283
284 if (obj->cookie->def->get_aux &&
285 config & FSCACHE_OBJLIST_CONFIG_AUX)
286 auxlen = obj->cookie->def->get_aux(
287 obj->cookie->netfs_data,
288 buf + keylen, 512 - keylen);
289
290 no_cookie = false;
291 } 263 }
292 spin_unlock(&obj->lock);
293 264
294 if (!no_cookie && (keylen > 0 || auxlen > 0)) { 265 seq_printf(m, "%-16s %s %2lx %16p",
266 cookie->def->name,
267 type,
268 cookie->flags,
269 cookie->netfs_data);
270
271 if (cookie->def->get_key &&
272 config & FSCACHE_OBJLIST_CONFIG_KEY)
273 keylen = cookie->def->get_key(cookie->netfs_data,
274 buf, 400);
275
276 if (cookie->def->get_aux &&
277 config & FSCACHE_OBJLIST_CONFIG_AUX)
278 auxlen = cookie->def->get_aux(cookie->netfs_data,
279 buf + keylen, 512 - keylen);
280 fscache_unuse_cookie(obj);
281
282 if (keylen > 0 || auxlen > 0) {
295 seq_printf(m, " "); 283 seq_printf(m, " ");
296 for (p = buf; keylen > 0; keylen--) 284 for (p = buf; keylen > 0; keylen--)
297 seq_printf(m, "%02x", *p++); 285 seq_printf(m, "%02x", *p++);
@@ -302,12 +290,11 @@ static int fscache_objlist_show(struct seq_file *m, void *v)
302 seq_printf(m, "%02x", *p++); 290 seq_printf(m, "%02x", *p++);
303 } 291 }
304 } 292 }
305 }
306 293
307 if (no_cookie)
308 seq_printf(m, "<no_cookie>\n");
309 else
310 seq_printf(m, "\n"); 294 seq_printf(m, "\n");
295 } else {
296 seq_printf(m, "<no_netfs>\n");
297 }
311 return 0; 298 return 0;
312} 299}
313 300
diff --git a/fs/fscache/object.c b/fs/fscache/object.c
index 8f17debd7979..86d75a60b20c 100644
--- a/fs/fscache/object.c
+++ b/fs/fscache/object.c
@@ -30,7 +30,6 @@ static const struct fscache_state *fscache_look_up_object(struct fscache_object
30static const struct fscache_state *fscache_object_available(struct fscache_object *, int); 30static const struct fscache_state *fscache_object_available(struct fscache_object *, int);
31static const struct fscache_state *fscache_parent_ready(struct fscache_object *, int); 31static const struct fscache_state *fscache_parent_ready(struct fscache_object *, int);
32static const struct fscache_state *fscache_update_object(struct fscache_object *, int); 32static const struct fscache_state *fscache_update_object(struct fscache_object *, int);
33static const struct fscache_state *fscache_detach_from_cookie(struct fscache_object *, int);
34 33
35#define __STATE_NAME(n) fscache_osm_##n 34#define __STATE_NAME(n) fscache_osm_##n
36#define STATE(n) (&__STATE_NAME(n)) 35#define STATE(n) (&__STATE_NAME(n))
@@ -92,7 +91,6 @@ static WORK_STATE(LOOKUP_FAILURE, "LCFL", fscache_lookup_failure);
92static WORK_STATE(KILL_OBJECT, "KILL", fscache_kill_object); 91static WORK_STATE(KILL_OBJECT, "KILL", fscache_kill_object);
93static WORK_STATE(KILL_DEPENDENTS, "KDEP", fscache_kill_dependents); 92static WORK_STATE(KILL_DEPENDENTS, "KDEP", fscache_kill_dependents);
94static WORK_STATE(DROP_OBJECT, "DROP", fscache_drop_object); 93static WORK_STATE(DROP_OBJECT, "DROP", fscache_drop_object);
95static WORK_STATE(DETACH_FROM_COOKIE, "DTCH", fscache_detach_from_cookie);
96static WORK_STATE(OBJECT_DEAD, "DEAD", (void*)2UL); 94static WORK_STATE(OBJECT_DEAD, "DEAD", (void*)2UL);
97 95
98static WAIT_STATE(WAIT_FOR_INIT, "?INI", 96static WAIT_STATE(WAIT_FOR_INIT, "?INI",
@@ -156,8 +154,8 @@ static inline void fscache_done_parent_op(struct fscache_object *object)
156 object->debug_id, parent->debug_id, parent->n_ops); 154 object->debug_id, parent->debug_id, parent->n_ops);
157 155
158 spin_lock_nested(&parent->lock, 1); 156 spin_lock_nested(&parent->lock, 1);
159 parent->n_ops--;
160 parent->n_obj_ops--; 157 parent->n_obj_ops--;
158 parent->n_ops--;
161 if (parent->n_ops == 0) 159 if (parent->n_ops == 0)
162 fscache_raise_event(parent, FSCACHE_OBJECT_EV_CLEARED); 160 fscache_raise_event(parent, FSCACHE_OBJECT_EV_CLEARED);
163 spin_unlock(&parent->lock); 161 spin_unlock(&parent->lock);
@@ -332,22 +330,10 @@ EXPORT_SYMBOL(fscache_object_init);
332static const struct fscache_state *fscache_abort_initialisation(struct fscache_object *object, 330static const struct fscache_state *fscache_abort_initialisation(struct fscache_object *object,
333 int event) 331 int event)
334{ 332{
335 struct fscache_cookie *cookie;
336
337 _enter("{OBJ%x},%d", object->debug_id, event); 333 _enter("{OBJ%x},%d", object->debug_id, event);
338 334
339 object->oob_event_mask = 0; 335 object->oob_event_mask = 0;
340 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags);
341
342 fscache_dequeue_object(object); 336 fscache_dequeue_object(object);
343
344 spin_lock(&object->lock);
345 cookie = object->cookie;
346 clear_bit_unlock(FSCACHE_COOKIE_CREATING, &cookie->flags);
347 spin_unlock(&object->lock);
348
349 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_CREATING);
350
351 return transit_to(KILL_OBJECT); 337 return transit_to(KILL_OBJECT);
352} 338}
353 339
@@ -357,8 +343,6 @@ static const struct fscache_state *fscache_abort_initialisation(struct fscache_o
357 * immediately to do a creation 343 * immediately to do a creation
358 * - we may need to start the process of creating a parent and we need to wait 344 * - we may need to start the process of creating a parent and we need to wait
359 * for the parent's lookup and creation to complete if it's not there yet 345 * for the parent's lookup and creation to complete if it's not there yet
360 * - an object's cookie is pinned until we clear FSCACHE_COOKIE_CREATING on the
361 * leaf-most cookies of the object and all its children
362 */ 346 */
363static const struct fscache_state *fscache_initialise_object(struct fscache_object *object, 347static const struct fscache_state *fscache_initialise_object(struct fscache_object *object,
364 int event) 348 int event)
@@ -373,14 +357,14 @@ static const struct fscache_state *fscache_initialise_object(struct fscache_obje
373 parent = object->parent; 357 parent = object->parent;
374 if (!parent) { 358 if (!parent) {
375 _leave(" [no parent]"); 359 _leave(" [no parent]");
376 return transit_to(DETACH_FROM_COOKIE); 360 return transit_to(DROP_OBJECT);
377 } 361 }
378 362
379 _debug("parent %s", parent->state->name); 363 _debug("parent: %s of:%lx", parent->state->name, parent->flags);
380 364
381 if (fscache_object_is_dying(parent)) { 365 if (fscache_object_is_dying(parent)) {
382 _leave(" [bad parent]"); 366 _leave(" [bad parent]");
383 return transit_to(DETACH_FROM_COOKIE); 367 return transit_to(DROP_OBJECT);
384 } 368 }
385 369
386 if (fscache_object_is_available(parent)) { 370 if (fscache_object_is_available(parent)) {
@@ -402,7 +386,7 @@ static const struct fscache_state *fscache_initialise_object(struct fscache_obje
402 spin_unlock(&parent->lock); 386 spin_unlock(&parent->lock);
403 if (!success) { 387 if (!success) {
404 _leave(" [grab failed]"); 388 _leave(" [grab failed]");
405 return transit_to(DETACH_FROM_COOKIE); 389 return transit_to(DROP_OBJECT);
406 } 390 }
407 391
408 /* fscache_acquire_non_index_cookie() uses this 392 /* fscache_acquire_non_index_cookie() uses this
@@ -438,8 +422,6 @@ static const struct fscache_state *fscache_parent_ready(struct fscache_object *o
438 * look an object up in the cache from which it was allocated 422 * look an object up in the cache from which it was allocated
439 * - we hold an "access lock" on the parent object, so the parent object cannot 423 * - we hold an "access lock" on the parent object, so the parent object cannot
440 * be withdrawn by either party till we've finished 424 * be withdrawn by either party till we've finished
441 * - an object's cookie is pinned until we clear FSCACHE_COOKIE_CREATING on the
442 * leaf-most cookies of the object and all its children
443 */ 425 */
444static const struct fscache_state *fscache_look_up_object(struct fscache_object *object, 426static const struct fscache_state *fscache_look_up_object(struct fscache_object *object,
445 int event) 427 int event)
@@ -460,22 +442,21 @@ static const struct fscache_state *fscache_look_up_object(struct fscache_object
460 ASSERT(fscache_object_is_available(parent)); 442 ASSERT(fscache_object_is_available(parent));
461 443
462 if (fscache_object_is_dying(parent) || 444 if (fscache_object_is_dying(parent) ||
463 test_bit(FSCACHE_IOERROR, &object->cache->flags)) { 445 test_bit(FSCACHE_IOERROR, &object->cache->flags) ||
446 !fscache_use_cookie(object)) {
464 _leave(" [unavailable]"); 447 _leave(" [unavailable]");
465 return transit_to(LOOKUP_FAILURE); 448 return transit_to(LOOKUP_FAILURE);
466 } 449 }
467 450
468 _debug("LOOKUP \"%s/%s\" in \"%s\"", 451 _debug("LOOKUP \"%s\" in \"%s\"",
469 parent->cookie->def->name, cookie->def->name, 452 cookie->def->name, object->cache->tag->name);
470 object->cache->tag->name);
471 453
472 fscache_stat(&fscache_n_object_lookups); 454 fscache_stat(&fscache_n_object_lookups);
473 fscache_stat(&fscache_n_cop_lookup_object); 455 fscache_stat(&fscache_n_cop_lookup_object);
474 ret = object->cache->ops->lookup_object(object); 456 ret = object->cache->ops->lookup_object(object);
475 fscache_stat_d(&fscache_n_cop_lookup_object); 457 fscache_stat_d(&fscache_n_cop_lookup_object);
476 458
477 if (test_bit(FSCACHE_OBJECT_EV_ERROR, &object->events)) 459 fscache_unuse_cookie(object);
478 set_bit(FSCACHE_COOKIE_UNAVAILABLE, &cookie->flags);
479 460
480 if (ret == -ETIMEDOUT) { 461 if (ret == -ETIMEDOUT) {
481 /* probably stuck behind another object, so move this one to 462 /* probably stuck behind another object, so move this one to
@@ -557,11 +538,6 @@ void fscache_obtained_object(struct fscache_object *object)
557 } 538 }
558 539
559 set_bit(FSCACHE_OBJECT_IS_AVAILABLE, &object->flags); 540 set_bit(FSCACHE_OBJECT_IS_AVAILABLE, &object->flags);
560
561 /* Permit __fscache_relinquish_cookie() to proceed */
562 clear_bit_unlock(FSCACHE_COOKIE_CREATING, &cookie->flags);
563 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_CREATING);
564
565 _leave(""); 541 _leave("");
566} 542}
567EXPORT_SYMBOL(fscache_obtained_object); 543EXPORT_SYMBOL(fscache_obtained_object);
@@ -572,16 +548,12 @@ EXPORT_SYMBOL(fscache_obtained_object);
572static const struct fscache_state *fscache_object_available(struct fscache_object *object, 548static const struct fscache_state *fscache_object_available(struct fscache_object *object,
573 int event) 549 int event)
574{ 550{
575 struct fscache_cookie *cookie = object->cookie;
576
577 _enter("{OBJ%x},%d", object->debug_id, event); 551 _enter("{OBJ%x},%d", object->debug_id, event);
578 552
579 object->oob_table = fscache_osm_run_oob; 553 object->oob_table = fscache_osm_run_oob;
580 554
581 spin_lock(&object->lock); 555 spin_lock(&object->lock);
582 556
583 ASSERTIF(cookie, !test_bit(FSCACHE_COOKIE_CREATING, &object->cookie->flags));
584
585 fscache_done_parent_op(object); 557 fscache_done_parent_op(object);
586 if (object->n_in_progress == 0) { 558 if (object->n_in_progress == 0) {
587 if (object->n_ops > 0) { 559 if (object->n_ops > 0) {
@@ -624,7 +596,6 @@ static const struct fscache_state *fscache_lookup_failure(struct fscache_object
624 int event) 596 int event)
625{ 597{
626 struct fscache_cookie *cookie; 598 struct fscache_cookie *cookie;
627 bool wake_looking_up = false;
628 599
629 _enter("{OBJ%x},%d", object->debug_id, event); 600 _enter("{OBJ%x},%d", object->debug_id, event);
630 601
@@ -634,19 +605,10 @@ static const struct fscache_state *fscache_lookup_failure(struct fscache_object
634 object->cache->ops->lookup_complete(object); 605 object->cache->ops->lookup_complete(object);
635 fscache_stat_d(&fscache_n_cop_lookup_complete); 606 fscache_stat_d(&fscache_n_cop_lookup_complete);
636 607
637 spin_lock(&object->lock);
638 cookie = object->cookie; 608 cookie = object->cookie;
639 set_bit(FSCACHE_COOKIE_UNAVAILABLE, &cookie->flags); 609 set_bit(FSCACHE_COOKIE_UNAVAILABLE, &cookie->flags);
640 if (cookie) { 610 if (test_and_clear_bit(FSCACHE_COOKIE_LOOKING_UP, &cookie->flags))
641 if (test_and_clear_bit(FSCACHE_COOKIE_LOOKING_UP, &cookie->flags))
642 wake_looking_up = true;
643 clear_bit_unlock(FSCACHE_COOKIE_CREATING, &cookie->flags);
644 }
645 spin_unlock(&object->lock);
646
647 if (wake_looking_up)
648 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_LOOKING_UP); 611 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_LOOKING_UP);
649 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_CREATING);
650 612
651 fscache_done_parent_op(object); 613 fscache_done_parent_op(object);
652 return transit_to(KILL_OBJECT); 614 return transit_to(KILL_OBJECT);
@@ -662,21 +624,20 @@ static const struct fscache_state *fscache_kill_object(struct fscache_object *ob
662 _enter("{OBJ%x,%d,%d},%d", 624 _enter("{OBJ%x,%d,%d},%d",
663 object->debug_id, object->n_ops, object->n_children, event); 625 object->debug_id, object->n_ops, object->n_children, event);
664 626
665 object->oob_event_mask = 0;
666
667 spin_lock(&object->lock);
668 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags); 627 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags);
669 spin_unlock(&object->lock); 628 object->oob_event_mask = 0;
670 629
671 if (list_empty(&object->dependents) && 630 if (list_empty(&object->dependents) &&
672 object->n_ops == 0 && 631 object->n_ops == 0 &&
673 object->n_children == 0) 632 object->n_children == 0)
674 return object->cookie ? 633 return transit_to(DROP_OBJECT);
675 transit_to(DETACH_FROM_COOKIE) : transit_to(DROP_OBJECT);
676 634
677 spin_lock(&object->lock); 635 if (object->n_in_progress == 0) {
678 fscache_start_operations(object); 636 spin_lock(&object->lock);
679 spin_unlock(&object->lock); 637 if (object->n_ops > 0 && object->n_in_progress == 0)
638 fscache_start_operations(object);
639 spin_unlock(&object->lock);
640 }
680 641
681 if (!list_empty(&object->dependents)) 642 if (!list_empty(&object->dependents))
682 return transit_to(KILL_DEPENDENTS); 643 return transit_to(KILL_DEPENDENTS);
@@ -698,64 +659,32 @@ static const struct fscache_state *fscache_kill_dependents(struct fscache_object
698} 659}
699 660
700/* 661/*
701 * withdraw an object from active service
702 */
703static const struct fscache_state *fscache_detach_from_cookie(struct fscache_object *object,
704 int event)
705{
706 struct fscache_cookie *cookie;
707 bool detached = false, awaken = false;
708
709 _enter("{OBJ%x},%d", object->debug_id, event);
710
711 spin_lock(&object->lock);
712 cookie = object->cookie;
713 if (cookie) {
714 /* need to get the cookie lock before the object lock, starting
715 * from the object pointer */
716 atomic_inc(&cookie->usage);
717 spin_unlock(&object->lock);
718
719 spin_lock(&cookie->lock);
720 spin_lock(&object->lock);
721
722 if (object->cookie == cookie) {
723 hlist_del_init(&object->cookie_link);
724 object->cookie = NULL;
725 if (test_and_clear_bit(FSCACHE_COOKIE_INVALIDATING,
726 &cookie->flags))
727 awaken = true;
728 detached = true;
729 }
730 spin_unlock(&cookie->lock);
731 fscache_cookie_put(cookie);
732 if (detached)
733 fscache_cookie_put(cookie);
734 }
735
736 spin_unlock(&object->lock);
737
738 if (awaken)
739 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_INVALIDATING);
740
741 fscache_stat(&fscache_n_object_dead);
742 _leave("");
743 return transit_to(DROP_OBJECT);
744}
745
746/*
747 * Drop an object's attachments 662 * Drop an object's attachments
748 */ 663 */
749static const struct fscache_state *fscache_drop_object(struct fscache_object *object, 664static const struct fscache_state *fscache_drop_object(struct fscache_object *object,
750 int event) 665 int event)
751{ 666{
752 struct fscache_object *parent = object->parent; 667 struct fscache_object *parent = object->parent;
668 struct fscache_cookie *cookie = object->cookie;
753 struct fscache_cache *cache = object->cache; 669 struct fscache_cache *cache = object->cache;
670 bool awaken = false;
754 671
755 _enter("{OBJ%x,%d},%d", object->debug_id, object->n_children, event); 672 _enter("{OBJ%x,%d},%d", object->debug_id, object->n_children, event);
756 673
757 ASSERTCMP(object->cookie, ==, NULL); 674 ASSERT(cookie != NULL);
758 ASSERT(hlist_unhashed(&object->cookie_link)); 675 ASSERT(!hlist_unhashed(&object->cookie_link));
676
677 /* Make sure the cookie no longer points here and that the netfs isn't
678 * waiting for us.
679 */
680 spin_lock(&cookie->lock);
681 hlist_del_init(&object->cookie_link);
682 if (test_and_clear_bit(FSCACHE_COOKIE_INVALIDATING, &cookie->flags))
683 awaken = true;
684 spin_unlock(&cookie->lock);
685
686 if (awaken)
687 wake_up_bit(&cookie->flags, FSCACHE_COOKIE_INVALIDATING);
759 688
760 /* Prevent a race with our last child, which has to signal EV_CLEARED 689 /* Prevent a race with our last child, which has to signal EV_CLEARED
761 * before dropping our spinlock. 690 * before dropping our spinlock.
@@ -816,6 +745,22 @@ static void fscache_put_object(struct fscache_object *object)
816 fscache_stat_d(&fscache_n_cop_put_object); 745 fscache_stat_d(&fscache_n_cop_put_object);
817} 746}
818 747
748/**
749 * fscache_object_destroy - Note that a cache object is about to be destroyed
750 * @object: The object to be destroyed
751 *
752 * Note the imminent destruction and deallocation of a cache object record.
753 */
754void fscache_object_destroy(struct fscache_object *object)
755{
756 fscache_objlist_remove(object);
757
758 /* We can get rid of the cookie now */
759 fscache_cookie_put(object->cookie);
760 object->cookie = NULL;
761}
762EXPORT_SYMBOL(fscache_object_destroy);
763
819/* 764/*
820 * enqueue an object for metadata-type processing 765 * enqueue an object for metadata-type processing
821 */ 766 */
@@ -925,7 +870,10 @@ static void fscache_dequeue_object(struct fscache_object *object)
925 * @data: The auxiliary data for the object 870 * @data: The auxiliary data for the object
926 * @datalen: The size of the auxiliary data 871 * @datalen: The size of the auxiliary data
927 * 872 *
928 * This function consults the netfs about the coherency state of an object 873 * This function consults the netfs about the coherency state of an object.
874 * The caller must be holding a ref on cookie->n_active (held by
875 * fscache_look_up_object() on behalf of the cache backend during object lookup
876 * and creation).
929 */ 877 */
930enum fscache_checkaux fscache_check_aux(struct fscache_object *object, 878enum fscache_checkaux fscache_check_aux(struct fscache_object *object,
931 const void *data, uint16_t datalen) 879 const void *data, uint16_t datalen)
@@ -974,6 +922,15 @@ static const struct fscache_state *_fscache_invalidate_object(struct fscache_obj
974 922
975 _enter("{OBJ%x},%d", object->debug_id, event); 923 _enter("{OBJ%x},%d", object->debug_id, event);
976 924
925 /* We're going to need the cookie. If the cookie is not available then
926 * retire the object instead.
927 */
928 if (!fscache_use_cookie(object)) {
929 ASSERT(object->cookie->stores.rnode == NULL);
930 set_bit(FSCACHE_COOKIE_RETIRED, &cookie->flags);
931 _leave(" [no cookie]");
932 return transit_to(KILL_OBJECT);
933 }
977 934
978 /* Reject any new read/write ops and abort any that are pending. */ 935 /* Reject any new read/write ops and abort any that are pending. */
979 fscache_invalidate_writes(cookie); 936 fscache_invalidate_writes(cookie);
@@ -982,14 +939,13 @@ static const struct fscache_state *_fscache_invalidate_object(struct fscache_obj
982 939
983 /* Now we have to wait for in-progress reads and writes */ 940 /* Now we have to wait for in-progress reads and writes */
984 op = kzalloc(sizeof(*op), GFP_KERNEL); 941 op = kzalloc(sizeof(*op), GFP_KERNEL);
985 if (!op) { 942 if (!op)
986 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags); 943 goto nomem;
987 _leave(" [ENOMEM]");
988 return transit_to(KILL_OBJECT);
989 }
990 944
991 fscache_operation_init(op, object->cache->ops->invalidate_object, NULL); 945 fscache_operation_init(op, object->cache->ops->invalidate_object, NULL);
992 op->flags = FSCACHE_OP_ASYNC | (1 << FSCACHE_OP_EXCLUSIVE); 946 op->flags = FSCACHE_OP_ASYNC |
947 (1 << FSCACHE_OP_EXCLUSIVE) |
948 (1 << FSCACHE_OP_UNUSE_COOKIE);
993 949
994 spin_lock(&cookie->lock); 950 spin_lock(&cookie->lock);
995 if (fscache_submit_exclusive_op(object, op) < 0) 951 if (fscache_submit_exclusive_op(object, op) < 0)
@@ -1011,6 +967,12 @@ static const struct fscache_state *_fscache_invalidate_object(struct fscache_obj
1011 _leave(" [ok]"); 967 _leave(" [ok]");
1012 return transit_to(UPDATE_OBJECT); 968 return transit_to(UPDATE_OBJECT);
1013 969
970nomem:
971 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags);
972 fscache_unuse_cookie(object);
973 _leave(" [ENOMEM]");
974 return transit_to(KILL_OBJECT);
975
1014submit_op_failed: 976submit_op_failed:
1015 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags); 977 clear_bit(FSCACHE_OBJECT_IS_LIVE, &object->flags);
1016 spin_unlock(&cookie->lock); 978 spin_unlock(&cookie->lock);
diff --git a/fs/fscache/operation.c b/fs/fscache/operation.c
index 4da211b21ddf..6935901bce38 100644
--- a/fs/fscache/operation.c
+++ b/fs/fscache/operation.c
@@ -424,14 +424,10 @@ void fscache_put_operation(struct fscache_operation *op)
424 424
425 object = op->object; 425 object = op->object;
426 426
427 if (test_bit(FSCACHE_OP_DEC_READ_CNT, &op->flags)) { 427 if (test_bit(FSCACHE_OP_DEC_READ_CNT, &op->flags))
428 if (atomic_dec_and_test(&object->n_reads)) { 428 atomic_dec(&object->n_reads);
429 clear_bit(FSCACHE_COOKIE_WAITING_ON_READS, 429 if (test_bit(FSCACHE_OP_UNUSE_COOKIE, &op->flags))
430 &object->cookie->flags); 430 fscache_unuse_cookie(object);
431 wake_up_bit(&object->cookie->flags,
432 FSCACHE_COOKIE_WAITING_ON_READS);
433 }
434 }
435 431
436 /* now... we may get called with the object spinlock held, so we 432 /* now... we may get called with the object spinlock held, so we
437 * complete the cleanup here only if we can immediately acquire the 433 * complete the cleanup here only if we can immediately acquire the
diff --git a/fs/fscache/page.c b/fs/fscache/page.c
index b4e4b424160a..780bac6ffde5 100644
--- a/fs/fscache/page.c
+++ b/fs/fscache/page.c
@@ -163,10 +163,12 @@ static void fscache_attr_changed_op(struct fscache_operation *op)
163 163
164 fscache_stat(&fscache_n_attr_changed_calls); 164 fscache_stat(&fscache_n_attr_changed_calls);
165 165
166 if (fscache_object_is_active(object)) { 166 if (fscache_object_is_active(object) &&
167 fscache_use_cookie(object)) {
167 fscache_stat(&fscache_n_cop_attr_changed); 168 fscache_stat(&fscache_n_cop_attr_changed);
168 ret = object->cache->ops->attr_changed(object); 169 ret = object->cache->ops->attr_changed(object);
169 fscache_stat_d(&fscache_n_cop_attr_changed); 170 fscache_stat_d(&fscache_n_cop_attr_changed);
171 fscache_unuse_cookie(object);
170 if (ret < 0) 172 if (ret < 0)
171 fscache_abort_object(object); 173 fscache_abort_object(object);
172 } 174 }
@@ -246,6 +248,7 @@ static void fscache_release_retrieval_op(struct fscache_operation *_op)
246 * allocate a retrieval op 248 * allocate a retrieval op
247 */ 249 */
248static struct fscache_retrieval *fscache_alloc_retrieval( 250static struct fscache_retrieval *fscache_alloc_retrieval(
251 struct fscache_cookie *cookie,
249 struct address_space *mapping, 252 struct address_space *mapping,
250 fscache_rw_complete_t end_io_func, 253 fscache_rw_complete_t end_io_func,
251 void *context) 254 void *context)
@@ -260,7 +263,10 @@ static struct fscache_retrieval *fscache_alloc_retrieval(
260 } 263 }
261 264
262 fscache_operation_init(&op->op, NULL, fscache_release_retrieval_op); 265 fscache_operation_init(&op->op, NULL, fscache_release_retrieval_op);
263 op->op.flags = FSCACHE_OP_MYTHREAD | (1 << FSCACHE_OP_WAITING); 266 atomic_inc(&cookie->n_active);
267 op->op.flags = FSCACHE_OP_MYTHREAD |
268 (1UL << FSCACHE_OP_WAITING) |
269 (1UL << FSCACHE_OP_UNUSE_COOKIE);
264 op->mapping = mapping; 270 op->mapping = mapping;
265 op->end_io_func = end_io_func; 271 op->end_io_func = end_io_func;
266 op->context = context; 272 op->context = context;
@@ -394,7 +400,8 @@ int __fscache_read_or_alloc_page(struct fscache_cookie *cookie,
394 if (fscache_wait_for_deferred_lookup(cookie) < 0) 400 if (fscache_wait_for_deferred_lookup(cookie) < 0)
395 return -ERESTARTSYS; 401 return -ERESTARTSYS;
396 402
397 op = fscache_alloc_retrieval(page->mapping, end_io_func, context); 403 op = fscache_alloc_retrieval(cookie, page->mapping,
404 end_io_func,context);
398 if (!op) { 405 if (!op) {
399 _leave(" = -ENOMEM"); 406 _leave(" = -ENOMEM");
400 return -ENOMEM; 407 return -ENOMEM;
@@ -465,6 +472,7 @@ nobufs_unlock_dec:
465 atomic_dec(&object->n_reads); 472 atomic_dec(&object->n_reads);
466nobufs_unlock: 473nobufs_unlock:
467 spin_unlock(&cookie->lock); 474 spin_unlock(&cookie->lock);
475 atomic_dec(&cookie->n_active);
468 kfree(op); 476 kfree(op);
469nobufs: 477nobufs:
470 fscache_stat(&fscache_n_retrievals_nobufs); 478 fscache_stat(&fscache_n_retrievals_nobufs);
@@ -522,7 +530,7 @@ int __fscache_read_or_alloc_pages(struct fscache_cookie *cookie,
522 if (fscache_wait_for_deferred_lookup(cookie) < 0) 530 if (fscache_wait_for_deferred_lookup(cookie) < 0)
523 return -ERESTARTSYS; 531 return -ERESTARTSYS;
524 532
525 op = fscache_alloc_retrieval(mapping, end_io_func, context); 533 op = fscache_alloc_retrieval(cookie, mapping, end_io_func, context);
526 if (!op) 534 if (!op)
527 return -ENOMEM; 535 return -ENOMEM;
528 op->n_pages = *nr_pages; 536 op->n_pages = *nr_pages;
@@ -589,6 +597,7 @@ nobufs_unlock_dec:
589 atomic_dec(&object->n_reads); 597 atomic_dec(&object->n_reads);
590nobufs_unlock: 598nobufs_unlock:
591 spin_unlock(&cookie->lock); 599 spin_unlock(&cookie->lock);
600 atomic_dec(&cookie->n_active);
592 kfree(op); 601 kfree(op);
593nobufs: 602nobufs:
594 fscache_stat(&fscache_n_retrievals_nobufs); 603 fscache_stat(&fscache_n_retrievals_nobufs);
@@ -631,7 +640,7 @@ int __fscache_alloc_page(struct fscache_cookie *cookie,
631 if (fscache_wait_for_deferred_lookup(cookie) < 0) 640 if (fscache_wait_for_deferred_lookup(cookie) < 0)
632 return -ERESTARTSYS; 641 return -ERESTARTSYS;
633 642
634 op = fscache_alloc_retrieval(page->mapping, NULL, NULL); 643 op = fscache_alloc_retrieval(cookie, page->mapping, NULL, NULL);
635 if (!op) 644 if (!op)
636 return -ENOMEM; 645 return -ENOMEM;
637 op->n_pages = 1; 646 op->n_pages = 1;
@@ -675,6 +684,7 @@ error:
675 684
676nobufs_unlock: 685nobufs_unlock:
677 spin_unlock(&cookie->lock); 686 spin_unlock(&cookie->lock);
687 atomic_dec(&cookie->n_active);
678 kfree(op); 688 kfree(op);
679nobufs: 689nobufs:
680 fscache_stat(&fscache_n_allocs_nobufs); 690 fscache_stat(&fscache_n_allocs_nobufs);
@@ -876,7 +886,9 @@ int __fscache_write_page(struct fscache_cookie *cookie,
876 886
877 fscache_operation_init(&op->op, fscache_write_op, 887 fscache_operation_init(&op->op, fscache_write_op,
878 fscache_release_write_op); 888 fscache_release_write_op);
879 op->op.flags = FSCACHE_OP_ASYNC | (1 << FSCACHE_OP_WAITING); 889 op->op.flags = FSCACHE_OP_ASYNC |
890 (1 << FSCACHE_OP_WAITING) |
891 (1 << FSCACHE_OP_UNUSE_COOKIE);
880 892
881 ret = radix_tree_preload(gfp & ~__GFP_HIGHMEM); 893 ret = radix_tree_preload(gfp & ~__GFP_HIGHMEM);
882 if (ret < 0) 894 if (ret < 0)
@@ -922,6 +934,7 @@ int __fscache_write_page(struct fscache_cookie *cookie,
922 op->op.debug_id = atomic_inc_return(&fscache_op_debug_id); 934 op->op.debug_id = atomic_inc_return(&fscache_op_debug_id);
923 op->store_limit = object->store_limit; 935 op->store_limit = object->store_limit;
924 936
937 atomic_inc(&cookie->n_active);
925 if (fscache_submit_op(object, &op->op) < 0) 938 if (fscache_submit_op(object, &op->op) < 0)
926 goto submit_failed; 939 goto submit_failed;
927 940
@@ -948,6 +961,7 @@ already_pending:
948 return 0; 961 return 0;
949 962
950submit_failed: 963submit_failed:
964 atomic_dec(&cookie->n_active);
951 spin_lock(&cookie->stores_lock); 965 spin_lock(&cookie->stores_lock);
952 radix_tree_delete(&cookie->stores, page->index); 966 radix_tree_delete(&cookie->stores, page->index);
953 spin_unlock(&cookie->stores_lock); 967 spin_unlock(&cookie->stores_lock);