2012-11-01
Abstract
First discovered in around April 2010, Ramnit is now not only a file infector that infects Windows Portable Executable files (.exe, .scr and .dll files) and HTML documents, but also a multi-component bot. Chao Chen takes a deep dive into Ramnit, analysing the functionalities of each of its components.
Copyright © 2012 Virus Bulletin
First discovered in around April 2010, Ramnit is now not only a file infector that infects Windows Portable Executable files (.exe, .scr and .dll files) and HTML documents, but also a multi-component bot. It has the ability to steal sensitive information such as stored FTP credentials and browser cookies. During the summer of 2011, Ramnit infection reached its peak, accounting for over 17% of all new infections. However, it is evident that the gang behind Ramnit was not satisfied with its achievement, as the malware’s interests shifted from simple infection and the stealing of credentials to hitting financial targets [1] by utilizing code and modules from the leaked source code of the infamous Zeus [2] trojan.
In this article we will take a deep dive into Ramnit, analysing the functionalities of each of its components. We will see what a powerful beast Ramnit has become, and shed light on its likely future development.
The Ramnit installer discussed in this article has two layers of packing: a custom packer and UPX. (In this article, analysis of the installer is based on a sample with MD5: 7eb449a0be9f008bee337c8d55ba921c.) After the installer arrives on a victim’s computer, it unpacks the payload, copies itself to system folders and adds an autorun registry entry to automatically launch the malware at system start-up. The installer’s major work is to inject two malicious dynamic-link libraries, named Rmnsoft.dll and Modules.dll, into the context of legitimate system processes or specific web browser processes. The two injected malicious modules communicate with each other and download other modules from the Command & Control (C&C) server. The downloaded modules have considerable capabilities in terms of stealing sensitive information from the local computer and hijacking online banking sessions. In addition, a rootkit driver is set up by the installer to protect itself by hiding registry keys and killing anti-virus software installed on compromised computers. Moreover, by disabling UAC (User Account Control) and Rapport Management Service, Ramnit gains the necessary privileges to avoid being detected and to be able to commit financial fraud. Figure 1 shows the installation routine.
In preparation for the injection of Rmnsoft.dll and Modules.dll, the installer searches for the locations of svchost.exe and an existing web browser’s executable file. The installer hijacks system services ZwWriteVirtualMemory and ZwCreateUserProcess, appending code for injection after the regular logic of each service. The injection method for the two modules is identical: the installer starts an instance of svchost.exe, which is utilized as the shell process for the injected module. If the attempt at injecting into svchost.exe fails, the previously found web browser executable file is used as an alternative. Once the installer has successfully injected the malicious module, an event is set to notify the installer to unhook the hijacked system services. Also, for each injected module, a mutex is created to make sure that only one instance of the module exists in the system. Figure 2 shows the procedure of injecting Rmnsoft.dll into a shell process.
As we mentioned before, there are different modules which provide different functions. We’ll detail their functionalities and working mechanisms in the following sections.
Rmnsoft.dll is the first module injected by the installer into a process of svchost.exe or a web browser. So we assume that it plays the key role among all modules. In fact, as the only module that communicates directly with the C&C server, Rmnsoft.dll is at the centre of all components distributed on the infected computer. Its work consists of several parts:
Two copies of the installer’s executable file are embedded in the Windows file system by Rmnsoft.dll. One copy is placed in the directory pointed to by registry key HKCU\Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders\Startup, making sure Windows will launch it automatically at start-up.
To decide where the second copy should be placed, Rmnsoft.dll makes an attempt on a series of directories in the following order:
%UserProfile%\Local Settings\Application Data\
%ProgramFiles%
%CommonProgramFiles%
%UserProfile%
%AppData%
System directory
%WinDir%
%Temp%
Current directory
Once Rmnsoft.dll has found a directory (from those listed above) in which a temporary file can be created successfully, it will create a subfolder with a random name and place the second copy of the Ramnit installer in it. A typical location of this copy is %UserProfile%\Local Settings\Application Data\slyaqmdg\brqmbmmw.exe. Two registry keys, HKLM\Software\Microsoft\Windows NT\CurrentVersion\Winlogon\Userinit and HKCU\Software\Microsoft\Windows\CurrentVersion\Run\BrqMbmmw, are set to point to the location of the second copy.
Rmnsoft.dll gets a name list of anti-virus software from the C&C server and attempts to kill the processes of any anti-virus software running on the victim’s computer. Moreover, it will send the list to the rootkit driver dropped by the installer, which will provide a second-time strike on security software in kernel mode. Figure 3 shows part of the list.
Rmnsoft.dll harvests the locations which store the cookies of various web browsers. These locations are used to collect and delete local cookies at the command of the C&C server. The web browsers targeted are as follows:
Windows IE
Firefox
Opera
Safari
Chrome
Flash SOL
Rmnsoft.dll will upload the collected cookies to the C&C server. However, the work of collecting local cookies is carried out by another module downloaded from the C&C server.
Rmnsoft.dll also creates a thread which has the ability to capture a snapshot of the user’s screen and encode the snapshot in JPEG format. Each snapshot is stored along with a time stamp. Just like the stolen cookies, these screenshots will be sent back to the C&C server for future use.
A TCP connection on port 443 (HTTPS) is utilized for communication between Rmnsoft.dll and the C&C server. RC4 encryption with crypt key ‘black’ is used for network communication. When stolen sensitive information is uploaded to the C&C server, or modules are downloaded from the C&C server, the transmitted data is encrypted.
The domain name of the C&C server is not hard-coded in the module. A DGA (Domain Generating Algorithm) is deployed here to construct domain names which have no literal meaning. Some examples of generated domain names are as follows:
htmthgurhtchwlhwklf.com
jiwucjyxjibyd.com
khddwukkbwhfdiufhaj.com
snoknwlgcwgaafbtqkt.com
tfgyaoingy.com
ukiixagdbdkd.com
Two MD5s are used to register an infected computer to the C&C server. To get the first MD5, information about the infected computer is obtained and stored in the following data structure:
typedef struct BotSysInfo { DWORD VolumeSerialNumber; DWORD BuildNumber; DWORD MajorVersion; DWORD MinorVersion; WORD ProcessorArchitecture; DWORD ActiveProcessorMask; DWORD NumberOfProcessors; DWORD ProcessorType; WORD ProcessorLevel; WORD ProcessorRevision; BYTE ComputerName[LenComputerName]; }
The MD5 of the data in this structure is used as the first MD5. Then a string is made by concatenating ‘45Bn99gT’ and the first MD5. The MD5 of the resultant string is the second MD5. As shown in Figure 4, these two MD5s are sent to port 443 of the C&C server to register the infected computer.
Figure 5 shows two RC4 encrypted MD5s sent to the C&C server.
The structure of the data highlighted in Figure 5 is as follows:
typedef struct BotRegInfo { BYTE Operation; //value is 0xE2 BYTE Zero; DWORD Len1; //value is 0x20 BYTE FirstEncryptedMD5[Len1]; BYTE Zero; DWORD Len2; //value is 0x20 BYTE SecondEncryptedMD5[Len2]; }
As for the Operation value, it should be noted that different communication data types are represented by different values of Operation, as follows:
0x10: upload screenshots
0x15: upload cookies
0x16: get information about when cookies should be uploaded
0x18: get information about when and how often screenshots should be taken
0x1A: get anti-virus software list
0x21: get a specific module
0x23: get module list
0x50: report bug
0xE2: register a bot
0xF0: upload local information and get commands
0xF8: report state of command execution.
Data transmitted between Rmnsoft.dll and the C&C server is organized in a structure which begins with 0xFF00:
typedef struct CommunicationData { WORD Flag; //value is 0xFF00 DWORD SizeOfFollowingData; BYTE Operation; DataEntry Array[]; }
Rmnsoft.dll calls the send API twice to send out data in a CommunicationData structure, the first time for the beginning six bytes and the second time for the rest of the data.
Data in a DataEntry structure begins with 0x00, 0x01 or 0x02. When beginning with 0x00, its structure is as follows:
typedef struct DataEntry { BYTE Flag; //value is 0x00 DWORD SizeOfRC4EncryptedData; BYTE RC4EncryptedData[SizeOfRC4EncryptedData]; }
When beginning with 0x01, its structure is as follows:
typedef struct DataEntry { BYTE Flag; //value is 0x01 DWORD Data; }
When beginning with 0x02, its structure is as follows:
typedef struct DataEntry { BYTE Flag; //value is 0x02 DWORD Data1; DWORD Data2; }
Rmnsoft.dll periodically connects to the C&C server, uploading local information and getting commands, as shown in Figure 6.
The MD5 used for bot registration and a crypt key are uploaded to the C&C server. This crypt key will be used by both the C&C server and the modules downloaded from the server.
The commands received from the C&C server are as follows:
getexec: download an executable file from a URL given by the C&C server, save it as [folder]\[subfolder]\[name].exe and execute it. Here, [folder] is a directory chosen by the method used when the second copy of the installer was made, while [subfolder] and [name] are two arguments of the command. Through this command, an arbitrary executable file distributed on any computer controlled by the gang behind Ramnit can be executed in the background on the victim’s computer. This has the capability to provide a pay-per-install service for other malware.
kos: shut down (kill) the operating system.
screen: take a screenshot and save it locally.
update: get the latest copy of the Ramnit installer from a URL given by the C&C server and replace the old Ramnit installer.
cookies: set the timestamp baseline. For example, if it is set to xxx, then all the saved cookies whose timestamp is greater than xxx will be uploaded to the C&C server.
removecookies: remove the cookies files on the local computer.
Working in conjunction with Modules.dll, Rmnsoft.dll downloads several other modules from the C&C server.
Rmnsoft.dll and Modules.dll use a named pipe, \\.\pipe\wtglasop, to communicate with each other. Modules.dll acts as the server of the pipe while Rmnsoft.dll acts as the client. To contact through the named pipe, Modules.dll creates an instance of it by calling CreateNamedPipe and waits for a client process to connect to this instance by calling ConnectNamedPipe. On the other end of the pipe, Rmnsoft.dll attempts to connect to any instance of the pipe that is in the listening state by calling CreateFile. If the pipe is busy, Rmnsoft.dll waits until an instance of the pipe is available for connection by calling WaitNamedPipe. This interaction is shown in Figure 7 and Figure 8.
Figure 9 shows the relationship between all participants in downloading modules from the C&C server.
The whole downloading procedure can be divided into several steps:
Step 1: Rmnsoft.dll connects to the pipe on whose other end Modules.dll is listening.
Step 2: A pipe instance is created for connection between Modules.dll and Rmnsoft.dll. At this time Modules.dll, which focuses on the management of all the modules downloaded from the C&C server, should deliver a flag (a double word) to Rmnsoft.dll through the named pipe. Each bit of this flag represents whether a particular module exists on the infected computer.
Step 3: The important flag is transmitted by Rmnsoft.dll to the C&C server.
Step 4: The C&C server responds with a name list of the available modules it can provide.
Step 5: Rmnsoft.dll transmits the list to Modules.dll through the named pipe.
Step 6: Modules.dll compares the list with another list extracted from a local log file, containing information about all the modules running on the local computer. According to the result of the comparison, Modules.dll performs subsequent steps.
Step 7: For each module that exists on the local computer but which is not included in the list received through the pipe, Modules.dll stops it from running on the local computer and removes the data associated with it from the log file used in the previous step.
Step 8: For each module that is included in the list received through the pipe but which does not exist on the local computer, Modules.dll asks Rmnsoft.dll to download it from the C&C server.
Step 9: Rmnsoft.dll issues a request to the C&C server for the modules required by Modules.dll. Figure 10 shows that Rmnsoft.dll sends a packet to the C&C server, requesting a module.
The structure of the data highlighted in Figure 10 is as follows:
typedef struct ModuleNameInfo { BYTE Operation; //value is 0x21 BYTE Zero; DWORD LenModuleName; BYTE EncryptedModuleName[LenModuleName]; BYTE One; DWORD Zero; }
Step 10: The required modules are RC4 encrypted by the C&C server and sent to the bot, as shown in Figure 11.
The structure of the data highlighted in Figure 11 is as follows:
typedef struct ModuleData { WORD Flag; //value is 0xFF00 DWORD SizeOfFollowingData; BYTE Operation; //value is 0x21 BYTE Zero; DWORD LenModuleName; BYTE EncryptedModuleName[LenModuleName]; BYTE Zero; DWORD Size; BYTE EncryptedModuleBlock[Size]; }
(The data structure EncryptedModuleBlock will be discussed in section 2.2.2.)
Step 11: Rmnsoft.dll decrypts the received modules and transmits them to Modules.dll.
Step 12: Modules.dll performs an RC4 encryption on these modules with a random crypt key generated on the basis of the volume serial number of the local computer, loads them into the process it resides in and stores the encrypted modules in the same log file as used in steps 6 and 7.
Modules.dll is designed to manage all the downloaded modules on the local computer. For this purpose, it maintains two threads, as shown in Figure 12.
One thread periodically updates the modules on the local machine, downloading new ones from the C&C server with the participation of Rmnsoft.dll and deleting the abandoned modules that are no longer supported by the C&C server.
A log file is used for storage of all encrypted modules in the compromised computer. Each time Modules.dll adds a new module to this log file or deletes an out-of-date one from it, an event is set so that the other thread can be notified to do its job, loading new modules and unloading abandoned modules in memory. All loaded modules reside in the shell process into which Modules.dll was injected.
Besides the entry-point function, each module has four other exported functions:
ModuleCode
StartRoutine
CommandRoutine
StopRoutine
When a module is loaded, its entry-point function is called by Modules.dll using the PROCESS_ATTACH parameter. Then the ModuleCode function is called, which returns a double word which has only one bit set. The result of an OR operation on the returned values of the ModuleCode function of all modules is the important double word which is sent to the C&C server to tell it which modules exist on the local computer. The Virtual Address of the CommandRoutine function is obtained and will be used in future. After that, the StartRoutine function is called to perform the main work of the module. Figure 13 shows this procedure.
It is unlikely that a module can keep living in the system. Once a module is considered out of date, the StopRoutine function is called by Modules.dll to unload it.
Throughout the life of a module, the CommandRoutine function is periodically called by Modules.dll, and given a handle to an instance of the named pipe between Rmnsoft.dll and Modules.dll. By doing this, the module can communicate with the C&C server while Rmnsoft.dll serves as an interpreter again. A crypt key (‘840480_n_uk’) is also passed to the CommandRoutine function as a parameter. This crypt key will be used by both the module and the C&C server for data encryption.
In order to manage all the modules downloaded from the C&C server, Modules.dll maintains a log file on the local system. In the log file, it stores all modules in a well designed storage structure described as follows:
typedef struct ModuleBlockInLog { DWORD HashRawModule; DWORD Flag; DWORD SizeEncryptedModuleBlock; DWORD HashEncryptedModuleBlock; BYTE EncryptedModuleBlock[SizeEncryptedModuleBlock]; }
HashRawModule: Hash of a module’s executable file, frequently used as the sign of the module.
Flag: Set to 1 when the module is useful, or 2 when the module is abandoned.
SizeEncryptedModuleBlock: Size of the EncryptedModuleBlock structure associated with the module.
HashEncryptedModuleBlock: Hash of the EncryptedModuleBlock structure associated with the module.
EncryptedModuleBlock: EncryptedModuleBlock structure associated with the module.
Figure 15 shows the data in the ModuleBlockInLog of the FTP grabber module.
The data of EncryptedModuleBlock is RC4 encrypted by Modules.dll. The data structure of the decrypted EncryptedModuleBlock can be described as follows:
typedef struct ModuleBlock { DWORD MagicNumber; BYTE ModuleInfo[0x114]; DWORD TimeStamp; DWORD HashRawModule; BYTE ModulePE[PESize]; }
MagicNumber: A double word hard-coded in Modules.dll. Each ModuleBlock must begin with this. In this version of Ramnit, its value is 0xC581F364.
ModuleInfo: Module description.
TimeStamp: Time stamp of the module.
HashRawModule: Hash of an unencrypted module’s executable file.
ModulePE: Decrypted module file, which is a dynamic-link library.
PESize: Size of the module’s executable file.
Figure 16 shows the data in the ModuleBlock of the FTP grabber module.
Now, let’s see the data structure describing a running module:
typedef struct ModuleInfoInMem { DWORD HashRawModule; DWORD RetValOfModuleCode; DWORD ModuleBase; DWORD ModuleSize; DWORD ModuleEntry; DWORD PtrCommandRoutine; }
HashRawModule: Hash of module’s executable file.
RetValOfModuleCode: Value returned by the ModuleCode function of this module.
ModuleBase: Image base address of the module.
ModuleSize: Image size of the module.
ModuleEntry: Entry point of the module.
PtrCommandRoutine: Virtual address of the CommandRoutine function of the module.
The bug report function is implemented by a self-designed exception handling mechanism in Modules.dll. When an incurable exception (possible bug) is raised by any module, first, Modules.dll will seek out the trouble-making module by checking the address at which the exception occurred and the address scope of each module in process. Then the information about the exception will be recorded in a local file by Modules.dll and sent back to the C&C server by Rmnsoft.dll. Modules.dll will also change the flag of the buggy module from 1 (useful) to 2 (abandoned) so that it will no longer be loaded. Finally, Modules.dll will call the ExitProcess API to terminate the buggy module’s process.
Each module downloaded from the C&C server implements a separate feature of the bot. A brief introduction to the modules found so far is as follows:
FTP grabber: steals FTP credentials from FTP client software, system management software and website management software listed as follows:
NetDrive
FtpControl
32bit FTP
WinScp
LeapFtp
SoftFx FTP
Fling FTP
Classic FTP
FtpExplorer
Core ftp
Coffee cup ftp
FFFtp
TurboFtp
Smart Ftp
BulletproofFTP
FtpCommander
FileZilla
FlashXp
Cute FTP
WS FTP
Directory opus
Frigate 3
Far Manager
WebSitePublisher
Windows/Total commander
Using the stolen credentials, Ramnit can spread even more widely. Users downloading infected files from FTP servers will become new victims.
FTP daemon: sets up an FTP server named ‘RMNetwork FTP’ on the infected computer. With username ‘userftp’ and password ‘passftp’, hackers can easily sneak into an infected computer. The FTP server enumerates local files and shows them to the hackers, allowing them to:
create/remove a directory
create/rename/delete a file
upload/download a file
execute a file.
So hackers can modify the file system on a victim’s computer, stealing the files they are interested in, and creating and executing arbitrary files.
Cookie grabber: cookies of the various web browsers installed on the local computer are collected and stored in a single archive containing one folder for each web browser. Data from this archive will be uploaded to the C&C server by Rmnsoft.dll.
VNC: Virtual Network Computing, a module borrowed from Zeus. It establishes a fully functioning virtual connection between the infected computer and the C&C server, allowing the hackers to use all of the victim’s hardware and software to avoid the fraud detection systems of online banks, and allowing access to a smartcard inserted into the computer when the victim is carrying out online transactions.
Hooker: a module borrowed from Zeus for web page injection. It injects HTML and JavaScript into legitimate pages, prompting the victim to input credentials that are not actually required by the financial website. This allows hackers to bypass security measures such as two-factor authentication and certificate-signed transactions, giving them the ability to hijack online banking sessions.
The Ramnit installer drops a rootkit driver, idrtbjfj.sys, to %Temp% and creates a service named ‘Microsoft Windows Service’ for it. After creating a device named ‘\Device\631D2408D44C4f47AC647AB96987D4D5’, the driver recovers SSDT and SSDT Shadow from system files stored on disk (typical files are ntkrnlpa.exe and win32k.sys), which eliminates anti-virus software and other competitive malware.
The rootkit driver hooks several system services to make the registries associated with Ramnit invisible. The hooked system services are as follows:
ZwOpenKey
ZwOpenKeyEx
ZwOpenKeyTransacted
ZwOpenKeyTransactedEx
ZwCreateKey
ZwCreateKeyTransacted
When a hooked service is invoked to access a registry key that has been changed or created by Ramnit, STATUS_ACCESS_DENIED is returned to prevent the malware from being detected.
In the IoDeviceControl dispatch function, the rootkit driver kills all running anti-virus software whose name is on the death list sent by Rmnsoft.dll.
Since its first discovery in April 2010, Ramnit has become a powerful bot with extensible modular architecture, integrating sophisticated components and posing a considerable threat to the informational and financial security of individuals and institutions alike.
Given Ramnit’s fast spread via social engineering and its continuous module upgrades, it is likely that the battle against Ramnit has only just begun.
[1] Gallagher, S. Part virus, part botnet, spreading fast: Ramnit moves past Facebook passwords. http://arstechnica.com/business/2012/01/part-virus-part-botnet-spreading-fast-ramnit-moves-past-facebook-passwords/.
[2] Stevens, K.; Jackson, D. ZeuS Banking Trojan Report. http://www.secureworks.com/research/threats/zeus/.