From patchwork Tue Nov 14 06:53:46 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Yu Zhang X-Patchwork-Id: 10057081 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id C3577601D3 for ; Tue, 14 Nov 2017 07:21:34 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8979128F80 for ; Tue, 14 Nov 2017 07:21:34 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 7E0DE28FD5; Tue, 14 Nov 2017 07:21:34 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-4.2 required=2.0 tests=BAYES_00, RCVD_IN_DNSWL_MED autolearn=ham version=3.3.1 Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) (using TLSv1.2 with cipher AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id F07E028F80 for ; Tue, 14 Nov 2017 07:21:33 +0000 (UTC) Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1eEVUr-0008U0-FU; Tue, 14 Nov 2017 07:19:01 +0000 Received: from mail6.bemta5.messagelabs.com ([195.245.231.135]) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1eEVUq-0008Tj-3E for xen-devel@lists.xen.org; Tue, 14 Nov 2017 07:19:00 +0000 Received: from [85.158.139.211] by server-15.bemta-5.messagelabs.com id D6/98-31004-3E89A0A5; Tue, 14 Nov 2017 07:18:59 +0000 X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFnrBLMWRWlGSWpSXmKPExsXS1taRovtoBle UwbSNehZLPi5mcWD0OLr7N1MAYxRrZl5SfkUCa8a2HUfZC5YrV9zbe5GlgfGdeBcjF4eQwHRG idszprN0MXJySAjwShxZNoMVwvaX6HvwixWiqJ1R4vS8tWwgCTYBbYkfq38zgtgiAtIS1z5fZ gQpYhaYwCixcOlKsCJhgViJ75MeMYPYLAKqEtsOvgGKc3DwCnhK7GgShFggJ3Hy2GTWCYzcCx gZVjGqF6cWlaUW6ZrrJRVlpmeU5CZm5ugaGpjq5aYWFyemp+YkJhXrJefnbmIE+pcBCHYwHpv sfIhRkoNJSZRX5TN7lBBfUn5KZUZicUZ8UWlOavEhRhkODiUJ3tbpXFFCgkWp6akVaZk5wECD SUtw8CiJ8FqApHmLCxJzizPTIVKnGI05ns183cDMMe1qaxOzEEtefl6qlDhvGkipAEhpRmke3 CBYBFxilJUS5mUEOk2IpyC1KDezBFX+FaM4B6OSMO9FkCk8mXklcPteAZ3CBHSKFMgXvMUliQ gpqQZGOzfB0EkNLwODFwhICShmrjqcXMRvMkFuSvSq0w+PbF29OKxNctNGo/Nr9/UzXXOc8zJ OYXlUze7afTs82TS4di1XXL7MvpLJ+vxJNauOKNNYX4Yvxc9/J3dns8UH6TDXMLr0MyY+D1r5 vGtlx+67d9pDPfL3XZNakCC34JKZYIHSZ2V+6wtKLMUZiYZazEXFiQCa6X50ewIAAA== X-Env-Sender: yu.c.zhang@linux.intel.com X-Msg-Ref: server-4.tower-206.messagelabs.com!1510643935!107031594!2 X-Originating-IP: [134.134.136.100] X-SpamReason: No, hits=0.0 required=7.0 tests= X-StarScan-Received: X-StarScan-Version: 9.4.45; banners=-,-,- X-VirusChecked: Checked Received: (qmail 30261 invoked from network); 14 Nov 2017 07:18:58 -0000 Received: from mga07.intel.com (HELO mga07.intel.com) (134.134.136.100) by server-4.tower-206.messagelabs.com with DHE-RSA-AES256-GCM-SHA384 encrypted SMTP; 14 Nov 2017 07:18:58 -0000 Received: from fmsmga005.fm.intel.com ([10.253.24.32]) by orsmga105.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 13 Nov 2017 23:18:54 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.44,393,1505804400"; d="scan'208";a="175523445" Received: from zhangyu-optiplex-9020.bj.intel.com ([10.238.135.159]) by fmsmga005.fm.intel.com with ESMTP; 13 Nov 2017 23:18:32 -0800 From: Yu Zhang To: xen-devel@lists.xen.org Date: Tue, 14 Nov 2017 14:53:46 +0800 Message-Id: <1510642427-3629-1-git-send-email-yu.c.zhang@linux.intel.com> X-Mailer: git-send-email 1.9.1 Cc: Andrew Cooper , julien.grall@arm.com, min.he@intel.com, Jan Beulich , yi.z.zhang@intel.com Subject: [Xen-devel] [PATCH v3 for-4.10 1/2] x86/mm: fix potential race conditions in map_pages_to_xen(). X-BeenThere: xen-devel@lists.xen.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: xen-devel-bounces@lists.xen.org Sender: "Xen-devel" X-Virus-Scanned: ClamAV using ClamSMTP From: Min He In map_pages_to_xen(), a L2 page table entry may be reset to point to a superpage, and its corresponding L1 page table need be freed in such scenario, when these L1 page table entries are mapping to consecutive page frames and having the same mapping flags. However, variable `pl1e` is not protected by the lock before L1 page table is enumerated. A race condition may happen if this code path is invoked simultaneously on different CPUs. For example, `pl1e` value on CPU0 may hold an obsolete value, pointing to a page which has just been freed on CPU1. Besides, before this page is reused, it will still be holding the old PTEs, referencing consecutive page frames. Consequently the `free_xen_pagetable(l2e_to_l1e(ol2e))` will be triggered on CPU0, resulting the unexpected free of a normal page. This patch fixes the above problem by protecting the `pl1e` with the lock. Also, there're other potential race conditions. For instance, the L2/L3 entry may be modified concurrently on different CPUs, by routines such as map_pages_to_xen(), modify_xen_mappings() etc. To fix this, this patch will check the _PAGE_PRESENT and _PAGE_PSE flags, after the spinlock is obtained, for the corresponding L2/L3 entry. Signed-off-by: Min He Signed-off-by: Yi Zhang Signed-off-by: Yu Zhang Reviewed-by: Jan Beulich --- Cc: Jan Beulich Cc: Andrew Cooper Changes in v3: According to comments from Jan Beulich: - use local variable instead of dereference pointer to pte to check flag. - also check the _PAGE_PRESENT for L2E/L3E. Others: - Commit message changes. Changes in v2: According to comments from Jan Beulich: - check PSE of pl2e and pl3e, and skip the re-consolidation if set. - commit message changes, e.g. add "From :" tag etc. - code style changes. - introduce a seperate patch to resolve the similar issue in modify_xen_mappings(). --- xen/arch/x86/mm.c | 36 ++++++++++++++++++++++++++++++++++-- 1 file changed, 34 insertions(+), 2 deletions(-) diff --git a/xen/arch/x86/mm.c b/xen/arch/x86/mm.c index a20fdca..1697be9 100644 --- a/xen/arch/x86/mm.c +++ b/xen/arch/x86/mm.c @@ -4844,9 +4844,29 @@ int map_pages_to_xen( { unsigned long base_mfn; - pl1e = l2e_to_l1e(*pl2e); if ( locking ) spin_lock(&map_pgdir_lock); + + ol2e = *pl2e; + /* + * L2E may be already cleared, or set to a superpage, by + * concurrent paging structure modifications on other CPUs. + */ + if ( !(l2e_get_flags(ol2e) & _PAGE_PRESENT) ) + { + if ( locking ) + spin_unlock(&map_pgdir_lock); + continue; + } + + if ( l2e_get_flags(ol2e) & _PAGE_PSE ) + { + if ( locking ) + spin_unlock(&map_pgdir_lock); + goto check_l3; + } + + pl1e = l2e_to_l1e(ol2e); base_mfn = l1e_get_pfn(*pl1e) & ~(L1_PAGETABLE_ENTRIES - 1); for ( i = 0; i < L1_PAGETABLE_ENTRIES; i++, pl1e++ ) if ( (l1e_get_pfn(*pl1e) != (base_mfn + i)) || @@ -4854,7 +4874,6 @@ int map_pages_to_xen( break; if ( i == L1_PAGETABLE_ENTRIES ) { - ol2e = *pl2e; l2e_write_atomic(pl2e, l2e_from_pfn(base_mfn, l1f_to_lNf(flags))); if ( locking ) @@ -4880,7 +4899,20 @@ int map_pages_to_xen( if ( locking ) spin_lock(&map_pgdir_lock); + ol3e = *pl3e; + /* + * L3E may be already cleared, or set to a superpage, by + * concurrent paging structure modifications on other CPUs. + */ + if ( !(l3e_get_flags(ol3e) & _PAGE_PRESENT) || + (l3e_get_flags(ol3e) & _PAGE_PSE) ) + { + if ( locking ) + spin_unlock(&map_pgdir_lock); + continue; + } + pl2e = l3e_to_l2e(ol3e); base_mfn = l2e_get_pfn(*pl2e) & ~(L2_PAGETABLE_ENTRIES * L1_PAGETABLE_ENTRIES - 1);