From mboxrd@z Thu Jan 1 00:00:00 1970 From: Olaf Hering Subject: Re: [PATCH 05/16] xenpaging: update machine_to_phys_mapping during page-in and page-out Date: Wed, 3 Nov 2010 19:32:19 +0100 Message-ID: <20101103183219.GA15803@aepfle.de> References: <20101102223010.603002116@aepfle.de> <20101102223012.460890479@aepfle.de> Mime-Version: 1.0 Content-Type: text/plain; charset=utf-8 Return-path: Content-Disposition: inline In-Reply-To: <20101102223012.460890479@aepfle.de> List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Sender: xen-devel-bounces@lists.xensource.com Errors-To: xen-devel-bounces@lists.xensource.com To: xen-devel@lists.xensource.com List-Id: xen-devel@lists.xenproject.org The machine_to_phys_mapping array needs updating during page-out. If a page is gone, a call to get_gpfn_from_mfn will still return the old gfn for an already paged-out page. This happens when the entire guest ram is paged-out before xen_vga_populate_vram() runs. Then XENMEM_populate_physmap is called with gfn 0xff000. A new page is allocated with alloc_domheap_pages. This new page does not have a gfn yet. However, in guest_physmap_add_entry() the passed mfn maps still to an old gfn. This old gfn is paged-out and has no mfn anymore. As a result, the ASSERT() triggers because p2m_is_ram() is true for p2m_ram_paging* types. If the machine_to_phys_mapping array is updated properly, both loops in guest_physmap_add_entry() turn into no-ops for the new page and the mfn/gfn mapping will be done at the end of the function. The same thing needs to happen dring a page-in. If XENMEM_add_to_physmap is used with XENMAPSPACE_gmfn, get_gpfn_from_mfn() will return an appearently valid gfn. As a result, guest_physmap_remove_page() is called. The ASSERT in p2m_remove_page triggers because the passed mfn does not match the old mfn for the passed gfn. Signed-off-by: Olaf Hering --- v2: call set_gpfn_from_mfn only if mfn is valid xen/arch/x86/mm/p2m.c | 3 +++ 1 file changed, 3 insertions(+) --- xen-unstable.hg-4.1.22353.orig/xen/arch/x86/mm/p2m.c +++ xen-unstable.hg-4.1.22353/xen/arch/x86/mm/p2m.c @@ -2742,6 +2742,7 @@ int p2m_mem_paging_evict(struct p2m_doma /* Remove mapping from p2m table */ p2m_lock(p2m); set_p2m_entry(p2m, gfn, _mfn(PAGING_MFN), 0, p2m_ram_paged); + set_gpfn_from_mfn(mfn_x(mfn), INVALID_M2P_ENTRY); p2m_unlock(p2m); /* Put the page back so it gets freed */ @@ -2820,6 +2821,8 @@ void p2m_mem_paging_resume(struct p2m_do mfn = gfn_to_mfn(p2m, rsp.gfn, &p2mt); p2m_lock(p2m); set_p2m_entry(p2m, rsp.gfn, mfn, 0, p2m_ram_rw); + if ( mfn_valid(mfn) ) + set_gpfn_from_mfn(mfn_x(mfn), rsp.gfn); p2m_unlock(p2m); /* Unpause domain */