欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

TEE/REE系统切换时ATF的寄存器的保存和恢复

程序员文章站 2022-07-13 16:11:59
...

1、设置运行时栈SP

bl31_entrypoint—>el3_entrypoint_common---->plat_set_my_stack—>platform_set_stack—>platform_get_stack

动态找到该cpu的栈地址

func platform_set_stack
	mov x9, x30 // lr
	bl  platform_get_stack
	mov sp, x0
	ret x9
endfunc platform_set_stack
/*
 * This macro calculates the base address of the current CPU's MP stack
 * using the plat_my_core_pos() index, the name of the stack storage
 * and the size of each stack
 * Out: X0 = physical address of stack base
 * Clobber: X30, X1, X2
 */
.macro get_my_mp_stack _name, _size
bl  plat_my_core_pos
ldr x2, =(\_name + \_size)
mov x1, #\_size
madd x

补充madd指令小知识
MADD Rd, Rn, Rm, Ra => Rd = Ra + Rn*Rm

2、寄存器的保存和恢复的实现

在tee/ree系统切换时,需要保存和恢复一些寄存器,这些寄存器包含:

  • general registers
  • system registers
  • fp registers
  • EL3_register

函数的实现
例如general registers的保存和恢复,如X0其实是保存在了当前sp + CTX_GPREGS_OFFSET + CTX_GPREG_X0处,也就是保存在了栈中

func save_gp_registers
	stp	x0, x1, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X0]
	stp	x2, x3, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X2]
	stp	x4, x5, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X4]
	stp	x6, x7, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X6]
	stp	x8, x9, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X8]
	stp	x10, x11, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X10]
	stp	x12, x13, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X12]
	stp	x14, x15, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X14]
	stp	x16, x17, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X16]
	stp	x18, x19, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X18]
	stp	x20, x21, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X20]
	stp	x22, x23, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X22]
	stp	x24, x25, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X24]
	stp	x26, x27, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X26]
	stp	x28, x29, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X28]
	mrs	x18, sp_el0
	str	x18, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_SP_EL0]
	ret
endfunc save_gp_registers
func restore_gp_registers_callee_eret
	ldp	x4, x5, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X4]
	ldp	x6, x7, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X6]
	ldp	x8, x9, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X8]
	ldp	x10, x11, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X10]
	ldp	x12, x13, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X12]
	ldp	x14, x15, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X14]
	ldp	x18, x19, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X18]
	ldp	x20, x21, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X20]
	ldp	x22, x23, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X22]
	ldp	x24, x25, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X24]
	ldp	x26, x27, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X26]
	ldp	x28, x29, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X28]
	ldp	 x30, x17, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_LR]
	msr	sp_el0, x17
	ldp	x16, x17, [sp, #CTX_GPREGS_OFFSET + CTX_GPREG_X16]
	eret
endfunc	restore_gp_registers_callee_eret

3、寄存器的保存和恢复的使用场景

在TEE/REE双系统切换的时候,会先保存当前系统的general registers、system registers,然后再恢复目标系统的general registers、system registers. 具体的操作流程如下图所示
TEE/REE系统切换时ATF的寄存器的保存和恢复