From patchwork Thu Jul 22 14:40:38 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Pali_Roh=C3=A1r?= X-Patchwork-Id: 1508746 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=vger.kernel.org (client-ip=23.128.96.18; helo=vger.kernel.org; envelope-from=linux-pci-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=kernel.org header.i=@kernel.org header.a=rsa-sha256 header.s=k20201202 header.b=EcrxJBfP; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by ozlabs.org (Postfix) with ESMTP id 4GVw9X522gz9sjJ for ; Fri, 23 Jul 2021 00:40:48 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232400AbhGVOAL (ORCPT ); Thu, 22 Jul 2021 10:00:11 -0400 Received: from mail.kernel.org ([198.145.29.99]:47592 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231374AbhGVOAL (ORCPT ); Thu, 22 Jul 2021 10:00:11 -0400 Received: by mail.kernel.org (Postfix) with ESMTPSA id D412F6120D; Thu, 22 Jul 2021 14:40:45 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1626964846; bh=9tR+kRwyug5hAo8l1aHHZ0emwfS+l+16NwfPpvcJKF8=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=EcrxJBfPY7jMYJkTX5AQip5uVW8EfvWcsZZOoZuSHlraqspVCHo/rhvrNdgbxO8YE 8TxsM92bH4xqOq+XTF4eKJZt4VQmw9RW9yG6LdrS+JlKwMnO8mTlB3OxlZEw3p6fRf IQ23jW0cAqKcT92VN90IySobX0KpL+k9ko7XsgdhU8pmg5fGHRPHzItMaolHQxNSul aZdKbUfhDM0MAd8g0VVLnksyZYZ1qgdXcx24S1Esay27f3hxNK2Ci2oKHWZnAinxlX nrfr5/TmdZk03FCd/f5HROAnqeUVFPNb7Rl4gKsePNyGlJ8CZDpedlQSUI4e0mt7TG qqGWTglXqt1uQ== Received: by pali.im (Postfix) id DA36112D9; Thu, 22 Jul 2021 16:40:43 +0200 (CEST) From: =?utf-8?q?Pali_Roh=C3=A1r?= To: Lorenzo Pieralisi , Thomas Petazzoni , Bjorn Helgaas Cc: =?utf-8?q?Marek_Beh=C3=BAn?= , linux-pci@vger.kernel.org, linux-kernel@vger.kernel.org, Evan Wang , Victor Gu Subject: [PATCH v2 1/4] PCI: aardvark: Fix checking for PIO status Date: Thu, 22 Jul 2021 16:40:38 +0200 Message-Id: <20210722144041.12661-2-pali@kernel.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20210722144041.12661-1-pali@kernel.org> References: <20210624213345.3617-1-pali@kernel.org> <20210722144041.12661-1-pali@kernel.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-pci@vger.kernel.org From: Evan Wang There is an issue that when PCIe switch is connected to an Armada 3700 board, there will be lots of warnings about PIO errors when reading the config space. According to Aardvark PIO read and write sequence in HW specification, the current way to check PIO status has the following issues: 1) For PIO read operation, it reports the error message, which should be avoided according to HW specification. 2) For PIO read and write operations, it only checks PIO operation complete status, which is not enough, and error status should also be checked. This patch aligns the code with Aardvark PIO read and write sequence in HW specification on PIO status check and fix the warnings when reading config space. Signed-off-by: Evan Wang Reviewed-by: Victor Gu Tested-by: Victor Gu [pali: Fix CRS handling when CRSSVE is not enabled] Signed-off-by: Pali Rohár Reviewed-by: Marek Behún Cc: stable@vger.kernel.org # b1bd5714472c ("PCI: aardvark: Indicate error in 'val' when config read fails") --- Changes in v2: * Fixed CRS handling when CRSSVE is not enabled (which is by default as support for CRSSVE is in followup patch) --- drivers/pci/controller/pci-aardvark.c | 62 +++++++++++++++++++++++---- 1 file changed, 54 insertions(+), 8 deletions(-) diff --git a/drivers/pci/controller/pci-aardvark.c b/drivers/pci/controller/pci-aardvark.c index 2f8380a1f84f..a74ac8addeae 100644 --- a/drivers/pci/controller/pci-aardvark.c +++ b/drivers/pci/controller/pci-aardvark.c @@ -58,6 +58,7 @@ #define PIO_COMPLETION_STATUS_CRS 2 #define PIO_COMPLETION_STATUS_CA 4 #define PIO_NON_POSTED_REQ BIT(10) +#define PIO_ERR_STATUS BIT(11) #define PIO_ADDR_LS (PIO_BASE_ADDR + 0x8) #define PIO_ADDR_MS (PIO_BASE_ADDR + 0xc) #define PIO_WR_DATA (PIO_BASE_ADDR + 0x10) @@ -461,7 +462,7 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie) advk_writel(pcie, reg, PCIE_CORE_CMD_STATUS_REG); } -static void advk_pcie_check_pio_status(struct advk_pcie *pcie) +static int advk_pcie_check_pio_status(struct advk_pcie *pcie, u32 *val) { struct device *dev = &pcie->pdev->dev; u32 reg; @@ -472,14 +473,49 @@ static void advk_pcie_check_pio_status(struct advk_pcie *pcie) status = (reg & PIO_COMPLETION_STATUS_MASK) >> PIO_COMPLETION_STATUS_SHIFT; - if (!status) - return; - + /* + * According to HW spec, the PIO status check sequence as below: + * 1) even if COMPLETION_STATUS(bit9:7) indicates successful, + * it still needs to check Error Status(bit11), only when this bit + * indicates no error happen, the operation is successful. + * 2) value Unsupported Request(1) of COMPLETION_STATUS(bit9:7) only + * means a PIO write error, and for PIO read it is successful with + * a read value of 0xFFFFFFFF. + * 3) value Completion Retry Status(CRS) of COMPLETION_STATUS(bit9:7) + * only means a PIO write error, and for PIO read it is successful + * with a read value of 0xFFFF0001. + * 4) value Completer Abort (CA) of COMPLETION_STATUS(bit9:7) means + * error for both PIO read and PIO write operation. + * 5) other errors are indicated as 'unknown'. + */ switch (status) { + case PIO_COMPLETION_STATUS_OK: + if (reg & PIO_ERR_STATUS) { + strcomp_status = "COMP_ERR"; + break; + } + /* Get the read result */ + if (val) + *val = advk_readl(pcie, PIO_RD_DATA); + /* No error */ + strcomp_status = NULL; + break; case PIO_COMPLETION_STATUS_UR: strcomp_status = "UR"; break; case PIO_COMPLETION_STATUS_CRS: + /* PCIe r4.0, sec 2.3.2, says: + * If CRS Software Visibility is not enabled, the Root Complex + * must re-issue the Configuration Request as a new Request. + * A Root Complex implementation may choose to limit the number + * of Configuration Request/CRS Completion Status loops before + * determining that something is wrong with the target of the + * Request and taking appropriate action, e.g., complete the + * Request to the host as a failed transaction. + * + * To simplify implementation do not re-issue the Configuration + * Request and complete the Request as a failed transaction. + */ strcomp_status = "CRS"; break; case PIO_COMPLETION_STATUS_CA: @@ -490,6 +526,9 @@ static void advk_pcie_check_pio_status(struct advk_pcie *pcie) break; } + if (!strcomp_status) + return 0; + if (reg & PIO_NON_POSTED_REQ) str_posted = "Non-posted"; else @@ -497,6 +536,8 @@ static void advk_pcie_check_pio_status(struct advk_pcie *pcie) dev_err(dev, "%s PIO Response Status: %s, %#x @ %#x\n", str_posted, strcomp_status, reg, advk_readl(pcie, PIO_ADDR_LS)); + + return -EFAULT; } static int advk_pcie_wait_pio(struct advk_pcie *pcie) @@ -734,10 +775,13 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn, return PCIBIOS_SET_FAILED; } - advk_pcie_check_pio_status(pcie); + /* Check PIO status and get the read result */ + ret = advk_pcie_check_pio_status(pcie, val); + if (ret < 0) { + *val = 0xffffffff; + return PCIBIOS_SET_FAILED; + } - /* Get the read result */ - *val = advk_readl(pcie, PIO_RD_DATA); if (size == 1) *val = (*val >> (8 * (where & 3))) & 0xff; else if (size == 2) @@ -801,7 +845,9 @@ static int advk_pcie_wr_conf(struct pci_bus *bus, u32 devfn, if (ret < 0) return PCIBIOS_SET_FAILED; - advk_pcie_check_pio_status(pcie); + ret = advk_pcie_check_pio_status(pcie, NULL); + if (ret < 0) + return PCIBIOS_SET_FAILED; return PCIBIOS_SUCCESSFUL; } From patchwork Thu Jul 22 14:40:39 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Pali_Roh=C3=A1r?= X-Patchwork-Id: 1508748 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=vger.kernel.org (client-ip=23.128.96.18; helo=vger.kernel.org; envelope-from=linux-pci-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=kernel.org header.i=@kernel.org header.a=rsa-sha256 header.s=k20201202 header.b=eb3fufsY; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by ozlabs.org (Postfix) with ESMTP id 4GVw9Y0LXMz9snk for ; Fri, 23 Jul 2021 00:40:49 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232434AbhGVOAL (ORCPT ); Thu, 22 Jul 2021 10:00:11 -0400 Received: from mail.kernel.org ([198.145.29.99]:47614 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232105AbhGVOAL (ORCPT ); Thu, 22 Jul 2021 10:00:11 -0400 Received: by mail.kernel.org (Postfix) with ESMTPSA id 4FB1261285; Thu, 22 Jul 2021 14:40:46 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1626964846; bh=AGW0hEbHDYJfNl3F7CYdm1S5nOzQVn1ScB3D2nURFRU=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=eb3fufsYCU4t7fcug59aWAmrzfXf1tFWAQ+4babi5AQuBdAi+RH23vQgyPO+5OxRf 5vPeVJKu1DTIBzcFK6K/Wh7WFjNoiUkRL7oM6cMq5mLtXpP5r1TbZZiAiYbLb9mPv6 RzXGkpOJpBxc3rq2BNur2l1KD4hr7nJR5jcjG5oOpMp4EBG80v79aG6y6h45N6Muif SKcL76bcbZMwjdfHZ+oP4K7xf5hl59tdVuLQddvmRe6C6keBwO7G14C8YEKbV+u1F2 bPK0NigCGyZhSazT3SKsMCYnGejxfecvLkAl27ZnVnycOJKae/asLmmPn8xfkS3Hhq 5itqPDCGjrIqQ== Received: by pali.im (Postfix) id 72076133C; Thu, 22 Jul 2021 16:40:44 +0200 (CEST) From: =?utf-8?q?Pali_Roh=C3=A1r?= To: Lorenzo Pieralisi , Thomas Petazzoni , Bjorn Helgaas Cc: =?utf-8?q?Marek_Beh=C3=BAn?= , linux-pci@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v2 2/4] PCI: aardvark: Increase polling delay to 1.5s while waiting for PIO response Date: Thu, 22 Jul 2021 16:40:39 +0200 Message-Id: <20210722144041.12661-3-pali@kernel.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20210722144041.12661-1-pali@kernel.org> References: <20210624213345.3617-1-pali@kernel.org> <20210722144041.12661-1-pali@kernel.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-pci@vger.kernel.org Measurements in different conditions showed that aardvark hardware PIO response can take up to 1.44s. Increase wait timeout from 1ms to 1.5s to ensure that we do not miss responses from hardware. After 1.44s hardware returns errors (e.g. Completer abort). The previous two patches fixed checking for PIO status, so now we can use it to also catch errors which are reported by hardware after 1.44s. After applying this patch, kernel can detect and print PIO errors to dmesg: [ 6.879999] advk-pcie d0070000.pcie: Non-posted PIO Response Status: CA, 0xe00 @ 0x100004 [ 6.896436] advk-pcie d0070000.pcie: Posted PIO Response Status: COMP_ERR, 0x804 @ 0x100004 [ 6.913049] advk-pcie d0070000.pcie: Posted PIO Response Status: COMP_ERR, 0x804 @ 0x100010 [ 6.929663] advk-pcie d0070000.pcie: Non-posted PIO Response Status: CA, 0xe00 @ 0x100010 [ 6.953558] advk-pcie d0070000.pcie: Posted PIO Response Status: COMP_ERR, 0x804 @ 0x100014 [ 6.970170] advk-pcie d0070000.pcie: Non-posted PIO Response Status: CA, 0xe00 @ 0x100014 [ 6.994328] advk-pcie d0070000.pcie: Posted PIO Response Status: COMP_ERR, 0x804 @ 0x100004 Without this patch kernel prints only a generic error to dmesg: [ 5.246847] advk-pcie d0070000.pcie: config read/write timed out Signed-off-by: Pali Rohár Reviewed-by: Marek Behún Cc: stable@vger.kernel.org # 7fbcb5da811b ("PCI: aardvark: Don't rely on jiffies while holding spinlock") --- drivers/pci/controller/pci-aardvark.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pci/controller/pci-aardvark.c b/drivers/pci/controller/pci-aardvark.c index a74ac8addeae..ebb48530024c 100644 --- a/drivers/pci/controller/pci-aardvark.c +++ b/drivers/pci/controller/pci-aardvark.c @@ -166,7 +166,7 @@ #define PCIE_CONFIG_WR_TYPE0 0xa #define PCIE_CONFIG_WR_TYPE1 0xb -#define PIO_RETRY_CNT 500 +#define PIO_RETRY_CNT 750000 /* 1.5 s */ #define PIO_RETRY_DELAY 2 /* 2 us*/ #define LINK_WAIT_MAX_RETRIES 10 From patchwork Thu Jul 22 14:40:40 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Pali_Roh=C3=A1r?= X-Patchwork-Id: 1508749 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=vger.kernel.org (client-ip=23.128.96.18; helo=vger.kernel.org; envelope-from=linux-pci-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=kernel.org header.i=@kernel.org header.a=rsa-sha256 header.s=k20201202 header.b=DiE6QIOC; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by ozlabs.org (Postfix) with ESMTP id 4GVw9Y3rhHz9sxS for ; Fri, 23 Jul 2021 00:40:49 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230343AbhGVOAM (ORCPT ); Thu, 22 Jul 2021 10:00:12 -0400 Received: from mail.kernel.org ([198.145.29.99]:47636 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232429AbhGVOAL (ORCPT ); Thu, 22 Jul 2021 10:00:11 -0400 Received: by mail.kernel.org (Postfix) with ESMTPSA id C66056128C; Thu, 22 Jul 2021 14:40:46 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1626964846; bh=5i956wmocYZv/fXWLyy+L9k7cUXLx3EZOFVHb1Ot4MQ=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=DiE6QIOCVuO+WT+Yye7PVSzICtVMmecpOXl0uCEe7x+4ITML7aez+uh7VV+3sGRrs NrwOVUBtFFaBI/9m08Gh6nHg0wRhi6A8SZqyzijM/hVla0gv5VGGLQpFBFdRZu/ri0 5yGEGK4u0Ql4nKUxhEVwMHuavGpyTeWwDBSD2Oz8wSOwCQMp1TtVdptU6eFqmFv2Rm R4sOgOBjdkQnAnpXVyYegOd6N2GM8b4EiMGGIuJtZ0UPRv9+/tKVr4WdnMJMyuHV4s iEJei+tkZdfJynRmtXvAFs0ZX24Trzkws3T9oAeK/6sK0aGCsOwERrDlRnFup8QOYo PKhrlm4O3uN1Q== Received: by pali.im (Postfix) id 01D9E13D6; Thu, 22 Jul 2021 16:40:44 +0200 (CEST) From: =?utf-8?q?Pali_Roh=C3=A1r?= To: Lorenzo Pieralisi , Thomas Petazzoni , Bjorn Helgaas Cc: =?utf-8?q?Marek_Beh=C3=BAn?= , linux-pci@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v2 3/4] PCI: pci-bridge-emul: Add PCIe Root Capabilities Register Date: Thu, 22 Jul 2021 16:40:40 +0200 Message-Id: <20210722144041.12661-4-pali@kernel.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20210722144041.12661-1-pali@kernel.org> References: <20210624213345.3617-1-pali@kernel.org> <20210722144041.12661-1-pali@kernel.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-pci@vger.kernel.org The 16-bit Root Capabilities register is at offset 0x1e in the PCIe Capability. Rename current 'rsvd' struct member to 'rootcap'. Signed-off-by: Pali Rohár Reviewed-by: Marek Behún --- drivers/pci/pci-bridge-emul.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/pci/pci-bridge-emul.h b/drivers/pci/pci-bridge-emul.h index b31883022a8e..49bbd37ee318 100644 --- a/drivers/pci/pci-bridge-emul.h +++ b/drivers/pci/pci-bridge-emul.h @@ -54,7 +54,7 @@ struct pci_bridge_emul_pcie_conf { __le16 slotctl; __le16 slotsta; __le16 rootctl; - __le16 rsvd; + __le16 rootcap; __le32 rootsta; __le32 devcap2; __le16 devctl2; From patchwork Thu Jul 22 14:40:41 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Pali_Roh=C3=A1r?= X-Patchwork-Id: 1508750 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=vger.kernel.org (client-ip=23.128.96.18; helo=vger.kernel.org; envelope-from=linux-pci-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=kernel.org header.i=@kernel.org header.a=rsa-sha256 header.s=k20201202 header.b=ry5wjePs; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by ozlabs.org (Postfix) with ESMTP id 4GVw9Y6B6fz9shx for ; Fri, 23 Jul 2021 00:40:49 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232440AbhGVOAN (ORCPT ); Thu, 22 Jul 2021 10:00:13 -0400 Received: from mail.kernel.org ([198.145.29.99]:47660 "EHLO mail.kernel.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232437AbhGVOAM (ORCPT ); Thu, 22 Jul 2021 10:00:12 -0400 Received: by mail.kernel.org (Postfix) with ESMTPSA id 5E2AE6135B; Thu, 22 Jul 2021 14:40:47 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=kernel.org; s=k20201202; t=1626964847; bh=e3z/cs4Ve/WGfWG2UNadwndIAWLqSwkZCOlXnCd1+CA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=ry5wjePs9UZpdZkhZZUvwYGXDDqjM3XeEtSPQ7Z1V86JfkR8F2dIuql+XzUdD1JlQ qZu7NYjZd2XjcL41rlsU6x06+YfN4OiarChFBqGvs20PmcojuB/OTIXFZMYmDG6YW1 O7Y0QFhDe4P8JRBfkio/JBjoiA/ZdRjvPHURLLP1oAiHR70v1/4VEbWzijJGezhDOp 7T3bFrvDCVERVhkvTkkWBWd85de5eYWxhcRQV1+ONYuWWrpV0f9mMoaFEggDeQWt29 AQoDWApO/CPM71jdM+KeEu79eSQ7/wWythcbfCMweTMfvcX/Sm5GNbYNzpCNSpSisl 8/SJBwDtO6rrA== Received: by pali.im (Postfix) id 8A4AD13E7; Thu, 22 Jul 2021 16:40:45 +0200 (CEST) From: =?utf-8?q?Pali_Roh=C3=A1r?= To: Lorenzo Pieralisi , Thomas Petazzoni , Bjorn Helgaas Cc: =?utf-8?q?Marek_Beh=C3=BAn?= , linux-pci@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v2 4/4] PCI: aardvark: Fix reporting CRS value Date: Thu, 22 Jul 2021 16:40:41 +0200 Message-Id: <20210722144041.12661-5-pali@kernel.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20210722144041.12661-1-pali@kernel.org> References: <20210624213345.3617-1-pali@kernel.org> <20210722144041.12661-1-pali@kernel.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-pci@vger.kernel.org Set CRSVIS flag in emulated root PCI bridge to indicate support for Completion Retry Status. Add check for CRSSVE flag from root PCI brige when issuing Configuration Read Request via PIO to correctly returns fabricated CRS value as it is required by PCIe spec. Signed-off-by: Pali Rohár Fixes: 8a3ebd8de328 ("PCI: aardvark: Implement emulated root PCI bridge config space") Cc: stable@vger.kernel.org # e0d9d30b7354 ("PCI: pci-bridge-emul: Fix big-endian support") --- drivers/pci/controller/pci-aardvark.c | 67 +++++++++++++++++++++++++-- 1 file changed, 63 insertions(+), 4 deletions(-) diff --git a/drivers/pci/controller/pci-aardvark.c b/drivers/pci/controller/pci-aardvark.c index ebb48530024c..abc93225ba20 100644 --- a/drivers/pci/controller/pci-aardvark.c +++ b/drivers/pci/controller/pci-aardvark.c @@ -177,6 +177,8 @@ #define MSI_IRQ_NUM 32 +#define CFG_RD_CRS_VAL 0xffff0001 + struct advk_pcie { struct platform_device *pdev; void __iomem *base; @@ -462,7 +464,7 @@ static void advk_pcie_setup_hw(struct advk_pcie *pcie) advk_writel(pcie, reg, PCIE_CORE_CMD_STATUS_REG); } -static int advk_pcie_check_pio_status(struct advk_pcie *pcie, u32 *val) +static int advk_pcie_check_pio_status(struct advk_pcie *pcie, bool allow_crs, u32 *val) { struct device *dev = &pcie->pdev->dev; u32 reg; @@ -504,9 +506,30 @@ static int advk_pcie_check_pio_status(struct advk_pcie *pcie, u32 *val) strcomp_status = "UR"; break; case PIO_COMPLETION_STATUS_CRS: + if (allow_crs && val) { + /* PCIe r4.0, sec 2.3.2, says: + * If CRS Software Visibility is enabled: + * For a Configuration Read Request that includes both + * bytes of the Vendor ID field of a device Function's + * Configuration Space Header, the Root Complex must + * complete the Request to the host by returning a + * read-data value of 0001h for the Vendor ID field and + * all '1's for any additional bytes included in the + * request. + * + * So CRS in this case is not an error status. + */ + *val = CFG_RD_CRS_VAL; + strcomp_status = NULL; + break; + } /* PCIe r4.0, sec 2.3.2, says: * If CRS Software Visibility is not enabled, the Root Complex * must re-issue the Configuration Request as a new Request. + * If CRS Software Visibility is enabled: For a Configuration + * Write Request or for any other Configuration Read Request, + * the Root Complex must re-issue the Configuration Request as + * a new Request. * A Root Complex implementation may choose to limit the number * of Configuration Request/CRS Completion Status loops before * determining that something is wrong with the target of the @@ -575,6 +598,7 @@ advk_pci_bridge_emul_pcie_conf_read(struct pci_bridge_emul *bridge, case PCI_EXP_RTCTL: { u32 val = advk_readl(pcie, PCIE_ISR0_MASK_REG); *value = (val & PCIE_MSG_PM_PME_MASK) ? 0 : PCI_EXP_RTCTL_PMEIE; + *value |= PCI_EXP_RTCAP_CRSVIS << 16; return PCI_BRIDGE_EMUL_HANDLED; } @@ -656,6 +680,7 @@ static struct pci_bridge_emul_ops advk_pci_bridge_emul_ops = { static int advk_sw_pci_bridge_init(struct advk_pcie *pcie) { struct pci_bridge_emul *bridge = &pcie->bridge; + int ret; bridge->conf.vendor = cpu_to_le16(advk_readl(pcie, PCIE_CORE_DEV_ID_REG) & 0xffff); @@ -679,7 +704,15 @@ static int advk_sw_pci_bridge_init(struct advk_pcie *pcie) bridge->data = pcie; bridge->ops = &advk_pci_bridge_emul_ops; - return pci_bridge_emul_init(bridge, 0); + /* PCIe config space can be initialized after pci_bridge_emul_init() */ + ret = pci_bridge_emul_init(bridge, 0); + if (ret < 0) + return ret; + + /* Indicates supports for Completion Retry Status */ + bridge->pcie_conf.rootcap = cpu_to_le16(PCI_EXP_RTCAP_CRSVIS); + + return 0; } static bool advk_pcie_valid_device(struct advk_pcie *pcie, struct pci_bus *bus, @@ -731,6 +764,7 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn, int where, int size, u32 *val) { struct advk_pcie *pcie = bus->sysdata; + bool allow_crs; u32 reg; int ret; @@ -743,7 +777,24 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn, return pci_bridge_emul_conf_read(&pcie->bridge, where, size, val); + /* + * Completion Retry Status is possible to return only when reading all + * 4 bytes from PCI_VENDOR_ID and PCI_DEVICE_ID registers at once and + * CRSSVE flag on Root Bridge is enabled. + */ + allow_crs = (where == PCI_VENDOR_ID) && (size == 4) && + (le16_to_cpu(pcie->bridge.pcie_conf.rootctl) & + PCI_EXP_RTCTL_CRSSVE); + if (advk_pcie_pio_is_running(pcie)) { + /* + * If it is possible return Completion Retry Status so caller + * tries to issue the request again instead of failing. + */ + if (allow_crs) { + *val = CFG_RD_CRS_VAL; + return PCIBIOS_SUCCESSFUL; + } *val = 0xffffffff; return PCIBIOS_SET_FAILED; } @@ -771,12 +822,20 @@ static int advk_pcie_rd_conf(struct pci_bus *bus, u32 devfn, ret = advk_pcie_wait_pio(pcie); if (ret < 0) { + /* + * If it is possible return Completion Retry Status so caller + * tries to issue the request again instead of failing. + */ + if (allow_crs) { + *val = CFG_RD_CRS_VAL; + return PCIBIOS_SUCCESSFUL; + } *val = 0xffffffff; return PCIBIOS_SET_FAILED; } /* Check PIO status and get the read result */ - ret = advk_pcie_check_pio_status(pcie, val); + ret = advk_pcie_check_pio_status(pcie, allow_crs, val); if (ret < 0) { *val = 0xffffffff; return PCIBIOS_SET_FAILED; @@ -845,7 +904,7 @@ static int advk_pcie_wr_conf(struct pci_bus *bus, u32 devfn, if (ret < 0) return PCIBIOS_SET_FAILED; - ret = advk_pcie_check_pio_status(pcie, NULL); + ret = advk_pcie_check_pio_status(pcie, false, NULL); if (ret < 0) return PCIBIOS_SET_FAILED;