如何检测用USB创建并进行类似Stuxnet传播的隐蔽网络

如今,为了保证信息安全,很多公司和政府机构都建有通信隔离网,或在不同网络之间使用受限数据。一般来说,这些计算机网络都是针对某些特定环境创建的,如工控系统、处理特殊数据的高安全环境或安全标准要求的网络系统等。近年的网络安全事件证明,震网病毒(Stuxnet)利用U盘创建隐蔽网络成功渗透进物理隔离的核电站中,该案例说明,不与网线或WIFI连接的物理隔离计算机网络并不就是安全的。接入某个网络的任何类型外部连接,都可能构成安全风险。本文通过分析利用USB设备创建的隐蔽网络可能性,对其检测和防护方法作出介绍。

网络连接方面存在的安全风险

就数据网络的安全性而言,大家趋向于使用以太网和WiFi等链路层连接来分析刻画网络。但有些企业网络远比这复杂,因此我们需要从多个角度来进行分析。

对数据网络的流量分析是了解企业网络环境的主要方式。另外,对一些提供重要服务或者承担关键作用的常用协议节点进行查找分析,也是一种有效可行的方法。根据以上描述可知,在不同准则和方法下,对网络的风险分析可以得到大量有用的数据信息。了解网络设置和节点的直观方法就是映射绘画出一副直观的网络图,因此,以风险分析为前提,对网络结构进行一些传导性测试显得必不可少。这些分析数据能让我们更好理解网络整体架构和其中存在的风险。

网络整体架构

在风险消控、检测攻击和安全实施的网络分析方面,为了理解内部网络的不同边界,节点的表示和连接结构尤为重要。

更多的问题在于对网络架构的理解上。通常,网络被定义为由不同技术和协议互联的一组计算机。大多情况下,用户或网络系统管理员倾向于将不同组织架构下的计算机通过网线或WIFI进行连接,因而,将存在更多针对网络系统的接入风险。在此,我们需要深入讨论的是,如果一个组织机构未对USB设备的使用实施保护或限制措施,那么,将会面临隐蔽网络威胁。攻击者可以使用USB设备创建这类隐蔽网络,自由潜伏在物理或逻辑隔离的计算机间进行通信。

网络隔离和USB连接

可以从下例中理解用USB设备创建的隐蔽网络危害。假设某机构网络由3类VLAN组成,其中第一个VLAN包括:

计算机A、计算机B,通过VLAN互连

第二个VLAN包括:

计算机C、计算机D、计算机E,通过VLAN互连

第三个VLAN包括:

计算机F,与该VLAN内的其他计算机互连

从以下网络拓扑图可以看出,不同VLAN间的计算机是相互隔离的。但如果该机构员工使用USB设备来进行数据交换,那么数据信息很有可能会在不同VLAN计算机间传输。USB设备的接入本身就是一个安全威胁,攻击者可以利用这种方式在组织机构内部网络中创建一个不易被发现的隐蔽网络。

网络拓扑图

假设计算机F和计算机E用户正在使用USB设备进行数据交换,本质上来说,此时E、F两台计算机和USB设备之间就形成了一个隐蔽网络。可以用如下结构表示:

隐蔽网络结构

USB设备在操作系统中的连接情况

一个USB设备在不同主机之间进行交叉使用的情况,就类似于生物界的“授粉”(Pollination)现象。这种交叉感染的概念,同样适用于不同网络内不同主机间的USB混用。

当用户在计算机中接入USB设备时,Windows注册表会创建一系列键值。这些键值信息非常有用,比如,在取证分析中,可借此对信息泄露或威胁引入进行溯源。

存在于Windows系统注册表中的USBStor键值,用来保存USB设备插入到计算机时的相关信息。当某USB设备插入到某台主机中时,可以在USBStor键值中找到与这个USB设备相关的识别信息,这些信息包括:

设备名

设备类型(Class)

设备唯一标识符(ClassGUID)

硬件标识符

设备所提供的服务,如硬盘

驱动

其他信息

隐蔽连接:如何检测此类网络

在了解了操作系统对USB设备相关信息的保存方式之后,就可以知道哪些主机在共享使用USB设备。通过这种方式,我们可以用两个结点来表示两台主机,一条弧线表示两台主机之间的连接。由于通过隐蔽连接可以发现隐蔽网络,另外,结合从操作系统中获取的一些注册表相关信息,可以识别USB设备在不同主机间的接入顺序,以此可以描绘出更准确的隐蔽网络结构。

