您的位置:首页 > 其它

移植u-boot到mini2440--board_init_r 分析

2016-05-04 17:25 459 查看
1> 首先调用 static int initr_reloc,设置 标志重定位已经完成,malloc已经初始化。

static int initr_reloc(void)
{
/* tell others: relocation done */
gd->flags |= GD_FLG_RELOC | GD_FLG_FULL_MALLOC_INIT;
return 0;
}


2> initr_caches 调用 函数
__weak void enable_caches(void)
,这个函数没有实质性工作,需要自己定义板级函数

3> initr_reloc_global_data

monitor_flash_len = _end - __image_copy_start;


这里是求出 u-boot 映像占用的flash 大小,bss因为是未初始化的变量,不占用flash空间。

4> initr_barrier 空函数

5> initr_malloc 初始化堆内存

6> tdio_init_tables –> 调用 INIT_LIST_HEAD 初始化 stdio_dev 结构体的 list 成员。

7> initr_serial –> serial_initialize (drivers/serial/serial.c)

  在源文件中可以看到 这个函数调用了很多串口初始化的函数。但是在反汇编文件中看到它所调用的大部分都是空函数
amirix_serial_initialize
有效的函数调用只有一个
s3c24xx_serial_initialize


void s3c24xx_serial_initialize(void)
{
serial_register(&s3c24xx_serial0_device);
serial_register(&s3c24xx_serial1_device);
serial_register(&s3c24xx_serial2_device);
}


void serial_register(struct serial_device *dev)
{
dev->next = serial_devices;
serial_devices = dev;
}


8> stdio_add_devices 这个函数又调用了2个函数:

drv_system_init ();
serial_stdio_init ()


static void drv_system_init (void)
{
struct stdio_dev dev;

memset (&dev, 0, sizeof (dev));

strcpy (dev.name, "serial");
dev.flags = DEV_FLAGS_OUTPUT | DEV_FLAGS_INPUT;
dev.putc = stdio_serial_putc;
dev.puts = stdio_serial_puts;
dev.getc = stdio_serial_getc;
dev.tstc = stdio_serial_tstc;
stdio_register (&dev);
}


  注意这里是
stdio_register
跟上面的
serial_register
还不一样。

/**
* serial_stdio_init() - Register serial ports with STDIO core
*
* This function generates a proxy driver for each serial port driver.
* These proxy drivers then register with the STDIO core, making the
* serial drivers available as STDIO devices.
*/
void serial_stdio_init(void)
{
struct stdio_dev dev;
struct serial_device *s = serial_devices;

while (s) {
memset(&dev, 0, sizeof(dev));

strcpy(dev.name, s->name);
dev.flags = DEV_FLAGS_OUTPUT | DEV_FLAGS_INPUT;

dev.start = serial_stub_start;
dev.stop = serial_stub_stop;
dev.putc = serial_stub_putc;
dev.puts = serial_stub_puts;
dev.getc = serial_stub_getc;
dev.tstc = serial_stub_tstc;
dev.priv = s;

stdio_register(&dev);

s = s->next;
}
}


  这里把
initr_serial
函数注册的所有
serial_device
serial_stub_xxx
系列函数关联起来,并且调用
stdio_register


9> console_init_r 调用了

inputdev  = search_device(DEV_FLAGS_INPUT,  "serial");
outputdev = search_device(DEV_FLAGS_OUTPUT, "serial");
errdev    = search_device(DEV_FLAGS_OUTPUT, "serial");


  分别获取 标准输入,输出,错误设备,参数为 “serial” 。通过分析这里可知道它们都是前面通过drv_system_init ()注册的设备。

然后又调用

console_doenv(stdout, outputdev);
console_doenv(stderr, errdev);
console_doenv(stdin, inputdev);


  把设备与句柄绑定。

  最后设置标志,意味着设备初始化完成。

gd->flags |= GD_FLG_DEVINIT;    /* device initialization completed */


至于printf 执行流由于变动不大可以参考别人写的博文
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息