From patchwork Mon Aug 9 17:56:12 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tianyu Lan X-Patchwork-Id: 12427061 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.8 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 52C4AC43216 for ; Mon, 9 Aug 2021 17:57:01 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 3604D6113B for ; Mon, 9 Aug 2021 17:57:01 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S235885AbhHIR5T (ORCPT ); Mon, 9 Aug 2021 13:57:19 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36640 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S235317AbhHIR5F (ORCPT ); Mon, 9 Aug 2021 13:57:05 -0400 Received: from mail-pj1-x1033.google.com (mail-pj1-x1033.google.com [IPv6:2607:f8b0:4864:20::1033]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 4FE9FC06179F; Mon, 9 Aug 2021 10:56:44 -0700 (PDT) Received: by mail-pj1-x1033.google.com with SMTP id a8so29209264pjk.4; Mon, 09 Aug 2021 10:56:44 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=+b7Gns6iR6iBk57ZYV5BIIcLDAAVsJ8v7NH3zL5Mg1I=; b=aU1nKcQ+nDmPFPy36XWpKTjwCuvMuOeOtKNuk1xPVGyxoxuMnaSYJneUW5xBdbS4mF EZRJlDW66/oI7E2Wx1IyV4mhOHU6VQLaysOdIZbmSWHfd5VhmRrwCUwrJRyfkyOnvk8c DABDw5o5QtCXWs7FVD6Yq7Noy7Bsts5MhfH7PiPCCCJ7RsIqAKrZykyMiDF/7fbZuHNb 1vMOIuVj+np2mkftpmkIY+gc57uZn61TrGeij/c4Wr9ZmZ2meUgtSPOJJW3jk0oHauD7 kGA8EGt3TprQFQB2ozu34RJbI1rKaUnojprdLwAyt6vGvk8hoDFLsG1rF5/di6hAastF RUxA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=+b7Gns6iR6iBk57ZYV5BIIcLDAAVsJ8v7NH3zL5Mg1I=; b=AKfa5Mo1VSiG6N+6940GSN2nwB2ZLluhQygGcMoPM7oahrrZo/u+r9dNNgzol0pY1i +oKLXVdzu73gPN10ITwIDaBzz9IbGgmV++xKdj79H6MpB8f6gJave/4HO8PyC16WVQkc IDzcbI2JpHmir8kAalHke1CmT3PesdLxGiqsC/SJF0sA/z9VOUUjeBtum1WO3FKMBwCD W95RS0IsSv8+/WrRl0Ny1vNXz2PFhFVtbPAkqHAcnfKBYXeduvFRtD+NbKZ5TJUdOtrL 3J27PmDUNcF5b0SHuupn54wr6V6H1l+TEAVwEPhpZcMkSmiftl0BNmoQv+focuYRtv6H L0rw== X-Gm-Message-State: AOAM532f74jGOLEnoyJamnhpO6lmgFoXLxtrzQVo5nkBERSFN4wQPYvf LYzpTTGXNIIxwVnr6sZ4b7E= X-Google-Smtp-Source: ABdhPJyE8zgrTkf5TWCMZX5Y6wi/PvPkIAsiw37aMcRj/e7Da+SgSl/RYbFUmBp26CFz8LzJX3R2bw== X-Received: by 2002:a63:ff4d:: with SMTP id s13mr397127pgk.237.1628531803843; Mon, 09 Aug 2021 10:56:43 -0700 (PDT) Received: from ubuntu-Virtual-Machine.corp.microsoft.com ([2001:4898:80e8:2:106e:6ed1:5da1:2ac4]) by smtp.gmail.com with ESMTPSA id x14sm20589708pfa.127.2021.08.09.10.56.43 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 09 Aug 2021 10:56:43 -0700 (PDT) From: Tianyu Lan To: kys@microsoft.com, haiyangz@microsoft.com, sthemmin@microsoft.com, wei.liu@kernel.org, decui@microsoft.com, tglx@linutronix.de, mingo@redhat.com, bp@alien8.de, x86@kernel.org, hpa@zytor.com, dave.hansen@linux.intel.com, luto@kernel.org, peterz@infradead.org, konrad.wilk@oracle.com, boris.ostrovsky@oracle.com, jgross@suse.com, sstabellini@kernel.org, joro@8bytes.org, will@kernel.org, davem@davemloft.net, kuba@kernel.org, jejb@linux.ibm.com, martin.petersen@oracle.com, arnd@arndb.de, hch@lst.de, m.szyprowski@samsung.com, robin.murphy@arm.com, thomas.lendacky@amd.com, brijesh.singh@amd.com, ardb@kernel.org, Tianyu.Lan@microsoft.com, pgonda@google.com, martin.b.radev@gmail.com, akpm@linux-foundation.org, kirill.shutemov@linux.intel.com, rppt@kernel.org, sfr@canb.auug.org.au, saravanand@fb.com, krish.sadhukhan@oracle.com, aneesh.kumar@linux.ibm.com, xen-devel@lists.xenproject.org, rientjes@google.com, hannes@cmpxchg.org, tj@kernel.org, michael.h.kelley@microsoft.com Cc: iommu@lists.linux-foundation.org, linux-arch@vger.kernel.org, linux-hyperv@vger.kernel.org, linux-kernel@vger.kernel.org, linux-scsi@vger.kernel.org, netdev@vger.kernel.org, vkuznets@redhat.com, parri.andrea@gmail.com, dave.hansen@intel.com Subject: [PATCH V3 08/13] HV/Vmbus: Initialize VMbus ring buffer for Isolation VM Date: Mon, 9 Aug 2021 13:56:12 -0400 Message-Id: <20210809175620.720923-9-ltykernel@gmail.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20210809175620.720923-1-ltykernel@gmail.com> References: <20210809175620.720923-1-ltykernel@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-scsi@vger.kernel.org From: Tianyu Lan VMbus ring buffer are shared with host and it's need to be accessed via extra address space of Isolation VM with SNP support. This patch is to map the ring buffer address in extra address space via ioremap(). HV host visibility hvcall smears data in the ring buffer and so reset the ring buffer memory to zero after calling visibility hvcall. Signed-off-by: Tianyu Lan --- drivers/hv/Kconfig | 1 + drivers/hv/channel.c | 10 +++++ drivers/hv/hyperv_vmbus.h | 2 + drivers/hv/ring_buffer.c | 84 ++++++++++++++++++++++++++++++--------- 4 files changed, 79 insertions(+), 18 deletions(-) diff --git a/drivers/hv/Kconfig b/drivers/hv/Kconfig index d1123ceb38f3..dd12af20e467 100644 --- a/drivers/hv/Kconfig +++ b/drivers/hv/Kconfig @@ -8,6 +8,7 @@ config HYPERV || (ARM64 && !CPU_BIG_ENDIAN)) select PARAVIRT select X86_HV_CALLBACK_VECTOR if X86 + select VMAP_PFN help Select this option to run Linux as a Hyper-V client operating system. diff --git a/drivers/hv/channel.c b/drivers/hv/channel.c index 4c4717c26240..60ef881a700c 100644 --- a/drivers/hv/channel.c +++ b/drivers/hv/channel.c @@ -712,6 +712,16 @@ static int __vmbus_open(struct vmbus_channel *newchannel, if (err) goto error_clean_ring; + err = hv_ringbuffer_post_init(&newchannel->outbound, + page, send_pages); + if (err) + goto error_free_gpadl; + + err = hv_ringbuffer_post_init(&newchannel->inbound, + &page[send_pages], recv_pages); + if (err) + goto error_free_gpadl; + /* Create and init the channel open message */ open_info = kzalloc(sizeof(*open_info) + sizeof(struct vmbus_channel_open_channel), diff --git a/drivers/hv/hyperv_vmbus.h b/drivers/hv/hyperv_vmbus.h index 40bc0eff6665..15cd23a561f3 100644 --- a/drivers/hv/hyperv_vmbus.h +++ b/drivers/hv/hyperv_vmbus.h @@ -172,6 +172,8 @@ extern int hv_synic_cleanup(unsigned int cpu); /* Interface */ void hv_ringbuffer_pre_init(struct vmbus_channel *channel); +int hv_ringbuffer_post_init(struct hv_ring_buffer_info *ring_info, + struct page *pages, u32 page_cnt); int hv_ringbuffer_init(struct hv_ring_buffer_info *ring_info, struct page *pages, u32 pagecnt, u32 max_pkt_size); diff --git a/drivers/hv/ring_buffer.c b/drivers/hv/ring_buffer.c index 2aee356840a2..d4f93fca1108 100644 --- a/drivers/hv/ring_buffer.c +++ b/drivers/hv/ring_buffer.c @@ -17,6 +17,8 @@ #include #include #include +#include +#include #include "hyperv_vmbus.h" @@ -179,43 +181,89 @@ void hv_ringbuffer_pre_init(struct vmbus_channel *channel) mutex_init(&channel->outbound.ring_buffer_mutex); } -/* Initialize the ring buffer. */ -int hv_ringbuffer_init(struct hv_ring_buffer_info *ring_info, - struct page *pages, u32 page_cnt, u32 max_pkt_size) +int hv_ringbuffer_post_init(struct hv_ring_buffer_info *ring_info, + struct page *pages, u32 page_cnt) { + u64 physic_addr = page_to_pfn(pages) << PAGE_SHIFT; + unsigned long *pfns_wraparound; + void *vaddr; int i; - struct page **pages_wraparound; - BUILD_BUG_ON((sizeof(struct hv_ring_buffer) != PAGE_SIZE)); + if (!hv_isolation_type_snp()) + return 0; + + physic_addr += ms_hyperv.shared_gpa_boundary; /* * First page holds struct hv_ring_buffer, do wraparound mapping for * the rest. */ - pages_wraparound = kcalloc(page_cnt * 2 - 1, sizeof(struct page *), + pfns_wraparound = kcalloc(page_cnt * 2 - 1, sizeof(unsigned long), GFP_KERNEL); - if (!pages_wraparound) + if (!pfns_wraparound) return -ENOMEM; - pages_wraparound[0] = pages; + pfns_wraparound[0] = physic_addr >> PAGE_SHIFT; for (i = 0; i < 2 * (page_cnt - 1); i++) - pages_wraparound[i + 1] = &pages[i % (page_cnt - 1) + 1]; - - ring_info->ring_buffer = (struct hv_ring_buffer *) - vmap(pages_wraparound, page_cnt * 2 - 1, VM_MAP, PAGE_KERNEL); - - kfree(pages_wraparound); + pfns_wraparound[i + 1] = (physic_addr >> PAGE_SHIFT) + + i % (page_cnt - 1) + 1; - - if (!ring_info->ring_buffer) + vaddr = vmap_pfn(pfns_wraparound, page_cnt * 2 - 1, PAGE_KERNEL_IO); + kfree(pfns_wraparound); + if (!vaddr) return -ENOMEM; - ring_info->ring_buffer->read_index = - ring_info->ring_buffer->write_index = 0; + /* Clean memory after setting host visibility. */ + memset((void *)vaddr, 0x00, page_cnt * PAGE_SIZE); + + ring_info->ring_buffer = (struct hv_ring_buffer *)vaddr; + ring_info->ring_buffer->read_index = 0; + ring_info->ring_buffer->write_index = 0; /* Set the feature bit for enabling flow control. */ ring_info->ring_buffer->feature_bits.value = 1; + return 0; +} + +/* Initialize the ring buffer. */ +int hv_ringbuffer_init(struct hv_ring_buffer_info *ring_info, + struct page *pages, u32 page_cnt, u32 max_pkt_size) +{ + int i; + struct page **pages_wraparound; + + BUILD_BUG_ON((sizeof(struct hv_ring_buffer) != PAGE_SIZE)); + + if (!hv_isolation_type_snp()) { + /* + * First page holds struct hv_ring_buffer, do wraparound mapping for + * the rest. + */ + pages_wraparound = kcalloc(page_cnt * 2 - 1, sizeof(struct page *), + GFP_KERNEL); + if (!pages_wraparound) + return -ENOMEM; + + pages_wraparound[0] = pages; + for (i = 0; i < 2 * (page_cnt - 1); i++) + pages_wraparound[i + 1] = &pages[i % (page_cnt - 1) + 1]; + + ring_info->ring_buffer = (struct hv_ring_buffer *) + vmap(pages_wraparound, page_cnt * 2 - 1, VM_MAP, PAGE_KERNEL); + + kfree(pages_wraparound); + + if (!ring_info->ring_buffer) + return -ENOMEM; + + ring_info->ring_buffer->read_index = + ring_info->ring_buffer->write_index = 0; + + /* Set the feature bit for enabling flow control. */ + ring_info->ring_buffer->feature_bits.value = 1; + } + ring_info->ring_size = page_cnt << PAGE_SHIFT; ring_info->ring_size_div10_reciprocal = reciprocal_value(ring_info->ring_size / 10);