提问人:Maxim Gershkovich 提问时间:6/20/2010 更新时间:6/21/2010 访问量:820
十亿英里的软件修补
Software patching at a billion miles
问:
这里有人可以阐明美国宇航局如何设计他们的航天器架构,以确保他们能够修补已部署代码中的错误吗?
我从未构建过任何“实时”类型的系统,这是阅读本文后想到的一个问题:
http://pluto.jhuapl.edu/overview/piPerspective.php?page=piPerspective_05_21_2010
“我们将做的第一件大事 下次我们唤醒航天器时做 一周将上传近 20 个未成年人 Bug 修复和其他代码增强功能 到我们的故障保护(或“自动驾驶仪” response“) 软件。
答:
好吧,我敢肯定他们有模拟器可以测试和热补丁机制。看看下面链接的文章 - 对航天器设计有一个很好的概述。第5节讨论了计算机。
http://www.boulder.swri.edu/pkb/ssr/ssr-fountain.pdf
注意:
- 冗余处理器
- 通过不需要处理器帮助的上行链路卡进行命令切换
- 时间滞后规则
我也从未构建过实时系统,但在这些系统中,我怀疑他们的系统不会有内存保护机制。他们不需要它,因为他们自己编写了自己的所有软件。如果没有内存保护,一个程序编写另一个程序的内存位置将是微不足道的,这可以用来热修补正在运行的程序(编写自修改代码是过去的流行技术,如果没有内存保护,用于自修改代码的相同技术可用于修改另一个程序的代码)。
Linux 已经能够在不重新启动的情况下使用 Ksplice 进行少量内核修补。这对于在任何停机时间都可能是灾难性的情况下使用是必要的。我自己从未使用过它,但我认为他们使用的技术基本上是这样的:
Ksplice 可以将补丁应用到 Linux 内核,而无需重新启动计算机。 Ksplice 将统一差异作为输入 和原始内核源代码, 它更新了正在运行的内核 记忆。使用 Ksplice 不需要 系统之前的任何准备工作都是 最初引导(正在运行的内核 不需要特别 例如,编译)。为了 生成更新,Ksplice 必须 确定内核中的代码 已被源代码更改 补丁。Ksplice 执行此分析 在 ELF 目标代码层,而不是 比在 C 源代码层。
要应用补丁,请先进行 Ksplice 冻结计算机的执行,使其 是唯一正在运行的程序。这 系统验证没有处理器 正在执行中 将由 补丁。Ksplice 修改开头 更改的功能,以便它们 而是指向新的、更新的版本 ,并修改数据 以及内存中需要 被改变。最后,Ksplice 恢复 每个处理器都从它离开的地方运行 关闭。
(来自维基百科)
我没有在航天器上工作过,但我工作过的机器都具有稳定的空闲状态,可以短暂关闭机器以修补固件。容纳“实时”更新的系统是那些被分解为交互组件的系统,您可以在其中关闭系统的一个部分足够长的时间以更新它,而其他组件可以继续正常运行,因为它们可以容忍服务组件的临时停机时间。
一种方法是具有并行(冗余)功能,例如所有执行相同任务的并行计算机,以便可以在服务中的计算机周围路由进程。这种方法的好处是,您可以将其关闭更长的时间,以获得更重要的服务,例如定期的硬件预防性维护。一旦你有了这个功能,支持固件补丁的停机时间就相当容易了。
过去使用的方法之一是使用 LISP。
我一直是公共电话交换系统软件的开发人员,该软件在可靠性、可用性、生存能力和性能方面有相当严重的限制,这些限制接近航天器系统的需求。我没有在航天器上工作过(尽管我在IBM工作时确实与许多前航天飞机程序员一起工作过),而且我不熟悉VXworks,这是许多航天器(包括火星探测器)使用的操作系统,它们有着惊人的运行记录)。
可修补性的核心要求之一是系统应从头开始设计用于修补。这包括模块结构,以便可以在不中断当前操作的情况下添加新变量和替换方法。这通常意味着更改方法的旧代码和新代码都将驻留,并且修补操作只是更新类或模块的调度向量。
将修补(和取消修补)软件集成到操作系统中几乎是强制性的。
当我在电话系统上工作时,我们通常使用系统中的补丁和模块替换功能来加载和测试我们的新功能以及错误修复,早在这些更改提交构建之前。每个开发人员都需要熟悉修补和替换模块,作为他们日常工作的一部分。它在这些组件中建立了一定程度的信任,并确保定期执行修补和替换代码。
这些系统的测试比您在任何其他项目中遇到的任何事情都要严格得多。部署系统的完整和部分模型将随时可用。可能还会有虚拟机环境,可以在其中运行和测试整个负载。单元测试以上的所有级别的测试计划都将被编写和正式审查,就像正式的代码检查一样(这些也将是例行公事)。
容错系统设计(包括软件设计)是必不可少的。我不具体了解航天器系统,但像高可用性集群这样的东西可能是标准的,它增加了同步和不同步运行的能力,并且能够在故障转移期间在双方之间传输信息。这种系统结构的另一个好处是,您可以拆分系统(如有必要),用新的软件负载重新加载非活动端,并在生产系统中对其进行测试,而无需连接到系统网络或总线。当您对新软件正常运行感到满意时,只需故障转移到它即可。
与修补一样,每个开发人员都应该知道如何进行故障转移,并且应该在开发和测试期间进行故障转移。此外,开发人员应该了解每个可能强制故障转移的软件更新问题,并且应该知道如何编写补丁和模块更换,以尽可能避免所需的故障转移。
通常,这些系统是针对这些环境从头开始设计的(硬件、操作系统、编译器,可能还有编程语言)。我不认为 Windows、Mac OSX、Linux 或任何 unix 变体足够强大。其中一部分是实时需求,但可靠性和生存能力的整个问题同样重要。
更新:作为另一个兴趣点,这是一位火星车驾驶员的博客。这将使您对维护运行航天器的日常生活有一个看法。整洁的东西!
评论