ARM64-A移植说明
4 分钟阅读
概述
XWOS的源码中,已包含了大部分ARM64-Cortex-A架构的代码:
- 架构描述层(ADL)
- ARMv8a:
XWOS/xwcd/soc/arm/v8a
- ARMv8a:
- CPU描述层(CDL)
- m0:
XWOS/xwcd/soc/arm/v8a/a72
- m0p:
XWOS/xwcd/soc/arm/v8a/a76_a55
- m0:
- SOC描述层(SDL)
- UNISOC UIS7870:
XWOS/xwcd/soc/arm/v8a/a76_a55/uis7870
- 树莓派4B SOC:
XWOS/xwcd/soc/arm/v8a/a72/bcm2711
- UNISOC UIS7870:
新的SOC芯片,只需在CPU文件夹中增加SOC文件夹,其中包括:
- 初始化:
soc_init.h
与soc_init.c
- 中断:
xwosimpl_irq.h
与xwosimpl_irq.c
- 其中需要给出XWOS内核移植层(XWOSPL)
XWOS/xwos/ospl/irq.h
中声明的函数的实现。
- 其中需要给出XWOS内核移植层(XWOSPL)
- 调度器:
xwosimpl_skd.h
与xwosimpl_skd.c
- 其中需要给出XWOS内核移植层(XWOSPL)
XWOS/xwos/ospl/skd.h
中声明的函数的实现。
- 其中需要给出XWOS内核移植层(XWOSPL)
- 滴答定时器:
xwosimpl_syshwt.h
与xwosimpl_syshwt.c
- 其中需要给出XWOS内核移植层(XWOSPL)
XWOS/xwos/ospl/syshwt.h
中声明的函数的实现。
- 其中需要给出XWOS内核移植层(XWOSPL)
.lds
:链接脚本
类型的定义
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/type.h
要求SOC给出标准类型的定义:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_type.h
编译器的宏定义
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_compiler.h
- gcc:
XWOS/xwcd/soc/arm/v8a/compiler/gcc.h
- llvm:
XWOS/xwcd/soc/arm/v8a/compiler/llvm.h
无锁队列的实现
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_lfq.h
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_lfq.c
自旋锁
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_spinlock.h
架构指令
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_isa.h
位操作
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwbop.h
XWOS/xwcd/soc/arm/v8a/xwbop/
8位原子操作
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/xwaop8.h
要求SOC在汇编指令层面给出单字节原子操作的实现:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwaop8.h
XWOS/xwcd/soc/arm/v8a/xwaop/xwaops8.c
XWOS/xwcd/soc/arm/v8a/xwaop/xwaopu8.c
16位原子操作
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/xwaop16.h
要求SOC在汇编指令层面给出双字节原子操作的实现:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwaop16.h
XWOS/xwcd/soc/arm/v8a/xwaop/xwaops16.c
XWOS/xwcd/soc/arm/v8a/xwaop/xwaopu16.c
32位原子操作
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/xwaop32.h
要求SOC在汇编指令层面给出4字节原子操作的实现:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwaop32.h
XWOS/xwcd/soc/arm/v8a/xwaop/xwaops32.c
XWOS/xwcd/soc/arm/v8a/xwaop/xwaopu32.c
64位原子操作
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/xwaop64.h
要求SOC在汇编指令层面给出8字节原子操作的实现:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwaop64.h
XWOS/xwcd/soc/arm/v8a/xwaop/xwaop64.c
XWOS/xwcd/soc/arm/v8a/xwaop/xwaopu64.c
位图原子操作
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/soc/xwbmpaop.h
要求SOC在汇编指令层面给出位图原子操作的实现:
XWOS/xwcd/soc/arm/v8a/xwosimpl_soc_xwbmpaop.h
XWOS/xwcd/soc/arm/v8a/xwbmpaop/
系统初始化
-
SPSel
设置为1
,不同EL等级使用不同的SP寄存器 -
SCTLR_EL1.EE = 0
:选择小端格式 -
SCTLR_EL1.SA = 1
:开启stack对齐检测 -
SCTLR_EL1.A = 0
:关闭对齐检测,对齐检测经常导致进sync异常 -
SCTLR_EL1.C = 1
:开启数据缓存 -
SCTLR_EL1.I = 1
:开启指令缓存 -
SCTLR_EL2.EE = 0
:选择小端格式 -
SCTLR_EL2.SA = 1
:开启stack对齐检测 -
SCTLR_EL2.A = 0
:关闭对齐检测,对齐检测经常导致进sync异常 -
SCTLR_EL2.C = 1
:开启数据缓存 -
SCTLR_EL2.I = 1
:开启指令缓存 -
CPACR_EL1.FPEN = 0b11
:开启浮点单元 -
暂时不启用虚拟化
HCR_EL2.VM = 0
HCR_EL2.TGE = 0
中断
XWOS移植实现层的 Adaptee 位于:
XWOS/xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_irq.h
XWOS/xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_irq.c
- 不在EL3响应异常
SCR_EL3.FIQ = 0
SCR_EL3.IRQ = 0
HCR_EL3.EA = 0
HCR_EL3.HCE = 1
开启 HVC
指令
-
CPTR_EL3
中关闭trap -
CPTR_EL2
中关闭trap -
在EL2中处理中断
HCR_EL2.AMO = 1
HCR_EL2.IMO = 1
HCR_EL2.FMO = 1
调度器
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/skd.h
要求SOC给出调度器切换上下文等操作的实现,各个型号的MCU采用不同的实现:
XWOS/xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_soc_skd.h
XWOS/xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_soc_skd.c
由于基于Cortex-M内核的单片机一致性比较好,所以不同的单片机最终都是调用下面文件中的函数来给出具体实现:
XWOS/xwcd/soc/arm/v8a/arch_skd.h
XWOS/xwcd/soc/arm/v8a/arch_skd.c
XWOS内核运行在EL2,使用sp_el2
线程
线程运行在 EL2T
,内核运行在 EL2H
。
栈
- 按照AAPCS64的要求,使用 16字节对齐 的 满递减 栈,
因此配置文件
cfg/xwos.h
XWMMCFG_FD_STACK
配置为1
XWMMCFG_ALIGNMENT
配置为16U
栈结构
+------------+-----------------------------+
sp+0x31c | reserved | |
sp+0x318 | reserved | |
sp+0x314 | reserved | |
sp+0x310 | FPSR | volatile (caller-saved) |
+------------+-----------------------------+
sp+0x300 | q31 | volatile (caller-saved) |
sp+0x2F0 | q30 | volatile (caller-saved) |
sp+0x2E0 | q29 | volatile (caller-saved) |
sp+0x2D0 | q28 | volatile (caller-saved) |
sp+0x2C0 | q27 | volatile (caller-saved) |
sp+0x2B0 | q26 | volatile (caller-saved) |
sp+0x2A0 | q25 | volatile (caller-saved) |
sp+0x290 | q24 | volatile (caller-saved) |
sp+0x280 | q23 | volatile (caller-saved) |
sp+0x270 | q22 | volatile (caller-saved) |
sp+0x260 | q21 | volatile (caller-saved) |
sp+0x250 | q20 | volatile (caller-saved) |
sp+0x240 | q19 | volatile (caller-saved) |
sp+0x230 | q18 | volatile (caller-saved) |
sp+0x220 | q17 | volatile (caller-saved) |
sp+0x210 | q16 | volatile (caller-saved) |
+------------+-----------------------------+
sp+0x200 | q15 | non-volatile (callee-saved) |
sp+0x1F0 | q14 | non-volatile (callee-saved) |
sp+0x1E0 | q13 | non-volatile (callee-saved) |
sp+0x1D0 | q12 | non-volatile (callee-saved) |
sp+0x1C0 | q11 | non-volatile (callee-saved) |
sp+0x1B0 | q10 | non-volatile (callee-saved) |
sp+0x1A0 | q9 | non-volatile (callee-saved) |
sp+0x190 | q8 | non-volatile (callee-saved) |
+------------+-----------------------------+
sp+0x180 | q7 | volatile (caller-saved) |
sp+0x170 | q6 | volatile (caller-saved) |
sp+0x160 | q5 | volatile (caller-saved) |
sp+0x150 | q4 | volatile (caller-saved) |
sp+0x140 | q3 | volatile (caller-saved) |
sp+0x130 | q2 | volatile (caller-saved) |
sp+0x120 | q1 | volatile (caller-saved) |
sp+0x110 | q0 | volatile (caller-saved) |
+------------+-----------------------------+
sp+0x108 | pstate | volatile (caller-saved) |
sp+0x100 | pc | volatile (caller-saved) |
sp+0xF8 | sp | volatile (caller-saved) |
sp+0xF0 | lr | volatile (caller-saved) |
---------+------------+-----------------------------+
sp+0xE8 | x29 | non-volatile (callee-saved) |
sp+0xE0 | x28 | non-volatile (callee-saved) |
sp+0xD8 | x27 | non-volatile (callee-saved) |
sp+0xD0 | x26 | non-volatile (callee-saved) |
sp+0xC8 | x25 | non-volatile (callee-saved) |
sp+0xC0 | x24 | non-volatile (callee-saved) |
sp+0xB8 | x23 | non-volatile (callee-saved) |
sp+0xB0 | x22 | non-volatile (callee-saved) |
sp+0xA8 | x21 | non-volatile (callee-saved) |
sp+0xA0 | x20 | non-volatile (callee-saved) |
sp+0x98 | x19 | non-volatile (callee-saved) |
sp+0x90 | x18 | non-volatile (callee-saved) |
---------+------------+-----------------------------+
sp+0x88 | x17 | volatile (caller-saved) |
sp+0x80 | x16 | volatile (caller-saved) |
sp+0x78 | x15 | volatile (caller-saved) |
sp+0x70 | x14 | volatile (caller-saved) |
sp+0x68 | x13 | volatile (caller-saved) |
sp+0x60 | x12 | volatile (caller-saved) |
sp+0x58 | x11 | volatile (caller-saved) |
sp+0x50 | x10 | volatile (caller-saved) |
sp+0x48 | x9 | volatile (caller-saved) |
sp+0x40 | x8 | volatile (caller-saved) |
sp+0x38 | x7 | volatile (caller-saved) |
sp+0x30 | x6 | volatile (caller-saved) |
sp+0x28 | x5 | volatile (caller-saved) |
sp+0x20 | x4 | volatile (caller-saved) |
sp+0x18 | x3 | volatile (caller-saved) |
sp+0x10 | x2 | volatile (caller-saved) |
sp+0x08 | x1 | volatile (caller-saved) |
sp+0x00 | x0 | volatile (caller-saved) |
--------------------------------------------
- 说明:x18寄存器按照官方手册描述,应该为 caller-saved ,
但Linux内核将此寄存器用作 ShadowCallStack 的指针(配置
CONFIG_SHADOW_CALL_STACK
为y
时), 此时x18应该为 callee-saved 的。 - XWOS和Linux保持一致,因此x18也为 callee-saved 。
- 需要增加编译选项
-ffixed-x18
。
滴答定时器
XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/syshwt.h
要求SOC给出滴答定时器的实现,各个型号的MCU采用不同的实现:
xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_soc_syshwt.h
xwcd/soc/arm/v8a/[CPU]/[SOC]/xwosimpl_soc_syshwt.c