From patchwork Thu Nov 17 05:30:02 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Shreyansh Jain X-Patchwork-Id: 17056 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@dpdk.org Delivered-To: patchwork@dpdk.org Received: from [92.243.14.124] (localhost [IPv6:::1]) by dpdk.org (Postfix) with ESMTP id 71A4458C8; Thu, 17 Nov 2016 06:29:06 +0100 (CET) Received: from NAM01-BY2-obe.outbound.protection.outlook.com (mail-by2nam01on0086.outbound.protection.outlook.com [104.47.34.86]) by dpdk.org (Postfix) with ESMTP id 01FB35599 for ; Thu, 17 Nov 2016 06:28:13 +0100 (CET) Received: from BLUPR0301CA0035.namprd03.prod.outlook.com (10.162.113.173) by CY1PR0301MB0748.namprd03.prod.outlook.com (10.160.159.154) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P384) id 15.1.721.10; Thu, 17 Nov 2016 05:28:11 +0000 Received: from BN1AFFO11OLC003.protection.gbl (2a01:111:f400:7c10::181) by BLUPR0301CA0035.outlook.office365.com (2a01:111:e400:5259::45) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P384) id 15.1.721.10 via Frontend Transport; Thu, 17 Nov 2016 05:28:10 +0000 Authentication-Results: spf=fail (sender IP is 192.88.168.50) smtp.mailfrom=nxp.com; nxp.com; dkim=none (message not signed) header.d=none; nxp.com; dmarc=fail action=none header.from=nxp.com; nxp.com; dkim=none (message not signed) header.d=none; Received-SPF: Fail (protection.outlook.com: domain of nxp.com does not designate 192.88.168.50 as permitted sender) receiver=protection.outlook.com; client-ip=192.88.168.50; helo=tx30smr01.am.freescale.net; Received: from tx30smr01.am.freescale.net (192.88.168.50) by BN1AFFO11OLC003.mail.protection.outlook.com (10.58.53.74) with Microsoft SMTP Server (version=TLS1_0, cipher=TLS_RSA_WITH_AES_256_CBC_SHA) id 15.1.721.5 via Frontend Transport; Thu, 17 Nov 2016 05:28:11 +0000 X-IncomingTopHeaderMarker: OriginalChecksum:; UpperCasedChecksum:; SizeAsReceived:647; Count:10 Received: from Tophie.ap.freescale.net ([10.232.14.87]) by tx30smr01.am.freescale.net (8.14.3/8.14.0) with ESMTP id uAH5S1ps018741; Wed, 16 Nov 2016 22:28:08 -0700 From: Shreyansh Jain To: CC: , Shreyansh Jain Date: Thu, 17 Nov 2016 11:00:02 +0530 Message-ID: <1479360605-20558-4-git-send-email-shreyansh.jain@nxp.com> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1479360605-20558-1-git-send-email-shreyansh.jain@nxp.com> References: <1479360605-20558-1-git-send-email-shreyansh.jain@nxp.com> X-IncomingHeaderCount: 10 X-EOPAttributedMessage: 0 X-Matching-Connectors: 131238340914282498; (91ab9b29-cfa4-454e-5278-08d120cd25b8); () X-Forefront-Antispam-Report: CIP:192.88.168.50; IPV:NLI; CTRY:US; EFV:NLI; SFV:NSPM; SFS:(10009020)(6009001)(7916002)(2980300002)(1109001)(1110001)(339900001)(336004)(43544003)(199003)(189002)(50226002)(8936002)(77096005)(81156014)(81166006)(4326007)(7846002)(2906002)(305945005)(104016004)(92566002)(76176999)(50986999)(8666005)(8676002)(86362001)(356003)(575784001)(5003940100001)(106466001)(105606002)(36756003)(33646002)(2351001)(47776003)(6666003)(2950100002)(6916009)(110136003)(48376002)(50466002)(5660300001)(626004)(68736007)(97736004)(87936001)(189998001)(85426001)(7059030)(21314002)(217873001); DIR:OUT; SFP:1101; SCL:1; SRVR:CY1PR0301MB0748; H:tx30smr01.am.freescale.net; FPR:; SPF:Fail; PTR:InfoDomainNonexistent; A:1; MX:1; LANG:en; X-Microsoft-Exchange-Diagnostics: 1; BN1AFFO11OLC003; 1:rjLmPuwao3AM53Ezim3Ru5/C83HXD2G7b3U//WrYpOIhokvJojnQrSDrYtIg4Mrdcg/QhclMzd95GH1z+qOZ9FCLYrwuJ8hNB6nLHgfZbjFJ0n9VKwQlz0aVvLUC+JW0AYz13vcfUa8JZGWKhFYgdJQ1ctrSDw3iN7h9DAgRzHynNf/yGyGnhA/vjA7yJYYCEnOfuYgQSbql1vgFWx0+kuKo5A3DOqQhJogV9O/x1IWqy8H4Rdm+qgdb89jO4WV4/u+CKfDUK5p9BD1OrZnPUaI0m/cZ1TJG/v33c2azCFCg9B0ow/ZhYkEFoRVtwJqttk+jOdUrFvEsy00YC4+kvlf5x2bV0MXFNQfnYFiW/WNkWYDGx2Dcj5jOuNzZElR2lXlRxdiBAFJ8BHYVmBAkt+E2LqNhG9NvzSTCD/juvIi0WC1b1QKSORiDX3qbh/gfF4czjVKgYOwg/0AQFZCy2nbIQZ2vTaK3Ef73Y4l9c7gfTrOXsxkw9cywZiMCQD3KBEmRSwKsxtQSr0hcRuBtkBns43E2y9a4HLVCAg62gq7TU4689XtMAh6kn6GB6eE2RbN1aQuzN5jTd4bqdN37UaNJHAg77AH0MKBBjmwXGO26IZuyMmUoFMHPsBb7nbLaNDgBBS+0yCtXKETUYKRrMJ+DJZVkBq3p25BfXv5oEiXCUufItY31eglQ2IQop1IIA1D9t+1D+c/fjqvDVuolZugvNwVxz9ryyjvCCbCXPow= MIME-Version: 1.0 X-Microsoft-Exchange-Diagnostics: 1; CY1PR0301MB0748; 2:ZdtTYvaTJKXNy3UnpBfFTBr7foE9A0DlGof5iIBNs7xmGDRzkcde/I0SwYu8wNBhLpoqYt8Di105DfxHC4GorRnWmvbEqmiVk/m8YmFU3gcVB80eTudQnbDp02/N6QkMeaiavRHu3xwxMlShRGRJbwtceY4HG1dfWnzbzR69VbQ=; 3:ic1ryyt84C+P/DyPZsoxkJN99nHTJh9YfTmL280T4hAteMF+oxpLsMWzqut9LqzkKTMGrxJtHEDXtcs3JDo9GbU+Tm4ymGsJjijypN+FRUL4NJOijNJsYpu/jXZzu6t9Dym1v21UclAu8yhNNaAFDvBW1jfnxJNaOZEbfiTvT54cTCGazy4QUP8ih5xHL5ACzkzA46JGuM0koMckhogyxoIjiAI1CfBSYKorY2zEzE1CZS3ggOqiijIESJ3eB75Vj5QrhepPedtsRAqVwI7Kow== X-MS-Office365-Filtering-Correlation-Id: f180d4cb-195c-4d37-7512-08d40eaa857f X-Microsoft-Antispam: UriScan:; BCL:0; PCL:0; RULEID:(22001); SRVR:CY1PR0301MB0748; X-Microsoft-Exchange-Diagnostics: 1; CY1PR0301MB0748; 25:j46nHi9Fi9M7a4eeMrEqNpab51u1fhnJ/7ThiYToUVKOv0uvoHUrZQkP/lYCX8dG0LBczbgSQYOE85bfozECaP3UrlcRFlwQqDUOWuy1v1TRLrhMAcKQbJdgiIwoPwuNEaLD+cEC5yXPZi2Wjzx071QVSHSLMEAm8eg/owx/u7/un9q+QP2+Hmtk5LuWD/OdkDkEEtP2B9td/hJl4EEF6oCoIaDYDWWGq/XUqduls/PS1S5j9wUb2Oey48/rPTx6NSf0rjK7ks7ivucRYJPnpieLn2PPIOqRDgbu1+v86QKgSGEko/aDMmp6+/SO+HOiV1BysdJ5OhjVO9IqazCdf7HOmArTa9Dh+iYhMCxV2JXXjPGr8h/cSYIRhuyERUSFQg3Q4BpbgN4xrHwqKM3mNH6SpzZyWp6h56n9jDfwTggwOqvqV7eohUzejZx4nSTqsRpyO8lHUIMYopTEYdckV9my2S4B+glG2j97lOY5pQaRsI05mu5elQBnSmNGyNgUjan8x37IiwkhO2RJ2nF4nLNhWscTM+7k9uZ0JM2hKpZmfFJyw4oR7KOEJFETbuHjtDi0uuJyprLQVQJ+a+Ce/E/LKmu7ahos7mObtTMHh4ExJUb1f03zVJ0nQpRXrnJJrbwf6i1oGNMnmifFFjPzCm8T4roVerd/JGnMd4oK46IE0fzpzv7bqLhyH6sKowYGjuJh3KQ8FdEzMyEQEEqVQ25ifhWElyx71ZPgUrwnxGh4xUO8tjXcTOAYInFa9h5XDXdH1kowDbNHEyBvRU2iUSY4uXms5JHHN0chgi7zArU= X-Microsoft-Exchange-Diagnostics: 1; CY1PR0301MB0748; 31:26Je23zfUxTfLS1tgInqhoZ8KRUt8lfSbK7qQeB584dq/iYytUT8JGCfdwdavoyF6T5kItKT+IpXLMBbCoIBAHs1Sz04SC9BDmzhSPcUIS4czfcpPRX37OLzmVWMHGBT+oLn6GXN2qv/7JCk7F/c3cwzABSBCc9JcIWzR5anxhmyhZXOOSVqzzWtMHgJLSUBt2GiP8g5K7dfw6jB1f4bE+aUEG7BARN5IhRZ5IxkI1IwSUqi7+WtKMBZ8zjBahi5WnQBpwMlQvbGvfcyNexLow==; 4:Qhroavt1S6owCP3XQthoME/QkLYR7kKo7IJyx56Xe0HyoxZqD5MTOo3sVNSclCe2UPwMmRwSqQZ+RnQLvhCjf1vd54UhDYml/YbisSPu+WYZjRZJsXqYGMPRKzmlaE4ZYfzm8/hjUvDuiwk1L+o6rjgHJTD+cy9t59Num/KJ0oNv4DtbMravWhWM22Ebj5WSSP+35hwYhXoFV7P7xz7eUEkGDhOFMDtk+IDvljKCDRbr5fMLzWBlMqN2S0jNR6Wl1LVeEPVILTR4bGKvCP8sHkgwsKWLDvk5Yv6N7oOlZtWPn5ciKuhPNOl7QBQCF6V2BeGv8sa1MYGBixDyoqrLdKpTt6Sem/1Ut8NxOwcUqS8rLaWMl1R+14cmebT5JC2ojWsxJMJj/MNKuCrLgBudNMdxgvU0jjpxPEqacHEPUNHwWnBtbbf2umF0lgfmvwYM+DcTk5pi23EUO3OFBwkmTC/2XEQsA69g8dpjmDmNJexnYSoXsRN6nRnGh4xDSlOnRUP9D1OKVEMewCtlhH2o6GS7rVM10TW365J6cEhwp21cVv6YMxPFEpHRkVBtoElSKeWSUq6gFiBQKdwxDm31fA== X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-Test: UriScan:(185117386973197); X-Exchange-Antispam-Report-CFA-Test: BCL:0; PCL:0; RULEID:(6095035)(601004)(2401047)(13023025)(5005006)(8121501046)(13018025)(13024025)(13015025)(13017025)(3002001)(10201501046)(6055026)(6096035); SRVR:CY1PR0301MB0748; BCL:0; PCL:0; RULEID:(400006); SRVR:CY1PR0301MB0748; X-Forefront-PRVS: 01294F875B X-Microsoft-Exchange-Diagnostics: =?us-ascii?Q?1; CY1PR0301MB0748; 23:Wn2KILw0J/1lM9cKT7fpEKB7tgxoFGx8Kvj5K+9?= =?us-ascii?Q?xTACIcHBuLDToL6Z6BcUis4pcODiW/fBqyoTdAa+HtRhfUgf4l7bGrgIzix+?= =?us-ascii?Q?7UyzvDaHKdRzwn4MU5oVfceH7z5xhZP19EdiYHw+OsGm5fMz8oAFnBGMiBXD?= =?us-ascii?Q?rKVykaoFv2DkeMUC3ugYb99/PB7nhEN/lKAHh/Hh1FfD9RA2RDicWBp48lsR?= =?us-ascii?Q?wHRX8cGumtstVYBy29YdyrKMZy9R2tF9BnoHQ5s+0EI9mVy3BXKZf/xsqdvJ?= =?us-ascii?Q?WyW8hVBmCYF1oAlsMFIPVrH+7XN2Dmcgpo/D2zGYCL7Txc5ykuOtlGGml0lc?= =?us-ascii?Q?CX/yiaTVTsPKUxDaigP1Y9TBkbPr3LtGStwIzg1wQNlV9A/UbofYu77ZTLnr?= =?us-ascii?Q?9HiemdcyPePuFmV0Iu20YfIT0FKRQbO5LiahSsviKljI2h03lviVruiu5Lhq?= =?us-ascii?Q?mkLsdgvol0eLrBha2O07x86u4YDamHeVZ3SsdOkB4zjQ3G46dp+++++DpbRH?= =?us-ascii?Q?3DvK6jij2NaQM1++LgRiaZLoT9sRBNOHLoRAT8ZR0iYk0IpEbsz/Vvz0Yek6?= =?us-ascii?Q?32Ofj6Grft+K2k5TIdhANr8JHakWAU1XUh2599fi4eNKcBksWUwqvVmjdGLb?= =?us-ascii?Q?oXoluCqZfoaXjEWuHnd3exqjmrUiIfJzm6MKsvnzKEQFQcPXM36jquP+5hkn?= =?us-ascii?Q?uyO72PWnU5wNR0FpZ5d/6G6okg4B5fupGy1sB9/G2QtPgzpUeB/jdHidPbjw?= =?us-ascii?Q?5tJu15n0lYZ5ffFlzSubi6o4vWAGJ7ioTMaKu914M1lYuR3E98Rp5ohYWDK3?= =?us-ascii?Q?4PvHrTUPAJw10XXnIxmI6OxIoUZ1oFm4ipTqM99qyWvAe/4gzNH2ujvXggJV?= =?us-ascii?Q?Bj3UAUuUAE2KzPJoTx/Vi8F/du5DCdtMGw4dGpWuxw02yZmUHGDHZ7FbC6eV?= =?us-ascii?Q?5MpwNwBUtogOkg0fdIRYGHK+35gZdM3DUvhE1MQQeI9uB/ro7cC6/CuDTY1p?= =?us-ascii?Q?Hz9ocjIgQbMhb0NmDbOftAY3u4UX5NQm8JH3wwS/zur74v0/OIegniuqJWtN?= =?us-ascii?Q?RoflhVWY3L82h7ZrJqXJchfK4/0DpvaYt+iJCznXBf69y2WJ7/7I368AYKR5?= =?us-ascii?Q?NOmjjWpFFcbefl4jqNyzRE7NHnYpDtNO5kgEBjgAznP/4P84OP6tNPx93F4a?= =?us-ascii?Q?yhHxP3aoYlzzE/cyFgtSqNjox6MA9A8jQzPXh?= X-Microsoft-Exchange-Diagnostics: 1; CY1PR0301MB0748; 6:5vXHjF9YOTt8mDtjMV2TPM73xa+FQ+2Mk5KHIRdc1PCGqV4AZ44WFrY3hQIw7U9i757NLGKYb4uc+I9XKsxAarHZwGywepwujxRaO0kv2KSzr85O8r3zsCu1R30SGsV+dfTVe9/TfKrvGFTJoO7EJLhKjPVcJHcNQtg5aBeuawd/1TxJPkOXT6UwFFNUYfMoZmTgHIAkK587ojZyjUCssOxxQuCTjdgNUYXy8S25FsJU5M1QfbNBqiPor0RqT38nJ7c/R+gTU86aNyId5eKzFK30iIHhoJlCccz0f5TJar/lrtS8G02HMxyEcTmqIqNIAccDW16+CWQtenLnDFf0Vg==; 5:vj+CRNEmC/65yV4wM/PHJBUcjKPWDpX2bLdJPSjScrFOjx1snr8sQiewMzdwGoAmag0DP1DmZySND7RwrbIx/dht3xQYTmk4qgrHvWq2nKNz89sVafCPA+xcKxtpcwLavXu4P94283iOYv1lBBOUVnpcaHPeAGqlbdsZ2vJ+lnkfKp4JyewHqkzLNutQmInA; 24:71L6K3iZ5hbLdzZzKZ1aPcEEKJQ/+YDCCxirD0lraxdd6ekM6pRTNGiC1FPRc4iqy3MsCpA+86NxT26yLBesiFqthx+kFDG8ZQUw0CHdqaU= SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-Microsoft-Exchange-Diagnostics: 1; CY1PR0301MB0748; 7:ZuTf5B1BgRiVZM4b9x88gQD4kAFKV8ZhsxvIQDPNbg3QNNvXpG0J9Z2APF1Wpntyg6C4EKbKq/kmMP5hdfaOYFHqxRy9c6EQgWdxHEUkaTB94bmcb7GA5HLXmIjvxo6+7zLGioTvO2bPIy8WrG4Bd6aUIkmg11OeGOGloMmSp8snFTsUDQ3WrtmU/dO9n+/LCOQQteugubuZ6SyeIA+MqkVNAu3R/ONfXob4jn3l5X0I6QioC18u3xwUF3WOcUtBXw4dtz/vFl2pGxJr1RPYuGgUAYqlNXhYFxPe4mNnZ2OohPn7biFxovFQuchaTZBuX0sup9TCynmg63GPKjv04akn403jqTCyT+0JNkSTlBc= X-MS-Exchange-CrossTenant-OriginalArrivalTime: 17 Nov 2016 05:28:11.1318 (UTC) X-MS-Exchange-CrossTenant-Id: 5afe0b00-7697-4969-b663-5eab37d5f47e X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=5afe0b00-7697-4969-b663-5eab37d5f47e; Ip=[192.88.168.50]; Helo=[tx30smr01.am.freescale.net] X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: CY1PR0301MB0748 Subject: [dpdk-dev] [RFC PATCH 3/6] bus: add bus driver layer X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: patches and discussions about DPDK List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org Sender: "dev" A bus is managed using a 'bus driver'. This patch introduces a sample PCI bus driver which essentially is the scan and match implementation for PCI. There are multiple possible alternatives to where such a driver can be kept within the DPDK code: 1. librte_bus - For each type of bus, there would a file like 'eal_xxx_bus' which would then be bound with the eal library. - Within this way, another possibility was librte_bus_xxx. 2. Within the drivers/* folder: - drivers/bus, parallel to drivers/net and drivers/crypto - This way, each bus implmentation would be within the drivers/* area and a new implementation would only mean adding a new set of files and corresponding changes to the Makefiles. 3. Problem with (3) is that the naming is misleading. drivers/net and drivers/crypto are essentially two functionalities rather than drivers. Putting driver/bus parallel to these would be misleading in literal terms. Another possibility is to keep the drivers parallel to 'drivers' folder in root of DPDK. This is the implementation preferred in this patch. A new bus would mean adding a new folder structure within 'bus' - including distinction between linuxapp and bsdapp. In all the three cases, the bus drivers would be instantiated using a constructor similar to RTE_PMD_REGISTER_XXX. OR, specifically in case of (2), it would be a priority based constructor. (__attribute__((contructor(XX))) to assure that buses are loaded before the drivers are loaded. Further, as of now the 'pci_bus.c' only shows the scan and dump hooks. rte_bus also includes hooks for 'dump'ing all devices on the bus and 'find_dev' for finding a device given its rte_device. Each of these 'optional' implementation are more like helpers but have implementation which is specific to the bus. Hooks for finding a device can be used for hotplugging (searching before adding a new device, removing existing). Similarly, 'dump' is a way to represent device information in bus specific way. Missing/Grey areas: - A lot of PCI specific code is still in EAL - for example mapping. These can be moved into bus. Mapping of memory should be a bus property. - PMDINFOGEN symbol support for bus - this patch doesn't take care of that - there would be multiple lists for each bus. Would those be shared across various libraries, internal or external, which can be associated with DPDK? Should a tailq registration like method be used? Pending work: - The integration of bus/* with librte_eal is not complete. There might be symbol issues. - Notification support for drivers over a bus doesn't exist yet. Probably that needs to be integrated with interrupt handling - no work on this has been done yet. Signed-off-by: Shreyansh Jain --- bus/Makefile | 36 ++++ bus/pci/Makefile | 37 ++++ bus/pci/linuxapp/pci_bus.c | 418 +++++++++++++++++++++++++++++++++++++++++++++ bus/pci/linuxapp/pci_bus.h | 55 ++++++ 4 files changed, 546 insertions(+) create mode 100644 bus/Makefile create mode 100644 bus/pci/Makefile create mode 100644 bus/pci/linuxapp/pci_bus.c create mode 100644 bus/pci/linuxapp/pci_bus.h diff --git a/bus/Makefile b/bus/Makefile new file mode 100644 index 0000000..cfa548c --- /dev/null +++ b/bus/Makefile @@ -0,0 +1,36 @@ +# BSD LICENSE +# +# Copyright(c) 2016 NXP. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in +# the documentation and/or other materials provided with the +# distribution. +# * Neither the name of NXP nor the names of its +# contributors may be used to endorse or promote products derived +# from this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +include $(RTE_SDK)/mk/rte.vars.mk + +DIRS-y += pci + +include $(RTE_SDK)/mk/rte.subdir.mk diff --git a/bus/pci/Makefile b/bus/pci/Makefile new file mode 100644 index 0000000..fb6cc44 --- /dev/null +++ b/bus/pci/Makefile @@ -0,0 +1,37 @@ +# BSD LICENSE +# +# Copyright(c) 2010-2014 Intel Corporation. All rights reserved. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in +# the documentation and/or other materials provided with the +# distribution. +# * Neither the name of Intel Corporation nor the names of its +# contributors may be used to endorse or promote products derived +# from this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +include $(RTE_SDK)/mk/rte.vars.mk + +DIRS-$(CONFIG_RTE_EXEC_ENV_LINUXAPP) += linuxapp +DIRS-$(CONFIG_RTE_EXEC_ENV_BSDAPP) += bsdapp + +include $(RTE_SDK)/mk/rte.subdir.mk diff --git a/bus/pci/linuxapp/pci_bus.c b/bus/pci/linuxapp/pci_bus.c new file mode 100644 index 0000000..b61cb0a --- /dev/null +++ b/bus/pci/linuxapp/pci_bus.c @@ -0,0 +1,418 @@ +/*- + * BSD LICENSE + * + * Copyright(c) 2016 NXP. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name of NXP nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "eal_filesystem.h" +#include "eal_private.h" +#include "eal_pci_init.h" + + + +/** + * Default PCI matching function called duing probe for drivers + * + * @param drv + * The PCI driver handle + * @param dev + * The PCI device handle + * @return + * 0 for successful match + * !0 for unsuccessful match + */ +int rte_eal_pci_match_default(struct rte_pci_driver *drv, + struct rte_pci_device *dev); + + +/* + * split up a pci address into its constituent parts. + */ +static int +parse_pci_addr_format(const char *buf, int bufsize, uint16_t *domain, + uint8_t *bus, uint8_t *devid, uint8_t *function) +{ + /* first split on ':' */ + union splitaddr { + struct { + char *domain; + char *bus; + char *devid; + char *function; + }; + char *str[PCI_FMT_NVAL]; + /* last element-separator is "." not ":" */ + } splitaddr; + + char *buf_copy = strndup(buf, bufsize); + if (buf_copy == NULL) + return -1; + + if (rte_strsplit(buf_copy, bufsize, splitaddr.str, PCI_FMT_NVAL, ':') + != PCI_FMT_NVAL - 1) + goto error; + /* final split is on '.' between devid and function */ + splitaddr.function = strchr(splitaddr.devid,'.'); + if (splitaddr.function == NULL) + goto error; + *splitaddr.function++ = '\0'; + + /* now convert to int values */ + errno = 0; + *domain = (uint16_t)strtoul(splitaddr.domain, NULL, 16); + *bus = (uint8_t)strtoul(splitaddr.bus, NULL, 16); + *devid = (uint8_t)strtoul(splitaddr.devid, NULL, 16); + *function = (uint8_t)strtoul(splitaddr.function, NULL, 10); + if (errno != 0) + goto error; + + free(buf_copy); /* free the copy made with strdup */ + return 0; +error: + free(buf_copy); + return -1; +} + +/* parse the "resource" sysfs file */ +static int +pci_parse_sysfs_resource(const char *filename, + struct rte_pci_device *dev) +{ + FILE *f; + char buf[BUFSIZ]; + int i; + uint64_t phys_addr, end_addr, flags; + + f = fopen(filename, "r"); + if (f == NULL) { + RTE_LOG(ERR, EAL, "Cannot open sysfs resource\n"); + return -1; + } + + for (i = 0; imem_resource[i].phys_addr = phys_addr; + dev->mem_resource[i].len = end_addr - phys_addr + 1; + /* not mapped for now */ + dev->mem_resource[i].addr = NULL; + } + } + fclose(f); + return 0; + +error: + fclose(f); + return -1; +} + +/* Scan one pci sysfs entry, and fill the devices list from it. */ +static int +pci_scan_one(const char *dirname, uint16_t domain, uint8_t bus,uint8_t devid, + uint8_t function) +{ + char filename[PATH_MAX]; + unsigned long tmp; + struct rte_pci_device *pci_dev; + struct rte_bus *pci_bus; + struct rte_device *dev; + char driver[PATH_MAX]; + int ret; + + /* Get the PCI bus for device; It it doesn't exist, can't continue */ + pci_bus = rte_eal_get_bus(PCI_BUS_NAME); + if (!pci_bus) { + RTE_LOG(ERR, EAL, "Unable to get PCI bus.\n"); + return -1; + } + + pci_dev = malloc(sizeof(*pci_dev)); + if (pci_dev == NULL) + return -1; + + memset(pci_dev, 0, sizeof(*pci_dev)); + pci_dev->addr.domain = domain; + pci_dev->addr.bus = bus; + pci_dev->addr.devid = devid; + pci_dev->addr.function = function; + + /* Set Bus */ + pci_dev->device->bus = pci_bus; + + /* get vendor id */ + snprintf(filename, sizeof(filename), "%s/vendor", dirname); + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + pci_dev->id.vendor_id = (uint16_t)tmp; + + /* get device id */ + snprintf(filename, sizeof(filename), "%s/device", dirname); + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + pci_dev->id.device_id = (uint16_t)tmp; + + /* get subsystem_vendor id */ + snprintf(filename, sizeof(filename), "%s/subsystem_vendor", + dirname); + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + pci_dev->id.subsystem_vendor_id = (uint16_t)tmp; + + /* get subsystem_device id */ + snprintf(filename, sizeof(filename), "%s/subsystem_device", + dirname); + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + pci_dev->id.subsystem_device_id = (uint16_t)tmp; + + /* get class_id */ + snprintf(filename, sizeof(filename), "%s/class", + dirname); + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + /* the least 24 bits are valid: class, subclass, program interface */ + pci_dev->id.class_id = (uint32_t)tmp & RTE_CLASS_ANY_ID; + + /* get max_vfs */ + pci_dev->max_vfs = 0; + snprintf(filename, sizeof(filename), "%s/max_vfs", dirname); + if (!access(filename, F_OK) && + eal_parse_sysfs_value(filename, &tmp) == 0) + pci_dev->max_vfs = (uint16_t)tmp; + else { + /* for non igb_uio driver, need kernel version >= 3.8 */ + snprintf(filename, sizeof(filename), + "%s/sriov_numvfs", dirname); + if (!access(filename, F_OK) && + eal_parse_sysfs_value(filename, &tmp) == 0) + pci_dev->max_vfs = (uint16_t)tmp; + } + + /* get numa node */ + snprintf(filename, sizeof(filename), "%s/numa_node", + dirname); + if (access(filename, R_OK) != 0) { + /* if no NUMA support, set default to 0 */ + pci_dev->device.numa_node = 0; + } else { + if (eal_parse_sysfs_value(filename, &tmp) < 0) { + free(pci_dev); + return -1; + } + pci_dev->device.numa_node = tmp; + } + + /* parse resources */ + snprintf(filename, sizeof(filename), "%s/resource", dirname); + if (pci_parse_sysfs_resource(filename, pci_dev) < 0) { + RTE_LOG(ERR, EAL, "%s(): cannot parse resource\n", __func__); + free(pci_dev); + return -1; + } + + /* parse driver */ + snprintf(filename, sizeof(filename), "%s/driver", dirname); + ret = pci_get_kernel_driver_by_path(filename, driver); + if (ret < 0) { + RTE_LOG(ERR, EAL, "Fail to get kernel driver\n"); + free(pci_dev); + return -1; + } + + if (!ret) { + if (!strcmp(driver, "vfio-pci")) + pci_dev->kdrv = RTE_KDRV_VFIO; + else if (!strcmp(driver, "igb_uio")) + pci_dev->kdrv = RTE_KDRV_IGB_UIO; + else if (!strcmp(driver, "uio_pci_generic")) + pci_dev->kdrv = RTE_KDRV_UIO_GENERIC; + else + pci_dev->kdrv = RTE_KDRV_UNKNOWN; + } else + pci_dev->kdrv = RTE_KDRV_NONE; + + /* device is valid, add in list (sorted) */ + if (TAILQ_EMPTY(&pci_bus->device_list)) { + rte_eal_bus_add_device(pci_bus, dev->device); + } else { + struct rte_device *dev2 = NULL; + struct rte_pci_device *pci_dev2; + int ret; + + TAILQ_FOREACH(dev2, &pci_bus->device_list, next) { + pci_dev2 = container_of(dev2, struct rte_pci_device, + device); + + ret = rte_eal_compare_pci_addr(&pci_dev->addr, + &pci_dev2->addr); + if (ret > 0) + continue; + + if (ret < 0) { + /* TODO Pending: 'before' handler for + * bus->device_list + */ + rte_eal_bus_add_device(pci_bus, + pci_dev2->device); + } else { /* already registered */ + pci_dev2->kdrv = pci_dev->kdrv; + pci_dev2->max_vfs = pci_dev->max_vfs; + memmove(pci_dev2->mem_resource, + pci_dev->mem_resource, + sizeof(pci_dev->mem_resource)); + free(pci_dev); + } + return 0; + } + rte_eal_device_insert(&pci_dev->device); + TAILQ_INSERT_TAIL(&pci_device_list, pci_dev, next); + } + + return 0; +} + +/* Default PCI match implementation */ +int +pci_bus_match(struct rte_pci_driver *drv, + struct rte_pci_device *dev) +{ + int ret = 1; + const struct rte_pci_id *id_table; + + for (id_table = drv->id_table; id_table->vendor_id != 0; id_table++) { + + /* check if device's identifiers match the driver's ones */ + if (id_table->vendor_id != dev->id.vendor_id && + id_table->vendor_id != PCI_ANY_ID) + continue; + if (id_table->device_id != dev->id.device_id && + id_table->device_id != PCI_ANY_ID) + continue; + if (id_table->subsystem_vendor_id != + dev->id.subsystem_vendor_id && + id_table->subsystem_vendor_id != PCI_ANY_ID) + continue; + if (id_table->subsystem_device_id != + dev->id.subsystem_device_id && + id_table->subsystem_device_id != PCI_ANY_ID) + continue; + if (id_table->class_id != dev->id.class_id && + id_table->class_id != RTE_CLASS_ANY_ID) + continue; + ret = 0; + break; + } + + /* Returning a >0 value as <0 is considered error by caller */ + return ret; +} + +/* + * Scan the content of the PCI bus, and the devices in the devices + * list + */ +int +pci_bus_scan(void) +{ + struct dirent *e; + DIR *dir; + char dirname[PATH_MAX]; + uint16_t domain; + uint8_t bus, devid, function; + + /* for debug purposes, PCI can be disabled */ + if (internal_config.no_pci) + return 0; + + dir = opendir(pci_get_sysfs_path()); + if (dir == NULL) { + RTE_LOG(ERR, EAL, "%s(): opendir failed: %s\n", + __func__, strerror(errno)); + return -1; + } + + while ((e = readdir(dir)) != NULL) { + if (e->d_name[0] == '.') + continue; + + if (parse_pci_addr_format(e->d_name, sizeof(e->d_name), + &domain, &bus, &devid, &function) != 0) + continue; + + snprintf(dirname, sizeof(dirname), "%s/%s", + pci_get_sysfs_path(), e->d_name); + if (pci_scan_one(dirname, domain, bus, devid, function) < 0) + goto error; + } + closedir(dir); + return 0; + +error: + closedir(dir); + return -1; +} + +struct rte_bus pci_bus = { + .scan = pci_bus_scan, + .match = pci_bus_match, + .dump = NULL, +}; + +RTE_PMD_REGISTER_BUS("pci_bus", pci_bus); diff --git a/bus/pci/linuxapp/pci_bus.h b/bus/pci/linuxapp/pci_bus.h new file mode 100644 index 0000000..580fa36 --- /dev/null +++ b/bus/pci/linuxapp/pci_bus.h @@ -0,0 +1,55 @@ +/*- + * BSD LICENSE + * + * Copyright(c) 2016 NXP + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * * Neither the name of NXP nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/** + * Default PCI matching function called duing probe for drivers + * + * @param drv + * The PCI driver handle + * @param dev + * The PCI device handle + * @return + * 0 for successful match + * !0 for unsuccessful match + */ +int bus_pci_match(struct rte_pci_driver *drv, + struct rte_pci_device *dev); + +/** +* Scan the content of the PCI bus, and the devices in the devices +* list +* +* @return +* 0 on success, negative on error +*/ +int bus_pci_scan(void);