3.10 嵌入式与实时系统
Overview and motivation
嵌入式系统是运行在某个设备上、而不是运行在通用计算机上的软件。它存在于汽车、心脏起搏器、恒温器、工厂机器人或制导装置内部。这类软件专属于该设备,而设备通常在内存、处理能力和能耗上都有严格限制。你不能总是靠在云控制台点一下按钮来增加资源。你交付出去的东西,往往就是要运行好几年的东西。
实时系统是指正确性不仅取决于给出正确答案,还取决于时机的系统。一个安全气囊控制器,如果算出了完美的展开指令,却晚了一秒钟给出,那就是彻底失败。实时工作给每一项任务都增加了一个硬性问题:在最坏情况下,这项任务是否每次都能在截止时间之前完成?这与 Web 和云软件中常见的、以吞吐量为先的思维方式截然不同。
对大型组织而言,这件事比乍看之下更重要。企业在建造联网汽车、医疗设备、工业控制器,以及数以十亿计的物联网(IoT)设备。政府运营着防务平台、航空电子设备、电网控制器和医疗监管系统。在这些领域,一个软件缺陷可能伤害人员、中断生产线,或危及国家安全。这里的规则更严格,测试更困难,标准也具有法律约束力。本章将帮助你在真实约束条件下构建正确、及时、安全且可靠的软件。它与软件构建(第 2.9 章)、分布式系统(第 3.3 章)、可扩展性与性能(第 3.5 章)、基础设施与云安全(第 4.3 章)以及软件维护(第 3.7 章)相衔接。
Key principles
- 时机是一项正确性要求,而不是锦上添花的性能优化。 一个迟到的答案可能就是一个错误的答案。
- 要为最坏情况设计,而不是为平均情况设计。 实时保证依赖于最坏情况下的表现,而不是典型速度。
- 确定性胜过原始速度。 一个总能按时完成、可预测的系统,胜过一个偶尔会错过截止时间、但更快的系统。
- 资源是有限且固定的。 要像预算资金一样,有意识地为内存、CPU 周期和能耗做预算。
- 安全性和保安性是在设计之初就工程化地内置进去的,而不是事后补上的。 在受监管的领域,你必须展示你的工作过程,而不只是宣称质量达标。
- 硬件是系统的一部分。 不联系芯片、传感器和物理规律,就无法推理软件。
- 现场更新是一种生命周期能力,而不是事后才想起的补救措施。 部署在外的设备需要一种安全的方式来接收修复。
Recommendations
Classify each timing requirement as hard, firm, or soft
并非所有截止时间都是平等的。硬实时截止时间绝不能被错过,因为一旦错过就会导致系统故障或伤害:比如发动机控制或飞行操纵面。固实时截止时间可以容忍极少数的错过,但一个迟到的结果是没用的,会被丢弃。软实时截止时间则会优雅地降低价值:一帧稍微迟到的视频画面会降低质量,但不会造成灾难。给每一项对时机敏感的任务打上其类别的标签,因为不同类别所需的投入、测试严格程度和成本相差极大。有两个属性描述时机行为。延迟是事件与响应之间的时间差。抖动是这个延迟在一次又一次发生之间的变化幅度。硬实时系统对约束抖动的关注程度,不亚于对降低延迟的关注,因为可预测性正是让你能够证明截止时间总能被满足的关键所在。
Choose your execution foundation deliberately: RTOS or bare metal
你有两种主要的执行基础可供选择。裸机固件直接运行在硬件之上,没有操作系统,使用一个简单的循环和中断处理程序。它是最小、最可预测的选项,适合任务单一明确的微小设备。实时操作系统(RTOS)是一种小型操作系统,按优先级调度任务,并保证时机上的边界。它为你提供多任务、调度器,以及计时器和消息队列等服务,同时保持时机的可预测性。当你有若干个截止时间各不相同的并发任务时,选择 RTOS。当设备资源极度受限,或时机必须能被简单地证明时,选择裸机。对于硬实时工作,优先选用抢占式的基于优先级的调度器,并用诸如速率单调调度这样的方法来分析它()该方法根据任务频率分配优先级,让你能够证明整个任务集是可调度的。
Budget memory, CPU, and power as first-class resources
把每一种稀缺资源都当作一个有硬性上限的预算来对待。在内存方面,优先使用静态分配而不是堆上的动态分配,因为动态内存可能产生碎片,并可能在最糟糕的时刻以不可预测的方式失败。正因如此,许多安全标准限制甚至禁止在启动之后使用堆。在 CPU 方面,要测量最坏情况执行时间(WCET),即一项任务可能耗费的最长时间,并按这个数字而不是平均值来做调度。在电力方面,要记住许多设备靠电池供电或靠采集环境能量运行,因此要设计占空比、休眠状态和唤醒事件,以达到必须维持数月甚至数年的能耗预算。把这些预算写下来,像对待其他任何需求一样对它们进行评审。
Handle interrupts and concurrency with strict discipline
中断是一种硬件信号,会暂停当前的工作,立即运行一个处理程序。中断是设备对外部世界做出即时反应的方式,也是许多隐蔽缺陷的主要来源。让处理程序尽可能短:确认事件、暂存最少量的数据,并把真正的工作推迟到一个普通任务中去做。由于中断可能在任意两条指令之间触发,你必须小心地保护共享数据不受竞态条件的影响。使用无锁技术、简短的临界区,或被充分理解的基本机制,并防范优先级反转()即一个持有锁的低优先级任务阻塞了一个高优先级任务。这种并发处理与第 3.3 章的推理方式相通,但时机要求更紧,也没有重试的余地。
Write device drivers that isolate hardware detail
设备驱动是与某个特定硬件(传感器、无线模块、电机控制器)通信的软件层。把硬件相关的代码保留在一个干净的接口背后,这样软件的其余部分依赖的是一个稳定的抽象,而不是寄存器地址。这使代码可以脱离目标硬件进行测试,在某款芯片停产时也更容易移植,推理起来也更简单。把关于时机、字节序和硬件怪癖的每一条假设都记录下来,因为正是这些细节导致了现场故障。这正是第 2.9 章的构建原则,应用在一个错误的比特位就可能让电机停转的场景中。
Adopt the functional-safety standard that governs your domain
如果你的设备可能伤害人员或财产,很可能会有一项功能安全标准适用于它,而且这往往就是法律要求。IEC 61508 是电子系统安全性的通用标准,也是其他若干标准的母标准。ISO 26262 管辖道路车辆的安全性。DO-178C 管辖民用航空中机载软件的安全性。IEC 62304 管辖医疗器械软件。在编码层面,MISRA C 是一套被广泛使用的规则集,限制了 C 语言中风险较高的特性,使代码更安全、更易于分析。这些标准要求从需求到代码再到测试的可追溯性、明确定义的流程,以及可以交给审计人员或监管机构的证据。要及早采用正确的标准,因为事后补齐这些书面记录既痛苦、有时甚至根本不可能。
Test with simulation and hardware in the loop
你不能像测试 Web 应用那样测试嵌入式软件。要构建一套分层策略。在普通计算机上针对硬件抽象接口运行单元测试。在真实硬件稀缺或操作起来有危险时,用仿真来对设备及其运行环境建模。然后使用硬件在环(HIL)测试,让真正的控制器针对它所控制的物理系统的仿真版本运行,这样你就能安全地测试传感器卡死或负载骤增这类故障情况。把这些测试自动化接入你的流水线,让每一次改动在到达设备之前都在贴近真实的条件下接受检验。
Design over-the-air updates and device security from day one
部署在外的设备迟早会需要修复,因此要提前规划空中下载(OTA)更新:一种通过网络安全交付新固件的方式。一个安全的 OTA 设计会对每次更新进行加密签名、在安装前校验签名、以原子方式完成更新,并且在新镜像无法启动时能够回滚到一个已知良好的镜像。把这些与第 4.3 章的安全原则结合起来,并根据受限硬件的情况加以调整。使用硬件信任根和安全启动,确保只有经过签名的固件才能运行。对传输中和静态存储的数据都进行加密。更改默认凭据,禁用未使用的接口。一支物联网设备群本质上是一个攻击面巨大的分布式系统,一个薄弱的默认密码就可能同时危及数百万台设备。
Trade-offs: pros and cons
| Choice | Pros | Cons / cost |
|---|---|---|
| RTOS | 多任务处理、优先级调度、计时服务 | 有开销、体积更大、存在学习曲线 |
| 裸机 | 最小、最可预测、完全可控 | 难以扩展到多任务场景,手工工作更多 |
| 静态分配 | 可预测、无碎片、对安全友好 | 灵活性较低,必须提前确定所有大小 |
| 正式安全认证 | 获得合法市场准入、有严谨证据、可信度更高 | 时间和金钱成本高,迭代更慢 |
| OTA 更新 | 修复并改进已部署设备,延长使用寿命 | 需要更新基础设施、有安全负担、存在回滚风险 |
最核心的权衡在于可预测性与灵活性之间。所有让通用系统变得方便的东西(动态内存、后台垃圾回收、尽力而为的调度、弹性资源)都在削弱”任务总能在固定资源占用内按时完成”这一保证。嵌入式与实时工程有意放弃灵活性,以换取确定性和安全性。真正的技巧在于:只在截止时间或风险真正要求的地方才做出这种取舍,并把灵活、迭代更快的部分(比如设备的云端后台)留在一条清晰边界的另一侧。
Questions to discuss with your team
在你们对时机要求苛刻的路径上,你们测量的是抖动,还是只测量平均延迟? 硬实时的正确性依赖于约束响应时间的变化幅度(抖动),而不只是降低典型延迟,因为可预测性正是让你能够证明截止时间总能被满足的关键。一个平均值很低、但偶尔出现大幅尖峰的控制回路,仍可能错过截止时间并造成伤害,而平均值会把这一点掩盖起来。为每一项对时机敏感的任务带来其波动范围的测量数据,包括最坏情况,并把每一项都标注为硬、固或软,使测试的严格程度与错过截止时间的后果相匹配。通用系统中所有便利的东西(动态内存、垃圾回收、尽力而为的调度)都在侵蚀可预测性,因此它们不应出现在硬实时路径上。如果你只汇报平均值,就无法诚实地宣称满足了硬性截止时间。
你们在 RTOS 与裸机之间的选择现在还合适吗?你们能证明这个任务集是可调度的吗? 执行基础是一个需要随设备演进而重新审视的决定:对于任务单一明确的场景,裸机最小、最可预测;而一旦你有若干个截止时间不同的并发任务,RTOS 的开销就值得付出。对于硬实时工作,本章指出应采用抢占式的基于优先级的调度器,并用诸如速率单调调度这样的方法来分析()这能让你证明任务确实能装得下,而不是寄希望于它能装得下。带来当前的任务集、它们的频率,以及它们的最坏情况执行时间,检查可调度性是否真正成立,还是任务已经悄悄累积到超出这套基础所能保证的范围。要防范优先级反转,即一个持有锁的低优先级任务拖慢了一个高优先级任务。凭习惯而不是凭任务集来选择执行基础,正是时机保证悄然瓦解的方式。
确定性设备与灵活的云端后台之间的边界究竟在哪里?这条边界是否足够干净,使得一侧能够快速推进而不危及另一侧? 本章所述的核心权衡是放弃灵活性以换取确定性和安全性,而技巧在于只在截止时间或风险真正要求的地方才付出这种代价。一条干净的边界能让安全攸关的固件保持保守和认证状态,同时让云端后台快速迭代,使两者各自以自己安全的节奏演进。带来你们的架构图,定位出这条接缝:哪些必须被证明是确定性的、并通过经签名、经验证的路径进行更新,哪些又可以在服务器上每周变化。模糊这条界线,要么会把云端式的习惯(动态分配、尽力而为的时机)拖入控制路径,要么会不必要地把后台拖慢到与固件相同的节奏。把这条边界划对,才能同时保住安全证据和交付速度。
每个产品由哪项功能安全标准管辖,当前的证据距离审计人员能够接受的程度还有多远? 相关标准(IEC 61508、面向道路车辆的 ISO 26262、面向机载软件的 DO-178C、面向医疗器械的 IEC 62304)往往就是法律,它要求从需求到代码再到测试具备可追溯性,而这一点在最后关头是无法弄虚作假的。对大型团队而言,风险在于各团队对这套书面记录的采用程度参差不齐,导致一条产品线已经做好审计准备,而另一条产品线却在认证过程进行到一半时才发现自己的需求从未被追溯过。与之竞争的拉力是速度:完整的可追溯性和 MISRA C 的强制执行会拖慢日常迭代,处于截止日期压力下的团队很容易被诱惑把证据的整理推迟到”以后再说”。带来当前的可追溯性矩阵、仍未关闭的静态分析发现项,以及针对目标保证等级的诚实差距分析。在企业和政府背景下,还要加上认证所需的提前期和审计人员的期望,因为在设计完成之后再补齐证据既缓慢又昂贵,有时根本不可能,而一次延误的认证可能会彻底堵死市场准入。
如果明天在一台已部署的设备上发现了严重缺陷,你们能以多快的速度在整个设备群中安全地修复它?你们演练过回滚吗? 一台无法打补丁的设备,会变成一项永久的安全性和保安性负债,而一次实物召回的成本要比一次经签名的空中下载更新高出几个数量级。这里的张力在于:一个考虑不周的更新机制本身就是一个攻击面,也是一个”变砖”风险()一条会安装未签名镜像、或无法在启动失败时回滚的 OTA 路径,可能把一次糟糕的发布变成数百万台报废的设备。带来你们的更新设计(加密签名、安装前的签名校验、原子式安装、自动回滚到已知良好的镜像)、安全启动和硬件信任根的状态,以及上一次真正在真实硬件上演练回滚是什么时候。对于企业或公共设备群,还要加上谁对签名密钥负责,以及一旦密钥泄露该如何吊销它,因为一个泄露的密钥或一个共享的默认凭据可能一次性危及整个设备群。
你们的内存、CPU 和电力预算是否已写明硬性上限?你们的测试策略是否同时覆盖了仿真和真实硬件? 实时保证依赖于最坏情况执行时间和固定的资源占用,而不是平均行为,因此一次未纳入预算的堆分配,或一次未经测试的最坏情况负载,正是确定性悄悄瓦解的地方。对大型团队而言,危险在于漂移:任务不断累积,内存占用不断攀升,却没有人真正负责这份预算,直到某台设备在现场运行数周之后才失效。这里的权衡是覆盖率与成本之间的取舍,因为一套能注入传感器卡死等故障的硬件在环装置搭建成本高昂,而纯粹的仿真又会隐藏只在真实芯片上才会出现的时机缺陷。带来已记录的预算、针对这些预算测量出的最坏情况执行时间,以及证据表明你们的流水线在发布前依次运行了抽象层上的单元测试、仿真和硬件在环测试。在受监管和政府场景中,把这一点与标准所要求的结构化测试覆盖率挂钩,因为审计人员想要的是故障情况确实被演练过的证据,而不是”平均情况看起来还行”的保证。
Sector lens
Startup. 速度和生存压倒一切,因此要选择一款轻量级 RTOS 或一个简单的裸机循环,禁止在启动之后进行动态分配,并测量你唯一关键循环的最坏情况耗时,而不是去追求你负担不起的认证预算。除非市场强制要求,否则可以跳过正式的功能安全流程,但绝不要跳过带自动回滚的经签名空中下载更新:一家年轻的公司承受不起一次现场召回,而远程修复正是”一个糟糕的夜晚”和”一款报废的产品”之间的分界线。保持设备固件小巧、保守,这样你稀缺的工程师就不必维护一条他们负担不起的流水线。
Small business. 由于没有嵌入式专职人员,应依靠成熟的模块、参考设计和供应商提供的 RTOS 发行版,而不是自己造一个调度器或引导加载程序。围绕”未来十年谁来给设备打补丁”来考虑自建还是外购的选择:一套买来的、你能信赖的安全与更新技术栈,胜过一套没有人还能维护的定制方案。把默认密码、开放的调试接口和未签名的更新,当作最可能伤害你的失误来对待,因为它们预防起来很便宜,而在现场被发现则会造成毁灭性后果。
Enterprise. 这里的难题是在众多产品线和团队之间保持一致性:一套共享的执行基础策略、通用的资源预算模板、强制执行的 MISRA C 与静态分析,以及一个经过认证的空中下载更新与安全启动平台,让每个团队不必重复造轮子。为功能安全和硬件在环所带来的负担明确编列预算,统一硬件抽象接口,使某款芯片停产时不至于让某个产品陷入困境,并把整个设备群的时机证据、安全工件和安全态势作为受治理的资产来管理,而不是让它们停留在各团队各自的口口相传之中。整个设备群中一个薄弱的默认凭据就是企业规模的负债,因此要把凭据和密钥管理集中起来。
Government. 采购规则、透明度和公共问责制塑造着每一个决策。要求供应商按照与危害程度相匹配的保证等级,依照相应的管辖标准(DO-178C、IEC 62304、IEC 61508)开发机载、医疗或国防软件,并移交审计人员将要审查的可追溯性证据和结构化覆盖率证据。要求安全启动、硬件信任根,以及一个受控的、经签名的现场更新流程,因为对飞行系统或电网系统进行未经验证的更新是不可接受的。优先选择那些授予源代码权利、安全工件权利,以及在必要时可由第二家供应商重新认证的合同条款,这样即便某个供应商倒闭,也不会让一个公众要依赖几十年的系统陷入困境。
Examples
Startup. 一家小型硬件初创公司正在打造一款电池供电的空气质量监测器,其固件基于一款轻量级 RTOS 编写,任务集固定,启动后不再进行动态分配,因此出货的设备就是能靠一枚纽扣电池运行多年的设备。即便没有认证预算,团队仍会测量其传感器读取循环的最坏情况耗时,并在每次发布前在实验台架上针对注入的故障情况测试整个单元。带自动回滚的经签名空中下载更新,让他们能够在所有已出货的设备上统一修复某个缺陷,因此现场出现一次错误读数,并不意味着这家年轻公司承受不起的一次召回。
Enterprise. 一家联网汽车制造商正在打造一款电子制动控制器。硬实时控制回路运行在一款采用速率单调调度和静态内存的 RTOS 之上,每一项任务都有实测的最坏情况执行时间。团队按照 ISO 26262 进行开发,具备从需求到代码再到测试的完整可追溯性,并在每次提交时用静态分析强制执行 MISRA C。一套硬件在环装置会在任何固件出货之前,回放数千个道路场景,包括注入的传感器故障。经签名的 OTA 更新让公司能够在整个设备群中修复某个缺陷,而无需昂贵的召回,如果某辆车无法启动新镜像,还会自动回滚。
Government. 某国家航空管理机构正在为一台新的飞行管理计算机颁发认证。供应商按照与危害程度相匹配的保证等级,依照 DO-178C 开发机载软件,提供需求覆盖率和结构化测试覆盖率的证据,供审计人员审查。时机在最坏情况负载下被证明是确定性的,中断延迟有明确边界,启动后不进行动态分配。安全启动和硬件信任根确保只有经过签名、经过认证的固件才能运行。现场更新遵循一套受控的、经签名的流程,因为对飞行系统进行未经验证的更新是不可接受的。
Business case: motivations, ROI, and TCO
这里的商业理由主要由失败的成本和市场准入的成本主导。在受监管的领域,没有安全认证,你根本无法出售产品,因此这一流程的成本不过是市场准入的门票价。除此之外,已部署硬件中的缺陷代价极其高昂:一次实物召回的成本远高于一次云端热修复,而一起安全事故所带来的责任、监管处罚和声誉损害,足以终结一整条产品线。从一开始就把安全性、确定性和可更新性内置进去,远比在现场才发现它们缺失要便宜得多。
围绕”避免的召回、更快的认证和更长的设备寿命”来构建投资回报的叙述。一套健壮的 OTA 能力,能把许多本会发生的召回转化为低成本的远程修复,每避免一次召回,都足以支付整个更新项目的成本。严谨的最坏情况执行时间分析和资源预算,让你能够放心地在更便宜的硬件上出货,从而在一个庞大的设备群中降低单台成本。就总拥有成本而言,要记住这些设备要运行数年甚至数十年:维护、安全补丁和支持方面的负担(第 3.7 章)远远超过最初的构建成本。为可更新性而设计、清晰的硬件抽象和有据可查的预算,正是让那条漫长的长尾成本保持可负担的关键。
Anti-patterns and pitfalls
- 为平均情况做优化。 “通常”能满足截止时间,就是没能满足硬实时要求。
- 在控制路径中进行动态分配。 堆碎片导致的故障,往往要等到运行数周之后才会显现。
- 臃肿的中断处理程序。 在中断中塞入繁重的处理逻辑,会耗尽你的时机预算,并制造竞态条件。
- 对标准置之不理,直到审计来临。 到后期才补齐可追溯性和证据,既缓慢又昂贵,有时根本不可能做到。
- 出货时没有更新路径。 一台无法打补丁的设备,会变成一项永久的安全性和保安性负债。
- 默认密码和开放接口。 一个薄弱的凭据就能把一支物联网设备群变成一个僵尸网络。
- 只在仿真器上测试,或只在硬件上测试。 二者各自会隐藏对方能够捕获的缺陷;你两者都需要。
- 把硬件当作别人的问题。 在这里,时机、字节序和传感器怪癖都是软件层面的关切。
Maturity model
- Level 1: Initiate. 时机只是被寄予希望,而未经分析。内存被随意动态分配。没有遵循任何功能安全标准。测试是手工进行的,且只在设备上进行。设备一旦出货就无法更新,因此一个现场缺陷就意味着召回或永久性负债。
- Level 2: Develop. 部分任务的时机已被测量,基本的 RTOS 或结构化循环已经到位,但各团队的实践并不一致。编码准则存在,但未被强制执行。测试包括一些仿真环节。某些产品上存在手工的、有风险的更新路径,另一些产品则没有。好的做法零星存在,但并不一致,也没有任何机制保证下一条产品线会继承这些好做法。
- Level 3: Standardize. 时机要求被分类为硬、固或软,并用最坏情况执行时间和一种可调度性方法加以分析,在整个组织范围内形成文档并强制执行。内存、CPU 和电力的资源预算被写明硬性上限。所管辖的功能安全标准得到遵循,具备从需求到代码再到测试的可追溯性,MISRA C 或同等标准在每次提交时都由静态分析强制执行。硬件在环测试已接入流水线。带回滚和安全启动的经签名、原子式空中下载更新,是所有地方都必须满足的基线要求。
- Level 4: Manage. 组织会对照基线来度量和管控其嵌入式资产。它追踪最坏情况执行时间余量、抖动分布、错过截止时间的比率、内存和电力余量、仍未关闭的静态分析发现项、认证证据的覆盖率,以及空中下载更新的成功率和回滚率,并将它们与商定的目标进行对比。一旦某项资源或时机预算出现漂移,就会在设备于现场失效之前触发行动,发布的”通过/不通过”决策依据的是这些数据,而不是当下的主观判断。管理者能够看清哪些产品线已具备审计准备、哪些产品线正趋向于错过截止时间或超出预算。
- Level 5: Orchestrate. 确定性、安全证据和保安性得到持续验证和自动化。故障注入和硬件在环测试在每一次改动时都会运行,认证工件作为流程的副产品自动生成。整个设备群在漫长的服务周期内得到安全的监控、打补丁和更新。随着芯片停产、威胁演变和法规变化,组织会调整其执行基础、资源预算和标准采用方式,依据证据而不是逐一应对危机来重新平衡整个设备组合。
Ideas for discussion
- 你设备中的哪些任务真正属于硬实时?你能证明每一项都总能满足其截止时间吗?
- 你是否知道你关键控制回路的最坏情况执行时间,还是只知道它的平均值?
- 哪项功能安全标准管辖你的产品?你目前的证据距离该标准的要求还有多远?
- 如果明天在一台已部署的设备上发现了严重缺陷,你会如何修复它?速度有多快?
- 你的控制路径中,动态内存分配还存在于哪些地方?如果它在第 1000 小时时失败会怎样?
- 如果攻击者发现了一个共享的默认凭据,你的物联网设备群将如何经受住这种攻击?
Key takeaways
- 嵌入式软件运行在资源受限的硬件上,实时正确性不仅取决于给出正确答案,还取决于时机。
- 把每一个截止时间分类为硬、固或软,并为最坏情况下的时机、有边界的抖动,以及确定性(而非原始速度)而设计。
- 有意识地在 RTOS 与裸机之间做选择,并把内存、CPU 和电力当作固定的、第一等级的资源来做预算。
- 让中断处理程序保持极小,保护好共享数据,并把硬件隐藏在干净的、可测试的驱动接口背后。
- 及早采用你所在领域要求的功能安全标准(IEC 61508、ISO 26262、DO-178C、IEC 62304、MISRA C),并确保完整的可追溯性。
- 结合仿真和硬件在环进行测试,并从第一天起就构建安全的、经签名的、具备回滚能力的 OTA 更新和设备保安性。
References and further reading
- IEC 61508, Functional Safety of Electrical/Electronic/Programmable Electronic Safety-related Systems
- ISO 26262, Road Vehicles: Functional Safety
- RTCA DO-178C, Software Considerations in Airborne Systems and Equipment Certification
- IEC 62304, Medical Device Software: Software Life Cycle Processes
- MISRA, MISRA C: Guidelines for the Use of the C Language in Critical Systems
- Michael Barr and Anthony Massa, Programming Embedded Systems
- Elecia White, Making Embedded Systems
- Jane W. S. Liu, Real-Time Systems
- Giorgio Buttazzo, Hard Real-Time Computing Systems: Predictable Scheduling Algorithms and Applications
- Colin Walls, Embedded Software: The Works
- Philip Koopman, Better Embedded System Software
- OWASP Internet of Things (IoT) security guidance