P4080 RCW总结

在Freescale DPAA QorIQ平台上的启动和non-DPAA QorIQ平台的启动有一些区别:

1.non-DPAA QorIQ平台在上电时通过采样配置管脚来决定对CPU的配置(P2020 ( e500核 ) 上电启动及uboot流程|http://bbs.ednchina.com/BLOG_ARTICLE_1988662.HTM),而DPAA QorIQ平台采用RCW (Reset ConfigurationWord)来决定对CPU的各种配置。

2. 在从SD Card/SPI flash启动的时候,non-DPAA平台是通过on-Chip ROM逻辑将U-Boot image拷贝到L2 SRAM中启动,而从NAND flash启动时,是将4K的启动代码拷贝到eLBC FCM的RAM buffer中,该段代码负责将U-Boot image搬移到L2 SRAM中启动;DPAA平台是通过PBL(Pre-Boot Loader)逻辑将U-Boot image搬移的CPC SRAM中启动。

 

大体启动流程是这样的:上电PBL会采样cfg_rcw_src管脚来判断RCW存放在那种存储介质中,然后从相应的存储设备读取RCW对CPU进行配置。如果是从NOR flash启动,则不需要执行PBI command和拷贝U-Boot image到alternate配置空间,直接跳转到0xFFFFFFFC处执行。如果不是从NOR flash启动,在配置完毕CPU后会读取PBI command完成部分初始化工作,然后根据PBI command中对alternate配置空间地址的配置将U-Boot image拷贝到alternate配置空间中开始执行。


1. RCW


RCW是存放在外部存储设备中的512bit的配置信息,用来对CPU进行配置。和non-DPAA平台中的配置管脚完成的功能是一样的。当然RCW是存放在哪里的?这个还是通过配置管脚来完成的。


在上电的时候,PBL首先会采样cfg_rcw_src管脚来判断RCW存放在那种存储介质中,然后从相应的存储介质读取RCW来对CPU进行配置。那么PBL是从哪里开始读取呢?下表列出了对不同介质PBL开始读取的地址:


Interface

Starting Address

eLBC

0x00000000

I2C

0x00000000

eSPI

0x00000000

eSDHC

0x00001000

 

其中比较特殊的是Hard-coded RCW options. 如果选择RCW为Hard-coded,那么PBL不会去外部存储设备去读取RCW而是使用预先定义好的RCW配置来对CPU进行配置。有以下两个好处:

1. 如果存储设备接口有问题从而没法存储RCW,可以选择使用Hard-coded启动。

2. 如果用户自己设置的RCW有问题导致系统没法启动,可以使用hard-coded RCW来启动,启动完成后可以恢复用户自己设置的RCW。

 

RCW主要完成对CPU一些资源的配置,比如Core的频率,serdes lane的使用,管脚复用的配置等等。对启动来说应该关注以下几个bit位的配置:

 

1. 选择PBI数据源的存放处,关于PBI的含义可以参考下面的PBL部分



2.Boot location的选择



3. 从PCIe启动时配置哪个PCIe controller为Agent模式



4.Secure boot模式


2. PBL


PBL(Pre-Boot Loader)用来辅助从I2C,SD,NAND flash,SPI flash启动的一个硬件单元。主要功能是在上电之初首先配置以上接口的寄存器来对接口初始化,根据cfg_rcw_src管脚的配置从相应的接口读取RCW和PBI命令,然后根据RCW来配置CPU,并执行PBI命令完成初始化操作,最后释放CPU core跳转到0xFFFFFFFC处执行第一条指令。

在释放CPU core后,CPU core去哪儿执行第一条指令?这个是很关键的一点,会影响到U-Boot image的TEXT_BASE的设置,而且在non-DPAA平台和DPAA平台上的实现是不同的。在non-DPAA平台上,若是从SD/SPI flash启动,on-chip ROM将U-Boot image拷贝到L2 SRAM后,会跳转到下面的控制字指定的地址去执行,我们知道CPU执行的第一条指令是存放到512K U-Boot image最后4个字节的一条跳转指令(bl start_e500),所以跳转指令的地址(下面的”Execution Starting Address”)应该指向U-Boot的TEXT_BASE的最后4个字节的地址。




如果是从NAND flash启动,on-chip ROM会将4K的启动代码拷贝到eLBC内部的RAM buffer,并将CPU释放到0xFFFFFFFC出执行指令,所以从NAND启动时的4K启动到代码的TEXT_BASE是0xfffff000。

non-DPAA平台的启动可以参考前期博文:http://blog.csdn.net/mingkai_hu/article/details/6769258


而在DPAA平台上CPU core,只要不是从NOR flash启动,PBL都会从相应的启动设备中拷贝RCW,执行PBI command,拷贝U-Boot image到CPC SRAM中(当然这个是PBI command指定的,下面会有详细的介绍),并将CPU core释放到到0xFFFFFFFC处执行第一条指令。

 
和non-DPAA平台的on-chip ROM一样,PBL也只能识别固定的数据格式,所以我们需要将RCW,PBI command(可选)封装为PBL能够识别的格式。Freescale提供了一套工具QCS来完成封装的工作。


2.1 RCW的封装

如果只是从NOR flash启动,我们只需要RCW即可,下面是RCW的封装格式:


SYS_ADDR地址是将n字节的数据写入的地址。SYS_ADDR是指向CCSRBAR空间或者alternate配置空间(ACS值决定)的地址。CCSRBAR空间比较好理解,那么alternate配置空间指的是哪里?该空间的高8位地址是多少?是由寄存器ALTCBARH/ALTCBARL/ALTCAR来决定的。





对于RCW DATA的SYS_ADDR来说就是CCSRBAR空间的device control and pincontrol block中的RCW状态寄存器(RCWSR[1-16]=64B),即:

fe_000000+ 0x0E_0000 + 0x100


2.2 RCW+PBI的封装

如果需要PBI command,比如配置CPC cache为SRAM,建立相应的LAW,配置alternate配置空间或者将U-Boot image拷贝到CPC SRAM等,都是通过

PBI command的设置完成的。



3. Boot from SD/NAND flash/SPI flash


3.1 代码解析

首先PBI command会做下面的初始化工作:

1. Invalidateand flush CPC cache

2. 将CPC SRAM配置为SRAM,地址为0xfff00000

3. 给CPC SRAM配置一个LAW entry(LAW16)

4. 配置alternate 配置空间,用来指示PBL将U-Boot image拷贝到CPC SRAM的0xfff80000开始的512K

5. 重新配置SPI controller的寄存器提高传输速率。PBL本身会配置各个接口的寄存器的,但SPI接口配置的速率比较低,传输U-Boot image花费的时间比较长,所有重新配置从而提高传输速率


下面是P4080DS的PBI command,从下面的command可以看出,CPC cache配置为SRAM,地址为0xfff0000,大小为1M,PBL将U-Boot iamge拷贝到0xfff80000开始

的地方。



下面是U-Boot image封装为PBI data的结构。

0x81f8000000的解析:

0x81 = 1000 0001 => ACS=1,CNT=1

F80000 => 指定alternate配置空间的低24位




然后在boards.cfg文件中添加对Boot from NAND的支持,并设置CONFIG_SYS_TEXT_BASE 为0xfff80000

[cpp] view plaincopy

  1. "boards.cfg"  

  2.   

  3. P5020DS_NAND                 powerpc     mpc85xx     corenet_ds          freescale                P5020DS:RAMBOOT_PBL,NAND,SYS_TEXT_BASE=0xFFF80000  

  4.   

  5.   

  6. "include/configs/corenet_ds.h"  

  7.   

  8. #ifdef CONFIG_RAMBOOT_PBL  

  9. #define CONFIG_RAMBOOT_TEXT_BASE        CONFIG_SYS_TEXT_BASE  

  10. #define CONFIG_RESET_VECTOR_ADDRESS     0xfffffffc  

  11. #endif  

  12.   

  13.   

  14. #define CONFIG_SYS_INIT_L3_ADDR         0xfff80000  

  15. #define CONFIG_SYS_INIT_L3_ADDR_PHYS    CONFIG_SYS_INIT_L3_ADDR  

  16. #define CONFIG_SYS_L3_SIZE              (1024 << 10)  

  17. #define CONFIG_SYS_INIT_L3_END (CONFIG_SYS_INIT_L3_ADDR CONFIG_SYS_L3_SIZE)  


配置CPC SRAM需要的TLB表项

[cpp] view plaincopy

  1. "board/freescale/common/p_corenet/tlb.c"  

  2.   

  3. struct fsl_e_tlb_entry tlb_table[]  

  4. #if defined(CONFIG_SYS_RAMBOOT) && defined(CONFIG_SYS_INIT_L3_ADDR)  

  5.           

  6.         SET_TLB_ENTRY(1, CONFIG_SYS_INIT_L3_ADDR, CONFIG_SYS_INIT_L3_ADDR,  

  7.                         MAS3_SX|MAS3_SW|MAS3_SR, MAS2_I|MAS2_G,  

  8.                         0, 0, BOOKE_PAGESZ_1M, 1),  

  9. #else  

  10.         SET_TLB_ENTRY(1, 0xfffff000, 0xfffff000,  

  11.                       MAS3_SX|MAS3_SW|MAS3_SR, MAS2_I|MAS2_G,  

  12.                       0, 0, BOOKE_PAGESZ_4K, 1),  

  13. #endif  

  14.   

  15. <p>会对齐到1M,即0xfff80000 -> 0xfff00000,目的是在跳转到AS0时, 还有TLB entry覆盖对L3 SRAM,因为此时代码是在L3中存放的,还没有relocate到DDR。</p><p></p><p>init_tlbs会执行上面的TLB entry</p><p>_start-> cpu_init_early_f &ndash;> init_tlbs run in AS=1</p>  


在invalidate CPC cache的时候,判断是否作为SRAM,若为SRAM则不invalidate, 因为代码还是在L3 SRAM中,若此时invalidateCPC SRAM,则执行的U-Boot代码也会被清掉。

[cpp] view plaincopy

  1. "arch/powerpc/cpu/mpc85xx/cpu_init.c"  

  2.   

  3. _start_cont -> cpu_init_f -> invalidate_cpc  

  4.   

  5. void invalidate_cpc(void)  

  6.  

  7.         int i;  

  8.         cpc_corenet_t *cpc (cpc_corenet_t *)CONFIG_SYS_FSL_CPC_ADDR;  

  9.   

  10.         for (i 0; CONFIG_SYS_NUM_CPC; i++, cpc++)  

  11.                   

  12.                 if (in_be32(&cpc->cpcsrcr0) CPC_SRCR0_SRAMEN)  

  13.                         continue;  

  14.                   

  15.                 out_be32(&cpc->cpccsr0, CPC_CSR0_FI CPC_CSR0_LFC);  

  16.                 while (in_be32(&cpc->cpccsr0) (CPC_CSR0_FI CPC_CSR0_LFC))  

  17.                          

  18.          

  19.  


在使能CPC cache时,disable PBI command为CPC SRAM配置的LAW16

[cpp] view plaincopy

  1. "arch/powerpc/cpu/mpc85xx/cpu_init.c"  

  2.   

  3. Relocate to RAM -> board_init_r -> cpu_init_r -> enable_cpc  

  4.   

  5. static void enable_cpc(void)  

  6.  

  7.         cpc_corenet_t *cpc (cpc_corenet_t *)CONFIG_SYS_FSL_CPC_ADDR;  

  8.   

  9.         for (i 0; CONFIG_SYS_NUM_CPC; i++, cpc++)  

  10.                 u32 cpccfg0 in_be32(&cpc->cpccfg0);  

  11.                 size += CPC_CFG0_SZ_K(cpccfg0);  

  12. #ifdef CONFIG_RAMBOOT_PBL  

  13.                 if (in_be32(&cpc->cpcsrcr0) CPC_SRCR0_SRAMEN)  

  14.                           

  15.                         struct law_entry law find_law(CONFIG_SYS_INIT_L3_ADDR);  

  16.   

  17.                         if (law.index == -1)  

  18.                                 printf("\nFatal error happened\n");  

  19.                                 return;  

  20.                          

  21.                         disable_law(law.index);  

  22.   

  23.                         clrbits_be32(&cpc->cpchdbcr0, CPC_HDBCR0_CDQ_SPEC_DIS);  

  24.                         out_be32(&cpc->cpccsr0, 0);  

  25.                         out_be32(&cpc->cpcsrcr0, 0);  

  26.                  

  27. #endif  

  28.   

  29.                 out_be32(&cpc->cpccsr0, CPC_CSR0_CE CPC_CSR0_PE);  

  30.                   

  31.                 in_be32(&cpc->cpccsr0);  

  32.   

  33.          

  34.  


3.2 启动image的制作

Freescale的SDK release中用相应的步骤,请参见下面的链接,这里不赘述。


http://www.freescale.com/infocenter/index.jsp?topic=%2Fwelcome%2Findex.html


4. Open source上的patch

  • 4
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值