Uboot学习笔记④---(start.S简单分析)

本文所有资料来至互联网,笔者加以整理和归纳,仅供以后复习

对于uboot的start.S,主要做的事情就是系统的各个方面的初始化。

从大的方面分,可以分成这几个部分:

  • 设置CPU模式
  • 关闭看门狗
  • 关闭中断
  • 设置堆栈sp指针
  • 清除bss段
  • 异常中断处理

1、分析.globl _start

         . global的语法
DirectiveDescriptionSyntaxExample
.globalMakes symbol visible to the linker.global symbol.global MyAsmFunc
.globlSame as .global.globl symbol.globl MyOtherAsmFunc

所以,意思很简单,就是相当于C语言中的Extern,声明此变量,并且告诉链接器此变量是全局的,外部可以访问

所以,你可以看到

board\开发板名\u-boot.lds

中,有用到此变量:

ENTRY(_start)

即指定入口为_start,而由下面的_start的含义可以得知,_start就是整个start.S的最开始,即整个uboot的代码的开始。

2、分析 _start: b    reset

start的值,也就是这个代码的位置了,此处即为代码的最开始,相对的0的位置。

在程序开始运行的时候,如果是从NorFlash或NandFlash启动,那么其地址是0,

_start=0

如果是重新relocate代码之后,就是我们定义的值了,即,在

board\开发板名\config.mk

中的:

TEXT_BASE = 0x33D00000

表示是代码段的基地址,即

_start=TEXT_BASE=0x33D00000

2、分析 LDR

    ldr    pc, _undefined_instruction
    ldr    pc, _software_interrupt
    ldr    pc, _prefetch_abort
    ldr    pc, _data_abort
    ldr    pc, _not_used
    ldr    pc, _irq
    ldr    pc, _fiq

LDR R0,[R1] ;将存储器地址为R1的字数据读入寄存器R0。

LDR R0,[R1,R2] ;将存储器地址为R1+R2的字数据读入寄存器R0。

LDR R0,[R1,#8] ;将存储器地址为R1+8的字数据读入寄存器R0。

LDR R0,[R1,R2]! ;将存储器地址为R1+R2的字数据读入寄存器R0,并将新地址R1+R2写入R1。

LDR R0,[R1,#8]! ;将存储器地址为R1+8的字数据读入寄存器R0,并将新地址R1+8写入R1。

LDR R0,[R1],R2 ;将存储器地址为R1的字数据读入寄存器R0,并将新地址R1+R2写入R1。

LDR R0,[R1,R2,LSL#2]! ;将存储器地址为R1+R2×4的字数据读入寄存器R0,并将新地址R1+R2×4写入R1。

LDR R0,[R1],R2,LSL#2 ;将存储器地址为R1的字数据读入寄存器R0,并将新地址R1+R2×4写入R1。

3、分析 .word

_undefined_instruction:
	.word undefined_instruction
_software_interrupt:
	.word software_interrupt
_prefetch_abort:
	.word prefetch_abort
_data_abort:
	.word data_abort
_not_used:
	.word not_used
_irq:
	.word irq
_fiq:
	.word fiq

表 1.2. .word的语法
DirectiveDescriptionSyntaxExample
.wordDefine word expr (32bit numbers).word expr {, …}.word 144511, 0x11223

所以上面的含义,以_undefined_instruction为例,就是,此处分配了一个word=32bit=4字节的地址空间,里面存放的值是undefined_instruction。

而此处_undefined_instruction也就是该地址空间的地址了。用C语言来表达就是:

_undefined_instruction = &undefined_instruction

*_undefined_instruction = undefined_instruction

在后面的代码,我们可以看到,undefined_instruction也是一个标号,即一个地址值,对应着就是在发生“未定义指令”的时候,系统所要去执行的代码。

(其他几个对应的“软件中断”,“预取指错误”,“数据错误”,“未定义”,“(普通)中断”,“快速中断”,也是同样的做法,跳转到对应的位置执行对应的代码。)

3、分析 .balignl

    .balignl 16,0xdeadbeef

表 1.3. balignl的语法
DirectiveDescriptionSyntaxExample
.balignlWord align the following code to alignment byte boundary (default=4). Fill skipped words with fill (default=0 or NOP). If the number of bytes skipped is greater than max, then don't align (default=alignment )..balignl {alignment} {, fill} {, max}.balignl

所以意思就是,接下来的代码,都要16字节对齐,不足之处,用0xdeadbeef填充。

其中关于所要填充的内容0xdeadbeef,此处0xdeadbeef本身没有真正的意义,但是很明显,字面上的意思是,(坏)死的牛肉。

虽然其本身没有实际意义,但是其是在十六进制下,能表示出来的,为数不多的,可读的单词之一了。

另外一个相对常见的是:0xbadc0de,意思是bad code,坏的代码,注意其中的o是0,因为十六进制中是没有o的。

这些“单词”,相对的作用是,使得读代码的人,以及在查看程序运行结果时,容易看懂,便于引起注意。


4、分析 _TEXT_BASE 和_armboot_start

/*
 *************************************************************************
 *
 * Startup Code (reset vector)
 *
 * do important init only if we don't start from memory!
 * setup Memory and board specific bits prior to relocation.
 * relocate armboot to ram
 * setup stack
 *
 *************************************************************************
 */

_TEXT_BASE:
    .word    TEXT_BASE

/*
 * Below variable is very important because we use MMU in U-Boot.
 * Without it, we cannot run code correctly before MMU is ON.
 * by scsuh.
 */
/* 此处的<pre name="code" class="objc">CFG_PHY_UBOOT_BASE应该在某处定义
*/
_TEXT_PHY_BASE: .word CFG_PHY_UBOOT_BASE.globl _armboot_start_armboot_start: .word _start

 
  
 

TEXT_BASE在\board\开发板名\config.mk中定义

同理,此含义可用C语言表示为:

*(_armboot_start) = _start

5、分析 bss_start和_bss_end

/*
 * These are defined in the board-specific linker script.
 */
.globl _bss_start
_bss_start:
	.word __bss_start

.globl _bss_end
_bss_end:
	.word _end
关于_bss_start和_bss_end都只是两个标号,对应着此处的地址。

而两个地址里面分别存放的值是__bss_start和_end,这两个的值,根据注释所说,是定义在开发板相关的链接脚本里面的,我们此处的开发板相关的链接脚本是:

board\开发板名\u-boot.lds

__bss_start = .;
	.bss : { *(.bss) }
	_end = .;

详细解析参考博客:http://www.crifan.com/about/me/

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值