注:下文都以S5PV210爲背景。
210的BL0決定了從SD卡拷貝到RAM中的程序最大隻能有16KB,如果我們希望允許的程序大小不受限制,就需要進行SD卡重定位。
一。如何進行重定位
SD卡是塊設備,對其的讀寫是時序操作,需要寫專門的函數處理讀寫,好在BL0中已經自帶了SD卡的讀函數。
函數參數分別是:
通道號,SD卡上源文件地址(塊爲單位),文件大小(塊爲單位),內存上的目標地址(字節爲單位), SD卡是否初始化。
通道號:由於BL0的原因,所以通道號是固定的。
SD卡上源文件地址(塊爲單位):我是將整個文件全部拷貝,又由於BL0造成了起始地址是block1所以, 這裏也是1。原因可見下圖。
文件大小:這需要計算。計算方法就是使用連接腳本,得到文件的起始地址和結束地址(不包括bss段), 兩者相減再加1。
內存上的目標地址:根據連接腳本設定。
這樣我們就可以使用這個函數將SD卡中的.bin文件拷貝到DDR上了,然後再在彙編中使用遠跳轉即可。
代碼如下:
sd_locate.c
#define CHANNEL 2
#define STARTBLK 1
#define MEMADDR 0x24000000
#define CARDINIT 0
typedef unsigned int bool;
typedef bool (*pCopySDMMCtoMem) (int, unsigned int, unsigned short, unsigned int *, bool);
void sd_relocate(unsigned int FileSize)
{
volatile unsigned int count;
pCopySDMMCtoMem p = (pCopySDMMCtoMem)(*(unsigned int *)0xD0037F98);
int i = (*p)(CHANNEL, STARTBLK, (FileSize/512)+1, MEMADDR, CARDINIT);
if(0 == i)
{
printf("sd_relocate failed\n");
while(1);
}
}
start.S
ldr r0, =_start //得到.bin文件大小
ldr r1, =bss_start
sub r0, r0, r1
bl sd_relocate //sd重定位
ldr r0, =bss_start //清bss
ldr r1, =bss_end
ldr r2, =0
cmp r0, r1
beq run_main
clear_loop:
str r2, [r0], #4
cmp r0, r1
bne clear_loop
bl led_off
run_main:
ldr pc, =main