imx8mm PCI enabling issues.

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

imx8mm PCI enabling issues.

Jump to solution
5,666 Views
mariusoctavian
Contributor III

Hi,
I have a custom board imx8mm. I am trying to enable the PCI1

This is on kernel: 5.10.

Is failing here. I am into this for 3 days already. I tried so many variants for the dtsi and I cannot pass this error

XXX Failed to get 'pciephy' reset control

 

 

[    3.578885] imx6q-pcie 33800000.pcie: XXX imx6_pcie_VARIANT = 5 XX
[    3.612272] imx6q-pcie 33800000.pcie:  reset_get exclusive failed for pciephy 
[    3.624251] imx6q-pcie 33800000.pcie: ?? XXX Failed to get 'pciephy' reset control -517

 

 

 

 

 

 

case IMX7D:
		if (dbi_base->start == IMX8MQ_PCIE2_BASE_ADDR)
			imx6_pcie->controller_id = 1;

		imx6_pcie->pciephy_reset = devm_reset_control_get_exclusive(dev,
									    "pciephy");
		if (IS_ERR(imx6_pcie->pciephy_reset)) {
			dev_err(dev, "?? XXX Failed to get 'pciephy' reset control %d\n",
						PTR_ERR(imx6_pcie->pciephy_reset));
			return PTR_ERR(imx6_pcie->pciephy_reset);
		}

 

 

 

 

 

 

My schematic is:  (is GPIO expander not pci expander  Sorry)

pci6.png

My dts file is:

 

 

 

 

 

 

/dts-v1/;

#include <dt-bindings/misc/nad-nmb.h>
#include <dt-bindings/clock/imx8mm-clock.h>
#include <dt-bindings/reset/imx8mq-reset.h>
#include <dt-bindings/clock/imx8mq-clock.h>
#include "imx8mm-pinfunc.h"
#include "imx8mq-pinfunc.h"

#define MX8MMN(a, b)	MX8MM_##a b
#define IMX8MMN(a)      IMX8MM_##a

/ {
    /* ...  */
    // -----------------------  PCIE
	pcie0: pcie@33800000 {
		///-xx compatible = "fsl,imx8mq-pcie", "snps,dw-pcie","fsl,imx7d-pcie-phy";
		compatible = "fsl,imx8mm-pcie", "snps,dw-pcie";
		reg = <0x0 0x33800000 0x0 0x400000>,	// host config space 4M 
			  <0x0 0x32f00000 0x0 0x10000>,		// IMX_REFERENCE_MANUAL page 109*/
			  <0x0 0x1ff00000 0x0 0x80000>;			
		reg-names = "dbi", "config";
		#address-cells = <3>; // was 3
		#size-cells = <2>;
		device_type = "pci";
		///-xx bus-range = <0x00 0xff>;
		
		ranges = <0x81000000 0 0x00000000 0x1ff80000 0 0x00010000 /* downstream I/O 64KB */
				  0x82000000 0 0x18000000 0x18000000 0 0x07f00000>; /* non-prefetchable memory */
		
		num-lanes = <1>;
		num-viewport = <4>;
		interrupts = <GIC_SPI 122 IRQ_TYPE_LEVEL_HIGH>,
					 <GIC_SPI 127 IRQ_TYPE_LEVEL_HIGH>; /* eDMA */
		interrupt-names = "msi"; ///-xx, "dma";
		#interrupt-cells = <1>;
		interrupt-map-mask = <0 0 0 0x7>;
		interrupt-map = <0 0 0 1 &gic GIC_SPI 125 IRQ_TYPE_LEVEL_HIGH>,
						<0 0 0 2 &gic GIC_SPI 124 IRQ_TYPE_LEVEL_HIGH>,
						<0 0 0 3 &gic GIC_SPI 123 IRQ_TYPE_LEVEL_HIGH>,
						<0 0 0 4 &gic GIC_SPI 122 IRQ_TYPE_LEVEL_HIGH>;
		fsl,max-link-speed = <2>;
		ctrl-id = <0>;
		// --x power-domains = <&pcie_pd>;
		power-domains = <&pgc_pcie>;  // my power domain
		
		resets = <&src IMX8MQ_RESET_PCIEPHY>,//<&gpio_expander_out 8 0>
				 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_EN>,
				 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_EN>, //IMX8MQ_RESET_PCIE_CTRL_APPS_CLK_REQ>,
				 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_TURNOFF>;
		reset-names = "pciephy", "apps", "clkreq", "turnoff";
		
        clocks = <&clk IMX8MM_CLK_PCIE1_ROOT>,
                 <&clk IMX8MM_CLK_PCIE1_AUX>,
                 <&clk IMX8MM_CLK_PCIE1_PHY>,
                 <&pcie0_refclk>;
        clock-names = "pcie", "pcie_aux", "pcie_phy", "pcie_bus";  

		//fsl,imx7d-pcie-phy = <&pcie_phy>;
		status = "okay";
	};	
    
    /* ...  */
};
	
