Skip to content

Commit

Permalink
x86: Fix CPA memtype reserving in the set_pages_array*() cases
Browse files Browse the repository at this point in the history
The code was incorrectly reserving memtypes using the page
virtual address instead of the physical address. Furthermore,
the code was not ignoring highmem pages as it ought to.

( upstream does not pass in highmem pages yet - but upcoming
  graphics code will do it and there's no reason to not handle
  this properly in the CPA APIs.)

Fixes: http://bugzilla.kernel.org/show_bug.cgi?id=13884

Signed-off-by: Thomas Hellstrom <thellstrom@vmware.com>
Acked-by: Suresh Siddha <suresh.b.siddha@intel.com>
Cc: <stable@kernel.org>
Cc: dri-devel@lists.sourceforge.net
Cc: venkatesh.pallipadi@intel.com
LKML-Reference: <1249284345-7654-1-git-send-email-thellstrom@vmware.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
  • Loading branch information
Thomas Hellstrom authored and Ingo Molnar committed Aug 3, 2009
1 parent bdc6340 commit 8523acf
Showing 1 changed file with 21 additions and 9 deletions.
30 changes: 21 additions & 9 deletions arch/x86/mm/pageattr.c
Original file line number Diff line number Diff line change
Expand Up @@ -591,9 +591,12 @@ static int __change_page_attr(struct cpa_data *cpa, int primary)
unsigned int level;
pte_t *kpte, old_pte;

if (cpa->flags & CPA_PAGES_ARRAY)
address = (unsigned long)page_address(cpa->pages[cpa->curpage]);
else if (cpa->flags & CPA_ARRAY)
if (cpa->flags & CPA_PAGES_ARRAY) {
struct page *page = cpa->pages[cpa->curpage];
if (unlikely(PageHighMem(page)))
return 0;
address = (unsigned long)page_address(page);
} else if (cpa->flags & CPA_ARRAY)
address = cpa->vaddr[cpa->curpage];
else
address = *cpa->vaddr;
Expand Down Expand Up @@ -697,9 +700,12 @@ static int cpa_process_alias(struct cpa_data *cpa)
* No need to redo, when the primary call touched the direct
* mapping already:
*/
if (cpa->flags & CPA_PAGES_ARRAY)
vaddr = (unsigned long)page_address(cpa->pages[cpa->curpage]);
else if (cpa->flags & CPA_ARRAY)
if (cpa->flags & CPA_PAGES_ARRAY) {
struct page *page = cpa->pages[cpa->curpage];
if (unlikely(PageHighMem(page)))
return 0;
vaddr = (unsigned long)page_address(page);
} else if (cpa->flags & CPA_ARRAY)
vaddr = cpa->vaddr[cpa->curpage];
else
vaddr = *cpa->vaddr;
Expand Down Expand Up @@ -1122,7 +1128,9 @@ int set_pages_array_uc(struct page **pages, int addrinarray)
int free_idx;

for (i = 0; i < addrinarray; i++) {
start = (unsigned long)page_address(pages[i]);
if (PageHighMem(pages[i]))
continue;
start = page_to_pfn(pages[i]) << PAGE_SHIFT;
end = start + PAGE_SIZE;
if (reserve_memtype(start, end, _PAGE_CACHE_UC_MINUS, NULL))
goto err_out;
Expand All @@ -1135,7 +1143,9 @@ int set_pages_array_uc(struct page **pages, int addrinarray)
err_out:
free_idx = i;
for (i = 0; i < free_idx; i++) {
start = (unsigned long)page_address(pages[i]);
if (PageHighMem(pages[i]))
continue;
start = page_to_pfn(pages[i]) << PAGE_SHIFT;
end = start + PAGE_SIZE;
free_memtype(start, end);
}
Expand Down Expand Up @@ -1164,7 +1174,9 @@ int set_pages_array_wb(struct page **pages, int addrinarray)
return retval;

for (i = 0; i < addrinarray; i++) {
start = (unsigned long)page_address(pages[i]);
if (PageHighMem(pages[i]))
continue;
start = page_to_pfn(pages[i]) << PAGE_SHIFT;
end = start + PAGE_SIZE;
free_memtype(start, end);
}
Expand Down

0 comments on commit 8523acf

Please sign in to comment.