Therac-25 放射治疗机软件事故深度复盘

一、事件概述

1. 事件背景

1985 年 6 月至 1987 年 1 月期间,加拿大原子能有限公司(AECL)制造的 Therac-25 放射治疗机发生了 6 起严重的辐射过量事故。这是软件工程史上最致命的软件故障案例之一,直接导致 4 人死亡、2 人重伤。

2. 影响范围

A. 影响用户数

6 名患者接受过度辐射治疗,其中 4 人因辐射伤害死亡,2 人终身残疾。

B. 影响时长

1985 年 6 月首起事故至 1987 年 1 月最后一起事故,持续约 19 个月。

C. 影响功能

机器在电子束治疗模式下出现致命故障,患者接受的辐射剂量比正常值高出 100 倍。

3. 严重程度

这是医疗设备软件安全领域最严重的灾难性事故之一,成为软件工程、计算机伦理和医疗设备安全教育的经典教材。

二、事件时间线

1. 第一阶段事故(1985 年 6 月 - 1986 年 1 月)

A. 1985 年 6 月:肯尼迪将军医院首起事故

加拿大安大略省肯尼迪将军癌症中心发生第一起已知过量辐射事故。患者接受治疗时出现异常灼伤,但 AECL 最初声称机器不可能出错。

B. 1985 年 7 月:汉密尔顿诊所事故

美国佐治亚州汉密尔顿诊所发生类似事故。AECL 仍拒绝承认软件问题,归咎于用户操作。

C. 1985 年 12 月:雅基马山谷医院事故

华盛顿州雅基马山谷纪念医院发生第三起事故。此时 FDA 开始介入调查。

2. 第二阶段事故(1986 年 - 1987 年 1 月)

A. 1986 年:初步修复尝试

AECL 发布软件补丁,增加了互锁机制和错误提示,但未能根除问题。

B. 1987 年 1 月:最后一起致命事故

加拿大一名患者因辐射过量死亡,这是第六起也是最后一起已知事故。

C. 事后调查

1987 年后,独立专家 Nancy Leveson 教授开始深入调查,最终于 1993 年发表里程碑式论文《An Investigation of the Therac-25 Accidents》。

timeline
    title Therac-25 事故时间线
    1985年6月 : 肯尼迪将军医院首起事故<br>患者严重灼伤
    1985年7月 : 汉密尔顿诊所事故<br>AECL 否认软件问题
    1985年12月 : 雅基马医院事故<br>FDA 开始调查
    1986年 : AECL 发布软件补丁<br>增加互锁机制
    1987年1月 : 最后一起致命事故<br>加拿大患者死亡
    1993年 : Leveson 发表调查论文<br>揭露系统性问题

Therac-25 事故时间线

三、问题分析

1. 直接原因

A. Race Condition(竞争条件)

软件存在经典的并发编程错误。当操作员快速输入治疗参数时(特别是快速修改参数后立即执行),共享变量可能被不一致地更新,导致机器状态混乱。

具体表现为:

  • 操作员在 8 秒内输入治疗参数
  • 按 Enter 键确认时,软件正在执行其他任务
  • 系统未能正确更新治疗模式参数
  • 导致机器在错误模式下以最大功率输出辐射

B. 算术溢出

软件中存在变量溢出 bug,特定条件下会导致安全检查失效。

C. 用户界面设计缺陷

  • 机器频繁显示无关紧要的错误提示
  • 操作员习惯性忽略错误信息
  • 关键错误信息被淹没

2. 根本原因(5 Whys 分析)

A. 为什么出现 Race Condition?

:软件设计时未充分考虑多任务并发场景。使用汇编语言编写,代码复杂度高,难以正确处理时序问题。

B. 为什么没有及时发现?

:AECL 过度依赖软件测试,未进行系统级的硬件-软件联合测试。测试用例未能覆盖快速参数输入场景。

C. 为什么移除硬件互锁?

:Therac-25 设计理念是软件化降低成本。早期型号 Therac-6 和 Therac-20 有硬件互锁保护,但 Therac-25 完全依赖软件安全控制,导致硬件保护层被移除。

D. 为什么事故持续发生?

