
本文是《STM32内核精讲》栏目的第十五篇也是第一阶段的收官之作。前十四篇我们深入学习了寄存器模型、异常处理、AAPCS、启动文件、低功耗、调试跟踪、内存屏障以及内核选型。本篇将聚焦于内核性能指标——CoreMark、DMIPS 的由来与测试方法中断延迟的定义与实测以及代码密度的对比。理解这些指标你才能真正看懂芯片数据手册上的数字做出有依据的选型决策。 一、引言数字背后的陷阱当你翻开任何一款 Cortex‑M 芯片的数据手册总会看到这样一串数字“1.25 DMIPS/MHz”、“3.42 CoreMark/MHz”。这些数字看似客观实则暗藏玄机——同一个内核在不同编译器、不同优化选项、不同测试配置下跑出来的分数可以相差数倍。不懂这些指标的来历和测试方法选型时就只能“比大小”很容易被厂商宣传误导。本章将带你穿透这些数字理解它们真正代表的含义。 二、Dhrystone 与 DMIPS一个 40 岁的“老将”2.1 Dhrystone 的起源Dhrystone 是由Reinhold P. Weicker在1984 年提出的一个基准测试程序其主要目的是测试处理器的整数运算和逻辑运算性能。Dhrystone 程序最初用 Ada 语言发布后来 Rick Richardson 为 Unix 开发了用 C 语言编写的 Version 1.1这个版本推动了 Dhrystone 的广泛应用。Dhrystone 程序的最新版本是 1988 年更新的Version 2.1。2.2 DMIPS 的含义Dhrystone 标准的测试方法很简单单位时间内跑了多少次 Dhrystone 程序其指标单位为DMIPS/MHz。MIPS Million Instructions Per Second每秒百万条指令DMIPS Dhrystone MIPS即在 Dhrystone 测试标准下的 MIPS 数值DMIPS/MHz这个比值消除了频率的影响使得不同主频的处理器可以在同一尺度下比较。2.3 Dhrystone 的局限性Dhrystone 虽然历史悠久、应用广泛但存在几个公认的缺陷代码量小整个测试程序规模有限无法充分体现现代处理器的缓存、流水线等微架构特性。容易被“优化”编译器可以通过内联、循环展开等手段大幅“优化”Dhrystone 的得分使得同一硬件在不同编译器下分数差异巨大。与实际应用脱节Dhrystone 的测试负载与真实嵌入式应用场景差异较大高分不一定代表实际性能好。正因如此CoreMark在 2009 年应运而生逐渐取代 Dhrystone 成为嵌入式领域的主流性能基准。 三、CoreMark更现代的嵌入式性能基准3.1 CoreMark 的诞生CoreMark 由EEMBC嵌入式微处理器基准评测协会的Shay Gal-On开发1.0 版本于 2009 年 6 月 1 日正式发布。EEMBC 是一个非营利性组织目前共发布了 46 个性能测试基准CoreMark 被认为是比陈旧的 Dhrystone 标准更有实际价值的测试基准。CoreMark 的源代码可以从www.coremark.org免费下载EEMBC 鼓励所有用户在网站上提交他们的分数和平台配置。3.2 CoreMark 的测试内容CoreMark 程序使用 C 语言编写包含以下四种核心算法算法说明列举List寻找并排序测试链表操作性能矩阵运算Matrix普通矩阵运算测试数学计算性能状态机State Machine确定输入流中是否包含有效数字CRC循环冗余校验测试数据校验和计算性能这些算法涵盖了嵌入式系统中常见的数据结构操作、数学计算、状态管理和数据校验比 Dhrystone 更贴近实际应用场景。3.3 CoreMark 的测试方法CoreMark 标准的测试方法很简单在某配置参数组合下单位时间内跑了多少次 CoreMark 程序其指标单位为CoreMark/MHz。CoreMark 数字越高意味着性能更高。移植要点如果将 CoreMark 移植到 ARM Cortex-M 平台下裸系统运行一般只需要修改\barebones目录下的文件即可仅需改动三个函数portable_init()、barebones_clock()、uart_send_char()以及core_portme.h中的若干宏定义。3.4 CoreMark 与 DMIPS 的对比维度Dhrystone (DMIPS)CoreMark提出时间1984 年2009 年测试内容整数/逻辑运算链表/矩阵/状态机/CRC代码规模较小较大抗优化能力较弱较强与实际应用相关性较低较高当前地位历史标准仍在用主流标准 四、Cortex‑M 各内核的典型性能数据以下是 ARM 官方和各厂商公布的 Cortex‑M 各内核典型性能数据内核架构DMIPS/MHz典型值CoreMark/MHz典型值M0ARMv6‑M0.962.33M0ARMv6‑M0.952.46M3ARMv7‑M1.253.32M4ARMv7E‑M1.253.42M7ARMv7E‑M2.145.29M23ARMv8‑M BL0.872.5M33ARMv8‑M ML1.54.2M55ARMv8.1‑M1.64.3M85ARMv8.1‑M3.136.28数据说明M0ARM 官方公布为 0.96/1.19/1.91 DMIPS/MHz三组不同编译配置表格取典型值 0.96。M0ARM 官方公布为 0.99/1.30/2.58 DMIPS/MHz三组不同编译配置表格取典型值 0.95。M7ST 官方公布为 2.14 DMIPS/MHz 和 5.29 CoreMark/MHz。M23ARM 官方公布为 0.87/1.13/2.32 DMIPS/MHz三组不同编译配置表格取典型值 0.87。M85ARM 官方公布为 3.13/4.52/8.76 DMIPS/MHz三组不同编译配置和 6.28 CoreMark/MHz。M55ARM 官方公布为 1.69/2.16/5.32 DMIPS/MHz三组不同编译配置表格取典型值 1.6。⚠️ M33 的重要说明M33 的 CoreMark 得分受TrustZone 配置影响。不使能 TrustZone 时约为 4.2 CoreMark/MHz使能 TrustZone 时可能降至约 3.8-4.0与 M4 的差距缩小。选型时需根据实际安全配置评估性能。关于 DMIPS 的多组数据ARM 官方为每个内核提供了三组 DMIPS 数据第一组严格遵守 Dhrystone 文档的所有规则第二组允许函数内联inline第三组允许多文件同时编译multi‑file compilation这三组数据对应不同的编译优化策略差异可达数倍。这就是为什么你在不同地方看到的同一内核 DMIPS 数值可能完全不同——它们使用的是不同的编译配置。 五、中断延迟实时系统的生命线5.1 中断延迟的定义中断延迟Interrupt Latency是指从中断请求IRQ信号置起开始到内核进入执行该中断 ISR 第一条指令时的时钟周期数。IRQ 信号置起 → 硬件压栈 → 取向量 → 执行 ISR 第一条指令 |-------------- 中断延迟 ----------------|在实际系统中中断延迟通常以时钟周期为单位测量也可以根据系统时钟频率换算为微秒μs。5.2 影响中断延迟的因素中断延迟并不是一个固定值它受多个因素影响当前执行的指令如果中断发生时正在执行一条长指令如除法指令处理器可能需要等待当前指令完成才能响应。不过 Cortex‑M 会放弃正在执行的除法指令去响应中断返回后再重新执行。中断嵌套如果已经有一个中断正在执行新来的低优先级中断必须等待。存储器等待状态如果 Flash 或 RAM 有等待周期压栈和取向量会增加延迟。尾链Tail‑Chaining和晚到Late‑Arriving这些机制可以减少连续中断的处理延迟。5.3 Cortex‑M 各内核的中断延迟在零等待存储器系统中Cortex‑M 各内核的典型中断延迟如下内核中断延迟周期说明M015 周期最高优先级中断零等待系统M015 周期最高优先级中断零等待系统M312 周期零等待系统M412 周期零等待系统M712 周期缓存命中时缓存未命中时可能增加至 14 周期或更多尾链Tail‑Chaining可以将连续中断的处理延迟降低到6 周期。当两个中断连续发生时硬件跳过出栈和重新压栈直接进入下一个中断处理程序。5.4 中断延迟的实测方法在实际硬件上测量中断延迟常用的方法有使用 DWT 性能计数器在 ISR 入口读取DWT_CYCCNT地址0xE0001004与触发中断前记录的值相减。使用 GPIO 翻转法在 ISR 入口翻转 GPIO 引脚用示波器测量从触发到翻转的时间。使用 SysTick 定时器在中断发生前启动 SysTickISR 中读取当前值。注意Cortex‑M 的某些仿真模型如 FVP不支持 DWT此时需要使用 SysTick 或其他计时手段。 六、代码密度Thumb vs ARM 的持久战6.1 Thumb 诞生的背景早期的 ARM 处理器如 ARM7、ARM9使用32 位固定长度指令ARM 指令集功能强大但代码密度低——嵌入式系统的 Flash 空间有限32 位指令浪费存储资源。为了提升代码密度ARM 在 1990 年代中期推出了Thumb 指令集将大部分指令压缩为16 位。Thumb 代码相比等效的 ARM 代码可以减少约30% 的代码体积。6.2 Thumb‑216/32 位混合的折中方案Cortex‑M 处理器只支持 Thumb 指令不支持原始的 32 位 ARM 指令集。但 Thumb 本身经历了演进原始 Thumb全部 16 位指令功能有限。Thumb‑216/32 位混合指令没有模式切换处理器自动识别指令宽度。Thumb‑2 的设计目标是在保持 Thumb 代码密度的同时达到接近 ARM 指令集的性能。事实证明这个目标基本达成——Thumb‑2 代码体积远小于 ARM 32 位代码性能损失控制在1-2%以内。6.3 代码密度对比的实际意义对于嵌入式系统代码密度直接影响Flash 容量需求更高的代码密度意味着可以用更小的 Flash 完成同样的功能降低芯片成本。功耗更少的 Flash 访问意味着更低的功耗。缓存效率在带缓存的 Cortex‑M7 上更高的代码密度意味着缓存命中率更高。实际对比ARM 的研究数据显示Thumb 指令集的平均代码体积比ARM 32 位指令集小约30%。这正是 Cortex‑M 在嵌入式领域占据主导地位的重要原因之一——用更少的 Flash 空间实现更多的功能。6.4 为什么 Cortex‑M 不支持原始 ARM 指令硬件简化只实现 Thumb 解码器节省芯片面积和功耗。代码密度Thumb‑2 的性能已经足够且代码密度更高。模式统一无需在 ARM 和 Thumb 状态之间切换早期的 ARM 处理器需要通过BX指令切换状态。 七、总结7.1 本篇核心要点DMIPS来自 1984 年的 Dhrystone 基准测试单位为DMIPS/MHz。优点是历史悠久、数据丰富缺点是代码量小、容易被优化、与实际应用脱节。CoreMark由 EEMBC 的 Shay Gal-On 开发1.0 版本于 2009 年 6 月 1 日正式发布单位为CoreMark/MHz。测试内容包括链表、矩阵、状态机、CRC 四种算法更贴近嵌入式实际应用已成为主流性能基准。DMIPS 的多组数据ARM 官方为每个内核提供三组 DMIPS 数据严格规则、允许内联、多文件编译差异可达数倍。看到 DMIPS 数值时务必确认其编译配置。中断延迟是实时系统的关键指标。Cortex‑M3/M4 在零等待系统中可达12 周期M0/M0 为15 周期尾链可将连续中断延迟降至6 周期。M7 在缓存命中时同样为 12 周期缓存未命中时可能增加至 14 周期或更多。代码密度Thumb 相比 ARM 32 位指令集可减少约30%代码体积。Cortex‑M 只支持 Thumb/Thumb‑2性能损失控制在 1-2% 以内这是嵌入式领域的明智选择。7.2 下篇预告《第二阶开启 —— 深入运行机制》从下一篇开始我们将进入专栏的第二阶段——进阶原理。我们将深入 NVIC 的高级话题、HardFault 故障分析、PendSV 与上下文切换、MPU 内存保护单元等更深入的内核机制。 读者问题专栏 · 问题征集你在评估处理器性能或实测中断延迟时是否遇到过同一款芯片在不同编译器下 CoreMark 分数差异巨大想实测中断延迟但不知道从哪里入手在选型时不知道应该看 DMIPS 还是 CoreMark代码密度对实际项目的影响有多大欢迎留言我会在《Cortex‑M 有问必答》中专题解答。 关于作者与更多内容我是BackCatK Chen长期关注嵌入式底层、国产半导体与 AI 算力芯片。如果你对芯片架构、行业趋势感兴趣欢迎关注我的公众号获取更多宏观技术观察。文章标签Cortex-MCoreMarkDMIPSDhrystone中断延迟代码密度Thumb性能指标