HI3559AV100下对emmc总线速率的调整

先前使用3559开发板时,一直没觉得emmc会是个问题,但是最近一个国产化的项目中3559配合的是一款国产128G的emmc,因为板上面积限制,走线有点限制,导致uboot启动emmc有时候会失败。

1、报错的打印如下:

MMC read: dev # 0, block # 2048, count 18432 ... sdhci_transfer_data: Error detected in status(0x208000)!
=========== REGISTER DUMP (mmc0)===========
Sys addr: 0x00002544 | Version:  0x00000005
Blk size: 0x00007200 | Blk cnt:  0x00000000
Argument: 0x00000800 | Trn mode: 0x00000033
Present:  0x03f702f2 | Host ctl: 0x0000003c
Power:    0x0000000f | Blk gap:  0x00000000
Wake-up:  0x00000000 | Clock:    0x0000000f
Timeout:  0x0000000e | Int stat: 0x00208000
Int enab: 0x027f003b | Sig enab: 0x00000000
ACMD err: 0x00000000 | Slot int: 0x00000000
Caps:     0x3f6ec881 | Caps_1:   0x08000077
Cmd:      0x0000123a | Max curr: 0x00000000
Host ctl2: 0x00000087 | ADMA Err: 0x00000060
 ADMA Ptr: 0x00000000_5fe6d588
===========================================
0 blocks read: ERROR
Load fip from 0x0000000042000000 ...
Firmware Image Package ToC:
---------------------------
- EL3 Runtime Firmware BL3-1: offset=0x88, size=0x7090
- Non-Trusted Firmware BL3-3: offset=0x7118, size=0x84E32A
---------------------------
Create Entry Point info ...
Get - EL3 Runtime Firmware BL3-1 
Get - Non-Trusted Firmware BL3-3 
kernel_size[0x84e32a] fdt_size[0x82ea] fdt_addr[0x00000000448c6000]
Invalid FDT at 0x0000000046000000, hdr at 0x000000004407ffc0

2、查看emmc的信息如下:

hisilicon # mmc info
Device: hisi-sdhci
Manufacturer ID: 88
OEM: 103
Name: 88A19 
Tran Speed: 200000000
Rd Block Len: 512
MMC version 5.1
High Capacity: Yes
Capacity: 123731968000
Bus Width: 8-bit DDR
Erase Group Size: 512 KiB
HC WP Group Size: 8 MiB
User Capacity: 115.2 GiB WRREL
Boot Capacity: 4 MiB ENH
RPMB Capacity: 4 MiB ENH
hisilicon # 

3、开发板上的emmc信息如下:

hisilicon # mmc info
Device: hisi-sdhci
Manufacturer ID: 11
OEM: 100
Name: 008G3 
Tran Speed: 200000000
Rd Block Len: 512
MMC version 5.1
High Capacity: Yes
Capacity: 7818182656
Bus Width: 8-bit DDR
Erase Group Size: 512 KiB
HC WP Group Size: 4 MiB
User Capacity: 7.3 GiB WRREL
Boot Capacity: 4 MiB ENH
RPMB Capacity: 4 MiB ENH

4、解决办法

查看emmc的信息看不出什么问题,因此我的第一反应就是去降低emmc的总线速率。因为先前在玩zynq和emmc是遇到过问题,降低emmc的时钟可以解决。zynq下降低速率最简单的办法就是在最小系统勾选时把emmc的时钟降低,编译就可以了。但是在海思的sdk中,我没有找到相应的配置方法,所以就只能去修改源码了!!!

5、uboot修改

分析代码的调用关系后,发现在uboot中drivers/mmc/mmc.c中函数static int mmc_startup(struct mmc *mmc)中屏蔽对hs400和hs200的代码,参考如下,则不会进入高速模式。
    mmc_set_clock(mmc, mmc->tran_speed);
#if 0
    if (mmc->card_caps & MMC_MODE_HS400ES) {
        err = mmc_select_hs400es(mmc);
        if (err)
            return err;
        mmc->ddr_mode = 1;
    } else if (mmc->card_caps & MMC_MODE_HS200) {
        err = mmc_select_hs200(mmc);
        if (err)
            return err;
    }
    #endif

6、设备树修改

设备树也要修改,linux-4.9.y_multi-core/arch/arm64/boot/dts/hisilicon/hi3559av100.dtsi中,屏蔽hs400的描述,参考如下:

        mmc0: eMMC@0x100f0000 {
            compatible = "hisi-sdhci";
            reg = <0x100f0000 0x1000>, <0x10290000 0x1000>;
            interrupts = <0 26 4>;
            clocks = <&clock HI3559AV100_MMC0_CLK>;
            clock-names = "mmc_clk";
            resets = <&clock 0x1a8 27>, <&clock 0x1a8 29>,  <&clock 0x1a8 30>;
            reset-names = "crg_reset", "dll_reset", "sampl_reset";
            max-frequency = <198000000>;
            crg_regmap = <&clock>;
            non-removable;
            bus-width = <8>;
            cap-mmc-highspeed;
    /*
            mmc-hs400-1_8v;
            mmc-hs400-enhanced-strobe;
    */

            cap-mmc-hw-reset;
            devid = <0>;
            status = "disabled";
        };

7、测试确认

修改以后确实测试没有问题。

同时也测试了调速前后对emmc的访问速度,对比如下:

写测试命令:dd if=/dev/zero of=/mnt/1.dat bs=1M count=1k
读测试命令:dd of=/dev/null if=/mnt/1.dat bs=1M count=1k

未降速时,写速度在160MB左右,读速度在210MB左右;

降速后,写速度在45MB左右,读速度在40MB左右。

HI3559AV100下对emmc总线速率的调整_第1张图片

你可能感兴趣的:(linux,hi3559,emmc)