summaryrefslogtreecommitdiff
path: root/include/linux
diff options
context:
space:
mode:
authorAndrew Morton <akpm@osdl.org>2004-05-22 08:00:42 -0700
committerLinus Torvalds <torvalds@ppc970.osdl.org>2004-05-22 08:00:42 -0700
commitd61ae266b334dfdd64697d4d5b5df9e3440666d8 (patch)
treebcbb1dd3670e96e1ac1922d95263962ce3d9af01 /include/linux
parente6dfd92e48a0d3d2738e30dc762233d85ac98612 (diff)
[PATCH] __set_page_dirty_nobuffers race fix
Running __mark_inode_dirty() against a swapcache page is illegal and will oops. I see a race in set_page_dirty() wherein it can be called with a PageSwapCache page, but if the page is removed from swapcache after __set_page_dirty_nobuffers() drops tree_lock(), we have the situation where PageSwapCache() is false, but local variable `mapping' points at swapcache. Handle that by checking for non-null mapping->host. We don't care about the page state at this point - we're only interested in the inode. There is a converse case: what if a page is added to swapcache as we are running set_page_dirty() against it? In this case the page gets its PG_dirty flag set but it is not tagged as dirty in the swapper_space radix tree. The swap writeout code will handle this OK and test_clear_page_dirty()'s call to radix_tree_tag_clear(PAGECACHE_TAG_DIRTY) will silently have no effect. The only downside is that future radix-tree-based writearound won't notice that such pages are dirty and swap IO scheduling will be a teensy bit worse. The patch also fixes the (silly) testing of local variable `mapping' to see if the page was truncated. We should test page_mapping() for that.
Diffstat (limited to 'include/linux')
0 files changed, 0 insertions, 0 deletions