首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

TRITON恶意软件攻击工业安全系统

简介

FireEye的Mandiant调查部最近响应了一个关于关键设施企业的应急事件,事件中攻击者用恶意软件来控制工业安全系统(industrial safety systems)。被攻击的工业安全系统能提供工业过程的急救关机功能。此次事件的攻击者具备对设备造成物理伤害和不可逆转的关机操作的能力。TRITON恶意软件是与Triconex Safety Instrumented System(SIS)控制器通信的攻击框架。FireEye分析说,攻击应该是某个国家发起的而不是某个威胁源

TRITON是少数被识别的针对工业控制系统(industrial control systems, ICS)的恶意软件家族。我们TRITON与Stuxnet、Industroyer是有传承关系的,都可以阻止安全机制执行原来的功能。

表1 TRITON恶意软件描述

事件总结

攻击者获取SIS工程站的远程访问权限后,利用TRITON攻击框架对SIS控制器进行重编程。在本次事件中,一些SIS控制器进入failed safe状态,该状态下会自动关闭工业生产过程,并促使资产所有者进行调查。调查结果显示,当冗余处理单元之间的应用代码没有完成有效性检查时,SIS控制器会进入safe shutdown状态,会产生MP诊断失败消息。

攻击者对设备可以产生物理伤害的原因有:

·修改SIS可以阻止SIS正确运行,增加了造成物理伤害的failure的概率。

·TRITON可以修改SIS控制器中的应用内存,这会导致有效性检查失败。

·TRITON运行的这段时间会产生failure。

·迄今没有发现现存的和外部条件在事件中引起错误(fault)。

过程控制和安全仪表系统SIS

图1 ICS架构

现在的工业处理控制和自动化系统依赖许多复杂的控制系统和安全功能。这些系统和功能就叫做ICS(Industrial Control Systems工业控制系统)和OT(Operational Technology操作技术)。分布式的控制系统(DCS)提供给操作员远程监控和控制工业过程的能力。这是一个计算机控制的系统,包括计算机、软件应用和控制器等。工程站用于配置、维护和诊断控制系统应用和其他控制系统装备。

SIS是独立监控控制过程的状态的自动控制系统。如果某个过程超过了定义为危险状态的参数值,SIS就会尝试让过程进入safe状态,或者自动对过程进行safe shutdown。如果SIS和DCS控制器都失效了,最后一道防线就是的工业facility的设计,包括对设备的机械保护、物理报警、紧急响应程序和其他缓解威胁情形的机制。

资产所有者用不同的方法来将DCS与SIS通信。传统的方法是依赖于通信基础设施和控制策略的分割原则。在过去的10年里,考虑到成本低、使用方便、DCS和SIS交换信息方便等因素,在设计中将DCS和SIS集成到一起是一种趋势。TRITON正是利用了这一点,证明了DCS和SIS集成时通信的风险。

安全仪表系统威胁模型和攻击场景

图2 Cyber Security和Safety之间的关系

针对ICS的破坏性攻击的生命周期与其他类型的网络攻击类似,但也有不同。首先,攻击者的目标是破坏运作过程而不是窃取数据。第二,攻击者必须执行OT侦测,也要有足够多的专业的工程知识才能理解要控制的工业过程,并成功操作它。

图2是在过程控制环境下cyber security和safety控制的关系。即使cyber security措施时效,safety控制可以抵挡一定的物理破坏。为了最大化物理影响,攻击者需要绕过一些安全控制。

SIS威胁模型强调了攻击者已成功黑掉SIS的一些可用选项。

Attack Option 1: 用SIS 来关闭过程

· 攻击者可以对SIS逻辑重编程,导致trip或关闭一个处于safe状态的过程,或者说,引入假阳性(false positive)。

· 过程宕机和宕机后的复杂流程带来的经济损失。

Attack Option 2: 对SIS重变成允许unsafe状态

· 攻击者可以对SIS逻辑进行重编程来允许unsafe条件持续。

· 因为SIS功能缺失导致的风险增加,最终导致对物理的结果。

Attack Option 3: 对SIS进行重编程来允许unsafe状态,即使用DCS来创建unsafe状态

· 攻击者可以操作过程进入unsafe状态,阻止SIS正常运行。

