ARM-Cortex-M移植说明

概述

XWOS的源码中,已包含了大部分ARM-Cortex-M架构的代码:

  • 架构描述层(ADL)
    • ARMv7m: XWOS/xwcd/soc/arm/v7m
    • ARMv6m: XWOS/xwcd/soc/arm/v6m
  • CPU描述层(CDL)
    • m0: XWOS/xwcd/soc/arm/v6m/m0
    • m0p: XWOS/xwcd/soc/arm/v6m/m0p
    • m3: XWOS/xwcd/soc/arm/v7m/m3
    • m4: XWOS/xwcd/soc/arm/v7m/m4
    • m7: XWOS/xwcd/soc/arm/v7m/m7
  • SOC描述层(SDL)
    • STM32:
      • L0/F0: XWOS/xwcd/soc/arm/v7m/m0/stm32
      • L1/F1: XWOS/xwcd/soc/arm/v7m/m3/stm32
      • L4/F4: XWOS/xwcd/soc/arm/v7m/m4/stm32
        • F7/H7: XWOS/xwcd/soc/arm/v7m/m7/stm32
    • S32K: XWOS/xwcd/soc/arm/v7m/m4/s32k14x
    • i.MX RT1052: XWOS/xwcd/soc/arm/v7m/m7/mimxrt1052

新的SOC芯片,只需在CPU文件夹中增加SOC文件夹,其中包括:

  • 初始化: soc_init.hsoc_init.c
  • 中断: xwosimpl_irq.hxwosimpl_irq.c
    • 其中需要给出XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/irq.h 中声明的函数的实现。
  • 调度器: xwosimpl_skd.hxwosimpl_skd.c
    • 其中需要给出XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/skd.h 中声明的函数的实现。
  • 滴答定时器: xwosimpl_syshwt.hxwosimpl_syshwt.c
    • 其中需要给出XWOS内核移植层(XWOSPL) XWOS/xwos/ospl/syshwt.h 中声明的函数的实现。
  • .lds :链接脚本

可以复制一个SDL文件夹(例如STM32)作为模板, 所有Cortex-M的单片机 XWOSIMPL 都是一样的。

类型的定义

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_type.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_type.h

编译器的宏定义

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_compiler.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_compiler.h

无锁队列的实现

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_lfq.h
XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_lfq.c
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_lfq.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_lfq.c

自旋锁

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_spinlock.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_spinlock.h

架构指令

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_isa.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_isa.h

位操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwbop.h
XWOS/xwcd/soc/arm/v6m/asmlib/xwbop/
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwbop.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwbop/
XWOS/xwcd/soc/arm/v7m/asmlib/xwbmpop/

8位原子操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwaop8.h
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xws8/
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xwu8/
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwaop8.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xws8/
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xwu8/

16位原子操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwaop16.h
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xws16/
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xwu16/
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwaop16.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xws16/
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xwu16/

32位原子操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwaop32.h
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xws32/
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xwu32/
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwaop32.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xws32/
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xwu32/

64位原子操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwaop64.h
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xws64/
XWOS/xwcd/soc/arm/v6m/asmlib/xwaop/xwu64/
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwaop64.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xws64/
XWOS/xwcd/soc/arm/v7m/asmlib/xwaop/xwu64/

位图原子操作

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/xwosimpl_soc_xwbmpaop.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_xwbmpaop.h
XWOS/xwcd/soc/arm/v7m/asmlib/xwbmpaop/

setjmp()/longjmp()

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_setjmp.h
XWOS/xwcd/soc/arm/v7m/xwosimpl_soc_setjmp.c

C标准库中定义的 setjmp()/longjmp() 是可在不同函数之间跳转的 goto , 有些libc的实现没有考虑浮点寄存器栈,因此XWOS重新实现了这两个函数。

  • 完整的栈结构如下:
            -----------------------------
   sp+0x64  | s31             |         |
   sp+0x60  | s30             |         |
   sp+0x5C  | s29             |         |
   sp+0x58  | s28             |         |
   sp+0x54  | s27             |         |
   sp+0x50  | s26             |         |
   sp+0x4C  | s25             |   FP    |
   sp+0x48  | s24             |  Frame  |
   sp+0x44  | s23             |         |
   sp+0x40  | s22             |         |
   sp+0x3C  | s21             |         |
   sp+0x38  | s20             |         |
   sp+0x34  | s19             |         |
   sp+0x30  | s18             |         |
   sp+0x2C  | s17             |         |
   sp+0x28  | s16             |         |
            -----------------------------
   sp+0x24  | r14 (lr)        |         |
   sp+0x20  | r13 (sp)        |         |
   sp+0x1C  | r11 (fp)        |         |
   sp+0x18  | r10 (sl)        |         |
   sp+0x14  | r9              |  Basic  |
   sp+0x10  | r8              |  Frame  |
   sp+0x0C  | r7              |         |
   sp+0x08  | r6              |         |
   sp+0x04  | r5              |         |
   sp+0x00  | r4              |         |
            -----------------------------
              setjmp/longjmp寄存器栈结构

线程本地存储TLS

TLS是C11标准开始引入的语言特性。XWOS支持TLS,Cortex-M的MCU采用统一实现:

XWOS/xwcd/soc/arm/v6m/xwosimpl_tls.c
XWOS/xwcd/soc/arm/v7m/xwosimpl_tls.c