首先,为了实现自动化的隐蔽连接检测,可以使用如下方案:(红线表示脚本的传输执行,绿线表示脚本执行产生的数据)

实现自动化的隐蔽连接检测方案

在上图的内部域网络环境中,各个结点主机中的Script脚本程序能以多种方式被执行,而程序执行之后在主机中产生的数据,也将对内部域网络造成威胁。为了发现这些在实际生产环境中的隐蔽连接,在这里,我们具体来讨论以上隐蔽连接的一些检测技术,如:

WinRM

SMB(服务器消息块协议)

WMI

我们先来了解一下微软内置系统中面向对象的命令行工具 Powershell,它能提供与操作系统任何功能交互的强大接口。例如用 Powershell 来对查看 USBStor 键值,获取插入的USB设备信息:

用 Powershell 来对查看 USBStor 键值

WinRM方式的隐蔽网络检测

PowerShell中使用WinRM检测脚本的前提是,在每台需要审计的主机上启用Windows远程管理服务(Windows Remote Management),以下为 WinRM 服务:

 WinRM 服务

另外,尽可能经测试过,且能在启用活动目录(AD)的单域网络中可自动化收集信息。当使用管理员凭据对本地网络中的另一远程主机进行登录认证时,在该脚本执行后,会弹出登录窗口需要用户凭据输入。如下所示:

弹出登录窗口需要用户凭据输入

该脚本的主要实现部分为“LaunchUSBHiddenNetworks.ps1”程序,该程序通过远程连接到目标审计主机,然后用“RecollectUSB.ps1”来收集主机内的USB设备相关接入信息。因此,需要对每台主机中单独执行这一脚本。

LaunchUSBHiddenNetworks脚本

这个脚本主要基于PowerShell的“Invoke-Command”命令来实现。在连接网络中的另一台主机时,“Invoke-Command”命令可以使用FQDN、主机名和IP地址作为参数,当然,也能用以下PowerShell方式执行脚本:

$salida=invoke-command -ComputerName (Get-Content servers.txt) -FilePath ‘PathToScript\RecollectUSBData.ps1′-Credential testdomain\administrador

-Computer Name参数将指定AD域中的目标审计主机,在该参数后面,可使用逗号隔开的主机名来指定多台目标审计主机。在这里,我们使用包含多个主机的列表文件servers.txt作为参数。

-FilePath定义了所需收集信息的具体路径。最后,-Credential参数指定了需要对审计主机进行远程连接所使用的管理员账户,在该脚本命令中,“testdomain”为域名,“administrator”为用户。

以上脚本的执行结果将保存在$salida对象中。我们也可以将收集到的信息存放在一个名为“USBDATA.csv”的CSV文件中,其中包括了计算机名、IP地址、USB设备名和惟一标识符ID,如:

$salida | Out-File USBDATA.csv

脚本的执行结果

收集到以上信息后,我们可以使用网络分析软件Gephi来创建一张如下的网络图,其中可以显示USB设备使用后发生的隐蔽连接:

使用网络分析软件Gephi来创建网络图

RecollectUSBData脚本

这个脚本需要在目标审计主机中本地运行,用来收集插入到计算主机上的USB设备的相关信息。脚本将会从Windows注册表中的某个特定键值路径读取信息:

$USBDevices = @()

$USBContainerID = @()

$USBComputerName = @()

$USBComputerIP = @()

$SubKeys2 = @()

$USBSTORSubKeys1 = @()

我们需要将与目标审计主机相关的信息保存到这些变量中,并且检查注册表中存储的USB设备的相关信息。在操作系统中,这些目标审计主机的相关信息,连同接入的USB设备信息会被存储,当该脚本连接到主机中时,会自动读取这些信息。

$Hive = “LocalMachine”

$Key = “SYSTEM\CurrentControlSet\Enum\USBSTOR”

$Hive和$Key两个变量保存了注册表中存储USB设备信息的完整路径。$Hive变量值为“LocalMachine”,与HKLM或HKEY_LOCAL_MACHINE等同。

$ComputerName = $Env:COMPUTERNAME

$ComputerIP = $localIpAddress=((ipconfig | findstr [0-9].\.)[0]).Split()[-1]

本地计算机名和IP地址被分别存储到$ComputerName及$ComputerIP变量中。

$Reg = [Microsoft.Win32.RegistryKey]::OpenRemoteBaseKey($Hive,$Computer)

