在完成地址无关fixup后,u-boot开始对一些系统寄存器进行初始化。
第一段代码如下:
pie_fixup_done:
#endif
#ifdef CONFIG_SYS_RESET_SCTRL
bl reset_sctrl --------------------------------------------------------------------- (1)
#endif
#if defined(CONFIG_ARMV8_SPL_EXCEPTION_VECTORS) || !defined(CONFIG_SPL_BUILD) ---------- (2)
.macro set_vbar, regname, reg
msr regname, reg
.endm
adr x0, vectors
#else
.macro set_vbar, regname, reg
.endm
#endif
/*
* Could be EL3/EL2/EL1, Initial State:
* Little Endian, MMU Disabled, i/dCache Disabled
*/
switch_el x1, 3f, 2f, 1f ---------------------------------------------------------- (3)
3: set_vbar vbar_el3, x0
mrs x0, scr_el3
orr x0, x0, #0xf /* SCR_EL3.NS|IRQ|FIQ|EA */
msr scr_el3, x0
msr cptr_el3, xzr /* Enable FP/SIMD */
b 0f
2: mrs x1, hcr_el2
tbnz x1, #34, 1f /* HCR_EL2.E2H */
set_vbar vbar_el2, x0
mov x0, #0x33ff
msr cptr_el2, x0 /* Enable FP/SIMD */
b 0f
1: set_vbar vbar_el1, x0
mov x0, #3 < < 20
msr cpacr_el1, x0 /* Enable FP/SIMD */
0:
#ifdef COUNTER_FREQUENCY -------------------------------------------------------------- (4)
branch_if_not_highest_el x0, 4f
ldr x0, =COUNTER_FREQUENCY
msr cntfrq_el0, x0 /* Initialize CNTFRQ */
#endif
4: isb ------------------------------------------------------------------------------- (5)
...
...
#ifdef CONFIG_SYS_RESET_SCTRL
reset_sctrl:
switch_el x1, 3f, 2f, 1f
3:
mrs x0, sctlr_el3
b 0f
2:
mrs x0, sctlr_el2
b 0f
1:
mrs x0, sctlr_el1
0:
ldr x1, =0xfdfffffa
and x0, x0, x1
switch_el x1, 6f, 5f, 4f
6:
msr sctlr_el3, x0
b 7f
5:
msr sctlr_el2, x0
b 7f
4:
msr sctlr_el1, x0
7:
dsb sy
isb
b __asm_invalidate_tlb_all ----------------------------------------------------- (6)
ret
#endif
- • (1)一般情况下此功能不需要使用,但是一些由其他固件引导启动的u-boot,board希望系统行为能按照自己预期行为执行而不受上一级加载器的影响,所以使用CONFIG_SYS_RESET_SCTRL来决定是否重置系统控制寄存器,包括保证处理器处于小端,关闭data cache,关闭mmu。 其中switch_el是一个宏,用于读取当前所处的异常级别,根据所处异常级别调用对应的系统控制寄存器。某些时候u-boot的加载并不是一定在el3级别,当存在atf等时,el3由atf控制,atf会将u-boot的运行级别切换到el2,以便保证自己的控制级别,所以u-boot通过switch_el来选择自己能够控制的系统寄存器。
- • (2)定义设置异常向量表的宏,将异常向量表的地址写入/reg设置的系统寄存器即可完成异常向量表的设置,这里u-boot是需要设置异常向量表的,而spl默认是不需要设置异常向量表的,毕竟spl只是一个加载器只会运行一次,不过当定义了CONFIG_ARMV8_SPL_EXCEPTION_VECTORS时可以为spl也设置一个异常向量表。
- • (3)同样的使用switch_el来跳转到对应级别的路径上去执行,在进行系统寄存器设置时,因为在这之前已经由SYS_RESET_SCTRL或者board自己保证处理器处于小端,mmu关,i-cache和d-cache处于关闭状态了,所以这里直接进行对应级别系统寄存器设置,首先是跳转到对应表设置对应级别的异常向量表。接着会有如下三种情况: 当处于EL3时,会设置安全配置系统寄存器(scr_el3),会将低四位bit设置为0xf,表示设置处理器处于非安全模式,任何级别的物理irq中断,物理fiq,异常abort中断,异常SError中断都将被路由到el3级别。后续这些设置将在启动Linux时被修改,这些设置仅用于在u-boot阶段。接着将cptr_el3清零,使用xzr是可以快速操作寄存器为零。这里保证任何级别下访问SIMD和floating-point指令不会导致触发异常陷入el3。 当处于EL2时,首先根据HCR_EL2.E2H判断系统是一个虚拟机管理器还是主机系统,当E2H = 0时,表示系统处于主机系统只需要做el3一样的操作配置SIMD和FP指令不会陷入el2即可。 当系统处于EL1时,则什么也不需要操作只需要配置SIMD和FP指令不会陷入el1。
- • (4)u-boot在启动时系统的时钟频率不一定配置了,所以当在include/configs/xxxxxx.h中定义了COUNTER_FREQUENCY的频率值时,说明需要在此处配置系统时钟,所以根据宏 branch_if_not_highest_el判断当系统不处于EL3时则需要设置系统的时钟工作频率cntfrq_el0,后续Linux或者u-boot根据读出的这个值计算出系统每纳秒的滴答数从而供软件获取时间流逝值。
- • (5)isb指令用于确保上述操作指令被正确真正的执行了,属于同步指令的一种。
- • (6)在进行系统控制器复位时,dsb sy,isb,__asm_invalidate_tlb_all三个操作在这里的意义是,因为对处理器的小端,mmu,d-cache进行了复位,所以这里必须通过dsb和isb确保数据和指令全部执行和写入,这里进行了mmu和cache关闭操作,那么如果有缓存的tlb在这个时候这些缓存的tlb数据就是无效的,这里对可能缓存的tlb进行全部无效化,确保后续任何可能的mmu开启操作不会使用到这些无用的tlb条目而导致系统异常。
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。
举报投诉
-
ARM
+关注
关注
134文章
9190浏览量
370113 -
寄存器
+关注
关注
31文章
5386浏览量
121519 -
Uboot
+关注
关注
4文章
126浏览量
28401 -
系统
+关注
关注
1文章
1020浏览量
21466
发布评论请先 登录
相关推荐
U-Boot介绍
在移植 Linux之前我们需要先移植一个 bootloader 代码,这个 bootloader 代码用于启动 Linux 内核, bootloader有很多,常用的就是 U-Boot。
U-boot的基本介绍
从本文开始,将陆续推送“手把手教你移植U-boot”系列文章,目标是由浅入深地讲解U-boot的工作流程、原理、配置方法和移植方法,手把手教你完成U-boot的移植工作,默认硬件开发平台为ARM,操作
发表于 07-14 16:52
•3250次阅读

