Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/arm/imx Fixed bug when using PCIe external clock.
details: https://anonhg.NetBSD.org/src/rev/878ef1bb7f61
branches: trunk
changeset: 464667:878ef1bb7f61
user: hkenken <hkenken%NetBSD.org@localhost>
date: Wed Oct 16 11:16:30 2019 +0000
description:
Fixed bug when using PCIe external clock.
diffstat:
sys/arch/arm/imx/fdt/imx6_pcie.c | 28 ++++----------
sys/arch/arm/imx/imx6_pcie.c | 22 +++++-----
sys/arch/arm/imx/imxpcie.c | 76 ++++++++++++++++++++++++---------------
sys/arch/arm/imx/imxpciereg.h | 28 +++++++-------
sys/arch/arm/imx/imxpcievar.h | 8 ++--
5 files changed, 83 insertions(+), 79 deletions(-)
diffs (truncated from 325 to 300 lines):
diff -r 772efcbce5e5 -r 878ef1bb7f61 sys/arch/arm/imx/fdt/imx6_pcie.c
--- a/sys/arch/arm/imx/fdt/imx6_pcie.c Wed Oct 16 07:42:22 2019 +0000
+++ b/sys/arch/arm/imx/fdt/imx6_pcie.c Wed Oct 16 11:16:30 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imx6_pcie.c,v 1.4 2019/09/02 01:28:41 hkenken Exp $ */
+/* $NetBSD: imx6_pcie.c,v 1.5 2019/10/16 11:16:30 hkenken Exp $ */
/*-
* Copyright (c) 2019 Genetec Corporation. All rights reserved.
* Written by Hashimoto Kenichi for Genetec Corporation.
@@ -25,7 +25,7 @@
* SUCH DAMAGE.
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: imx6_pcie.c,v 1.4 2019/09/02 01:28:41 hkenken Exp $");
+__KERNEL_RCSID(0, "$NetBSD: imx6_pcie.c,v 1.5 2019/10/16 11:16:30 hkenken Exp $");
#include "opt_pci.h"
#include "opt_fdt.h"
@@ -158,18 +158,18 @@
return;
}
- sc->sc_clk_pcie_axi = fdtbus_clock_get(phandle, "pcie");
- if (sc->sc_clk_pcie_axi == NULL) {
+ sc->sc_clk_pcie = fdtbus_clock_get(phandle, "pcie");
+ if (sc->sc_clk_pcie == NULL) {
aprint_error(": couldn't get clock pcie_axi\n");
return;
}
- sc->sc_clk_lvds1_gate = fdtbus_clock_get(phandle, "pcie_bus");
- if (sc->sc_clk_lvds1_gate == NULL) {
+ sc->sc_clk_pcie_bus = fdtbus_clock_get(phandle, "pcie_bus");
+ if (sc->sc_clk_pcie_bus == NULL) {
aprint_error(": couldn't get clock lvds1_gate\n");
return;
}
- sc->sc_clk_pcie_ref = fdtbus_clock_get(phandle, "pcie_phy");
- if (sc->sc_clk_pcie_ref == NULL) {
+ sc->sc_clk_pcie_phy = fdtbus_clock_get(phandle, "pcie_phy");
+ if (sc->sc_clk_pcie_phy == NULL) {
aprint_error(": couldn't get clock pcie_ref\n");
return;
}
@@ -198,18 +198,6 @@
aprint_error(": couldn't get clock pcie_ext_src\n");
return;
}
-
- struct clk *clk_lvds1_in = imx6_get_clock("lvds1_in");
- if (clk_lvds1_in == NULL) {
- aprint_error(": couldn't get clock lvds1_in\n");
- return;
- }
- int error = clk_set_parent(sc->sc_clk_pcie_ext_src, clk_lvds1_in);
- if (error) {
- aprint_error_dev(sc->sc_dev,
- "couldn't set '%s' parent to '%s': %d\n",
- sc->sc_clk_pcie_ext_src->name, clk_lvds1_in->name, error);
- }
} else {
sc->sc_ext_osc = false;
sc->sc_clk_pcie_ext = NULL;
diff -r 772efcbce5e5 -r 878ef1bb7f61 sys/arch/arm/imx/imx6_pcie.c
--- a/sys/arch/arm/imx/imx6_pcie.c Wed Oct 16 07:42:22 2019 +0000
+++ b/sys/arch/arm/imx/imx6_pcie.c Wed Oct 16 11:16:30 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imx6_pcie.c,v 1.13 2019/07/27 08:02:04 skrll Exp $ */
+/* $NetBSD: imx6_pcie.c,v 1.14 2019/10/16 11:16:30 hkenken Exp $ */
/*
* Copyright (c) 2016 Genetec Corporation. All rights reserved.
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: imx6_pcie.c,v 1.13 2019/07/27 08:02:04 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: imx6_pcie.c,v 1.14 2019/10/16 11:16:30 hkenken Exp $");
#include "opt_pci.h"
@@ -151,19 +151,19 @@
imx6_set_gpio(self, "imxpcie-reset-gpio", &ipsc->sc_gpio_reset,
&ipsc->sc_gpio_reset_active, GPIO_PIN_OUTPUT);
- sc->sc_clk_pcie_axi = imx6_get_clock("pcie_axi");
- if (sc->sc_clk_pcie_axi == NULL) {
- aprint_error(": couldn't get clock pcie_axi\n");
+ sc->sc_clk_pcie = imx6_get_clock("pcie_axi");
+ if (sc->sc_clk_pcie == NULL) {
+ aprint_error(": couldn't get clock pcie\n");
return;
}
- sc->sc_clk_lvds1_gate = imx6_get_clock("lvds1_gate");
- if (sc->sc_clk_lvds1_gate == NULL) {
- aprint_error(": couldn't get clock lvds1_gate\n");
+ sc->sc_clk_pcie_bus = imx6_get_clock("lvds1_gate");
+ if (sc->sc_clk_pcie_bus == NULL) {
+ aprint_error(": couldn't get clock pcie_bus\n");
return;
}
- sc->sc_clk_pcie_ref = imx6_get_clock("pcie_ref_125m");
- if (sc->sc_clk_pcie_ref == NULL) {
- aprint_error(": couldn't get clock pcie_ref\n");
+ sc->sc_clk_pcie_phy = imx6_get_clock("pcie_ref_125m");
+ if (sc->sc_clk_pcie_phy == NULL) {
+ aprint_error(": couldn't get clock pcie_phy\n");
return;
}
diff -r 772efcbce5e5 -r 878ef1bb7f61 sys/arch/arm/imx/imxpcie.c
--- a/sys/arch/arm/imx/imxpcie.c Wed Oct 16 07:42:22 2019 +0000
+++ b/sys/arch/arm/imx/imxpcie.c Wed Oct 16 11:16:30 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imxpcie.c,v 1.2 2019/09/02 01:28:41 hkenken Exp $ */
+/* $NetBSD: imxpcie.c,v 1.3 2019/10/16 11:16:30 hkenken Exp $ */
/*
* Copyright (c) 2019 Genetec Corporation. All rights reserved.
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: imxpcie.c,v 1.2 2019/09/02 01:28:41 hkenken Exp $");
+__KERNEL_RCSID(0, "$NetBSD: imxpcie.c,v 1.3 2019/10/16 11:16:30 hkenken Exp $");
#include "opt_pci.h"
#include "opt_fdt.h"
@@ -133,6 +133,7 @@
v |= __SHIFTIN(20, IOMUX_GPR8_PCS_TX_DEEMPH_GEN1);
sc->sc_gpr_write(sc, IOMUX_GPR8, v);
+ v = sc->sc_gpr_read(sc, IOMUX_GPR12);
v &= ~IOMUX_GPR12_DEVICE_TYPE;
v |= IOMUX_GPR12_DEVICE_TYPE_PCIE_RC;
sc->sc_gpr_write(sc, IOMUX_GPR12, v);
@@ -244,12 +245,12 @@
static int
imxpcie_assert_core_reset(struct imxpcie_softc *sc)
{
+ uint32_t gpr1 = sc->sc_gpr_read(sc, IOMUX_GPR1);
+
if (sc->sc_have_sw_reset) {
- uint32_t gpr1 = sc->sc_gpr_read(sc, IOMUX_GPR1);
gpr1 |= IOMUX_GPR1_PCIE_SW_RST;
sc->sc_gpr_write(sc, IOMUX_GPR1, gpr1);
} else {
- uint32_t gpr1 = sc->sc_gpr_read(sc, IOMUX_GPR1);
uint32_t gpr12 = sc->sc_gpr_read(sc, IOMUX_GPR12);
/* already enabled by bootloader */
@@ -263,12 +264,12 @@
gpr12 &= ~IOMUX_GPR12_APP_LTSSM_ENABLE;
sc->sc_gpr_write(sc, IOMUX_GPR12, gpr12);
}
+ }
- gpr1 |= IOMUX_GPR1_TEST_POWERDOWN;
- sc->sc_gpr_write(sc, IOMUX_GPR1, gpr1);
- gpr1 &= ~IOMUX_GPR1_REF_SSP_EN;
- sc->sc_gpr_write(sc, IOMUX_GPR1, gpr1);
- }
+ gpr1 |= IOMUX_GPR1_TEST_POWERDOWN;
+ sc->sc_gpr_write(sc, IOMUX_GPR1, gpr1);
+ gpr1 &= ~IOMUX_GPR1_REF_SSP_EN;
+ sc->sc_gpr_write(sc, IOMUX_GPR1, gpr1);
return 0;
}
@@ -278,29 +279,28 @@
{
int error;
- error = clk_enable(sc->sc_clk_pcie_axi);
+ error = clk_enable(sc->sc_clk_pcie);
if (error) {
- aprint_error_dev(sc->sc_dev, "couldn't enable pcie_axi: %d\n", error);
+ aprint_error_dev(sc->sc_dev, "couldn't enable pcie: %d\n", error);
return error;
}
if (sc->sc_ext_osc) {
- clk_set_parent(sc->sc_clk_pcie_ext, sc->sc_clk_pcie_ext_src);
error = clk_enable(sc->sc_clk_pcie_ext);
if (error) {
aprint_error_dev(sc->sc_dev, "couldn't enable ext: %d\n", error);
return error;
}
} else {
- error = clk_enable(sc->sc_clk_lvds1_gate);
+ error = clk_enable(sc->sc_clk_pcie_bus);
if (error) {
- aprint_error_dev(sc->sc_dev, "couldn't enable lvds1_gate: %d\n",
+ aprint_error_dev(sc->sc_dev, "couldn't enable pcie_bus: %d\n",
error);
return error;
}
}
- error = clk_enable(sc->sc_clk_pcie_ref);
+ error = clk_enable(sc->sc_clk_pcie_phy);
if (error) {
aprint_error_dev(sc->sc_dev, "couldn't enable pcie_ref: %d\n", error);
return error;
@@ -328,24 +328,40 @@
delay(200);
}
- if (sc->sc_ext_osc) {
- delay(5 * 1000);
+ uint64_t rate;
+ if (sc->sc_ext_osc)
+ rate = clk_get_rate(sc->sc_clk_pcie_ext);
+ else
+ rate = clk_get_rate(sc->sc_clk_pcie_phy);
+ aprint_normal_dev(sc->sc_dev, "PCIe ref clk %d MHz\n", (int)(rate / 1000 / 1000));
- uint32_t val;
- val = imxpcie_phy_read(sc, PCIE_PHY_MPLL_OVRD_IN_LO);
- val &= ~MPLL_MULTIPLIER;
- val |= __SHIFTIN(0x19, MPLL_MULTIPLIER);
- val |= MPLL_MULTIPLIER_OVRD;
- imxpcie_phy_write(sc, PCIE_PHY_MPLL_OVRD_IN_LO, val);
+ int mult;
+ int div;
+ if (rate == 100000000) {
+ mult = 25;
+ div = 0;
+ } else if (rate == 125000000) {
+ mult = 40;
+ div = 1;
+ } else if (rate == 200000000) {
+ mult = 25;
+ div = 1;
+ } else {
+ return -1;
+ }
- delay(5 * 1000);
+ uint32_t val;
+ val = imxpcie_phy_read(sc, PCIE_PHY_MPLL_OVRD_IN_LO);
+ val &= ~MPLL_MULTIPLIER;
+ val |= __SHIFTIN(mult, MPLL_MULTIPLIER);
+ val |= MPLL_MULTIPLIER_OVRD;
+ imxpcie_phy_write(sc, PCIE_PHY_MPLL_OVRD_IN_LO, val);
- val = imxpcie_phy_read(sc, PCIE_PHY_ATEOVRD);
- val |= REF_USB2_EN;
- imxpcie_phy_write(sc, PCIE_PHY_ATEOVRD, val);
-
- delay(5 * 1000);
- }
+ val = imxpcie_phy_read(sc, PCIE_PHY_ATEOVRD);
+ val &= ~REF_CLKDIV2;
+ val |= __SHIFTIN(div, REF_CLKDIV2);
+ val |= ATEOVRD_EN;
+ imxpcie_phy_write(sc, PCIE_PHY_ATEOVRD, val);
return 0;
}
diff -r 772efcbce5e5 -r 878ef1bb7f61 sys/arch/arm/imx/imxpciereg.h
--- a/sys/arch/arm/imx/imxpciereg.h Wed Oct 16 07:42:22 2019 +0000
+++ b/sys/arch/arm/imx/imxpciereg.h Wed Oct 16 11:16:30 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imxpciereg.h,v 1.2 2019/09/02 01:28:41 hkenken Exp $ */
+/* $NetBSD: imxpciereg.h,v 1.3 2019/10/16 11:16:30 hkenken Exp $ */
/*
* Copyright (c) 2015 Ryo Shimizu <ryo%nerv.org@localhost>
@@ -220,21 +220,21 @@
#define PCIE_PHY_SS_PHASE 0x0005
#define PCIE_PHY_SS_FREQ 0x0006
#define PCIE_PHY_ATEOVRD 0x0010
-#define ATEOVRD_EN __BIT(3)
-#define REF_USB2_EN __BIT(2)
-#define REF_CLKDIV2 __BIT(1)
+#define ATEOVRD_EN __BIT(2)
+#define REF_USB2_EN __BIT(1)
+#define REF_CLKDIV2 __BIT(0)
#define PCIE_PHY_MPLL_OVRD_IN_LO 0x0011
#define PCIE_PHY_MPLL_OVRD_IN_HI 0x0011
-#define RES_ACK_IN_OVRD __BIT(15)
-#define RES_ACK_IN __BIT(14)
-#define RES_REQ_IN_OVRD __BIT(13)
-#define RES_REQ_IN __BIT(12)
-#define RTUNE_REQ_OVRD __BIT(11)
-#define RTUNE_REQ __BIT(10)
-#define MPLL_MULTIPLIER_OVRD __BIT(9)
-#define MPLL_MULTIPLIER __BITS(8, 2)
-#define MPLL_EN_OVRD __BIT(1)
-#define MPLL_EN __BIT(0)
+#define RES_ACK_IN_OVRD __BIT(15)
+#define RES_ACK_IN __BIT(14)
+#define RES_REQ_IN_OVRD __BIT(13)
+#define RES_REQ_IN __BIT(12)
+#define RTUNE_REQ_OVRD __BIT(11)
+#define RTUNE_REQ __BIT(10)
+#define MPLL_MULTIPLIER_OVRD __BIT(9)
+#define MPLL_MULTIPLIER __BITS(8, 2)
+#define MPLL_EN_OVRD __BIT(1)
+#define MPLL_EN __BIT(0)
Home |
Main Index |
Thread Index |
Old Index