:AECL 缺乏透明的故障报告机制。医院之间的事故信息未能有效共享,导致重复事故发生。

E. 为什么监管未能预防?

:当时的医疗设备监管体系对软件安全的认识不足,缺乏针对软件密集型医疗设备的专门审查标准。

3. 深层反思

A. 软件工程认知局限

1980 年代中期,软件工程作为一门学科仍在发展,业界对软件复杂性和系统性风险的认识不足。AECL 错误地认为软件可以完全替代硬件安全机制。

B. 系统性失效

这不是单一的代码 bug,而是系统性失效的典型案例:

  • 设计哲学错误:过度依赖软件,移除硬件保护
  • 开发流程缺陷:缺乏严格的软件验证和测试
  • 企业文化问题:回避问题、拒绝承认错误
  • 监管体系漏洞:缺乏有效的医疗设备软件审查

四、技术深度分析

1. Therac-25 系统架构

graph TB
    subgraph 输入系统
        A[键盘输入]
        B[参数编辑]
    end

    subgraph 控制系统
        C[处理单元]
        D[模式控制]
        E[剂量监测]
    end

    subgraph 执行系统
        F[转靶]
        G[平坦过滤器]
        H[电子束]
        I[模式开关]
    end

    subgraph 安全系统
        J[软件互锁<br>Therac-25 新增]
        K[硬件互锁<br>已移除]
    end

    A --> C
    B --> C
    C --> D
    D --> E
    D --> I
    I --> F
    I --> G
    I --> H
    E -.软件检查.-> J
    J -.失效.-> K

Therac-25 系统架构图

2. Race Condition 技术细节

A. 正常工作流程

  1. 操作员输入治疗参数(能量、模式、剂量)
  2. 软件验证参数合法性
  3. 设置机器模式(电子束模式或 X 射线模式)
  4. 配置硬件(转靶位置、平坦过滤器)
  5. 执行治疗

B. 故障触发流程

sequenceDiagram
    participant O as 操作员
    participant S as 软件
    participant H as 硬件

    O->>S: 快速输入参数
    O->>S: 按 Edit 修改
    O->>S: 8 秒内按 Enter 确认
    Note over S: Race Condition 发生
    S->>S: 共享变量不一致
    S->>H: 错误的模式参数
    H->>H: 转靶位置错误
    H->>O: 输出高剂量辐射
    Note over O,H: 患者接受 100 倍过量辐射

Race Condition 触发流程

C. 代码层面问题

  • 使用汇编语言编写,代码可读性差
  • 缺乏代码审查机制
  • 没有使用成熟的并发控制原语
  • 变量共享区域未正确保护

3. 与早期型号对比

特性Therac-6 / Therac-20Therac-25
硬件互锁✅ 有硬件保护❌ 完全依赖软件
控制方式硬件为主,软件辅助纯软件控制
编程语言混合语言汇编语言
事故记录无严重事故6 起严重事故
设计理念硬件优先软件优先

关键发现:Therac-6 和 Therac-20 的硬件互锁实际上掩盖了类似的软件 bug,但无人察觉这些潜在故障的存在。

五、解决方案

1. 临时方案

A. 软件补丁

  • 增加参数修改后的确认步骤
  • 添加额外的软件互锁检查
  • 改进错误提示机制

B. 效果评估

临时补丁未能根本解决问题,事故仍继续发生。

2. 永久方案

A. 硬件恢复

在后续型号中恢复硬件互锁机制,不再完全依赖软件。

B. 流程改进

  • 建立强制性的故障报告共享机制
  • 要求所有医院报告异常事件
  • AECL 建立专门的事故响应团队

C. 监管改革

  • FDA 加强医疗设备软件审查
  • 推动医疗设备软件开发规范化
  • 要求独立的软件安全验证

3. 预防措施

A. 软件工程层面

  • 防御性编程:假设软件可能出错,设计多层防护
  • 形式化验证:对关键安全代码进行数学证明
  • 独立测试:第三方机构进行安全测试
  • 代码审查:建立严格的审查流程

B. 系统设计层面

  • 冗余设计:软件和硬件双重保护
  • 故障安全:系统失效时自动进入安全状态
  • 最小权限:关键功能限制访问