基于开发板的U-Boot移植
bootloader,也就是通用的bootloader。它存在于nandflash或者SD卡中,它是在开机上点之后,操作系统起来之前用来引导的一个程序。U-boot 的主要作用是进行内存的初
发表于 01-14 14:31
U-BOOT的启动流程分享
Bootloader移植(下)U-BOOT 启动流程u-boot启动三个2启动步骤(重点)U-boot 启动源码分析U-BOOT 启动流程u-boo
发表于 01-18 10:17
u-boot简介
。 U-Boot是BootLoader的一种,是在操作系统内核运行之前运行。可以初始化硬件设备、建立内存空间映射图,从而将系统的软硬件环境带到一个
发表于 10-14 11:17
•3607次阅读
NAND闪存中启动U-BOOT的设计解析
U-BOOT 支持ARM、 PowerPC等多种架构的处理器,也支持Linux、NetBSD和VxWorks等多种操作系统,主要用来开发嵌入式系统初
发表于 10-29 11:29
•2次下载
如何使用Xilinx SDK调试u-boot代码
了解如何使用Xilinx SDK调试u-boot代码。
概述了技术以获得重定位偏移量,以便可以在SDK中应用它。
U-Boot启动内核的工作过程详细说明
U-Boot 启动内核的过程可以分为两个阶段,两个阶段的功能如下:(1)第一阶段的功能
硬件设备初始化
加载 U-Boot 第二阶段代码到 RAM 空间
设置好栈
跳转到第二阶段
发表于 12-28 08:00
•3次下载

tiny4412编译与移植U-Boot
U-Boot 是一个主要用于嵌入式系统的引导加载程序, U-Boot本质是一个裸机程序,是一种普遍用于嵌入式系统中的开源的Bootloader,作用是用来引导操作

u-boot在汇编启动阶段的相关操作介绍
u-boot在汇编启动阶段对系统的一些初始化 当cpu交由u-boot接管进入u-boot后, 首先会到_start符号处开始执行
评论