· 对人身安全、环境和设备的损害和程度取决于工业过程和工厂设计的物理限制。

攻击意图分析

攻击者的长期目的是对培养造成物理破坏的能力。因为攻击者在DCS上站住脚之后,本来可以操作过程或者关闭工厂系统,但是攻击者选择了黑近SIS系统。黑进DCS和SIS系统可以使攻击者培养和实施带来最大可能破坏的物理攻击。

在SIS网络中,攻击者用TRITON框架与SIS控制器进行交互,使用的协议是TriStation协议。攻击者可以通过halt命令或上传有漏洞的代码到SIS控制器来使过程停止。攻击者的目的不是让过程停止或者关闭这么简单,而是引发物理破坏这样的特定结果。

恶意软件能力总结

TRITON攻击工具有很多的特征,包括读写程序、读写单个函数、查询SIS控制器的状态。但是在trilog.exe样本中只使用了部分功能。TRITON恶意软件能与Triconex SIS控制器进行通信,用攻击者定义的payload对SIS控制器进行重编程。分析的TRITON样本在Triconex的执行列表中增加了攻击者提供的程序。

攻击样本并没有替换原来的程序,应该是希望控制器能够继续运行。如果控制器报错,TRITON就会尝试把它变回running状态。如果控制器没有在一定的时间窗口内恢复,样本就会用无效数据覆写恶意程序来避免被追踪。

建议

资产所有者想要防御上面提到的攻击能力,可以考虑下面几点:

· 如果技术上可行,把安全系统网络和过程控制、信息系统网络隔离开。能够对SIS控制器编程的工程站不应该对任何的DCS过程和信息系统网络双宿主机。

· 用提供物理控制的硬件特征来对安全控制器进行编程。通常采取物理钥匙控制开关的形式。

· 对key保存位置的变更进行变更管理步骤。对现在的密钥状态进行定期审计。

· 依赖SIS提供的数据的应用的网络连接使用用单向网关而不是双向网络连接。

· 对可以通过TCP/IP接触SIS系统的所有服务器和终端实施严格的访问控制和应用白名单。

· 监控ICS网络流量来检查意外的通信流和异常活动。

图3 Triconex 钥匙开关

技术分析

图4 TRITON架构和攻击场景

TRITON应用在运行Windows操作系统的SIS工程站上。恶意软件的名字伪装成合法的Triconex Trilog应用。该应用用于检查日志,而且是TriStation应用套件的一部分。恶意软件通过Py2EXE编译的python脚本进行传递,python脚本依赖于含有标准python库、开源库的文件和攻击者开发的Triconex攻击框架。应用到控制器的payload中除了可执行文件外,还有2个二进制文件,nject.bin (恶意功能代码) 和imain.bin (恶意控制逻辑)。这些文件名都被硬编码到Py2EXE编译的python脚本中。

Trilog.exe在命令行中有一个选项,即目标Triconex设备的IP地址。在Triconex设备发现时并没有用TRITON库,而对于环境中的每个目标控制器,都需要trilog.exe的实例来单独调用。一旦调用,trilog.exe就会检查控制器的状态,读取暴露给TriStation协议的配置信息。如果控制器是running状态,trilog.exe对inject.bin和imain.bin两个payload文件进行编码,并传递到通信库加到控制器程序的内存和执行列表中。

当payload文件插入到Triconex控制器的内存中,脚本就会进行倒计时,周期性地检查控制器的状态。如果检测到错误信息,通信库的方法SafeAppendProgramMod会尝试用TriStation协议命令重置控制器到之前的状态。如果这个方法失败了,trilog.exe会尝试把dummy程序写入内存。这是一种反取证技术,用来隐藏Triconex控制器中的攻击者代码。

研究人员同时发现恶意软件有一个条件检查,可以阻止payload二进制文件保留在环境中。在修复了该条件检查后,payload二进制文件可以持续保留在控制器内存中,控制器可以继续运行。

TriStation协议是合法的TriStation应用用来配置控制器的协议。

TsHi是高级接口,允许威胁者的操作者用TRITON框架实施攻击脚本。暴露的功能是侦查和攻击。这些函数从用户处接受二进制数据,处理代码签名,检查校验和。

