In the latter half of 2015, the FireEye Labs Advanced Reverse
Engineering (FLARE) team identified several versions of an ICS-focused
malware crafted to manipulate a specific industrial process running
within a simulated Siemens control system environment. We named this
family of malware IRONGATE.
FLARE found the samples on VirusTotal while researching droppers
compiled with PyInstaller — an approach used by numerous malicious
actors. The IRONGATE samples stood out based on their references to
SCADA and associated functionality. Two samples of the malware payload
were uploaded by different sources in 2014, but none of the antivirus
vendors featured on VirusTotal flagged them as malicious.
Siemens Product Computer Emergency Readiness Team (ProductCERT)
confirmed that IRONGATE is not viable against operational Siemens
control systems and determined that IRONGATE does not exploit any
vulnerabilities in Siemens products. We are unable to associate
IRONGATE with any campaigns or threat actors. We acknowledge that
IRONGATE could be a test case, proof of concept, or research activity
for ICS attack techniques.
Our analysis finds that IRONGATE invokes ICS attack concepts first
seen in href="http://www.symantec.com/content/en/us/enterprise/media/security_response/whitepapers/stuxnet_0_5_the_missing_link.pdf">Stuxnet,
but in a simulation environment. Because the body of industrial
control systems (ICS) and supervisory control and data acquisition
(SCADA) malware is limited, we are sharing details with the broader community.
Deceptive Man-in-the-Middle
IRONGATE's key feature is a man-in-the-middle (MitM) attack against
process input-output (IO) and process operator software within
industrial process simulation. The malware replaces a Dynamic Link
Library (DLL) with a malicious DLL, which then acts as a broker
between a PLC and the legitimate monitoring software. This malicious
DLL records five seconds of 'normal' traffic from a PLC to the user
interface and replays it, while sending different data back to the
PLC. This could allow an attacker to alter a controlled process
unbeknownst to process operators.
Sandbox Evasion
IRONGATE's second notable feature involves sandbox evasion. Some
droppers for the IRONGATE malware would not run if VMware or Cuckoo
Sandbox environments were employed. The malware uses these techniques
to avoid detection and resist analysis, and developing these
anti-sandbox techniques indicates that the author wanted the code to
resist casual analysis attempts. It also implies that IRONGATE’s
purpose was malicious, as opposed to a tool written for other
legitimate purposes.
Dropper Observables
We first identified IRONGATE when investigating droppers compiled
with PyInstaller — an approach used by numerous malicious actors. In
addition, strings found in the dropper include the word “payload”,
which is commonly associated with malware.
While IRONGATE malware does not compare to Stuxnet in terms of
complexity, ability to propagate, or geopolitical implications,
IRONGATE leverages some of the same features and techniques Stuxtnet
used to attack centrifuge rotor speeds at the Natanz uranium
enrichment facility; it also demonstrates new features for ICS malware.
IRONGATE’s characteristics lead us to conclude that it is a test,
proof of concept, or research activity.
Even though process operators face no increased risk from the
currently identified members of the IRONGATE malware family, IRONGATE
provides valuable insight into adversary mindset.
Network security monitoring, indicator of compromise (IoC) matching,
and good practice guidance from vendors and other stakeholders
represent important defensive techniques for ICS networks.
To specifically counter IRONGATE’s process attack techniques, ICS
asset owners may, over the longer term, implement solutions that:
FireEye has identified six IRONGATE droppers: class="code">bla.exe, update.exe1,
update_no_pipe.exe1, update_no_pipe.exe2,
update_no_pipe.exe2,
update.exe3. All but one of these Python-based
droppers first checks for execution in a VMware or Cuckoo Sandbox
environment. If found, the malware exits.
If not found, the IRONGATE dropper extracts a UPX-packed, publicly
available utility ( href="http://www.nirsoft.net/utils/netresview.html">NirSoft
NetResView version 1.27) to class="code">audiodg.exe in the same directory as the dropper.
The dropper then executes the utility using the command class="code">audiodg.exe /scomma scxrt2.ini. This command
populates the file scxrt2.ini with a
comma-separated list of network resources identified by the host system.
The dropper iterates through each entry in class="code">scxrt2.ini, looking for paths named class="code">move-to-operational or class="code">move-to-operational.lnk. If a path is found, the
dropper first extracts the Base64-encoded .NET executable class="code">scada.exe to the current directory and then
moves the file to the path containing
move-to-operational or class="code">move-to-operational.lnk. The path class="code">move-to-operational is interesting as well,
perhaps implying that IRONGATE was not seeking the actual running
process, but rather a staging area for code promotion. The dropper
does not execute the scada.exe payload after
moving it.
Anti-Analysis Techniques
Each IRONGATE dropper currently identified deploys the same .NET
payload, scada.exe. All but one of the
droppers incorporated anti-detection/analysis techniques to identify
execution in VMware or the Cuckoo Sandbox. If such environments are
detected, the dropper will not deploy the .NET executable ( class="code">scada.exe) to the host.
Four of the droppers (update.exe1,
update_no_pipe.exe1,
update_no_pipe.exe2, and class="code">update.exe3) detect Cuckoo environments
by scanning subdirectories of the style="color: rgb(216,36,53);">%SystemDrive%. Directories with
names greater than five, but fewer than ten characters are inspected
for the subdirectories drop, files, logs,
memory, and shots. If a matching
directory is found, the dropper does not attempt to deploy the class="code">scada.exe payload.
The update.exe1 and class="code">update.exe3 droppers contain code for
an additional Cuckoo check using the SysInternals pipelist program,
install.exe, but the code is disabled in each.
The update.exe2 dropper
includes a check for VMware instead of Cuckoo. The VMWare check looks
for the registry key HKLM\SOFTWARE\VMware,
Inc.\VMware Tools and the files
style="color: rgb(216,36,53);">%WINDIR%\system32\drivers\vmmouse.sys
and
style="color: rgb(216,36,53);">%WINDIR%\system32\drivers\vmhgfs.sys.
If any of these are found, the dropper does not attempt to deploy the
scada.exe payload.
The dropper bla.exe does not include an
environment check for either Cuckoo or VMware.
scada.exe Payload
We surmise that scada.exe is a
user-created payload used for testing the malware. First, our analysis
did not indicate what triggers scada.exe to
run. Second, Siemens ProductCERT informed us that class="code">scada.exe is not a default file name associated
with Siemens industrial control software.
When scada.exe executes, it scans drives
attached to the system for filenames ending in class="code">Step7ProSim.dll. According to the Siemens
ProductCERT, Step7ProSim.dll is not part of
the Siemens PLCSIM software. We were unable to determine whether this
DLL was created specifically by the malware author, or if it was from
another source, such as example code or a particular custom ICS
implementation. We surmise this DLL simulates generation of IO values,
which would normally be provided by an S7-based controller, since the
functions it includes appear derived from the Siemens PLCSIM environment.
If scada.exe finds a matching DLL file
name, it kills all running processes with the name class="code">biogas.exe. The malware then moves class="code">Step7ProSim.dll to class="code">Step7ConMgr.dll and drops a malicious class="code">Step7ProSim.dll – the IRONGATE payload – to the
same directory.
The malicious Step7ProSim.dll acts as an
API proxy between the original user-created class="code">Step7ProSim.dll (now named class="code">Step7ConMgr.dll) and the application class="code">biogas.exe that loads it. Five seconds after
loading, the malicious Step7ProSim.dll
records five seconds of calls to class="code">ReadDataBlockValue. All future calls to class="code">ReadDataBlockValue return the recorded data.
Simultaneously, the malicious DLL discards all calls to class="code">WriteDataBlockValue and instead calls class="code">WriteInputPoint(0x110, 0, 0x7763) and class="code">WriteInputPoint(0x114, 0, 0x7763) every
millisecond. All of these functions are named similarly to Siemens
S7ProSim v5.4 COM interface. It appears that other calls to API
functions are passed through the malicious DLL to the legitimate DLL
with no other modification.
Biogas.exe
As mentioned previously, IRONGATE seeks to manipulate code similar
to that found on a blog dealing with simulating PLC communications
using PLCSIM, including the use of an executable named biogas.exe.
Examination of the executable from that blog’s demo code shows that
the WriteInputPoint function calls with byte
indices 0x110 and class="code">0x114 set pressure and temperature values, respectively:
IRONGATE:
WriteInputPoint(0x110, 0, 0x7763)
WriteInputPoint(0x114, 0, 0x7763)
Equivalent pseudo code from Biogas.exe:
S7ProSim.WriteInputPoint(0x110, 0,
(short)this.Pressure.Value)
S7ProSim.WriteInputPoint(0x114, 0, (short)this.Temperature.Value)
We have been unable to determine the significance of the hardcoded
value 0x7763, which is passed in both
instances of the write function.
Because of the noted indications that IRONGATE is a proof of
concept, we cannot conclude IRONGATE’s author intends to manipulate
specific temperature or pressure values associated with the specific
biogas.exe process, but find the similarities to this example code striking.
The IRONGATE droppers are Python scripts converted to executables
using PyInstaller. The compiled droppers contain PyInstaller artifacts
from the system the executables were created on. These artifacts may
link other samples compiled on the same system. Five of the six file
droppers (bla.exe, update.exe1,
update_no_pipe.exe1, update_no_pipe.exe2 and
update.exe3) all share the same PyInstaller
artifacts listed in Table 1.

Table 1: Pyinstaller Artifacts
The remaining dropper, class="code">update.exe2, contains the artifacts
listed in Table 2.

Table 2: Pyinstaller Artifacts for update.exe2
Figure 1 and 2 list the unique strings discovered in the class="code">scada.exe and Step7ProSim.dll binaries.

Figure 1: Scada.exe Unique Strings

Figure 2: Step7ProSim.dll Unique Strings
Table 3 contains the MD5 hashes, file and architecture type, and
compile times for the malware analyzed in this report.

Table 3: File MD5 Hashes and Compile Times
FireEye detects IRONGATE. A list of indicators can be found here.
Special thanks to the Siemens ProductCERT for providing support and
context to this investigation.