$USBSTORKey = $Reg.OpenSubKey($Key)

$nop=$false

在$Reg对象中,使用OpenRemoteBaseKey命令来查询注册表,而$Hive和$Computer变量则为注册表路径查询参数,最后的$nop变量用于程序执行控制。

Try {
$USBSTORSubKeys1 = $USBSTORKey.GetSubKeyNames()
} Catch {
Write-Host "Computer: ",$ComputerName -foregroundcolor "white" -
backgroundcolor "red" Write-Host "No USB data found" $nop=$true
} 

其中的Try-Catch函数块用来处理在未获取到USB设备信息时可能发生的错误,此时,$nop变量就会被赋值为$true,提前中断整个对USB设备信息进行检测识别的机制。

if(-Not $nop)

如果脚本检测到与USB设备有关的任何记录信息,程序将会执行如下代码(Block 1):

ForEach($SubKey1 in $USBSTORSubKeys1)
{ $Key2 = "SYSTEM\CurrentControlSet\Enum\USBSTOR\$SubKey1" $RegSubKey2 = $Reg.OpenSubKey($Key2) $SubkeyName2 = $RegSubKey2.GetSubKeyNames() $Subkeys2 += "$Key2\$SubKeyName2" $RegSubKey2.Close()
} 

在信息获取过程中,注册表路径中存在的每一项信息都为不同的USB设备所有。这些项别信息会被储存到@Subkeys2键值数组中。

Block 2代码:

ForEach($Subkey2 in $Subkeys2)
{
$USBKey = $Reg.OpenSubKey($Subkey2)
$USBDevice = $USBKey.GetValue('FriendlyName')
$USBContainerID = $USBKey.GetValue('ContainerID') If($USBDevice)
{
$USBDevices += New-Object -TypeName PSObject -Property @{
USBDevice = $USBDevice
USBContainerID = $USBContainerID
USBComputerName= $ComputerName
ComputerIP = $ComputerIP
}
}
$USBKey.Close()
} 

该代码块则用来处理上一段代码Block1中储存在@Subkeys2键值数组中的USB设备信息。由于每一项中都包含了$USBDevice字段,所以,USB设备相关的ID信息USBContainerID就能被获取。同时,其中还包括了主机名和IP地址,以便导出到统一格式的CSV文件中。存放USB设备信息的注册表路径如下:

存放USB设备信息的注册表路径

Block 3代码:

for ($i=0; $i -lt $USBDevices.length; $i++) {
$IDUnico=$USBDevices[$i] | Select -ExpandProperty "USBContainerID" $USBNombre=$USBDevices[$i] | Select -ExpandProperty "USBDevice" Write-Host "Computer: ",$ComputerName -foregroundcolor "black" -
backgroundcolor "green" Write-Host "IP: ",$ComputerIP
Write-Host "USB found: ",$USBNombre
Write-Host "USB ID: ",$IDUnico
Echo "$ComputerName,$ComputerIP,$USBNombre,$IDUnico" } 

最后,这段代码还能通过Write-Host命令,把在远程审计主机中获取的信息打印显示,Echo命令用于数据输出,以便在后续的CSV文件中写入数据。

通过Write-Host命令,把在远程审计主机中获取的信息打印显示

SMB和PSExec方式的隐蔽网络检测

为了在SMB下运行检测脚本,需先安装PSTools,也就是说,我们需要在审计主机中运行PSExec命令。这个脚本的功能与WinRM脚本大致相同。本地主机需要使用远程审计主机的管理员账户,与远程主机进行连接,之后,运行检测脚本,收集USB设备相关信息。

 为了适应这种连接,LaunchUSBHiddenNetworks.ps1脚本被作了适当修改。主要改动为没有使用Invoke-Command命令来远程运行检测脚本,而是通过Powershell开启shell接口来执行脚本。而脚本则托管在某个网络服务或HTTP方式的Web服务器中,需要被下载。这种方式,可以在访问共享资源时,避免一些脚本执行时的资源策略或权限问题。

与前述的WinRM脚本类似,检测执行结果将储存在一个CSV文件中。为了避免出现同步问题,也为远程主机的脚本执行给足时间,我们在检测代码中设置了一些延迟。

LaunchUSBHiddenNetworks脚本

$computers = gc "C:\scripts\HiddenNetworks\PSExec\USBHiddenNetworks_for_SMB\servers.txt" $url = "http://192.168.1.14/test/RecollectUSBData.ps1" $sincro = 40 

