[JFFS2]The patch "jffs2: Fix lock acquisition order bug in jffs2_write_begin" introduces another dead lock bug.
Thomas.Betker at rohde-schwarz.com
Thomas.Betker at rohde-schwarz.com
Mon Jul 29 06:33:16 EDT 2013
Hello Chao:
> The full header of the patch is below:
> author Thomas Betker <thomas.betker at freenet.de> 2012-10-17 20:59:30
(GMT)
> committer Artem Bityutskiy <artem.bityutskiy at linux.intel.com>
> 2012-11-09 15:02:50 (GMT)
> commit 5ffd3412ae5536a4c57469cb8ea31887121dcb2e?(patch)
> tree 33c9d89eabf70c49e683a36be800be3b4582a358?/fs/jffs2
> parent 0131950ebd146b5e31508233352d6f4625af25b1?(diff)
>
> jffs2: Fix lock acquisition order bug in jffs2_write_begin.
>
> jffs2_write_begin first acquires the c->alloc_sem, then the page
> lock. This causes an ABBA dead lock with jffs2_write_end, which
> already have hold the page lock, then the c->alloc_sem:
> THREAD ONE:
> jffs2_write_begin
> jffs2_reserve_space
> mutex_lock(&c->alloc_sem) A
> grab_cache_page_write_begin
> find_lock_page
> lock_page(page) B
> THERAD TWO:
> jffs2_write_end B(already has taken the page lock because the
> preceding jffs2_write_begin)
> jffs2_write_inode_range
> jffs2_reserve_space
> mutex_lock(&c->alloc_sem) A
I looked at the code, and you are right: When swapping
jffs2_reserve_space() and grab_cache_page_write_begin() in my patch, this
changed the lock acquisition order from lock_page / c->alloc_sem / f->sem
to c->alloc_sem / f->sem / lock_page. [The intention was to acquire f->sem
before lock_page, but c->alloc_sem must be acquired before f->sem
according to README.Locking.]
However, I am surprised that jffs2_write_end() may run, for the same page,
in parallel with jffs2_write_begin(); I would expect that it cannot be
called before jffs2_write_begin() returns. Did your kernel actually panic
on this? Do you have any further information about it?
Best regards,
Thomas
More information about the linux-mtd
mailing list