From 032c09d76cdb448484859cc84dac4bba8f5f8f14 Mon Sep 17 00:00:00 2001 From: Hugh Dickins Date: Fri, 2 Dec 2005 15:59:59 +0000 Subject: [SCSI] sg and st unmap_user_pages allow PageReserved 2.6.15-rc1 made sg's st_unmap_user_pages and st's sgl_unmap_user_pages BUG on a PageReserved page. But that's wrong: they could be unmapping the ZERO_PAGE, which is marked PG_reserved; and perhaps others (while get_user_pages is still permitted on VM_PFNMAP areas - that may change). More change is needed here: sg claims to dirty even pages written from, and st claims not to dirty even pages read into; and SetPageDirty is not adequate for this nowadays. Fixes to those follow in a later patch: for the moment just fix the 2.6.15 regression. Signed-off-by: Hugh Dickins Acked-by: Nick Piggin Signed-off-by: James Bottomley --- drivers/scsi/sg.c | 2 -- 1 file changed, 2 deletions(-) (limited to 'drivers/scsi/sg.c') diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c index 72ec59456e69..6de7ff9faf2d 100644 --- a/drivers/scsi/sg.c +++ b/drivers/scsi/sg.c @@ -1878,8 +1878,6 @@ st_unmap_user_pages(struct scatterlist *sgl, const unsigned int nr_pages, for (i=0; i < nr_pages; i++) { struct page *page = sgl[i].page; - /* XXX: just for debug. Remove when PageReserved is removed */ - BUG_ON(PageReserved(page)); if (dirtied) SetPageDirty(page); /* unlock_page(page); */ -- cgit v1.2.3 From 4d5cda069b3f0a3bbc18576bc15903ed665d0295 Mon Sep 17 00:00:00 2001 From: Hugh Dickins Date: Fri, 2 Dec 2005 15:58:09 +0000 Subject: [SCSI] sg: fix a bug in st_map_user_pages failure path sg's st_map_user_pages is modelled on an earlier version of st's sgl_map_user_pages, and has the same bug: if get_user_pages got some but not all of the pages, then those got were released, but the positive res code returned implied that they were still to be freed. Signed-off-by: Hugh Dickins Signed-off-by: Douglas Gilbert Signed-off-by: James Bottomley --- drivers/scsi/sg.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'drivers/scsi/sg.c') diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c index 6de7ff9faf2d..b55c2a8a547c 100644 --- a/drivers/scsi/sg.c +++ b/drivers/scsi/sg.c @@ -1860,9 +1860,11 @@ st_map_user_pages(struct scatterlist *sgl, const unsigned int max_pages, unlock_page(pages[j]); */ res = 0; out_unmap: - if (res > 0) + if (res > 0) { for (j=0; j < res; j++) page_cache_release(pages[j]); + res = 0; + } kfree(pages); return res; } -- cgit v1.2.3