From patchwork Fri Mar 17 16:11:50 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mason X-Patchwork-Id: 9631043 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 8CD8C60132 for ; Fri, 17 Mar 2017 16:12:54 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8EB3D286DC for ; Fri, 17 Mar 2017 16:12:54 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 820F9286E0; Fri, 17 Mar 2017 16:12:54 +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=-1.9 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,FREEMAIL_FROM autolearn=ham version=3.3.1 Received: from bombadil.infradead.org (bombadil.infradead.org [65.50.211.133]) (using TLSv1.2 with cipher AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id ECFF2286DC for ; Fri, 17 Mar 2017 16:12:53 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20170209; h=Sender: Content-Transfer-Encoding:Content-Type:Cc:List-Subscribe:List-Help:List-Post: List-Archive:List-Unsubscribe:List-Id:MIME-Version:Date:Message-ID:Subject: From:To:Reply-To:Content-ID:Content-Description:Resent-Date:Resent-From: Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:In-Reply-To:References: List-Owner; bh=O5G4nam+FJA9YGvXTCO2Lq7Z736fs07rvbWk9+S6SGs=; b=qfrNCjXFwtIDr7 zbp3RI6UbTViupPN5K4mewrNHWJJ4poD52ySBOQ9W9vzoAVKIyhpyVMP9fO5l45r+rKsW97/tClHn YMXobP+tGOCb9L25H6QqpnlwobHNwOjKf89HETKoO98fUPRZOTodEOZohIY6Jkr523gTgiHYpBqf2 kfE++qndZgZEGsOM913btXuNmnE9I254tnpWpsjhvNxdMFLgLgEUBIiaqQ2QTmxPvHu/ADiEqufeM NZanJ9E1zqukhtWmDfOlfHw0o/s26jccHJggyaDUncWpE01Qmmiiaj4pFqObvYoCbHFNgTXrIQAUu 5Asum+gSz03hpJsmq6dQ==; Received: from localhost ([127.0.0.1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.87 #1 (Red Hat Linux)) id 1couUd-0004Us-Bm; Fri, 17 Mar 2017 16:12:43 +0000 Received: from smtp5-g21.free.fr ([212.27.42.5]) by bombadil.infradead.org with esmtps (Exim 4.87 #1 (Red Hat Linux)) id 1couUY-0004NA-0s for linux-arm-kernel@lists.infradead.org; Fri, 17 Mar 2017 16:12:41 +0000 Received: from [172.27.0.114] (unknown [92.154.11.170]) (Authenticated sender: slash.tmp) by smtp5-g21.free.fr (Postfix) with ESMTPSA id D0E805FFFD; Fri, 17 Mar 2017 17:11:51 +0100 (CET) To: Bjorn Helgaas From: Mason Subject: [RFC PATCH v0.001] PCI: Add support for tango PCIe controller Message-ID: Date: Fri, 17 Mar 2017 17:11:50 +0100 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:51.0) Gecko/20100101 Firefox/51.0 SeaMonkey/2.48 MIME-Version: 1.0 X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20170317_091238_451271_3C80D89B X-CRM114-Status: GOOD ( 17.79 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Lorenzo Pieralisi , linux-pci , Thibaud Cornic , Liviu Dudau , David Laight , Phuong Nguyen , Robin Murphy , Linux ARM Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+patchwork-linux-arm=patchwork.kernel.org@lists.infradead.org X-Virus-Scanned: ClamAV using ClamSMTP This is version 0.001 pre-alpha. I have several questions embedded as comments in the code. Bjorn, can you tell me if something looks really wrong, or if this driver can be accepted in this shape? Regards. --- drivers/pci/host/pcie-tango.c | 125 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 125 insertions(+) create mode 100644 drivers/pci/host/pcie-tango.c diff --git a/drivers/pci/host/pcie-tango.c b/drivers/pci/host/pcie-tango.c new file mode 100644 index 000000000000..9d7fed75fd1d --- /dev/null +++ b/drivers/pci/host/pcie-tango.c @@ -0,0 +1,125 @@ +#include + +#define VENDOR_SIGMA 0x1105 + +/* + * How do I reach dev->driver_data in the config accessors? + */ +static void __iomem *mux; + +static int smp8759_config_read(struct pci_bus *bus, + unsigned int devfn, int where, int size, u32 *val) +{ + int ret; + + /* + * QUIRK #1 + * Reads in configuration space outside devfn 0 return garbage. + */ + if (devfn != 0) { + *val = 0xffffffff; /* ~0 means "nothing here" right? */ + return PCIBIOS_SUCCESSFUL; /* Should we return error or success? */ + } + + /* + * QUIRK #2 + * The root complex advertizes a fake BAR, which is used to filter + * bus-to-cpu requests. Hide it from Linux. + */ + if (where == PCI_BASE_ADDRESS_0 && bus->number == 0) { + *val = 0; /* 0 or ~0 to hide the BAR from Linux? */ + return PCIBIOS_SUCCESSFUL; /* Should we return error or success? */ + } + + /* + * QUIRK #3 + * Unfortunately, config and mem spaces are muxed. + * Linux does not support such a setting, since drivers are free + * to access mem space directly, at any time. + * Therefore, we can only PRAY that config and mem space accesses + * NEVER occur concurrently. + */ + writel(1, mux); + ret = pci_generic_config_read(bus, devfn, where, size, val); + writel(0, mux); + + return ret; +} + +static int smp8759_config_write(struct pci_bus *bus, + unsigned int devfn, int where, int size, u32 val) +{ + int ret; + + writel(1, mux); + ret = pci_generic_config_write(bus, devfn, where, size, val); + writel(0, mux); + + return ret; +} + +static struct pci_ecam_ops smp8759_ecam_ops = { + .bus_shift = 20, + .pci_ops = { + .map_bus = pci_ecam_map_bus, + .read = smp8759_config_read, + .write = smp8759_config_write, + } +}; + +static const struct of_device_id tango_pcie_ids[] = { + { .compatible = "sigma,smp8759-pcie" }, + { /* sentinel */ }, +}; + +static int tango_pcie_probe(struct platform_device *pdev) +{ + void __iomem *base; + struct resource *res; + + res = platform_get_resource(pdev, IORESOURCE_MEM, 1); + base = devm_ioremap_resource(&pdev->dev, res); + if (IS_ERR(base)) + return PTR_ERR(base); + + mux = base + 0x48; + + return pci_host_common_probe(pdev, &smp8759_ecam_ops); +} + +static struct platform_driver tango_pcie_driver = { + .probe = tango_pcie_probe, + .driver = { + .name = KBUILD_MODNAME, + .of_match_table = tango_pcie_ids, + }, +}; + +/* + * This should probably be module_platform_driver ? + */ +builtin_platform_driver(tango_pcie_driver); + +/* + * QUIRK #4 + * The root complex advertizes the wrong device class. + * Header Type 1 are handled by PCI-to-PCI bridges. + */ +static void tango_fixup_class(struct pci_dev *dev) +{ + dev->class = PCI_CLASS_BRIDGE_PCI << 8; +} +DECLARE_PCI_FIXUP_EARLY(VENDOR_SIGMA, PCI_ANY_ID, tango_fixup_class); + +/* + * QUIRK #5 + * Only transfers within the BAR are forwarded to the host. + * By default, the DMA framework expects that + * PCI address 0x8000_0000 -> CPU address 0x8000_0000 + * which is where DRAM0 is mapped. + */ +static void tango_fixup_bar(struct pci_dev *dev) +{ + pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, 0x80000000); +} +DECLARE_PCI_FIXUP_FINAL(VENDOR_SIGMA, PCI_ANY_ID, tango_fixup_bar);