TsBase是另一个攻击模块,包含TsHi的函数,翻译检查者的意图动作为适当的TriStation协议功能代码。对特定的函数,还需要对数据打包并整理为适当的格式。

TsLow 是另一个实施TriStation UDP有线协议的攻击模块。TsBase库主要依赖的是ts_exec 方法,该方法获取函数代码和期待的响应代码,对UDP上的命令payload序列化。同时检查控制器的响应,如果返回的是结果数据结构就说明success,如果返回False对象就代表failure状态。

TsLow也暴露了用来检查与目标控制器连接的连接方法。如果没有目标唤醒,就会运行设备发现功能detect_ip。使用TriStation协议上的ping消息广播来发现哪些控制器通过调用脚本的路由器是可达的。

IoC

检测规则

rule TRITON_ICS_FRAMEWORK

{

meta:

author = "nicholas.carr @itsreallynick"

md5 = "0face841f7b2953e7c29c064d6886523"

description = "TRITON framework recovered during Mandiant ICS incident response"

strings:

$python_compiled = ".pyc" nocase ascii wide

$python_module_01 = "__module__" nocase ascii wide

$python_module_02 = "" nocase ascii wide

$python_script_01 = "import Ts" nocase ascii wide

$python_script_02 = "def ts_" nocase ascii wide

$py_cnames_01 = "TS_cnames.py" nocase ascii wide

$py_cnames_02 = "TRICON" nocase ascii wide

$py_cnames_03 = "TriStation " nocase ascii wide

$py_cnames_04 = " chassis " nocase ascii wide

$py_tslibs_01 = "GetCpStatus" nocase ascii wide

$py_tslibs_02 = "ts_" ascii wide

$py_tslibs_03 = " sequence" nocase ascii wide

$py_tslibs_04 = /import Ts(HiLowBase)[^:alpha:]/ nocase ascii wide

$py_tslibs_05 = /modules?version/ nocase ascii wide

$py_tslibs_06 = "bad " nocase ascii wide

$py_tslibs_07 = "prog_cnt" nocase ascii wide

$py_tsbase_01 = "TsBase.py" nocase ascii wide

$py_tsbase_02 = ".TsBase(" nocase ascii wide

$py_tshi_01 = "TsHi.py" nocase ascii wide

$py_tshi_02 = "keystate" nocase ascii wide

$py_tshi_03 = "GetProjectInfo" nocase ascii wide

$py_tshi_04 = "GetProgramTable" nocase ascii wide

$py_tshi_05 = "SafeAppendProgramMod" nocase ascii wide

$py_tshi_06 = ".TsHi(" ascii nocase wide

$py_tslow_01 = "TsLow.py" nocase ascii wide

$py_tslow_02 = "print_last_error" ascii nocase wide

$py_tslow_03 = ".TsLow(" ascii nocase wide

$py_tslow_04 = "tcm_" ascii wide

$py_tslow_05 = " TCM found" nocase ascii wide

$py_crc_01 = "crc.pyc" nocase ascii wide

$py_crc_02 = "CRC16_MODBUS" ascii wide

$py_crc_03 = "Kotov Alaxander" nocase ascii wide

$py_crc_04 = "CRC_CCITT_XMODEM" ascii wide

$py_crc_05 = "crc16ret" ascii wide

$py_crc_06 = "CRC16_CCITT_x1D0F" ascii wide

$py_crc_07 = /CRC16_CCITT[^_]/ ascii wide

$py_sh_01 = "sh.pyc" nocase ascii wide

$py_keyword_01 = " FAILURE" ascii wide

$py_keyword_02 = "symbol table" nocase ascii wide

$py_TRIDENT_01 = "inject.bin" ascii nocase wide

$py_TRIDENT_02 = "imain.bin" ascii nocase wide

condition:

2 of ($python_*) and 7 of ($py_*) and filesize < 3MB

}

  • 发表于:
  • 原文链接http://kuaibao.qq.com/s/20171218G0N8Y600?refer=cp_1026
  • 腾讯「腾讯云开发者社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。
  • 如有侵权,请联系 cloudcommunity@tencent.com 删除。

扫码

添加站长 进交流群

领取专属 10元无门槛券

私享最新 技术干货

扫码加入开发者社群
领券