XWOS将TLS数据段放在线程栈内存起始的位置。

            ------------------------
            | Thread Stack Memmory |
            +----------------------+
   SP --->  |                      |
            |                      |
            |                      |
            |                      |
            |                      |
            |                      |
            |     Stack Region     |
            |                      |
            |                      |
            |                      |
            |                      |
            |                      |
            |                      |
            +----------------------+
            |                      |
            |     Stack Guard      |
            |                      |
            +----------------------+
            |                      |
            |      TLS Region      |
            |                      |
            ------------------------

调度器

XWOS移植实现层的 Adaptee 位于:

XWOS/xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_soc_skd.h
XWOS/xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_soc_skd.c
XWOS/xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_soc_skd.h
XWOS/xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_soc_skd.c

由于基于Cortex-M内核的单片机一致性比较好,所以不同的单片机最终都是调用下面文件中的函数来给出具体实现:

XWOS/xwcd/soc/arm/v6m/arch_skd.h
XWOS/xwcd/soc/arm/v6m/arch_skd.c
XWOS/xwcd/soc/arm/v7m/arch_skd.h
XWOS/xwcd/soc/arm/v7m/arch_skd.c

线程的栈

  • XWOS在ARMv6/7-m平台的实现上,使用 8字节对齐 的栈, 因此必须在芯片初始化的最早阶段将CCR寄存器中的STKALIGN设置为1:
cm_scs.scb.ccr.bit.stkalign = 1;
  • 使用满递减栈,即配置文件 cfg/xwos.hXWMMCFG_FD_STACK 配置为 1
  • 当CPU中包含浮点单元时,开启浮点上下文自动保存与恢复,即
cm_scs.scb.fpu.fpccr.bit.aspen = 1;

线程的栈结构

C语言一般将寄存器分为两部分:易失性的(volatile)和非易失性的(non-volatile)。 当使用到易失性(volatile)寄存器时不需要保存值和恢复; 当使用到非易失性(non-volatile)寄存器时需要保存值和恢复。

易失性(volatile)栈结构

ARMv6/v7-m的CPU,从线程模式进入中断模式时,会自动将易失性(volatile)寄存器保存到栈中。

            ------------------------
            | Prev Frame           |
            +------------+---------+
   sp+0x3C  |            |         |
   sp+0x38  | FPSCR      |         |
   sp+0x3C  | s15        |         |
   sp+0x38  | s14        |         |
   sp+0x34  | s13        |         |
   sp+0x30  | s12        |         |
   sp+0x2C  | s11        |         |
   sp+0x28  | s10        |         |
   sp+0x24  | s9         |   FP    |
   sp+0x20  | s8         |  Frame  |
   sp+0x3C  | s7         |         |
   sp+0x38  | s6         |         |
   sp+0x34  | s5         |         |
   sp+0x30  | s4         |         |
   sp+0x2C  | s3         |         |
   sp+0x28  | s2         |         |
   sp+0x24  | s1         |         |
   sp+0x20  | s0         |         |
            ------------------------
   sp+0x1C  | xpsr       |         |
   sp+0x18  | pc         |         |
   sp+0x14  | lr         |         |
   sp+0x10  | r12 (ip)   |  Basic  |
   sp+0x0C  | r3         |  Frame  |
   sp+0x08  | r2         |         |
   sp+0x04  | r1         |         |
   sp+0x00  | r0         |         |
            ------------------------
          易失性(volatile)寄存器栈结构
非易失性(non-volatile)栈结构

编译器能自动处理非易失性(non-volatile)寄存器,因此在同一个上下文中恢复环境,不需要 保存非易失性(non-volatile)寄存器。但当操作系统切换任务时,不同的任务的 非易失性(non-volatile)寄存器环境是不一样的,需要进行保存与恢复。

XWOS在ARMv6/7-m平台上的非易失性(non-volatile)寄存器栈结构如下:

            -----------------------------
            |   Volatile stack Frame    |
            +-----------------+---------+
   sp+0x64  | s31             |         |
   sp+0x60  | s30             |         |
   sp+0x5C  | s29             |         |
   sp+0x58  | s28             |         |
   sp+0x54  | s27             |         |
   sp+0x50  | s26             |         |
   sp+0x4C  | s25             |   FP    |
   sp+0x48  | s24             |  Frame  |
   sp+0x44  | s23             |         |
   sp+0x40  | s22             |         |
   sp+0x3C  | s21             |         |
   sp+0x38  | s20             |         |
   sp+0x34  | s19             |         |
   sp+0x30  | s18             |         |
   sp+0x2C  | s17             |         |
   sp+0x28  | s16             |         |
            -----------------------------
   sp+0x24  | lr (EXC_RETURN) |         |
   sp+0x20  | r11 (fp)        |         |
   sp+0x1C  | r10 (sl)        |         |
   sp+0x18  | r9              |         |
   sp+0x14  | r8              |  Basic  |
   sp+0x10  | r7              |  Frame  |
   sp+0x0C  | r6              |         |
   sp+0x08  | r5              |         |
   sp+0x04  | r4              |         |
   sp+0x00  | CONTROL         |         |
            -----------------------------
          非易失性(non-volatile)寄存器栈结构

中断

XWOS移植实现层的 Adaptee 位于:

xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_irq.h
xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_irq.c
xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_irq.h
xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_irq.c

滴答定时器

XWOS移植实现层的 Adaptee 位于:

xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_syshwt.h
xwcd/soc/arm/v6m/[CPU]/[SOC]/xwosimpl_syshwt.c
xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_syshwt.h
xwcd/soc/arm/v7m/[CPU]/[SOC]/xwosimpl_syshwt.c