HRTOS 模块文档

内存保护(Memory Protection)

内存保护机制用于实现任务隔离与访问控制, 通过硬件 MPU/MMU 或软件策略限制任务访问范围, 防止非法读写、越界访问及内核数据破坏。

内存管理 系统安全 任务隔离

概述

内存保护(Memory Protection)用于防止任务越界访问、 非法修改内核空间或破坏其他任务数据。

在多任务实时系统中, 每个任务通常应仅访问自身数据区域及授权共享资源, 超出范围的访问需要被阻止或触发异常。

内存保护是高可靠RTOS的重要组成部分, 常用于工业控制、车载系统及安全关键场景。

内存保护机制通过硬件MPU(Memory Protection Unit)或MMU(Memory Management Unit)实现访问控制。MPU提供区域级别的访问权限控制,支持多个内存区域,每个区域可配置读、写、执行权限。MMU提供更精细的页级别控制,支持虚拟地址映射,适用于复杂的应用场景。HRTOS优先采用MPU实现,因为MPU开销较小,适合实时系统,同时提供足够的安全保护能力。

内存保护的核心价值在于任务隔离与系统安全。通过为每个任务配置独立的内存区域,系统确保任务无法访问其他任务的数据或内核空间,防止恶意或错误代码破坏系统稳定性。在安全关键系统(如汽车电子、医疗设备)中,内存保护是功能安全标准(如ISO 26262、IEC 61508)的强制要求,必须满足严格的隔离与保护要求。

内存保护还支持栈溢出检测与数据段保护。通过配置栈区域的权限为读写但不执行,系统可检测栈溢出导致的非法执行。通过配置代码段为只读执行,系统可防止代码被意外修改。这些保护机制共同构建了多层防御体系,提高系统的鲁棒性与安全性。

工作原理

系统通过 MPU(Memory Protection Unit) 或 MMU(Memory Management Unit) 定义不同内存区域的访问权限。

权限控制: - 可读(Read) - 可写(Write) - 可执行(Execute) 访问范围: - 用户任务空间 - 内核空间 - 共享资源区

任务切换时,系统会加载对应任务的访问配置, 实现动态权限切换。

当任务访问未授权区域时, 系统通常触发 Fault Handler 进行异常处理。

MPU的内部实现依赖于区域寄存器与权限配置。每个MPU支持多个区域(通常为8-16个),每个区域包含基地址、大小、访问权限(读、写、执行)等字段。系统初始化时配置内核区域为只读执行,防止任务修改内核代码。任务创建时,系统为任务配置独立的栈区域、数据区域与代码区域,确保任务仅能访问自己的内存空间。

任务切换时的MPU配置切换是内存保护的关键机制。当系统从一个任务切换到另一个任务时,内核更新MPU区域寄存器,加载新任务的内存区域配置。这个过程必须在临界区中快速完成,避免影响切换延迟。HRTOS采用优化的配置切换策略,减少寄存器写入次数,确保切换开销最小。

内存访问违规检测由硬件自动完成。当任务尝试访问未授权区域时,MPU立即触发异常,暂停任务执行,将控制权转移到Fault Handler。Fault Handler记录违规信息(地址、类型、任务ID),根据配置决定行为:终止违规任务、重启系统或进入安全模式。这种硬件级检测确保了违规行为无法绕过,提供了最高级别的安全保护。

关键接口 / 结构

os_mpu_init() os_mpu_region_config() os_memory_protect_enable() struct mpu_region { void* base; uint32_t size; uint32_t permission; };

os_mpu_init()用于初始化MPU硬件,参数包括MPU配置指针。该接口使能MPU,配置内核区域为只读执行,初始化区域寄存器。初始化操作必须在系统启动时调用,未初始化的MPU行为未定义。该接口通常在内核初始化阶段自动调用,开发者无需手动调用。

os_mpu_region_config()用于配置MPU区域,参数包括区域索引、基地址、大小、访问权限。该接口设置指定区域的基地址、大小与权限,使能该区域。区域索引必须在MPU支持的范围内(通常为0-7或0-15)。配置成功返回0,失败返回错误码。该接口在任务创建时自动调用,配置任务的内存区域。

os_memory_protect_enable()用于使能内存保护功能,参数包括保护级别。该接口全局使能或禁用内存保护,支持不同的保护级别(如仅内核保护、全任务保护)。使能成功返回0,失败返回错误码。该接口通常在系统配置阶段调用,根据应用需求选择合适的保护级别。

mpu_region结构体定义了MPU区域的核心属性。base字段存储区域的基地址。size字段存储区域的大小。permission字段存储访问权限标志(读、写、执行)。该结构体还可能包含区域索引、属性字段(缓存策略、共享属性)等字段。结构体大小取决于硬件平台,HRTOS通过抽象层适配不同的MPU实现。

