代码之家  ›  专栏  ›  技术社区  ›  Doug Currie

现场安全更新嵌入式Linux的推荐技术

  •  9
  • Doug Currie  · 技术社区  · 17 年前

    运行脚本将文件复制到设备内部闪存上是一件简单的事情。然而,有一种危险,即设备在更新过程中会失去功率,并最终成为一块砖头。

    应用程序文件的情况更容易一些,因为有复制应用程序目录、更新一个副本以及快速交换新旧目录的空间,从而最大限度地减少了故障窗口。

    对于内核和系统文件来说,事情更加棘手,因为它们分布在整个文件系统中。

    我们在文件系统中使用硬链接和软链接来识别关键文件。我们对文件和归档文件使用哈希来验证文件的完整性。我们已经考虑在内核中使用紧急ramfs,以便在从更新的文件系统启动失败时提供回退。

    您对这一要求采取了哪些方法?

    5 回复  |  直到 17 年前
        1
  •  2
  •   florin    17 年前

    如果您必须确保可靠性,您可以有两个闪存分区(甚至芯片),一个具有当前工作配置,另一个具有新配置。然后使用硬件看门狗,该看门狗将重置设备,并将活动引导闪存分区切换到“最后已知良好”配置。

        2
  •  2
  •   Tim Williscroft    16 年前

    至少有两个分区。我建议4个

    • 靴子

    • 备用启动

    • 程序数据备份

    • 程序易失性数据

    永远不要更新引导加载程序。

    现在,除非闪存盘死掉,否则不能失败。

        3
  •  1
  •   flolo    17 年前

    创建关键文件并完成自己的分区,链接到它们,然后复制分区。在所有init中,您应该首先检查链接是否显示所有指向同一分区的链接,如果没有,则重置它们(指向包含某个文件最新日期的文件的分区)。如果要更新,只需将所有内容复制到新分区上,如果一切正常(crcs ok),则在文件上循环并为每个文件设置从一个文件系统到另一个文件系统的链接。

    这样,您的关键文件应始终处于正常状态。

    情节:

    1. 没问题,因为链接仍然显示为旧的工作链接。

    2. 链接时更新失败

        4
  •  0
  •   sbabic    12 年前

    通常,制造商希望从固件x.x.x更新到版本y.y.y,而不必担心内核和/或单个文件是否更新。更新单个文件可能成为服务的噩梦,因为很难理解客户硬件上运行的是什么。可能您正在混合使用双拷贝方法(应用程序是冗余的)和单拷贝方法。我认为这没有多大帮助,因为系统的完整性是由链中的薄弱部分完成的。如果根文件系统的更新失败,复制应用程序并不重要。

    如果您需要,双拷贝方法可以保证在不停止服务的情况下进行更新。但它需要大量资源,因为所有组件都必须重复。就我个人而言,我使用一种回退方法,在主应用程序失败或上次更新不成功的情况下,启动RAM中的一个小rootfs。如果出现任何错误,引导加载程序将自动启动此回退系统,并从USB笔更新系统(如果需要本地更新)。

    我从来没有找到一个关于这些问题的OSS项目,根据我以前的经验,我最近开始了一个新的项目。我有几个产品在运行它,我的客户对此很满意。

    github.com/sbabic/swupdate .

    斯特凡诺

        5
  •  0
  •   rduio    10 年前

    我认为您在这里试图实现的是更新过程的原子性。原子性对于嵌入式设备至关重要,其中一个突出的原因是功耗;但也可能存在其他问题,如硬件/网络问题。我在更新上下文中使用的原子性定义是:

    对于嵌入式Linux,您可能需要更新几个软件组件,并选择不同的设计;这里有一篇关于这方面的论文: https://mender.io/user/pages/04.resources/_white-papers/Software%20Updates.pdf

    推荐文章