Received: by 2002:a05:6a10:9848:0:0:0:0 with SMTP id x8csp115076pxf; Wed, 10 Mar 2021 01:45:38 -0800 (PST) X-Google-Smtp-Source: ABdhPJzHTtCr8IurLdQ1CmyangQEwYdByON6lx1M80w6bciD1dpZgzeiRZgXyWJ8ENy7qW5GbgSD X-Received: by 2002:aa7:d445:: with SMTP id q5mr2237288edr.382.1615369538220; Wed, 10 Mar 2021 01:45:38 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1615369538; cv=none; d=google.com; s=arc-20160816; b=AEkZFtwIhEM4qjpfqSWoEihwvg+ScSR5QyDOyPfLEyG1e5g6SlE4Y3WKFLCa5BL2oL M7QiP62YBgeejwJyvju9fsoks0qG7CWisZturSIczdXmkWpx1OMRloiV6W8NdsWdkevb poGF5/+/BnQD0NscqeUFnffnTV2ZxKgMZZXj/PF2fGtz/+eAJ5bjMTJY9mbz8PZvRtsn 5vlZL/qBEImEAV3fTCtDy6DXItD9Ey3ebMUehhcSpcjUdF8a0PUk8YjwB5zurCYvFDpX bqs0shamlwRwaVVCtnBmAg/XMnwi37lNYT8Xg7rOo9zwEAwMYMm1PtQc9OdZJqiR1KSm +JcQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:mime-version:references:in-reply-to:message-id :date:subject:cc:to:from; bh=gbILdnpIXvLhUl08/hPcQgOwNyVrANa6wkhhIWbcNk0=; b=n+mf6QKamWC70m15VqhXtHxfTI0F7jcK2YxRWYDATdc1jc8g333GDamYejFRwVyW0K q4KwW1iQaUgs/aysXLC1IqMA2A5Dj9ieE8kluKw0H70nCGYhRZaHwzYavCJ9/9sCy7OB VMYgSPNVAi/VJvIimVBKp1AgW+lFjHGs6Wwls35v19TwNxiVDeRYIDNFVxgQxREHzGCC AWOx1u+tWnx1uEWXSeu+l5k/5xDOVb1tEPuU9HkfSMg3jjN8OvqRz8haSsXt7avrs8BM CjCcAxO92jmSUOnjvthf4WgAuSJJ/Imo917zz7CnzhuQHuoM9TYhTQ7Dy1YYsGrp1cuG LgFg== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id q11si1480042edn.333.2021.03.10.01.45.15; Wed, 10 Mar 2021 01:45:38 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) client-ip=23.128.96.18; Authentication-Results: mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232444AbhCJJoL (ORCPT + 99 others); Wed, 10 Mar 2021 04:44:11 -0500 Received: from szxga06-in.huawei.com ([45.249.212.32]:13901 "EHLO szxga06-in.huawei.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232244AbhCJJnh (ORCPT ); Wed, 10 Mar 2021 04:43:37 -0500 Received: from DGGEMS412-HUB.china.huawei.com (unknown [172.30.72.59]) by szxga06-in.huawei.com (SkyGuard) with ESMTP id 4DwRtg0c5szkX1y; Wed, 10 Mar 2021 17:42:03 +0800 (CST) Received: from DESKTOP-TMVL5KK.china.huawei.com (10.174.187.128) by DGGEMS412-HUB.china.huawei.com (10.3.19.212) with Microsoft SMTP Server id 14.3.498.0; Wed, 10 Mar 2021 17:43:23 +0800 From: Yanan Wang To: Marc Zyngier , Will Deacon , "Catalin Marinas" , James Morse , "Julien Thierry" , Suzuki K Poulose , Gavin Shan , Quentin Perret , , , , CC: , , , Yanan Wang Subject: [RFC PATCH v2 2/3] KVM: arm64: Install the block entry before unmapping the page mappings Date: Wed, 10 Mar 2021 17:43:18 +0800 Message-ID: <20210310094319.18760-3-wangyanan55@huawei.com> X-Mailer: git-send-email 2.8.4.windows.1 In-Reply-To: <20210310094319.18760-1-wangyanan55@huawei.com> References: <20210310094319.18760-1-wangyanan55@huawei.com> MIME-Version: 1.0 Content-Type: text/plain X-Originating-IP: [10.174.187.128] X-CFilter-Loop: Reflected Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org When KVM needs to coalesce the existing normal page mappings into a block mapping, we currently follow the following steps successively: 1) invalidate the table entry in the PMD/PUD table 2) flush TLB by VMID 3) unmap the old sub-level tables 4) install the new block entry to the PMD/PUD table It will cost a long time to unmap the old page mappings in step 3, which means there will be a long period when the PMD/PUD table entry could be found invalid (step 1, 2, 3). So the other vcpus have a really big chance to trigger unnecessary translations if they access any page within the block and find the table entry invalid. So let's quickly install the block entry at first to ensure uninterrupted memory access of the other vcpus, and then unmap the page mappings after installation. This will reduce most of the time when the table entry is invalid, and avoid most of the unnecessary translation faults. After this patch the steps can be like: 1) invalidate the table entry in the PMD/PUD table 2) flush TLB by VMID 3) install the new block entry to the PMD/PUD table 4) unmap the old sub-level tables Signed-off-by: Yanan Wang --- arch/arm64/kvm/hyp/pgtable.c | 44 ++++++++++++++++++++++++------------ 1 file changed, 30 insertions(+), 14 deletions(-) diff --git a/arch/arm64/kvm/hyp/pgtable.c b/arch/arm64/kvm/hyp/pgtable.c index 829a34eea526..b40b1f1615c7 100644 --- a/arch/arm64/kvm/hyp/pgtable.c +++ b/arch/arm64/kvm/hyp/pgtable.c @@ -434,6 +434,7 @@ struct stage2_map_data { kvm_pte_t attr; kvm_pte_t *anchor; + kvm_pte_t *follow; struct kvm_s2_mmu *mmu; struct kvm_mmu_memory_cache *memcache; @@ -545,6 +546,24 @@ static int stage2_map_walker_try_leaf(u64 addr, u64 end, u32 level, return 0; } +static void stage2_coalesce_tables_into_block(u64 addr, u32 level, + kvm_pte_t *ptep, + struct stage2_map_data *data) +{ + u64 granule = kvm_granule_size(level), phys = data->phys; + kvm_pte_t new = kvm_init_valid_leaf_pte(phys, data->attr, level); + + kvm_set_invalid_pte(ptep); + + /* + * Invalidate the whole stage-2, as we may have numerous leaf entries + * below us which would otherwise need invalidating individually. + */ + kvm_call_hyp(__kvm_tlb_flush_vmid, data->mmu); + smp_store_release(ptep, new); + data->phys += granule; +} + static int stage2_map_walk_table_pre(u64 addr, u64 end, u32 level, kvm_pte_t *ptep, struct stage2_map_data *data) @@ -555,15 +574,14 @@ static int stage2_map_walk_table_pre(u64 addr, u64 end, u32 level, if (!kvm_block_mapping_supported(addr, end, data->phys, level)) return 0; - kvm_set_invalid_pte(ptep); - /* - * Invalidate the whole stage-2, as we may have numerous leaf - * entries below us which would otherwise need invalidating - * individually. + * If we need to coalesce existing table entries into a block here, + * then install the block entry first and the sub-level page mappings + * will be unmapped later. */ - kvm_call_hyp(__kvm_tlb_flush_vmid, data->mmu); data->anchor = ptep; + data->follow = kvm_pte_follow(*ptep); + stage2_coalesce_tables_into_block(addr, level, ptep, data); return 0; } @@ -616,20 +634,18 @@ static int stage2_map_walk_table_post(u64 addr, u64 end, u32 level, kvm_pte_t *ptep, struct stage2_map_data *data) { - int ret = 0; - if (!data->anchor) return 0; - free_page((unsigned long)kvm_pte_follow(*ptep)); - put_page(virt_to_page(ptep)); - - if (data->anchor == ptep) { + if (data->anchor != ptep) { + free_page((unsigned long)kvm_pte_follow(*ptep)); + put_page(virt_to_page(ptep)); + } else { + free_page((unsigned long)data->follow); data->anchor = NULL; - ret = stage2_map_walk_leaf(addr, end, level, ptep, data); } - return ret; + return 0; } /* -- 2.19.1