&nmb {
	/* ...  */
    // -----------------------  PCIE
	export-names =
		"reset-pcie",
		"enable-pcie";							
	export-gpios =
		<&gpio_expander_out 8 0>,
		<&gpio_expander_out 5 0>;
	export-flags =
		<NMB_GPIO_OUT_LOW>,
		<NMB_GPIO_OUT_LOW>;
    /* ...  */    
};

&iomuxc {

    // -----------------------  PCIE
	pcie0_refclk: pcie0-refclk {
		compatible = "fixed-clock";
		#clock-cells = <0>;
		clock-frequency = <100000000>;
	};
		
    // -----------------------  PCIE
	pinctrl_pcie0: pcie0grp {
		fsl,pins = <
			#define GP_PCIE0_RESET <&gpio_expander_out 8 0>
			//MX8MMN(IOMUXC_SAI3_TXFS_GPIO4_IO31, 0x100)
			#define GP_PCIE0_DISABLE <&gpio_expander_out 5 0>
			//MX8MMN(IOMUXC_GPIO1_IO04_GPIO1_IO4, 0x100)	
		>;
	};
};

// -----------------------  PCIE
&pcie0 {
	pinctrl-names = "default";
	pinctrl-0 = <&pinctrl_pcie0>;
	disable-gpio = GP_PCIE0_DISABLE;
	reset-gpio = GP_PCIE0_RESET;
	ext_osc = <0>;
	status = "okay";
    
  
};

 

 

 

 

 

 

Thank you.

 

 

0 Kudos
1 Solution
5,652 Views
igorpadykov
NXP Employee
NXP Employee

Hi Marius

 

for enabling PCIe on i.MX8M Mini one can look at NXP implementation in EVK, p.9

SCH-31407 schematic (seems it does not use PCIE_RST# signal)

 i.MX 8M Mini Evaluation Kit LPDDR4 Design Files

and sect.3.8. PCIE connectivity  i.MX 8M Mini Hardware Developer’s Guide

dts file :

https://source.codeaurora.org/external/imx/linux-imx/tree/arch/arm64/boot/dts/freescale/imx8mm-evk.d...

 

Best regards
igor

 

View solution in original post

0 Kudos
6 Replies
3,582 Views
tzeng015
Contributor II

Hi

Can I ask you a question ? How about the I210 function on your platform now ?

I have a big trouble here.  https://www.youtube.com/shorts/3jO6BhMUrl8

The attach file is error message.

 

0 Kudos
5,536 Views
mariusoctavian
Contributor III

RESOLVED

The project I was working was using kernel 5.10.0-01182 as a base
and the implementation for internal clock for PCIe was missing.
Thanks to Igor we found that in 5.10-y branch; see above answers . 
We merged (customer wanted to stick with 011.. kernel) the missing
code from imx6_pcie.c to our imx6_pcie.c.
We ran in

Failed to get PCIEPHY reset control


Later on we found that the 011.. kernel did not have the reset controller up to date
so we brought in few files from the /drivers/reset/* and some required headers from dt-binding


 

Viewing (22/30): 'drivers/reset/gpio-reset.c'
Viewing (23/30): 'drivers/reset/reset-dispmix.c'
Viewing (24/30): 'drivers/reset/reset-imx7.c'
Viewing (26/30): 'include/dt-bindings/reset/imx8mm-dispmix.h'
Viewing (27/30): 'include/dt-bindings/reset/imx8mn-dispmix.h'
Viewing (28/30): 'include/dt-bindings/reset/imx8mp-reset.h'
Viewing (29/30): 'include/dt-bindings/reset/imx8mq-reset.h'

 

 

Then we've also grabbed the Kconfig and makefile for the reset controller an enable it in the
kernel config.

Now I have the PCI up and working fine with internal clock config.


 

0 Kudos
5,569 Views
mariusoctavian
Contributor III

Hi,


We found out that in the code we had couple of errors regarding the PHY reset controllers.
We have 100%  the dts-es for the PCIE0 as from the links mentioned above for imx8mm.

We get:

Failed to get PCIEPHY reset control



https://source.codeaurora.org/external/imx/linux-imx/tree/arch/arm64/boot/dts/freescale/imx8mm.dtsi?...
and
https://source.codeaurora.org/external/imx/linux-imx/tree/arch/arm64/boot/dts/freescale/imx8mm-evk.d...

We just reconfigured the power domain accordingly.

Out power domain:

 

 

gpc: gpc@303a0000 {
				compatible = "fsl,imx8mm-gpc";
				reg = <0x303a0000 0x10000>;
				interrupts = <GIC_SPI 87 IRQ_TYPE_LEVEL_HIGH>;
				interrupt-parent = <&gic>;
				interrupt-controller;
				#interrupt-cells = <3>;

				pgc {
					#address-cells = <1>;
					#size-cells = <0>;

					pgc_hsiomix: power-domain@0 {
						#power-domain-cells = <0>;
						reg = <IMX8MM_POWER_DOMAIN_HSIOMIX>;
						clocks = <&clk IMX8MM_CLK_USB_BUS>;
					};

                     pgc_pcie: power-domain@1 {
                            #power-domain-cells = <0>;
                            reg = <IMX8MM_POWER_DOMAIN_PCIE>;
                            power-domains = <&pgc_hsiomix>;
                            clocks = <&clk IMX8MM_CLK_PCIE1_ROOT>;
                     };

 

 

And the change:

 

 

			power-domains = <&pgc_pcie>;
		
			// #define IMX8MQ_RESET_PCIEPHY			26
			resets = <&src IMX8MQ_RESET_PCIEPHY>,
					 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_EN>,
					 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_CLK_REQ>,
					 <&src IMX8MQ_RESET_PCIE_CTRL_APPS_TURNOFF>;
			reset-names = "pciephy", "apps", "clkreq", "turnoff";

 

 


Now all the calls to the reset controller fails as (we let the error go trough):

 

 

[    1.793909] imx6q-pcie 33800000.pcie: xxxx.pcie imx6_pcie_probe 2404
[    1.800640] imx6q-pcie 33800000.pcie: supply epdev_on not found, using dummy regulator
[    1.812090] imx6q-pcie 33800000.pcie: Failed to get PCIEPHY reset control
[    1.830531] imx6q-pcie 33800000.pcie: Failed to get PCIE APPS reset control
[    1.840459] imx6q-pcie 33800000.pcie: xxxx.pcie imx6_pcie_probe 2649
[    1.840472] imx6q-pcie 33800000.pcie: Failed to get TURNOFF reset control
[    1.849718] imx6q-pcie 33800000.pcie: xxxx.pcie imx6_pcie_probe 2658
[    1.863540] imx6q-pcie 33800000.pcie: Failed to get CLKREQ reset control
[    1.888080] imx6q-pcie 33800000.pcie: xxxx.pcie imx6_pcie_probe 2666

 

 


A help would be appreciated.

Thank you.




 

 

 

 

 

0 Kudos
5,653 Views
igorpadykov
NXP Employee
NXP Employee

Hi Marius

 

for enabling PCIe on i.MX8M Mini one can look at NXP implementation in EVK, p.9

SCH-31407 schematic (seems it does not use PCIE_RST# signal)

 i.MX 8M Mini Evaluation Kit LPDDR4 Design Files

and sect.3.8. PCIE connectivity  i.MX 8M Mini Hardware Developer’s Guide

dts file :

https://source.codeaurora.org/external/imx/linux-imx/tree/arch/arm64/boot/dts/freescale/imx8mm-evk.d...

 

Best regards
igor

 

0 Kudos
5,595 Views
mariusoctavian
Contributor III

Hi,

I merged the code from https://source.codeaurora.org/external/imx/linux-imx/tree/drivers/pci/controller/dwc/pci-imx6.c?h=lf... to our pci which lacked support for internal clock.

Now we pass the Phy registers setup but we end up with the message:

 

 

[    6.452989] imx6q-pcie 33800000.pcie: Phy link never came up

 

 

We also debunked the DEBUG0 and DEBUG1 registers before as in (see next excerpt )

 

static int imx6_pcie_establish_link(struct imx6_pcie *imx6_pcie)
{
	/*..removed for clarity..*/
	
	uint32_t debug0 = readl(pci->dbi_base + PCIE_PORT_DEBUG0); /// 728
	uint32_t debug1 = readl(pci->dbi_base + PCIE_PORT_DEBUG1); /// 72
	printk(" zzzzzz.pci  dbg regs %x %x \n",debug0,debug1 );
	
	/* Start LTSSM. */
	imx6_pcie_ltssm_enable(dev);
	
	ret = dw_pcie_wait_for_link(pci);
	if (ret){
		dev_err(dev, "Failed to wait for LINK.\n");
		debug0 = readl(pci->dbi_base + PCIE_PORT_DEBUG0); /// 728
		debug1 = readl(pci->dbi_base + PCIE_PORT_DEBUG1); /// 72
		
		printk(" zzzzzz.pci  dbg regs %x %x \n",debug0,debug1 );
		goto err_reset_phy;
	}
	/*..removed for clarity..*/
}

 

 

The prints we get and the register interpretation are:

 

 

[    1.490492] imx6q-pcie 33800000.pcie: PLL REF_CLK is used!.
[    2.014537] imx6q-pcie 33800000.pcie: PCIe PLL locked after 0 us.
[    2.020644] xxxx.pcie dw_pcie_dbi_ro_wr_en DONE
[    2.025358] imx6q-pcie 33800000.pcie: host bridge /soc@0/pcie@33800000 ranges:
[    2.032779] xxxx.pcie dw_pcie_dbi_ro_wr_en DONE
[    2.037419] imx6q-pcie 33800000.pcie: invalid resource  									<<<< the "atu"   entry
[    2.042567] imx6q-pcie 33800000.pcie: Resource bypassed: pci->atu_base=ffff800011f00000  <<< using reg offset for atu
[    2.057330] xxxx.pcie dw_pcie_setup_rc one
[    2.061520] xxxx.pcie dw_pcie_dbi_ro_wr_en DONE
[    2.066154] xxxx.pcie Establishing LINK link
[    2.070517] xxxx.pcie dw_pcie_dbi_ro_wr_en DONE
[    2.087074]  zzzzzz.pci  dbg regs ee8105 8200000                                         <<<<< before loop
[    2.102213] xxx.pcie Waiting for link
[    6.304896] zzzz.pcie-deb LTSSM current state: 0x5 (S_PRE_DETECT_QUIET)
[    6.311520] zzzz.pcie-deb PIPE transmit K indication: 0
[    6.316764] zzzz.pcie-deb PIPE Transmit data: 0x16ac
[    6.321735] zzzz.pcie-deb Receiver is receiving logical idle: 0
[    6.327671] zzzz.pcie-deb Second symbol is also idle (16-bit PHY interface only): 0
[    6.335343] zzzz.pcie-deb Currently receiving k237 (PAD) in place of link number: 0
[    6.343010] zzzz.pcie-deb Currently receiving k237 (PAD) in place of lane number: 0
[    6.350683] zzzz.pcie-deb Link control bits advertised by link partner: 0x0
[    6.357659] zzzz.pcie-deb Receiver detected lane reversal: 0
[    6.363325] zzzz.pcie-deb TS2 training sequence received: 0
[    6.368913] zzzz.pcie-deb TS1 training sequence received: 0
[    6.374492] zzzz.pcie-deb Receiver reports skip reception: 0
[    6.380165] zzzz.pcie-deb LTSSM reports PHY link up: 0
[    6.385315] zzzz.pcie-deb A skip ordered set has been transmitted: 0
[    6.391677] zzzz.pcie-deb Link number advertised/confirmed by link partner: 0
[    6.398827] zzzz.pcie-deb Application request to initiate training reset: 0
[    6.405803] zzzz.pcie-deb PIPE transmit compliance request: 0
[    6.411556] zzzz.pcie-deb PIPE transmit electrical idle request: 1
[    6.417750] zzzz.pcie-deb PIPE receiver detect/loopback request: 0
[    6.423938] zzzz.pcie-deb LTSSM-negotiated link reset: 1
[    6.429263] zzzz.pcie-deb LTSSM testing for polarity reversal: 0
[    6.435287] zzzz.pcie-deb LTSSM performing link training: 0
[    6.440866] zzzz.pcie-deb LTSSM in DISABLE state; link inoperable: 0
[    6.447234] zzzz.pcie-deb Scrambling disabled for the link: 0
[    6.452989] imx6q-pcie 33800000.pcie: Phy link never came up
[    6.458663] imx6q-pcie 33800000.pcie: Failed to wait for LINK.
[    6.464505]  zzzzzz.pci  dbg regs 12a205 8200000                            <<<<<<<<<<<<<<<<<  after loop
[    6.469303] imx6q-pcie 33800000.pcie: failed to initialize host
[    6.475243] imx6q-pcie 33800000.pcie: unable to add pcie port.

 


A suggestion where to look would be appreciated. I am wondering if LTSSM is used to test the link up in the imx8mm
because in the imx6_pcie_ltssm_enable() function for IMX8MM  all it does is a reset, and regmap_update_bits is used for other
models.

 

Thank you.

 

0 Kudos
5,590 Views
igorpadykov
NXP Employee
NXP Employee

for "pcie: Phy link never came up" one can try several pcie cards.

 

Best regards
igor

0 Kudos