aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/mm/pageattr.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/mm/pageattr.c')
-rw-r--r--arch/x86/mm/pageattr.c39
1 files changed, 27 insertions, 12 deletions
diff --git a/arch/x86/mm/pageattr.c b/arch/x86/mm/pageattr.c
index c106f7852424..dce282f65700 100644
--- a/arch/x86/mm/pageattr.c
+++ b/arch/x86/mm/pageattr.c
@@ -592,9 +592,12 @@ static int __change_page_attr(struct cpa_data *cpa, int primary)
592 unsigned int level; 592 unsigned int level;
593 pte_t *kpte, old_pte; 593 pte_t *kpte, old_pte;
594 594
595 if (cpa->flags & CPA_PAGES_ARRAY) 595 if (cpa->flags & CPA_PAGES_ARRAY) {
596 address = (unsigned long)page_address(cpa->pages[cpa->curpage]); 596 struct page *page = cpa->pages[cpa->curpage];
597 else if (cpa->flags & CPA_ARRAY) 597 if (unlikely(PageHighMem(page)))
598 return 0;
599 address = (unsigned long)page_address(page);
600 } else if (cpa->flags & CPA_ARRAY)
598 address = cpa->vaddr[cpa->curpage]; 601 address = cpa->vaddr[cpa->curpage];
599 else 602 else
600 address = *cpa->vaddr; 603 address = *cpa->vaddr;
@@ -698,9 +701,12 @@ static int cpa_process_alias(struct cpa_data *cpa)
698 * No need to redo, when the primary call touched the direct 701 * No need to redo, when the primary call touched the direct
699 * mapping already: 702 * mapping already:
700 */ 703 */
701 if (cpa->flags & CPA_PAGES_ARRAY) 704 if (cpa->flags & CPA_PAGES_ARRAY) {
702 vaddr = (unsigned long)page_address(cpa->pages[cpa->curpage]); 705 struct page *page = cpa->pages[cpa->curpage];
703 else if (cpa->flags & CPA_ARRAY) 706 if (unlikely(PageHighMem(page)))
707 return 0;
708 vaddr = (unsigned long)page_address(page);
709 } else if (cpa->flags & CPA_ARRAY)
704 vaddr = cpa->vaddr[cpa->curpage]; 710 vaddr = cpa->vaddr[cpa->curpage];
705 else 711 else
706 vaddr = *cpa->vaddr; 712 vaddr = *cpa->vaddr;
@@ -998,12 +1004,15 @@ EXPORT_SYMBOL(set_memory_array_uc);
998int _set_memory_wc(unsigned long addr, int numpages) 1004int _set_memory_wc(unsigned long addr, int numpages)
999{ 1005{
1000 int ret; 1006 int ret;
1007 unsigned long addr_copy = addr;
1008
1001 ret = change_page_attr_set(&addr, numpages, 1009 ret = change_page_attr_set(&addr, numpages,
1002 __pgprot(_PAGE_CACHE_UC_MINUS), 0); 1010 __pgprot(_PAGE_CACHE_UC_MINUS), 0);
1003
1004 if (!ret) { 1011 if (!ret) {
1005 ret = change_page_attr_set(&addr, numpages, 1012 ret = change_page_attr_set_clr(&addr_copy, numpages,
1006 __pgprot(_PAGE_CACHE_WC), 0); 1013 __pgprot(_PAGE_CACHE_WC),
1014 __pgprot(_PAGE_CACHE_MASK),
1015 0, 0, NULL);
1007 } 1016 }
1008 return ret; 1017 return ret;
1009} 1018}
@@ -1120,7 +1129,9 @@ int set_pages_array_uc(struct page **pages, int addrinarray)
1120 int free_idx; 1129 int free_idx;
1121 1130
1122 for (i = 0; i < addrinarray; i++) { 1131 for (i = 0; i < addrinarray; i++) {
1123 start = (unsigned long)page_address(pages[i]); 1132 if (PageHighMem(pages[i]))
1133 continue;
1134 start = page_to_pfn(pages[i]) << PAGE_SHIFT;
1124 end = start + PAGE_SIZE; 1135 end = start + PAGE_SIZE;
1125 if (reserve_memtype(start, end, _PAGE_CACHE_UC_MINUS, NULL)) 1136 if (reserve_memtype(start, end, _PAGE_CACHE_UC_MINUS, NULL))
1126 goto err_out; 1137 goto err_out;
@@ -1133,7 +1144,9 @@ int set_pages_array_uc(struct page **pages, int addrinarray)
1133err_out: 1144err_out:
1134 free_idx = i; 1145 free_idx = i;
1135 for (i = 0; i < free_idx; i++) { 1146 for (i = 0; i < free_idx; i++) {
1136 start = (unsigned long)page_address(pages[i]); 1147 if (PageHighMem(pages[i]))
1148 continue;
1149 start = page_to_pfn(pages[i]) << PAGE_SHIFT;
1137 end = start + PAGE_SIZE; 1150 end = start + PAGE_SIZE;
1138 free_memtype(start, end); 1151 free_memtype(start, end);
1139 } 1152 }
@@ -1162,7 +1175,9 @@ int set_pages_array_wb(struct page **pages, int addrinarray)
1162 return retval; 1175 return retval;
1163 1176
1164 for (i = 0; i < addrinarray; i++) { 1177 for (i = 0; i < addrinarray; i++) {
1165 start = (unsigned long)page_address(pages[i]); 1178 if (PageHighMem(pages[i]))
1179 continue;
1180 start = page_to_pfn(pages[i]) << PAGE_SHIFT;
1166 end = start + PAGE_SIZE; 1181 end = start + PAGE_SIZE;
1167 free_memtype(start, end); 1182 free_memtype(start, end);
1168 } 1183 }