From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from NAM03-CO1-obe.outbound.protection.outlook.com (mail-co1nam03on0076.outbound.protection.outlook.com [104.47.40.76]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-SHA384 (256/256 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id 0980E21E62BBE for ; Fri, 1 Sep 2017 04:21:47 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=amdcloud.onmicrosoft.com; s=selector1-amd-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version; bh=ubVfET7lFhfzEyhKst/snPd4ceW9zaXge4P0+2g6rGk=; b=RfgRtXOTiT653kWmIA7r3A8bIIHC0m/ivmYyNmpenaXGo19KbmG06jv1EL6FBLXCPT6TubWBmZ1RUqadML7uaYKLirzh+dLjRnsm492hS0hQQ1rP/LktKm/lZp8sMq4EigzaVph6/FG5FmM2e0V1oZUHTk0I8FdkzTbJSxXEr8s= Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=brijesh.singh@amd.com; Received: from brijesh-build-machine.amd.com (165.204.77.1) by BY2PR12MB0146.namprd12.prod.outlook.com (10.162.82.19) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P256) id 15.20.13.10; Fri, 1 Sep 2017 11:24:29 +0000 From: Brijesh Singh To: edk2-devel@lists.01.org Cc: Brijesh Singh , Ard Biesheuvel , Jordan Justen , Tom Lendacky , Laszlo Ersek Date: Fri, 1 Sep 2017 07:24:04 -0400 Message-Id: <1504265045-19008-5-git-send-email-brijesh.singh@amd.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1504265045-19008-1-git-send-email-brijesh.singh@amd.com> References: <1504265045-19008-1-git-send-email-brijesh.singh@amd.com> MIME-Version: 1.0 X-Originating-IP: [165.204.77.1] X-ClientProxiedBy: BN6PR03CA0012.namprd03.prod.outlook.com (10.168.230.150) To BY2PR12MB0146.namprd12.prod.outlook.com (10.162.82.19) X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: ab6c561d-af9d-4b10-4394-08d4f12c0370 X-MS-Office365-Filtering-HT: Tenant X-Microsoft-Antispam: UriScan:; BCL:0; PCL:0; RULEID:(300000500095)(300135000095)(300000501095)(300135300095)(22001)(300000502095)(300135100095)(2017030254152)(48565401081)(300000503095)(300135400095)(2017052603199)(201703131423075)(201703031133081)(201702281549075)(300000504095)(300135200095)(300000505095)(300135600095)(300000506095)(300135500095); SRVR:BY2PR12MB0146; X-Microsoft-Exchange-Diagnostics: 1; BY2PR12MB0146; 3:Y/yCSXUymMMJEKXoDGGIVPIRpSqT/53yhlnSF7Ip5xgkm8dlyeeLVEtcq5H3Lw4EwaEaP1CkZeXD1yxH1numlxq6eNE8hYMKXQh+tCWGd9fqgbBuVF0za2E/kXGwxeSaAEaiq+DIYk82lKUP7QxZwd8cb/uHqpQfah5s/0iwly/ALR86cz43b28aAIWHrxSVY6kfUDOK8D/qMCVFVntWDBJpiCp2hzVrWXuQbKXLgr4YondER8NtugKsfrQfoBku; 25:bf9CeKEtFPCKFfVCkwxu48jIwUceMIneDPPSNHO0MBdbc3cLa6fx52ohspGsR+z4126eArhMw5tTJcyrnZBjOJV6CL+ty+sHrrY8Pzix7YQBe6tc/SrwdV/siacRWeQofLro+wjIdCA5rXHobFSFbvwlWDEBFtWuOyty8VrK5JpmJv5Ne4kmyhsFajRwq0q6y8NoLaCVqwv2ppuSK4s0XsjWcPs2EhiYzyamEGneSCI8h1KSQt+X9gIty8cv9raLW55U0Td7eCVOz5JBmngdKEfaN6nLL57yb5hElq/3MA1RtGUNzGr/4woimcuwX3AlD/yu9WQOFp3/uQ2SjVwI7g==; 31:os5+V3uQEqVdJ8Bp879DoNlv7rcxRsZlPTLg9JNhroYZLPRh1qJy5DUXsfoo3GHIGKfzFc+9IRpZ/l8/4vQlKse4iND+GZnS6QteoKY1JudodWzE9Y0awOFhBdqcgYtd1GXChQPNDs3edvYETf1esAaMPcGLu7bgL3UYGudMuHc/C4Y1hXEJ6Iwj03FMLdqx/nLptSvVk/s0MpyczE4gDHlVjBEePjRiw9dac+PdPj0= X-MS-TrafficTypeDiagnostic: BY2PR12MB0146: X-Microsoft-Exchange-Diagnostics: 1; BY2PR12MB0146; 20:R0trl3qK9rdyQByfglo5mjwNSAB3nIse6M75aGdCWr+wVQjz0Mi8VzPIdT6j0iNtHmYuCEImCqWo24mW+FbOyaatT6INqDs2bRV5cdvRbnVF0lky6AthrSP8+9BHkxW1yiK+yOYJETATnnL21+HHPU9dnXbpUl8Wu4v6kPl0q0yx1TJqlrowxhj06CSkqh3IAPP3cIf4Hi34CPET18NejzwX/IWAjEgGNP+cB6XxmQ2CFO2yK85XQWx95a68iHoocxIAX6d4cYdzxvTACQ6WVncz1SS7UIbz0eY+ANM0IcJthdCAIFvtYnv9EVjRAAgKK8a9Q1nz34Tem3AsPSiVeAAVYkpVmfZK25hc7imPn/0XaFgRhY+Xo5574kF7HxYry7O0to+ew7xEo8eTUgU75/wh/tzJJvypugeXTsVtU8nsQeQcpNa0wa3oG+kDUCitKduWi23MbwEd8B7ImPlPI2P/UVvLPq7jRmRuC4XVcCi2LPBt36QChWT/MtjZykBM; 4:mWr4Qs2OAOvgFTI2F4UWsYVQsG3w83PwKhcjJO45SAO3ni8D6oCepZb99n789SDw8uyVbD06FU1in9VplsMTQHtJTjcDhsXq53mAmZjgyVtkgxDAQEHsPKNuHFN8A3T8M1qmL61dkshLO4B+/asTzOi+XHTEF2Rqc0VxDvlDTpWgWN6ned+J8fRW8GYfvTmsG2qJsxIeJLKTS0HkX9aCa0eQemdHtwamP6/WKdz0CLlVvmpPFJl/3BHT8JQPLCKd9Y3/RKgCLboqHDFkBEl2BYutr439MQfxXJoFRoyFagufmYhWpv1Ve1Ky8pzSQUkOq+o0Mo06ZxqI8TzlOv8u0o4vF1i+YqOTiYxmybSRLww= X-Exchange-Antispam-Report-Test: UriScan:(20558992708506)(767451399110)(228905959029699); X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-CFA-Test: BCL:0; PCL:0; RULEID:(100000700101)(100105000095)(100000701101)(100105300095)(100000702101)(100105100095)(6040450)(601004)(2401047)(8121501046)(5005006)(10201501046)(3002001)(93006095)(93001095)(100000703101)(100105400095)(6055026)(6041248)(20161123560025)(20161123562025)(20161123555025)(20161123564025)(201703131423075)(201702281528075)(201703061421075)(201703061406153)(20161123558100)(6072148)(201708071742011)(100000704101)(100105200095)(100000705101)(100105500095); SRVR:BY2PR12MB0146; BCL:0; PCL:0; RULEID:(100000800101)(100110000095)(100000801101)(100110300095)(100000802101)(100110100095)(100000803101)(100110400095)(100000804101)(100110200095)(100000805101)(100110500095); SRVR:BY2PR12MB0146; X-Forefront-PRVS: 0417A3FFD2 X-Forefront-Antispam-Report: SFV:NSPM; SFS:(10009020)(6009001)(39860400002)(199003)(189002)(50466002)(54906002)(6666003)(8936002)(66066001)(4326008)(50226002)(48376002)(47776003)(53936002)(478600001)(25786009)(110136004)(189998001)(76176999)(42186005)(53416004)(5003940100001)(2351001)(68736007)(106356001)(105586002)(3846002)(6116002)(2950100002)(6916009)(2361001)(305945005)(36756003)(50986999)(5660300001)(33646002)(2906002)(101416001)(7736002)(97736004)(81166006)(6486002)(8676002)(81156014)(575784001)(86362001); DIR:OUT; SFP:1101; SCL:1; SRVR:BY2PR12MB0146; H:brijesh-build-machine.amd.com; FPR:; SPF:None; PTR:InfoNoRecords; A:1; MX:1; LANG:en; Received-SPF: None (protection.outlook.com: amd.com does not designate permitted sender hosts) X-Microsoft-Exchange-Diagnostics: =?us-ascii?Q?1; BY2PR12MB0146; 23:adHX4Ttk14t2gQQRrgBn4rXFyA+444Dd3rIZ+c1fH?= =?us-ascii?Q?P5Z8b/lEw6/MbvoZ8exedL2BGjXYHs7V3kBa5k/9lGU82KaiSPSLjojzzVn6?= =?us-ascii?Q?nirpRlcAAtkah4ZBvKyflf6cDtOuiF1J2JK1YqR2TwilivmSRbUPBjHHSprg?= =?us-ascii?Q?oYgjd/yn8WseBzmCVTKYF4QmXKKCp90uo5omdvNX02NdfEmTS2w5d6Q1PAKj?= =?us-ascii?Q?gOYBJ7GssSUVOkwn36z+TwAQ4qqaRJS3WiK6MxWrYz4tNXuIWq+iJbmrHz2T?= =?us-ascii?Q?wl2+e8O/QJkTqhPPGdyDf0bKz5pyAzqu5aQ04aweGPzqY0efn3TtexuroC2h?= =?us-ascii?Q?JWn3rl0vjRlzqact58asolH5oP4/nV6L+mZFEpdVmWmuTU8a3vxDUH3g7OvS?= =?us-ascii?Q?o0vm5SZvg/2mxTJtiOk0lFDAplYv9rnDuJ4ziDebCvnSK9mMKktXIgKeST6X?= =?us-ascii?Q?z48ydt76Dqmc3FBEVsb7SNfNnn/Es4Qj7HFnvPT/rt5ZXws2oGEAMWbIlEFW?= =?us-ascii?Q?uXDTYDavsDDD3GoSaoVo+Rnhpxn3lqxPuTgy4ypXc/maOs3K8IZ3AmemUue9?= =?us-ascii?Q?hp6gtmEu5foN1a6RxiLWL7+c1LsuREQg4TIFreo0CVXB8Y4Ovwgk4K8ltn20?= =?us-ascii?Q?MRkFLD/YZWdXZtSeLA99YglkScHMQTqq1hxVMKIQns3N1cEgc/2euTIllS0t?= =?us-ascii?Q?XhlMb3FgAMZIdR/1dEp+EItGFAlrc7cjIVghSQ/twHwjDcNQMUzZj0VdSyu7?= =?us-ascii?Q?l468B8cQYGMlAUiml/WY8Nb56sC30nNV2v36tmkiHyZOLdwLCWn/KeToJUzo?= =?us-ascii?Q?QFlyIUriaSDQXEnweV0avoYB8XlGpM6KNSbzKPmOrlF8jQPM5C+uq/SBDbnj?= =?us-ascii?Q?0KAYaEdWYZI+LpAn/ogBq1Qb36WufWjIL1vh5F5lxMUvC+fSrhL6fFMt7uJa?= =?us-ascii?Q?Mov1K4HE6j7yXuIPogyMOF9WYJeffYRVq8vqYkiPsl96E5wOhcqG/DEzkw6u?= =?us-ascii?Q?La69nnzu4n16TPSqRNAQW/Gxr33rU0lcuf0r3UHPJbbu7aX9zNBLY1WVtv7w?= =?us-ascii?Q?OUUYqjPzC3xiI6nHBRG6BMh7RUCi3WuIxQijQDYYMf/RuFRoPFf+tKgcU3SO?= =?us-ascii?Q?sVEj+zaLSo=3D?= X-Microsoft-Exchange-Diagnostics: 1; BY2PR12MB0146; 6:p1AlskKqE2hsLpiSGrwR2jCg28+DAgI5XD8Omvhy99IhxV18GHREMTRA26jQItrRth6kc20YL20bihCIR1c1wpQh8xNLsgaj73RLjoxGaOU+l6eR0//13cpFzVHxHpMnhrYzsuTkOdJ7vx9Gx95e5K0uBYU1rnQDZNChoPBa9f7q/o1OByzK2T2PT1z/Vpeab71Q1T7m7sBB7Y3/LEjANWSIAj0k9HHDBGRdJYzUQ44BUrbaKfZZMec21dw0HYSWqHZfmLZxBNHvOF62QJGq/U+WBbKN06Ajna0wYpUML448UEHpO4YveqPOJoBVJJpvpoq+ipodwfuenZip2G6BPA==; 5:VzG9BCsMBAa7z3yQtRd121cgzwgcyek/rCIF+OH1rGnKzPqUzRKaifepzT9A0PGP/aCMW1lhv/8V4hFU0DlFXVXO2cQjG9owb9Um7pqgfHSUeYEMEYNKjCqabEt/elAA3TXK79+RQrw9qhShRfK3dw==; 24:Ds93nu+69fC6rWG9Gee4FvJ3OCeK1YMjnUWqwia3irgHiHzOLER2w4+fDd8qjOKjonhE4SocEqabxx59I9T8SNfQLHgyJU4GxsvKCvmTxf4=; 7:59js3gJP6yqeFqp3pL2FYP6lP3XRX1rNUvJdxd3PuWNVZeNpJszHbp0vNglfI6YWw05EEeafGFuS1QJENsh5nf9EMYPc2iUGcUxAekCFkBrMwK/cQPIq/jr5pw+fQCCODl7yc/sEJpojcHqHfg5wF5PEFHzIQ5I38pHAjDyWyWBi7uTBkBa++oL9s4qVZeisOXvvW1V/TZlnzMDI1XS6vLIhs1y6CYvH3tJ4/lWDcf8= SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-Microsoft-Exchange-Diagnostics: 1; BY2PR12MB0146; 20:7NUsR4bHvEZ17XmCAQa439Z0gbpZUpEJvBYMT7iUA6a8nYr7LRWft92jnM7RbfU+Kly7mtq1mSjeAHNlMPts0censEmO5wWs36ZyToLKtiQIjA0sRKcBet3ifMPS4FnN0tH5kSum+VB1fkS4VHrKU/FhMyd72A3SytLyY75USO1eEZtMzKwIPfxMdeM8LWXilm3BHZOAGC0oXsQn4DeGF42NTd5a/QckkHPSSXjPHu4E2o8/UpzM7T8TCSjyXF6c X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 01 Sep 2017 11:24:29.5407 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 3dd8961f-e488-4e60-8e11-a82d994e183d X-MS-Exchange-Transport-CrossTenantHeadersStamped: BY2PR12MB0146 Subject: [PATCH 4/5] OvmfPkg/VirtioNetDxe: map virtio-net transmit request buffer X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.22 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 01 Sep 2017 11:21:47 -0000 Content-Type: text/plain When device is behind the IOMMU, driver is require to pass the device address of transmit buffer for the bus master operations. The patch uses VirtioMapAllBytesInSharedBuffer() to map transmit buffer system physical address to the device address. Since the transmit buffers are returned back to caller in VirtioNetGetStatus() hence we use OrderCollection library interface to save the host to device address mapping. After the buffer is succesfully transmited we do reverse lookup in OrderCollection data structure to get the host address for the transmitted device address. Cc: Ard Biesheuvel Cc: Jordan Justen Cc: Tom Lendacky Cc: Laszlo Ersek Contributed-under: TianoCore Contribution Agreement 1.1 Signed-off-by: Brijesh Singh --- OvmfPkg/VirtioNetDxe/VirtioNet.inf | 1 + OvmfPkg/VirtioNetDxe/VirtioNet.h | 19 +++ OvmfPkg/VirtioNetDxe/SnpGetStatus.c | 30 +++- OvmfPkg/VirtioNetDxe/SnpSharedHelpers.c | 157 ++++++++++++++++++++ OvmfPkg/VirtioNetDxe/SnpTransmit.c | 37 ++++- 5 files changed, 232 insertions(+), 12 deletions(-) diff --git a/OvmfPkg/VirtioNetDxe/VirtioNet.inf b/OvmfPkg/VirtioNetDxe/VirtioNet.inf index a855ad4ac154..9ff6d87e6190 100644 --- a/OvmfPkg/VirtioNetDxe/VirtioNet.inf +++ b/OvmfPkg/VirtioNetDxe/VirtioNet.inf @@ -49,6 +49,7 @@ [LibraryClasses] DebugLib DevicePathLib MemoryAllocationLib + OrderedCollectionLib UefiBootServicesTableLib UefiDriverEntryPoint UefiLib diff --git a/OvmfPkg/VirtioNetDxe/VirtioNet.h b/OvmfPkg/VirtioNetDxe/VirtioNet.h index 3efe95a735d8..d931969af795 100644 --- a/OvmfPkg/VirtioNetDxe/VirtioNet.h +++ b/OvmfPkg/VirtioNetDxe/VirtioNet.h @@ -269,6 +269,25 @@ VirtioNetShutdownTx ( IN OUT VNET_DEV *Dev ); +EFI_STATUS +EFIAPI +VirtioMapTxBuf ( + IN VNET_DEV *Dev, + IN UINT16 Index, + IN EFI_PHYSICAL_ADDRESS HostAddress, + IN UINTN NumberOfBytes, + OUT EFI_PHYSICAL_ADDRESS *DeviceAddress + ); + +EFI_STATUS +EFIAPI +VirtioUnmapTxBuf ( + IN VNET_DEV *Dev, + IN UINT16 Index, + OUT EFI_PHYSICAL_ADDRESS *HostAddress, + IN EFI_PHYSICAL_ADDRESS DeviceAddress + ); + // // event callbacks // diff --git a/OvmfPkg/VirtioNetDxe/SnpGetStatus.c b/OvmfPkg/VirtioNetDxe/SnpGetStatus.c index 694940ea1d97..10ca26de6d7a 100644 --- a/OvmfPkg/VirtioNetDxe/SnpGetStatus.c +++ b/OvmfPkg/VirtioNetDxe/SnpGetStatus.c @@ -5,6 +5,7 @@ Copyright (C) 2013, Red Hat, Inc. Copyright (c) 2006 - 2014, Intel Corporation. All rights reserved.
+ Copyright (c) 2017, AMD Inc, All rights reserved.
This program and the accompanying materials are licensed and made available under the terms and conditions of the BSD License which accompanies this @@ -47,7 +48,8 @@ @retval EFI_INVALID_PARAMETER One or more of the parameters has an unsupported value. @retval EFI_DEVICE_ERROR The command could not be sent to the network - interface. + interface or failed to map TxBuf to bus master + address. @retval EFI_UNSUPPORTED This function is not supported by the network interface. @@ -126,8 +128,10 @@ VirtioNetGetStatus ( *TxBuf = NULL; } else { - UINT16 UsedElemIdx; - UINT32 DescIdx; + UINT16 UsedElemIdx; + UINT32 DescIdx; + EFI_PHYSICAL_ADDRESS BufferAddress; + EFI_PHYSICAL_ADDRESS DeviceAddress; // // fetch the first descriptor among those that the hypervisor reports @@ -141,9 +145,27 @@ VirtioNetGetStatus ( ASSERT (DescIdx < (UINT32) (2 * Dev->TxMaxPending - 1)); // + // Ring descriptor contains the device address for the caller buffer. + // Lets unmap the device address and find its corresponding system + // physical address. + // + DeviceAddress = Dev->TxRing.Desc[DescIdx + 1].Addr; + Status = VirtioUnmapTxBuf ( + Dev, + DescIdx + 1, + &BufferAddress, + DeviceAddress + ); + if (EFI_ERROR (Status)) { + Status = EFI_DEVICE_ERROR; + goto Exit; + } + + // + // // report buffer address to caller that has been enqueued by caller // - *TxBuf = (VOID *)(UINTN) Dev->TxRing.Desc[DescIdx + 1].Addr; + *TxBuf = (VOID *)(UINTN) BufferAddress; // // now this descriptor can be used again to enqueue a transmit buffer diff --git a/OvmfPkg/VirtioNetDxe/SnpSharedHelpers.c b/OvmfPkg/VirtioNetDxe/SnpSharedHelpers.c index aeb9e6605f0d..b91ddd3e4ede 100644 --- a/OvmfPkg/VirtioNetDxe/SnpSharedHelpers.c +++ b/OvmfPkg/VirtioNetDxe/SnpSharedHelpers.c @@ -14,10 +14,25 @@ **/ +#include #include +#include #include "VirtioNet.h" +typedef struct { + UINT16 Value; +} USER_KEY; + +typedef struct { + USER_KEY Key; + EFI_PHYSICAL_ADDRESS HostAddress; + EFI_PHYSICAL_ADDRESS DeviceAddress; + VOID *BufMap; +} USER_STRUCT; + +STATIC ORDERED_COLLECTION *Collection; + /** Release RX and TX resources on the boundary of the EfiSimpleNetworkInitialized state. @@ -63,3 +78,145 @@ VirtioNetShutdownTx ( FreePool (Dev->TxFreeStack); } + +STATIC +INTN +EFIAPI +KeyCompare ( + IN CONST VOID *StandaloneKey, + IN CONST VOID *UserStruct + ) +{ + CONST USER_KEY *CmpKey; + CONST USER_STRUCT *CmpStruct; + + CmpKey = StandaloneKey; + CmpStruct = UserStruct; + + return CmpKey->Value < CmpStruct->Key.Value ? -1 : + CmpKey->Value > CmpStruct->Key.Value ? 1 : + 0; +} + +STATIC +INTN +EFIAPI +UserStructCompare ( + IN CONST VOID *UserStruct1, + IN CONST VOID *UserStruct2 + ) +{ + CONST USER_STRUCT *CmpStruct1; + + CmpStruct1 = UserStruct1; + + return KeyCompare (&CmpStruct1->Key, UserStruct2); +} + +EFI_STATUS +EFIAPI +VirtioMapTxBuf ( + IN VNET_DEV *Dev, + IN UINT16 Index, + IN EFI_PHYSICAL_ADDRESS HostAddress, + IN UINTN NumberOfBytes, + OUT EFI_PHYSICAL_ADDRESS *DeviceAddress + ) +{ + EFI_STATUS Status; + ORDERED_COLLECTION_ENTRY *Entry; + USER_STRUCT *UserStruct; + EFI_PHYSICAL_ADDRESS Address; + VOID *Mapping; + + // + // If ordered collection is not initialized then initialize it. + // + if (Collection == NULL) { + Collection = OrderedCollectionInit (UserStructCompare, KeyCompare); + if (Collection == NULL) { + return EFI_OUT_OF_RESOURCES; + } + } + + UserStruct = AllocatePool (sizeof (*UserStruct)); + if (UserStruct == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + Status = VirtioMapAllBytesInSharedBuffer ( + Dev->VirtIo, + VirtioOperationBusMasterRead, + (VOID *) (UINTN) HostAddress, + NumberOfBytes, + &Address, + &Mapping + ); + if (EFI_ERROR (Status)) { + goto ReleaseUserStruct; + } + + UserStruct->Key.Value = Index; + UserStruct->HostAddress = HostAddress; + UserStruct->DeviceAddress = Address; + UserStruct->BufMap = Mapping; + + Status = OrderedCollectionInsert (Collection, &Entry, UserStruct); + switch (Status) { + case RETURN_OUT_OF_RESOURCES: + Status = EFI_OUT_OF_RESOURCES; + goto UnmapBuffer; + case RETURN_ALREADY_STARTED: + Status = EFI_INVALID_PARAMETER; + goto UnmapBuffer; + default: + ASSERT (Status == RETURN_SUCCESS); + break; + } + + ASSERT (OrderedCollectionUserStruct (Entry) == UserStruct); + + *DeviceAddress = Address; + return EFI_SUCCESS; + +UnmapBuffer: + Dev->VirtIo->UnmapSharedBuffer (Dev->VirtIo, Mapping); + +ReleaseUserStruct: + FreePool (UserStruct); + return Status; +} + +EFI_STATUS +EFIAPI +VirtioUnmapTxBuf ( + IN VNET_DEV *Dev, + IN UINT16 Index, + OUT EFI_PHYSICAL_ADDRESS *HostAddress, + IN EFI_PHYSICAL_ADDRESS DeviceAddress + ) +{ + USER_KEY StandaloneKey; + ORDERED_COLLECTION_ENTRY *Entry; + USER_STRUCT *UserStruct; + VOID *Ptr; + EFI_STATUS Status; + + StandaloneKey.Value = Index; + Entry = OrderedCollectionFind (Collection, &StandaloneKey); + if (Entry == NULL) { + return EFI_INVALID_PARAMETER; + } + + OrderedCollectionDelete (Collection, Entry, &Ptr); + + UserStruct = Ptr; + ASSERT (UserStruct->DeviceAddress == DeviceAddress); + ASSERT (UserStruct->Key.Value == Index); + + *HostAddress = UserStruct->HostAddress; + Status = Dev->VirtIo->UnmapSharedBuffer (Dev->VirtIo, UserStruct->BufMap); + FreePool (UserStruct); + + return Status; +} diff --git a/OvmfPkg/VirtioNetDxe/SnpTransmit.c b/OvmfPkg/VirtioNetDxe/SnpTransmit.c index 7ca40d5d0650..1bd6e0d70d7c 100644 --- a/OvmfPkg/VirtioNetDxe/SnpTransmit.c +++ b/OvmfPkg/VirtioNetDxe/SnpTransmit.c @@ -55,7 +55,8 @@ @retval EFI_INVALID_PARAMETER One or more of the parameters has an unsupported value. @retval EFI_DEVICE_ERROR The command could not be sent to the network - interface. + interface or failed to map the Buffer to + bus master address. @retval EFI_UNSUPPORTED This function is not supported by the network interface. @@ -73,11 +74,12 @@ VirtioNetTransmit ( IN UINT16 *Protocol OPTIONAL ) { - VNET_DEV *Dev; - EFI_TPL OldTpl; - EFI_STATUS Status; - UINT16 DescIdx; - UINT16 AvailIdx; + VNET_DEV *Dev; + EFI_TPL OldTpl; + EFI_STATUS Status; + UINT16 DescIdx; + UINT16 AvailIdx; + EFI_PHYSICAL_ADDRESS DeviceAddress; if (This == NULL || BufferSize == 0 || Buffer == NULL) { return EFI_INVALID_PARAMETER; @@ -144,10 +146,29 @@ VirtioNetTransmit ( } // - // virtio-0.9.5, 2.4.1 Supplying Buffers to The Device + // Get the available descriptor // DescIdx = Dev->TxFreeStack[Dev->TxCurPending++]; - Dev->TxRing.Desc[DescIdx + 1].Addr = (UINTN) Buffer; + + // + // Map the transmit buffer system physical address to device address. + // + Status = VirtioMapTxBuf ( + Dev, + DescIdx + 1, + (EFI_PHYSICAL_ADDRESS) (UINTN) Buffer, + BufferSize, + &DeviceAddress + ); + if (EFI_ERROR (Status)) { + Status = EFI_DEVICE_ERROR; + goto Exit; + } + + // + // virtio-0.9.5, 2.4.1 Supplying Buffers to The Device + // + Dev->TxRing.Desc[DescIdx + 1].Addr = DeviceAddress; Dev->TxRing.Desc[DescIdx + 1].Len = (UINT32) BufferSize; // -- 2.7.4