C. 组织管理层面

  • 透明文化:鼓励报告问题而非隐瞒
  • 持续学习:建立事故案例库
  • 跨机构协作:行业共享安全信息

六、经验总结

1. 做得好的地方

A. 事后调查深入

Nancy Leveson 教授的调查报告成为行业标杆,其分析方法至今仍被引用。

B. 教育价值

Therac-25 案例被编入全球软件工程课程,教育了数代工程师。

2. 需要改进的地方

A. 初始响应

AECL 最初否认问题、归咎于用户,导致事故重复发生。应第一时间承认问题并采取行动。

B. 信息共享

各医院的事故信息未能及时共享,缺乏有效的行业协作机制。

C. 监管体系

当时的监管体系对软件安全认识不足,需要加强技术审查能力。

3. 流程优化建议

A. 建立多层次的防御体系

第一层:硬件互锁(物理保护)
第二层:软件检查(逻辑验证)
第三层:操作培训(人工防护)
第四层:事故响应(紧急处理)

B. 推动行业标准

  • 制定医疗设备软件安全标准(如 IEC 62304)
  • 建立强制性的软件验证流程
  • 要求透明的故障报告机制

C. 教育培训

  • 在软件工程课程中纳入安全关键系统案例
  • 培养工程师的安全意识和责任感
  • 推广形式化验证等高级验证技术

七、历史影响与遗产

1. 软件工程领域

Therac-25 事故成为软件工程史上的转折点:

  • 促成了软件安全工程的兴起
  • 推动了形式化方法在实际系统中的应用
  • 确立了安全关键系统的开发规范

2. 医疗设备监管

  • FDA 加强了对医疗设备软件的审查
  • 推动国际电工委员会(IEC)制定 IEC 62304 标准
  • 建立了更严格的医疗设备上市前审查流程

3. 法律与伦理

  • 确立了医疗设备制造商的产品责任
  • 推动了软件工程伦理的发展
  • 促进了患者安全权益的保护

4. 学术研究

Leveson 的论文成为引用率最高的软件安全论文之一(2160+ 次引用),开启了系统安全理论(STAMP)的研究方向。

八、当代启示

1. AI 安全与医疗 AI

Therac-25 案例对当代 AI 安全仍有重要启示:

  • 黑箱问题:现代 AI 系统的可解释性问题比 1980 年代的软件更严重
  • 测试局限:即使经过大量测试,AI 系统仍可能在边界情况下失效
  • 人机协作:需要保留人类专家的最终决策权

2. 自动驾驶与安全关键系统

  • 软件定义的汽车、航空器等系统面临类似挑战
  • 需要建立软件更新的安全验证机制
  • 平衡创新速度与安全保障

3. 开源软件与责任认定

  • 当代软件依赖复杂的开源供应链
  • 需要重新思考责任认定和质量追溯
  • 建立更透明的安全漏洞披露机制

参考资料

  1. An Investigation of the Therac-25 Accidents - IEEE Computer 1993 - Nancy G. Leveson, Clark S. Turner - 权威学术期刊论文(2160+ 引用)
  2. Therac-25 Wikipedia - 综合性百科条目,包含完整事件概述
  3. Therac-25 Case Narrative - Online Ethics Center - 伦理研究中心的案例叙述
  4. Therac-25 事故分析 - 斯坦福大学课程材料 - 大学教学材料
  5. MIT Therac-25 研究资料 - Nancy Leveson 的 MIT 研究页面
  6. Therac-25 案例分析 - 维基百科中文 - 中文维基百科
  7. 软件 bug 致命的经典案例:Therac-25 医疗事故 - 腾讯云开发者社区 - 中文技术媒体分析
  8. 软件工程的史前时代-- Therac-25 事件 - 知乎专栏 - 中文社区分析文章
  9. Therac-25: The Software Bug That Killed Patients - Medium - 技术博客深度分析
  10. Killed By A Machine: The Therac-25 - Hackaday - 工程技术媒体专题报道
最后修改:2026 年 01 月 18 日
如果觉得我的文章对你有用,请随意赞赏