这段代码中指定了几个变量。servers.txt列表中的主机名或IP地址信息会被保存到$computers变量中,$url变量则用来存放RecollectUSBData.ps1脚本的网络托管地址,最后的$sincro则定义了需等待的同步时间,可以根据不同环境来调整时长。执行示例如下:

执行示例

servers.txt文件存有需要检测的主机名或IP地址信息,如下所示:

需要检测的主机名或IP地址信息

foreach ($computer in $computers) {
$Process = [Diagnostics.Process]::Start("cmd.exe","/c psexec.exe
\\$computer powershell.exe -C IEX (New-Object Net.Webclient).Downloadstring('$url') >>
C:\scripts\HiddenNetworks\PSExec\USBHiddenNetworks_for_SMB\usbdata.csv")
$id = $Process.Id sleep $sincro
Write-Host "Process created. Process id is $id" taskkill.exe /PID $id
} 

以上循环代码会对servers.txt中的所有主机进行检测。该段代码,主要部分为$Process对象,在其中,脚本会开启远程电脑的控制台连接,之后,该控制台连接将启动其他Powershell控制台,然后,通过$url参数传入RecollectUSBData.ps1文件。

在进行文件列表中下一台主机检测之前,当前的信息收集进程必须结束。对于此,有多种方法实现,例如在这里,可在在每次动作后添加一个X秒延迟的sleep命令。一旦当前审计主机的信息收集进程结束,在对下一台主机进行审计前,为了彻底清除进程,可通过taskkill命令来执行结束,脚本会将当前的进程ID和结果显示到屏幕上:

命令脚本

RecollectUSBData脚本

在这个脚本中,检测结果导出文件USBData.CSV与之前版本一致,但为了使输出和执行环境适配,我们只对前述的第3个代码块(Block 3)进行了修改。在以下代码中,“Echo”已经被“Write-Host”替换,最终完成屏显输出:

for ($i=0; $i -lt $USBDevices.length; $i++) {
$IDUnico=$USBDevices[$i] | Select -ExpandProperty "USBContainerID" $USBNombre=$USBDevices[$i] | Select -ExpandProperty "USBDevice" Write-Host "$ComputerName,$ComputerIP,$USBNombre,$IDUnico" }

历史记录信息收集

我们可以收集USB设备首次接入到计算机上的记录日期,以了解隐蔽网络中的USB设备具体路由信息。在Windows版本中都默认禁用了包含丰富信息的事件日志功能,这一功能的路径为:

Windows Logs -> Applications and Services Logs ->Microsoft-> Windows -> DriverFrameworks->UserMode -> Operational

因此对以下功能文件进行分析后,无需对计算机进行进一步的检查,就能获取USB设备的首次接入日期:

C:\Windows\inf\setuoapi.dev.log

这个文件记录的数据中包含了USB的首次接入时间。为了对某些USB设备进行准确定位,可以在“RecollectUSBData.ps1”脚本中,保存一个DiskID字段:

保存DiskID字段

该字段值在当前Windows系统中是唯一的,但接入到其他主机中时,该值就会发生改变。它与在每台Windows主机都一致的ContainerId字段不同。因此,我们可以在setupoapi.dev.log文件中使用这个DiskID字段值识别USB设备。如下图所示,通过 DiskID 值可以获取 USB 设备位置和首次插入操作系统的日期:

使用DiskID字段值识别USB设备

OS X系统中的隐蔽连接检测

对于苹果MAC OS操作系统来说,其中有com.apple.finder.plist文件用来储存接入计算机的USB设备信息,如下图所示:

com.apple.finder.plist文件储存接入计算机的USB设备信息

缓解措施

在高安全要求下的网络环境中限制USB设备的使用

强制设置活动目录策略,用户授权USB设备接入

使用其它数据交换或摆渡系统

如设置USB接入限制策略后,USB无法接入系统:

USB无法接入系统

总结

除了信息泄露风险外,隐蔽网络还可能会对企业网络的完整性造成影响,如USB设备的恶意软件传播。简单的把企业内网和互联网隔离,并不能实现更有效的安全防护,一方面,这将产生更多的系统漏洞,另外,没有限制的USB滥用会给内部网络带来潜在威胁,最后将造成严重的信息安全影响。

*参考来源:exploit-db,freebuf小编clouds编译