]> xenbits.xensource.com Git - people/liuw/xen.git/commitdiff
x86/pv: properly map and unmap page tables in mark_pv_pt_pages_rdonly
authorWei Liu <wei.liu2@citrix.com>
Tue, 5 Feb 2019 16:32:54 +0000 (16:32 +0000)
committerWei Liu <wei.liu2@citrix.com>
Tue, 5 Feb 2019 17:30:04 +0000 (17:30 +0000)
Signed-off-by: Wei Liu <wei.liu2@citrix.com>
xen/arch/x86/pv/dom0_build.c

index 837ef7bca1e0c8973acc264f55c1a000afcce558..b6d6498bcbf7182ce0774c5841deee8207d4c9f4 100644 (file)
@@ -50,17 +50,17 @@ static __init void mark_pv_pt_pages_rdonly(struct domain *d,
     unsigned long count;
     struct page_info *page;
     l4_pgentry_t *pl4e;
-    l3_pgentry_t *pl3e;
-    l2_pgentry_t *pl2e;
-    l1_pgentry_t *pl1e;
+    l3_pgentry_t *pl3e, *l3t;
+    l2_pgentry_t *pl2e, *l2t;
+    l1_pgentry_t *pl1e, *l1t;
 
     pl4e = l4start + l4_table_offset(vpt_start);
-    pl3e = l4e_to_l3e(*pl4e);
-    pl3e += l3_table_offset(vpt_start);
-    pl2e = l3e_to_l2e(*pl3e);
-    pl2e += l2_table_offset(vpt_start);
-    pl1e = l2e_to_l1e(*pl2e);
-    pl1e += l1_table_offset(vpt_start);
+    l3t = map_xen_pagetable_new(l4e_get_mfn(*pl4e));
+    pl3e = l3t + l3_table_offset(vpt_start);
+    l2t = map_xen_pagetable_new(l3e_get_mfn(*pl3e));
+    pl2e = l2t + l2_table_offset(vpt_start);
+    l1t = map_xen_pagetable_new(l2e_get_mfn(*pl2e));
+    pl1e = l1t + l1_table_offset(vpt_start);
     for ( count = 0; count < nr_pt_pages; count++ )
     {
         l1e_remove_flags(*pl1e, _PAGE_RW);
@@ -85,12 +85,23 @@ static __init void mark_pv_pt_pages_rdonly(struct domain *d,
             if ( !((unsigned long)++pl2e & (PAGE_SIZE - 1)) )
             {
                 if ( !((unsigned long)++pl3e & (PAGE_SIZE - 1)) )
-                    pl3e = l4e_to_l3e(*++pl4e);
-                pl2e = l3e_to_l2e(*pl3e);
+                {
+                    unmap_xen_pagetable_new(l3t);
+                    l3t = map_xen_pagetable_new(l4e_get_mfn(*++pl4e));
+                    pl3e = l3t;
+                }
+                unmap_xen_pagetable_new(l2t);
+                l2t = map_xen_pagetable_new(l3e_get_mfn(*pl3e));
+                pl2e = l2t;
             }
-            pl1e = l2e_to_l1e(*pl2e);
+            unmap_xen_pagetable_new(l1t);
+            l1t = map_xen_pagetable_new(l2e_get_mfn(*pl2e));
+            pl1e = l1t;
         }
     }
+    unmap_xen_pagetable_new(l1t);
+    unmap_xen_pagetable_new(l2t);
+    unmap_xen_pagetable_new(l3t);
 }
 
 static __init void setup_pv_physmap(struct domain *d, unsigned long pgtbl_pfn,