OSDN Git Service

block: Do not call folio_next() on an unreferenced folio
authorMatthew Wilcox (Oracle) <willy@infradead.org>
Tue, 3 May 2022 04:09:31 +0000 (00:09 -0400)
committerMatthew Wilcox (Oracle) <willy@infradead.org>
Thu, 5 May 2022 04:47:29 +0000 (00:47 -0400)
commit170f37d6aa6ad4582eefd7459015de79e244536e
treeef00e910fd14cf1e14dd739d00575127b6655df1
parenta7391ad3572431a354c927cf8896e86e50d7d0bf
block: Do not call folio_next() on an unreferenced folio

It is unsafe to call folio_next() on a folio unless you hold a reference
on it that prevents it from being split or freed.  After returning
from the iterator, iomap calls folio_end_writeback() which may drop
the last reference to the page, or allow the page to be split.  If that
happens, the iterator will not advance far enough through the bio_vec,
leading to assertion failures like the BUG() in folio_end_writeback()
that checks we're not trying to end writeback on a page not currently
under writeback.  Other assertion failures were also seen, but they're
all explained by this one bug.

Fix the bug by remembering where the next folio starts before returning
from the iterator.  There are other ways of fixing this bug, but this
seems the simplest.

Reported-by: Darrick J. Wong <djwong@kernel.org>
Tested-by: Darrick J. Wong <djwong@kernel.org>
Reported-by: Brian Foster <bfoster@redhat.com>
Tested-by: Brian Foster <bfoster@redhat.com>
Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org>
include/linux/bio.h