arch/arm: add consistency check to REMOVE p2m changes
authorArianna Avanzini <avanzini.arianna@gmail.com>
Sat, 30 Aug 2014 16:29:36 +0000 (18:29 +0200)
committerIan Campbell <ian.campbell@citrix.com>
Wed, 3 Sep 2014 11:49:37 +0000 (12:49 +0100)
Currently, the REMOVE case of the switch in apply_p2m_changes()
does not perform any consistency check on the mapping to be removed.
More in detail, the code does not check if the guest address to be
unmapped is actually mapped to the machine address given as a
parameter.
This commit adds the above-described consistency check to the REMOVE
path of apply_p2m_changes() and lets a warning be emitted when trying
to remove a non-existent mapping. This is instrumental to one of the
following commits, which implements the possibility to trigger the
removal of p2m ranges via the memory_mapping DOMCTL for ARM.

Signed-off-by: Arianna Avanzini <avanzini.arianna@gmail.com>
Acked-by: Stefano Stabellini <stefano.stabellini@eu.citrix.com>
Reviewed-by: Julien Grall <julien.grall@citrix.com>
Cc: Dario Faggioli <dario.faggioli@citrix.com>
Cc: Paolo Valente <paolo.valente@unimore.it>
Cc: Ian Campbell <Ian.Campbell@eu.citrix.com>
Cc: Jan Beulich <JBeulich@suse.com>
Cc: Keir Fraser <keir@xen.org>
Cc: Tim Deegan <tim@xen.org>
Cc: Ian Jackson <Ian.Jackson@eu.citrix.com>
Cc: Andrew Cooper <andrew.cooper3@citrix.com>
Cc: Eric Trudeau <etrudeau@broadcom.com>
Cc: Viktor Kleinik <viktor.kleinik@globallogic.com>
Cc: Andrii Tseglytskyi <andrii.tseglytskyi@globallogic.com>
Acked-by: Ian Campbell <ian.campbell@citrix.com>
xen/arch/arm/p2m.c

index 143199bdf50f708512faaca564fbd7d3c5eba239..8f83d17df23f79a14664c24f4a5c2d48a3ea0f8a 100644 (file)
@@ -601,6 +601,7 @@ static int apply_one_level(struct domain *d,
         {
             /* Progress up to next boundary */
             *addr = (*addr + level_size) & level_mask;
+            *maddr = (*maddr + level_size) & level_mask;
             return P2M_ONE_PROGRESS_NOP;
         }
 
@@ -632,12 +633,29 @@ static int apply_one_level(struct domain *d,
             }
         }
 
+        /*
+         * Ensure that the guest address addr currently being
+         * handled (that is in the range given as argument to
+         * this function) is actually mapped to the corresponding
+         * machine address in the specified range. maddr here is
+         * the machine address given to the function, while
+         * orig_pte.p2m.base is the machine frame number actually
+         * mapped to the guest address: check if the two correspond.
+         */
+         if ( op == REMOVE &&
+              pfn_to_paddr(orig_pte.p2m.base) != *maddr )
+             printk(XENLOG_G_WARNING
+                    "p2m_remove dom%d: mapping at %"PRIpaddr" is of maddr %"PRIpaddr" not %"PRIpaddr" as expected\n",
+                    d->domain_id, *addr, pfn_to_paddr(orig_pte.p2m.base),
+                    *maddr);
+
         *flush = true;
 
         memset(&pte, 0x00, sizeof(pte));
         p2m_write_pte(entry, pte, flush_cache);
 
         *addr += level_size;
+        *maddr += level_size;
 
         p2m->stats.mappings[level]--;