运行流程

任务创建后,系统为其分配对应权限区域。

1. 初始化 MPU/MMU 2. 配置任务权限区域 3. 任务切换时加载配置 4. 执行内存访问校验 5. 异常访问触发 Fault Handler

所有运行期间内存访问均经过权限验证, 保证系统边界不被破坏。

完整的MPU初始化流程包括:系统启动时调用os_mpu_init()接口,内核使能MPU硬件;配置内核区域为只读执行,防止任务修改内核代码;初始化区域寄存器,清空所有区域配置;配置共享内存区域(如消息队列、邮箱)为读写权限,允许任务间通信;完成初始化,内存保护功能生效。

完整的任务区域配置流程包括:任务创建时,内核计算任务的栈区域、数据区域、代码区域地址与大小;调用os_mpu_region_config()接口,配置栈区域为读写但不执行,检测栈溢出;配置数据区域为读写,允许任务访问全局变量;配置代码区域为只读执行,防止代码被修改;将区域配置关联到任务控制块,任务切换时自动加载。

完整的任务切换配置流程包括:调度器选择下一个运行任务;内核进入临界区;从任务控制块读取MPU区域配置;更新MPU区域寄存器,加载新任务的内存区域配置;退出临界区,切换到新任务。整个过程必须在临界区中快速完成,避免影响切换延迟。HRTOS采用优化的配置切换策略,减少寄存器写入次数。

完整的内存访问违规处理流程包括:任务尝试访问未授权区域;MPU硬件检测到违规,立即触发异常;CPU暂停任务执行,跳转到Fault Handler;Fault Handler保存上下文,记录违规信息(地址、类型、任务ID);根据配置决定行为:终止违规任务、重启系统或进入安全模式;系统继续运行或执行恢复操作。

扩展说明

在高可靠系统中, 内存保护通常与任务隔离、异常检测和安全启动机制联合使用。

推荐实践: - 内核空间只读保护 - 用户任务隔离 - 栈边界检查 - 异常访问日志记录

内核空间保护是内存保护的核心要求。通过配置内核区域为只读执行,系统确保任务无法修改内核代码或读取内核数据。这种保护防止了恶意任务或错误代码破坏系统稳定性,是功能安全标准的基本要求。HRTOS在系统初始化时自动配置内核保护,无需开发者手动干预。

用户任务隔离是内存保护的另一个关键特性。通过为每个任务配置独立的内存区域,系统确保任务无法访问其他任务的数据。这种隔离不仅防止了数据泄露,还限制了错误传播范围,单个任务出错不会影响整个系统。HRTOS支持动态区域配置,在任务创建时自动分配独立区域,在任务销毁时释放区域资源。

栈溢出检测是内存保护的重要功能。通过配置栈区域为读写但不执行,系统可检测栈溢出导致的非法执行。当栈指针超出栈区域时,访问未授权区域会触发MPU异常,系统可及时终止任务并记录错误。这种检测机制比软件栈检查更高效,因为由硬件自动完成,无需额外的运行时开销。

  • 模块职责:内存保护管理负责实现任务隔离与访问控制,确保系统安全性与稳定性
  • 内部机制:基于MPU/MMU硬件、区域配置、权限验证、异常处理实现,支持硬件级保护
  • 状态迁移:MPU区域在ENABLED/DISABLED状态间切换,权限配置在任务切换时动态更新
  • 调用流程:init → region_config → task_switch → access_check → fault_handle
  • 资源管理:MPU寄存器为硬件资源需保护并发访问,区域配置为任务私有资源
  • 工程案例:汽车电子ECU、医疗设备控制器、工业控制系统、安全关键设备
  • 边界条件:区域数量限制、区域大小对齐、权限组合限制、切换延迟
  • 错误场景:区域配置冲突、违规访问、栈溢出、配置失败、硬件故障
  • 异常处理:违规终止、系统重启、安全模式、错误日志、恢复策略
  • 模块关系:与调度器模块协作切换区域配置,与中断模块协调ISR内存访问

内存保护的性能优化是实时系统工程的重要环节。HRTOS采用优化的区域配置策略,减少任务切换时的寄存器写入次数。系统支持区域复用,多个任务共享相同的区域配置,避免重复配置。对于多核SMP系统,每个核心独立配置MPU,避免核心间干扰。这些优化确保了内存保护的高效性,满足实时系统的性能要求。

对于功耗敏感的嵌入式系统,内存保护的使用会影响系统功耗管理。MPU硬件在每次内存访问时执行权限检查,可能增加功耗开销。HRTOS提供动态MPU使能机制,在系统空闲时禁用MPU以降低功耗,在任务运行时重新使能。系统还支持低功耗模式下的保护降级,平衡安全性与功耗。