Commit a30efe26 authored by David Howells's avatar David Howells

CacheFiles: Fix incorrect test for in-memory object collision

When CacheFiles cache objects are in use, they have in-memory representations,
as defined by the cachefiles_object struct.  These are kept in a tree rooted in
the cache and indexed by dentry pointer (since there's a unique mapping between
object index key and dentry).

Collisions can occur between a representation already in the tree and a new
representation being set up because it takes time to dispose of an old
representation - particularly if it must be unlinked or renamed.

When such a collision occurs, cachefiles_mark_object_active() is meant to check
to see if the old, already-present representation is in the process of being
discarded (ie. FSCACHE_OBJECT_IS_LIVE is not set on it) - and, if so, wait for
the representation to be removed (ie. CACHEFILES_OBJECT_ACTIVE is then
cleared).

However, the test for whether the old representation is still live is checking
the new object - which always will be live at this point.  This leads to an
oops looking like:

	CacheFiles: Error: Unexpected object collision
	object: OBJ1b354
	objstate=LOOK_UP_OBJECT fl=8 wbusy=2 ev=0[0]
	ops=0 inp=0 exc=0
	parent=ffff88053f5417c0
	cookie=ffff880538f202a0 [pr=ffff8805381b7160 nd=ffff880509c6eb78 fl=27]
	key=[8] '2490000000000000'
	xobject: OBJ1a600
	xobjstate=DROP_OBJECT fl=70 wbusy=2 ev=0[0]
	xops=0 inp=0 exc=0
	xparent=ffff88053f5417c0
	xcookie=ffff88050f4cbf70 [pr=ffff8805381b7160 nd=          (null) fl=12]
	------------[ cut here ]------------
	kernel BUG at fs/cachefiles/namei.c:200!
	...
	Workqueue: fscache_object fscache_object_work_func [fscache]
	...
	RIP: ... cachefiles_walk_to_object+0x7ea/0x860 [cachefiles]
	...
	Call Trace:
	 [<ffffffffa04dadd8>] ? cachefiles_lookup_object+0x58/0x100 [cachefiles]
	 [<ffffffffa01affe9>] ? fscache_look_up_object+0xb9/0x1d0 [fscache]
	 [<ffffffffa01afc4d>] ? fscache_parent_ready+0x2d/0x80 [fscache]
	 [<ffffffffa01b0672>] ? fscache_object_work_func+0x92/0x1f0 [fscache]
	 [<ffffffff8107e82b>] ? process_one_work+0x16b/0x400
	 [<ffffffff8107fc16>] ? worker_thread+0x116/0x380
	 [<ffffffff8107fb00>] ? manage_workers.isra.21+0x290/0x290
	 [<ffffffff81085edc>] ? kthread+0xbc/0xe0
	 [<ffffffff81085e20>] ? flush_kthread_worker+0x80/0x80
	 [<ffffffff81502d0c>] ? ret_from_fork+0x7c/0xb0
	 [<ffffffff81085e20>] ? flush_kthread_worker+0x80/0x80
Reported-by: default avatarManuel Schölling <manuel.schoelling@gmx.de>
Signed-off-by: default avatarDavid Howells <dhowells@redhat.com>
Acked-by: default avatarSteve Dickson <steved@redhat.com>
parent a3b7c004
......@@ -189,7 +189,7 @@ static int cachefiles_mark_object_active(struct cachefiles_cache *cache,
/* an old object from a previous incarnation is hogging the slot - we
* need to wait for it to be destroyed */
wait_for_old_object:
if (fscache_object_is_live(&object->fscache)) {
if (fscache_object_is_live(&xobject->fscache)) {
pr_err("\n");
pr_err("Error: Unexpected object collision\n");
cachefiles_printk_object(object, xobject);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment