PetaLinux学习笔记 2

现在遇到这样一个问题,没有USB,甚至于USB都没有电压输出,检查电路,USB供电是由一个TPS2051BDBV来控制的,这个芯片又是USB3320C来控制的,说明这个芯片没有工作。经过一天的排查,最后终于找到原因了。是因为没有设置设备树。设备树这方面我并不是很懂,所以整理一下。
首先,先找到编译出来的设备树。文件是images/linux/system.dtb
在这篇文章 《设备树(device tree)学习笔记》 找到了反向编译工具fdtdump,使用fdtdump工具将其反向编译。
结果就是这样的:

$ fdtdump image/linux/system.dtb 
/dts-v1/;
// magic:		0xd00dfeed
// totalsize:		0x3681 (13953)
// off_dt_struct:	0xb8
// off_dt_strings:	0x22ec
// off_mem_rsvmap:	0x28
// version:		17
// last_comp_version:	16
// boot_cpuid_phys:	0x0
// size_dt_strings:	0x395
// size_dt_struct:	0x2234

/ {										// 根节点
    #address-cells = <0x00000001>;			// 这部分可以在官方手册UG585/4.1 Address Map 章得到证实,寻址最大不超过FFFF_FFFF,所以是32位。而设备树中cell规定为32位,所以是1
    #size-cells = <0x00000001>;				// TODO: 这里我是不是可以这么理解,寻址只有32位,大小也超不过32位呢?这里标记一下,等之后研究过MPU后再来处理这个。
    compatible = "xlnx,zynq-7000";			// 机器的标识,xlnx为厂家名称,后面的是板子的名字
    cpus {
        #address-cells = <0x00000001>;		// CPU 在32位总线上寻址
        #size-cells = <0x00000000>;			// 不在整个总线上占有地址空间,所以是0?
        cpu@0 {
            compatible = "arm,cortex-a9";		// CPU的型号,这个就是和驱动用来配对的字符串。
            device_type = "cpu";				// 设备类型
            reg = <0x00000000>;					// 不懂,说是标识号
            clocks = <0x00000001 0x0000003d>;	// 这里要参考build/tmp/work-shared/plnx-zynq7/kernel-source/arch/arm/boot/dts/zynq-7000.dtsi 这个文件的内容,文件中这个位置的数据是:clocks = <&clkc 3>;而这个clk也是有迹可循的。
            clock-latency = <0x000003e8>;		// 延迟?
            cpu0-supply = <0x00000002>;			// ??
            operating-points = <0x000a2c2a 0x00000002 0x00000003 0x636f7274>;	// ??
        };
        cpu@1 {
            compatible = "arm,cortex-a9";		// CPU的型号
            device_type = "cpu";				// 设备类型
            reg = <0x00000001>;					// 不懂,说是标识号
            clocks = <0x00000001 0x00000001>;	// 不懂
        };
    };
    fpga-full {
        compatible = "fpga-region";				// 应该是PL部分的接口
        fpga-mgr = <0x00000003>;
        #address-cells = <0x00000001>;
        #size-cells = <0x00000001>;
        ranges;
    };
    pmu@f8891000 {								// Performance Monitor Unit
        compatible = "arm,cortex-a9-pmu";
        interrupts = <0x00000000 0x00000006 0x00000083 0x00000032 0x00001000 0x64726567>;
        interrupt-parent = <0x00000004>;
        reg = <0xf8891000 0x00000002 0x756c6174 0x0000001b>;
    };
    fixedregulator {
        compatible = "regulator-fixed";
        regulator-name = "VCCPINT";
        regulator-min-microvolt = <0x000f4240>;
        regulator-max-microvolt = <0x000f4240>;
        regulator-boot-on;
        regulator-always-on;
        linux,phandle = <0x00000002>;
        phandle = <0x00000002>;
    };
    											// 先进微控制器总线体系结构(就是ARM的总线)
    amba {										// Advanced Microcontroller Bus Architecture
        u-boot,dm-pre-reloc;
        compatible = "simple-bus";
        #address-cells = <0x00000001>;
        #size-cells = <0x00000001>;
        interrupt-parent = <0x00000004>;
        ranges;
        adc@f8007100 {
            compatible = "xlnx,zynq-xadc-1.00.a";
            reg = <0xf8007100 0x00000078>;
            interrupts = <0x00000000 0x00000004 0x00000008>;
            interrupt-parent = <0x00000004>;
            clocks = <0x00000001 0x63616e40>;
        };
        can@e0008000 {
            compatible = "xlnx,zynq-can-1.0";
            status = "disabled";
            clocks = <0x00000001 0x00000003 0x636c6b00 0x00000008>;
            clock-names = "can_clk", "pclk";
            reg = <0xe0008000 0x00000078>;
            interrupts = <0x00000000 0x00000004 0x00000004>;
            interrupt-parent = <0x00000004>;
            tx-fifo-depth = <0x00000040>;
            rx-fifo-depth = <0x00000040>;
        };
        can@e0009000 {
            compatible = "xlnx,zynq-can-1.0";
            status = "disabled";
            clocks = <0x00000001 0x00000003 0x636c6b00 0x00000008>;
            clock-names = "can_clk", "pclk";
            reg = <0xe0009000 0x00000078>;
            interrupts = <0x00000000 0x00000004 0x00000004>;
            interrupt-parent = <0x00000004>;
            tx-fifo-depth = <0x00000040>;
            rx-fifo-depth = <0x00000040>;
        };
        gpio@e000a000 {
            compatible = "xlnx,zynq-gpio-1.0";
            #gpio-cells = <0x00000002>;
            clocks = <0x00000001 0x00000156>;
            gpio-controller;
            interrupt-controller;
            #interrupt-cells = <0x00000002>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe000a000 0x0000018c>;
            emio-gpio-width = <0x00000040>;
            gpio-mask-high = <0x00000000>;
            gpio-mask-low = <0x00005600>;
            linux,phandle = <0x00000005>;
            phandle = <0x00000005>;
        };
        i2c@e0004000 {
            compatible = "cdns,i2c-r1p10";
            status = "disabled";
            clocks = <0x00000001 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0004000 0x00000000>;
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
        };
        i2c@e0005000 {
            compatible = "cdns,i2c-r1p10";
            status = "disabled";
            clocks = <0x00000001 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0005000 0x00000000>;
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
        };
        interrupt-controller@f8f01000 {
            compatible = "arm,cortex-a9-gic";
            #interrupt-cells = <0x00000003>;
            interrupt-controller;
            reg = <0xf8f01000 0x00000003 0x00000003 0x00000003>;
            num_cpus = <0x00000002>;
            num_interrupts = <0x00000060>;
            linux,phandle = <0x00000004>;
            phandle = <0x00000004>;
        };
        cache-controller@f8f02000 {
            compatible = "arm,pl310-cache";
            reg = <0xf8f02000 0x00000078>;
            interrupts = <0x00000000 0x0000000c 0x00000002>;
            arm,data-latency = <0x00000003 0x0000000c 0x00000002>;
            arm,tag-latency = <0x00000002 0x00000000 0x00000200>;
            cache-unified;
            cache-level = <0x00000002>;
        };
        memory-controller@f8006000 {
            compatible = "xlnx,zynq-ddrc-a05";
            reg = <0xf8006000 0x6f636d63>;
        };
        ocmc@f800c000 {
            compatible = "xlnx,zynq-ocmc-1.0";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000002>;
            reg = <0xf800c000 0x73657269>;
        };
        serial@e0000000 {
            compatible = "xlnx,xuartps", "cdns,uart-r1p8";
            status = "disabled";
            clocks = <0x00000001 0x00000003 0x5f636c6b 0x00000008>;
            clock-names = "uart_clk", "pclk";
            reg = <0xe0000000 0x00000078>;
            interrupts = <0x00000000 0x00000001 0x30303000>;
        };
        serial@e0001000 {
            compatible = "xlnx,xuartps", "cdns,uart-r1p8";
            status = "okay";
            clocks = <0x00000001 0x00000003 0x5f636c6b 0x00000008>;
            clock-names = "uart_clk", "pclk";
            reg = <0xe0001000 0x00000078>;
            interrupts = <0x00000000 0x00000007 0x00000003>;
            device_type = "serial";
            port-number = <0x00000000>;
        };
        spi@e0006000 {
            compatible = "xlnx,zynq-spi-r1p6";
            reg = <0xe0006000 0x0000011b>;
            status = "disabled";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000010 0x00000001>;
            clocks = <0x00000001 0x00000003 0x636c6b00 0x00000004>;
            clock-names = "ref_clk", "pclk";
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
        };
        spi@e0007000 {
            compatible = "xlnx,zynq-spi-r1p6";
            reg = <0xe0007000 0x0000011b>;
            status = "disabled";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000010 0x00000001>;
            clocks = <0x00000001 0x00000003 0x636c6b00 0x00000004>;
            clock-names = "ref_clk", "pclk";
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
        };
        spi@e000d000 {
            clock-names = "ref_clk", "pclk";
            clocks = <0x00000001 0x00000003 0x2c7a796e 0x00000003>;
            compatible = "xlnx,zynq-qspi-1.0";
            status = "okay";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe000d000 0x00000000>;
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
            is-dual = <0x00000000>;
            num-cs = <0x00000001>;
            spi-rx-bus-width = <0x00000004>;
            spi-tx-bus-width = <0x00000004>;
            flash@0 {
                compatible = "n25q512a", "micron,m25p80";
                reg = <0x00000000>;
                #address-cells = <0x00000001>;
                #size-cells = <0x00000001>;
                spi-max-frequency = <0x02faf080>;
                partition@0x00000000 {
                    label = "boot";
                    reg = <0x00000000 0x70617274>;
                };
                partition@0x00040000 {
                    label = "bootenv";
                    reg = <0x00040000 0x70617274>;
                };
                partition@0x00060000 {
                    label = "kernel";
                    reg = <0x00060000 0x00000002>;
                };
            };
        };
        memory-controller@e000e000 {
            #address-cells = <0x00000001>;
            #size-cells = <0x00000001>;
            status = "disabled";
            clock-names = "memclk", "aclk";
            clocks = <0x00000001 0x00000003 0x706c3335 0x00000003>;
            compatible = "arm,pl353-smc-r2p1";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000000 0x00000032>;
            ranges;
            reg = <0xe000e000 0x68406531>;
            flash@e1000000 {
                status = "disabled";
                compatible = "arm,pl353-nand-r2p1";
                reg = <0xe1000000 0x00000000>;
                #address-cells = <0x00000001>;
                #size-cells = <0x00000001>;
            };
            flash@e2000000 {
                status = "disabled";
                compatible = "cfi-flash";
                reg = <0xe2000000 0x00000000>;
                #address-cells = <0x00000001>;
                #size-cells = <0x00000001>;
            };
        };
        ethernet@e000b000 {
            compatible = "cdns,zynq-gem", "cdns,gem";
            reg = <0xe000b000 0x0000011b>;
            status = "okay";
            interrupts = <0x00000000 0x00000018 0x00000001>;
            clocks = <0x00000001 0x00000001 0x00000122 0x5f636c6b 0x00000000 0x0000000f>;
            clock-names = "pclk", "hclk", "tx_clk";
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
            enet-reset = <0x00000005 0x00000009 0x00000000>;
            phy-mode = "rgmii-id";
            xlnx,ptp-enet-clock = <0x069f6bcb>;
            local-mac-address = [00 0a 35 00 22 01];
        };
        ethernet@e000c000 {
            compatible = "cdns,zynq-gem", "cdns,gem";
            reg = <0xe000c000 0x0000011b>;
            status = "disabled";
            interrupts = <0x00000000 0x00000018 0x00000001>;
            clocks = <0x00000001 0x00000001 0x00000122 0x5f636c6b 0x00000000 0x0000000f>;
            clock-names = "pclk", "hclk", "tx_clk";
            #address-cells = <0x00000001>;
            #size-cells = <0x00000000>;
        };
        mmc@e0100000 {
            compatible = "arasan,sdhci-8.9a";
            status = "okay";
            clock-names = "clk_xin", "clk_ahb";
            clocks = <0x00000001 0x00000003 0x00000003 0x00000018>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0100000 0x0000029b>;
            xlnx,has-cd = <0x00000001>;
            xlnx,has-power = <0x00000000>;
            xlnx,has-wp = <0x00000000>;
        };
        mmc@e0101000 {
            compatible = "arasan,sdhci-8.9a";
            status = "okay";
            clock-names = "clk_xin", "clk_ahb";
            clocks = <0x00000001 0x00000003 0x00000003 0x0000002f>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0101000 0x0000029b>;
            xlnx,has-cd = <0x00000000>;
            xlnx,has-power = <0x00000000>;
            xlnx,has-wp = <0x00000000>;
        };
		slcr@f8000000 {
            u-boot,dm-pre-reloc;
            #address-cells = <0x00000001>;
            #size-cells = <0x00000001>;
            compatible = "xlnx,zynq-slcr", "syscon", "simple-mfd";
            reg = <0xf8000000 0x00000071>;
            ranges;
            linux,phandle = <0x00000006>;
            phandle = <0x00000006>;
            clkc@100 {
                u-boot,dm-pre-reloc;
                #clock-cells = <0x00000001>;
                compatible = "xlnx,ps7-clkc";
                fclk-enable = <0x00000000>;
                clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x", "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x", "dci", "lqspi", "smc", "pcap", "gem0", "gem1", "fclk0", "fclk1", "fclk2", "fclk3", "can0", "can1", "sdio0", "sdio1", "uart0", "uart1", "spi0", "spi1", "dma", "usb0_aper", "usb1_aper", "gem0_aper", "gem1_aper", "sdio0_aper", "sdio1_aper", "spi0_aper", "spi1_aper", "can0_aper", "can1_aper", "i2c0_aper", "i2c1_aper", "uart0_aper", "uart1_aper", "gpio_aper", "lqspi_aper", "smc_aper", "swdt", "dbg_trc", "dbg_apb";
                reg = <0x00000100 0x000002ee>;
                ps-clk-frequency = <0x01fca055>;
                linux,phandle = <0x00000001>;
                phandle = <0x00000001>;
            };
            rstc@200 {
                compatible = "xlnx,zynq-reset";
                reg = <0x00000200 0x000002ff>;
                #reset-cells = <0x00000001>;
                syscon = <0x00000006>;
            };
            pinctrl@700 {
                compatible = "xlnx,pinctrl-zynq";
                reg = <0x00000700 0x0000030c>;
                syscon = <0x00000006>;
            };
        };
        dmac@f8003000 {
            compatible = "arm,pl330", "arm,primecell";
            reg = <0xf8003000 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupt-names = "abort", "dma0", "dma1", "dma2", "dma3", "dma4", "dma5", "dma6", "dma7";
            interrupts = <0x00000000 0x0000000e 0x00000004 0x00000000 0x00000028 0x00000004 0x00000000 0x00000004 0x00000004 0x00000004 0x00000008 0x00000003 0x70636c6b 0x64657663 0x00000003 0x2c7a796e 0x00000000 0x00000004 0x00000000 0x00000008 0x00000003 0x0000000c 0x00000010 0x00000012 0x7265665f 0x6c6b3100 0x00000003>;
            #dma-cells = <0x00000001>;
            #dma-channels = <0x00000008>;
            #dma-requests = <0x00000004>;
            clocks = <0x00000001 0x00000122>;
            clock-names = "apb_pclk";
        };
        devcfg@f8007000 {
            compatible = "xlnx,zynq-devcfg-1.0";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xf8007000 0x00000036>;
            clocks = <0x00000001 0x00000001 0x00000001 0x00000122 0x30006663 0x6c6b3300 0x00000006 0x00000003 0x00000003 0x65406638>;
            clock-names = "ref_clk", "fclk0", "fclk1", "fclk2", "fclk3";
            syscon = <0x00000006>;
            linux,phandle = <0x00000003>;
            phandle = <0x00000003>;
        };
        efuse@f800d000 {
            compatible = "xlnx,zynq-efuse";
            reg = <0xf800d000 0x74696d65>;
        };
        timer@f8f00200 {
            compatible = "arm,cortex-a9-global-timer";
            reg = <0xf8f00200 0x00000078>;
            interrupts = <0x00000001 0x00000004 0x00000008>;
            interrupt-parent = <0x00000004>;
            clocks = <0x00000001 0x74696d65>;
        };
        timer@f8001000 {
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x0000000b 0x00000004 0x63646e73 0x00000008 0x00000003 0x00001000 0x72406638 0x00000004>;
            compatible = "cdns,ttc";
            clocks = <0x00000001 0x00000032>;
            reg = <0xf8001000 0x74696d65>;
        };
        timer@f8002000 {
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000026 0x00000004 0x63646e73 0x00000008 0x00000003 0x00001000 0x72406638 0x00000004>;
            compatible = "cdns,ttc";
            clocks = <0x00000001 0x00000032>;
            reg = <0xf8002000 0x74696d65>;
        };
        timer@f8f00600 {
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000001 0x00000018 0x65782d61>;
            compatible = "arm,cortex-a9-twd-timer";
            reg = <0xf8f00600 0x00000036>;
            clocks = <0x00000001 0x75736240>;
        };
        usb@e0002000 {
            compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
            status = "okay";
            clocks = <0x00000001 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0002000 0x0000034a>;
            phy_type = "ulpi";
            usb-reset = <0x00000005 0x00000001 0x00000000>;
        };
        usb@e0003000 {
            compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
            status = "disabled";
            clocks = <0x00000001 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0003000 0x0000034a>;
            phy_type = "ulpi";
        };
        watchdog@f8005000 {
            clocks = <0x00000001 0x0000001b>;
            compatible = "cdns,wdt-r1p2";
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xf8005000 0x0000035d>;
            timeout-sec = <0x0000000a>;
        };
    };
    chosen {
        bootargs = "console=ttyPS0,115200 earlyprintk";
        stdout-path = "serial0:115200n8";
    };
    aliases {
        ethernet0 = "/amba/ethernet@e000b000";
        serial0 = "/amba/serial@e0001000";
        spi0 = "/amba/spi@e000d000";
    };
    memory {
        device_type = "memory";
        reg = <0x00000000 0x00000009>;
    };
};

通过阅读《5. 设备树的规范 - DTS格式》,可以对设备树比较好的了解一番。感谢Jalyn_Fang的文章,讲的非常详细。但是根节点的#address-cells, #size-cells看的我已一俩蒙蔽,找到这个例子:由《设备树中#address-cells和#size-cells作用》文中举出例子。这样很好理解

相对的我也在内核的代码里找到了一官方的板子的设备树文件:

		usb@e0002000 {
            compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
            status = "okay";
            clocks = <0x00000001 0x00000083>;
            interrupt-parent = <0x00000004>;
            interrupts = <0x00000000 0x00000008 0x00000003>;
            reg = <0xe0002000 0x0000034a>;
            phy_type = "ulpi";
            usb-reset = <0x00000005 0x00000001 0x00000000>;
        };

可以看到status是OK,说明这个部分已经启用了。
全局搜索xlnx,zynq-usb-2.20a

Searching 61690 files for "xlnx,zynq-usb-2.20a"

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/arch/arm/boot/dts/zynq-7000.dtsi:
  393  
  394  		usb0: usb@e0002000 {
  395: 			compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
  396  			status = "disabled";
  397  			clocks = <&clkc 28>;
  ...
  403  
  404  		usb1: usb@e0003000 {
  405: 			compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
  406  			status = "disabled";
  407  			clocks = <&clkc 29>;

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/Documentation/devicetree/bindings/usb/ci-hdrc-usb2.txt:
   14  	"qcom,ci-hdrc"
   15  	"chipidea,usb2"
   16: 	"xlnx,zynq-usb-2.20a"
   17  - reg: base address and length of the registers
   18  - interrupts: interrupt for the USB controller

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/drivers/usb/chipidea/ci_hdrc_usb2.c:
   39  static const struct of_device_id ci_hdrc_usb2_of_match[] = {
   40  	{ .compatible = "chipidea,usb2"},
   41: 	{ .compatible = "xlnx,zynq-usb-2.20a", .data = &ci_zynq_pdata},
   42  	{ }
   43  };

4 matches across 3 files

跳转到文档 /home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/Documentation/devicetree/bindings/usb/ci-hdrc-usb2.txt
里面有说明:

Recommended properies:
- phy_type: the type of the phy connected to the core. Should be one
  of "utmi", "utmi_wide", "ulpi", "serial" or "hsic". Without this
  property the PORTSC register won't be touched.
- dr_mode: One of "host", "peripheral" or "otg". Defaults to "otg"

不供电可能是因为默认为OTG模式。

Optional properties:
- clocks: reference to the USB clock
- phys: reference to the USB PHY
- phy-names: should be "usb-phy"
- vbus-supply: reference to the VBUS regulator
- maximum-speed: limit the maximum connection speed to "full-speed".
- tpl-support: TPL (Targeted Peripheral List) feature for targeted hosts
- itc-setting: interrupt threshold control register control, the setting
  should be aligned with ITC bits at register USBCMD.
- ahb-burst-config: it is vendor dependent, the required value should be
  aligned with AHBBRST at SBUSCFG, the range is from 0x0 to 0x7. This
  property is used to change AHB burst configuration, check the chipidea
  spec for meaning of each value. If this property is not existed, it
  will use the reset value.
- tx-burst-size-dword: it is vendor dependent, the tx burst size in dword
  (4 bytes), This register represents the maximum length of a the burst
  in 32-bit words while moving data from system memory to the USB
  bus, the value of this property will only take effect if property
  "ahb-burst-config" is set to 0, if this property is missing the reset
  default of the hardware implementation will be used.
- rx-burst-size-dword: it is vendor dependent, the rx burst size in dword
  (4 bytes), This register represents the maximum length of a the burst
  in 32-bit words while moving data from the USB bus to system memory,
  the value of this property will only take effect if property
  "ahb-burst-config" is set to 0, if this property is missing the reset
  default of the hardware implementation will be used.
- extcon: phandles to external connector devices. First phandle should point to
  external connector, which provide "USB" cable events, the second should point
  to external connector device, which provide "USB-HOST" cable events. If one
  of the external connector devices is not required, empty <0> phandle should
  be specified.
- phy-clkgate-delay-us: the delay time (us) between putting the PHY into
  low power mode and gating the PHY clock.
- non-zero-ttctrl-ttha: after setting this property, the value of register
  ttctrl.ttha will be 0x7f; if not, the value will be 0x0, this is the default
  value. It needs to be very carefully for setting this property, it is
  recommended that consult with your IC engineer before setting this value.
  On the most of chipidea platforms, the "usage_tt" flag at RTL is 0, so this
  property only affects siTD.
  If this property is not set, the max packet size is 1023 bytes, and if
  the total of packet size for pervious transactions are more than 256 bytes,
  it can't accept any transactions within this frame. The use case is single
  transaction, but higher frame rate.
  If this property is set, the max packet size is 188 bytes, it can handle
  more transactions than above case, it can accept transactions until it
  considers the left room size within frame is less than 188 bytes, software
  needs to make sure it does not send more than 90%
  maximum_periodic_data_per_frame. The use case is multiple transactions, but
  less frame rate.

i.mx specific properties
- fsl,usbmisc: phandler of non-core register device, with one
  argument that indicate usb controller index
- disable-over-current: disable over current detect
- over-current-active-high: over current signal polarity is high active,
  typically over current signal polarity is low active.
- external-vbus-divider: enables off-chip resistor divider for Vbus

刚刚发现可以挂代理了,在Google上搜到了这个:《Zynq Linux USB Device Driver》
有给出要设置为主机模式需要的设备树如何写。

    usb_0: usb@e0002000 {
         compatible = "xlnx,zynq-usb-2.20.a", "chipidea,usb2";
         clocks = <&clkc 28>;
         dr_mode = "host";
         interrupt-parent = <&intc>;
         interrupts = <0 21 4>;
         reg = <0xe0002000 0x1000>;
         usb-phy = <&usb_phy0>;
     };
 
 usb_phy0: phy0 {
    compatible = "ulpi-phy";
    #phy-cells = <0>;
    reg = <0xe0002000 0x1000>;
    view-port = <0x170>;
    drv-vbus;
}

其中就出现了dr_mode,比起目前的文件多了

dr_mode = "host";
view-port = <0x170>;
drv-vbus;

有比较明显不同的:

compatible = "ulpi-phy";

dr_mode,USB模式,view-port 可以在UG585中找到,寄存器的地址是0xE0002170。搜索这个参数:

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/drivers/usb/phy/phy-ulpi.c:
  334  		return PTR_ERR(uphy->regs);
  335  
  336: 	ret = of_property_read_u32(np, "view-port", &uphy->vp_offset);
  337  	if (IS_ERR(uphy->regs)) {
  338: 		dev_err(&pdev->dev, "view-port register not specified\n");
  339  		return PTR_ERR(uphy->regs);
  340  	}

可以看出,这个是一个偏移量,所以view-port = <0x170>;就说得通了。这个文件名字是phy-ulpi所以compatible = "ulpi-phy";这个也说的通把。最后就是`drv-vbus:

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/drivers/usb/phy/phy-ulpi.c:
  340  	}
  341  
  342: 	flag = of_property_read_bool(np, "drv-vbus");
  343  	if (flag)
  344  		uphy->flags |= ULPI_OTG_DRVVBUS | ULPI_OTG_DRVVBUS_EXT;

这个是一个bool型的参数:

static inline bool of_property_read_bool(const struct device_node *np,
					 const char *propname)
{
	struct property *prop = of_find_property(np, propname, NULL);

	return prop ? true : false;
}

这个参数只要写在设备树中,就是1。之后设置了两个标志位:ULPI_OTG_DRVVBUSULPI_OTG_DRVVBUS_EXT,而这两个参数,在USB3320中也可以找到,不如说这个是ulpi的一部分,在这里插入图片描述
这两个信号貌似是一样的,用来外部启动5V供电的。这样5V就可以供电了。说起来OTG也是向外部供电,所以dr_mode不设置应该也是可以的。

再翻一下这个文件,发现一开始有枚举:

static struct ulpi_info ulpi_ids[] = {
	ULPI_INFO(ULPI_ID(0x04cc, 0x1504), "NXP ISP1504"),
	ULPI_INFO(ULPI_ID(0x0424, 0x0006), "SMSC USB331x"),
	ULPI_INFO(ULPI_ID(0x0424, 0x0007), "SMSC USB3320"),
	ULPI_INFO(ULPI_ID(0x0424, 0x0009), "SMSC USB334x"),
	ULPI_INFO(ULPI_ID(0x0451, 0x1507), "TI TUSB1210"),
};

开发板上的就是这个芯片。而在函数ulpi_init中也有遍历

	for (i = 0; i < ARRAY_SIZE(ulpi_ids); i++) {
		if (ulpi_ids[i].id == ULPI_ID(vid, pid)) {
			pr_info("Found %s ULPI transceiver.\n",
				ulpi_ids[i].name);
			break;
		}
	}

这样就说的通了,难怪之前在USB文件夹中没有找到这个以这个芯片命名的文件。而。compatible = "ulpi-phy"自然就是必须的了。
加上这三个去编译不通过,对照了一下,发现忽略了一个东西:

usb-phy = <&usb_phy0>

找一下

/home/godenfreemans/FTP_Folder/project_1/project_1.petalinux/build/tmp/work-shared/plnx-zynq7/kernel-source/drivers/usb/chipidea/core.c:
  939  		ci->usb_phy = ci->platdata->usb_phy;
  940  	} else {
  941: 		ci->phy = devm_phy_get(dev->parent, "usb-phy");
  942  		ci->usb_phy = devm_usb_get_phy(dev->parent, USB_PHY_TYPE_USB2);

这些东西不能直接添加在usb中,我想是因为ulpi的寄存器不能映射在USB这个外设上,但是它可以被USB间接的存取。所以是一个子节点。直接添加Xilinx给的东西是不能通过编译的。需要稍微修改一下,

/include/ "system-conf.dtsi"

/{
	aliases {
		usb0 = &usb0;
	};
	usb_phy0: usb_phy@0 {
		compatible = "ulpi-phy";
		#phy-cells = <0>;
		reg = <0xe0002000 0x1000>;
		view-port = <0x0170>;
		drv-vbus;
	};
};

&usb0 {
	compatible = "xlnx,zynq-usb-2.20.a", "chipidea,usb2";
	clocks = <&clkc 28>;
	dr_mode = "host";
	interrupt-parent = <&intc>;
	interrupts = <0 21 4>;
	reg = <0xe0002000 0x1000>;
	usb-phy = <&usb_phy0>;
};

但是还是不工作,我寻思着有啥问题呢,找来找去都没发现问题。
吃完饭后重新看了一遍生成的system.dtb。偶然发现这个东西有点奇怪啊。xlnx,zynq-usb-2.20.a这个.是哪里冒出来的,我还去官网确认了一下有,但是全局搜索这个没有找到对应的文件。这里有问题,把这里改一下。

/include/ "system-conf.dtsi"

/{
	aliases {
		usb0 = &usb0;
	};
	usb_phy0: usb_phy@0 {
		compatible = "ulpi-phy";
		#phy-cells = <0>;
		reg = <0xe0002000 0x1000>;
		view-port = <0x0170>;
		drv-vbus;
	};
};

&usb0 {
	compatible = "xlnx,zynq-usb-2.20a", "chipidea,usb2";
	clocks = <&clkc 28>;
	dr_mode = "host";
	interrupt-parent = <&intc>;
	interrupts = <0 21 4>;
	reg = <0xe0002000 0x1000>;
	usb-phy = <&usb_phy0>;
};

现在USB可以正常工作了。官方文档挖坑了?

root@project_1:/proc/bus/pci# dmesg | grep USB
ehci_hcd: USB 2.0 'Enhanced' Host Controller (EHCI) Driver
Found SMSC USB3320 ULPI transceiver.
ci_hdrc ci_hdrc.0: new USB bus registered, assigned bus number 1
ci_hdrc ci_hdrc.0: USB 2.0 started, EHCI 1.00
hub 1-0:1.0: USB hub found
usbhid: USB HID core driver
usb 1-1: new high-speed USB device number 2 using ci_hdrc
hub 1-1:1.0: USB hub found
usb 1-1.1: new high-speed USB device number 3 using ci_hdrc
usb-storage 1-1.1:1.0: USB Mass Storage device detected

打开一下lsusb命令,猜测是rootfs里的:

-> Filesystem Packages -> base -> [*] usbutils
-> Filesystem Packages -> base -> [*] usbutils-dbg
-> Filesystem Packages -> base -> [*] usbutils-dev
root@ax7021:~# lsusb
Bus 001 Device 003: ID 12d1:1f01 Huawei Technologies Co., Ltd. E353/E3131 (Mass storage mode)
Bus 001 Device 002: ID 0424:2514 Standard Microsystems Corp. USB 2.0 Hub
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
root@ax7021:~# 

插在上面的U盘已经被识别出来了。USB部分就是OK的了。
说起来我的SPI好像也没工作,SPI的设备树配置的是:

			flash@0 {
                compatible = "n25q512a", "micron,m25p80";
                reg = <0x00000000>;
                #address-cells = <0x00000001>;
                #size-cells = <0x00000001>;
                spi-max-frequency = <0x02faf080>;
                partition@0x00000000 {
                    label = "boot";
                    reg = <0x00000000 0x70617274>;
                };
                partition@0x00040000 {
                    label = "bootenv";
                    reg = <0x00040000 0x70617274>;
                };
                partition@0x00060000 {
                    label = "kernel";
                    reg = <0x00060000 0x00000002>;
                };
            };

这个n25q512amicron,m25p80肯定不对,下一篇再来修复它。

  • 1
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值