一个数据加密恶意样本分析

一个数据加密恶意样本分析

该样本为帖子[讨论]抠下来的,过火绒-软件逆向-看雪论坛-安全社区|安全招聘|bbs.pediy.com看到的,当时闲的没事下载来看了看。样本运行后会对电脑文件加密,并且删除了卷影文件,防止通过磁盘工具恢复。

运行效果以及行为

弹出网页

document_image_rId6

隐藏了所有的文件夹,并创建了新的文件夹,实则为快捷方式,右键属性可看到重定向。

document_image_rId7

document_image_rId8

document_image_rId9

加密了文件,无法打开

document_image_rId10

document_image_rId11

对文件进行了截断操作,加密。

document_image_rId12

document_image_rId13

手动检查启动项后发现,在启动中添加了一个html,该html为样本弹出的html。

document_image_rId14

样本分析:

MD5 8f2050c9937f5f21b118c18dce3054fb
SHA1 0df872ae7916dd70e69b3a319ef57612e0ace739
SHA256 32e504c5664ee16d00149c1d8fe8184b872b07f9fad93ed3bce2bf11c1cc7c3a

document_image_rId15

突破口:通过VirusTotal和微云沙盒分析的得知可能的操作有分配内存,写内存。在给WriteProcessMemory下断调试观察参数时发现当前区域为动态分配的内存,

document_image_rId16

document_image_rId17

故其首先调用了VirtualAlloc,ida进行交叉引用可到

1
int __thiscall sub_2001DC0(int this, struct tagCREATESTRUCTA *a2)

该函数内部进行了shellcode初始化及解密后进行调用

document_image_rId18

在dbg里对VirtualAlloc下断后跟踪后可得到解密的内容

document_image_rId19

这里直接对shellcode进行dump。

因为是从EF0000开始dump,所以拖进ida分析的时候需要修复一下头部,从28开始。

document_image_rId20

document_image_rId21

ShellCode分析

函数进来后会进行初始化字符串。

document_image_rId22

然后调用InitProcAddr获取LoadLibrary和GetProcAddress地址。InitProcAddr的实现也是从Ldr中去遍历

document_image_rId23

紧接着分别获取以下这些函数地址

1
2
3
4
5
6
7
8
9
GetModuleFileNameW
CreateFileW
VirtualAlloc
GetFileSize
ReadFile
CloseHandle
SHGetSpecialFolderPathW
CopyFileW
SetFileAttributesW

document_image_rId24

随后获取了AppData和StartUp的路径,其中AppData进行了以下拼接

%AppData%\CSIDL_
%AppData%\CSIDL_X

然后检查当前运行的实例是否存在于其中一个目录中,如果不存在则自我复制后,将文件设置为隐藏状态(单独分析shellcode时路径不存在,猜测为主程序创建目录

document_image_rId25

中间存在一些对文件读写操作,经过分析后发现是为了给新的shellcode申请空间。

document_image_rId26

老规矩,直接弄出他的shellcode。

document_image_rId27

ShellCode1分析

document_image_rId28

以0,1和0,0不同参数执行了两次call

函数进来会进行字符串初始化,用于后面调用api

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
strcpy(str_kernel32, "kernel32.dll");
strcpy(str_ntdll, "ntdll.dll");
strcpy(str_shell32, "shell32.dll");
strcpy(str_advapi32, "advapi32.dll");
strcpy(str_psapi, "psapi.dll");
strcpy(str_GetProcAddress, "GetProcAddress");
strcpy(str_GetModuleHandleA, "GetModuleHandleA");
strcpy(str_GetModuleFileNameA, "GetModuleFileNameA");
strcpy(str_GetModuleFileNameW, "GetModuleFileNameW");
strcpy(str_CreateProcessA, "CreateProcessA");
strcpy(str_CreateProcessW, "CreateProcessW");
strcpy(str_CreateToolhelp32Snapshot, "CreateToolhelp32Snapshot");
strcpy(str_Process32First, "Process32First");
strcpy(str_Process32Next, "Process32Next");
strcpy(str_Module32First, "Module32First");
strcpy(str_Module32Next, "Module32Next");
strcpy(str_CloseHandle, "CloseHandle");
strcpy(str_GetCurrentProcess, "GetCurrentProcess");
strcpy(str_GlobalAlloc, "GlobalAlloc");
strcpy(str_OpenProcessToken, "OpenProcessToken");
strcpy(str_GetTokenInformation, "GetTokenInformation");
strcpy(str_AllocateAndInitializeSid, "AllocateAndInitializeSid");
strcpy(str_EqualSid, "EqualSid");
strcpy(str_LookupAccountSidA, "LookupAccountSidA");
strcpy(str_OpenMutexA, "OpenMutexA");
strcpy(str_CreateMutexA, "CreateMutexA");
strcpy(str_CreateFileA, "CreateFileA");
strcpy(str_CreateFileW, "CreateFileW");
strcpy(str_GetFileSize, "GetFileSize");
strcpy(str_ReadFile, "ReadFile");
strcpy(str_GetSystemDirectoryA, "GetSystemDirectoryA");
strcpy(str_GetSystemDirectoryW, "GetSystemDirectoryW");
strcpy(str_SetFileAttributesW, "SetFileAttributesW");
strcpy(str_MoveFileExW, "MoveFileExW");
strcpy(str_SHGetSpecialFolderPathA, "SHGetSpecialFolderPathA");
strcpy(str_SHGetSpecialFolderPathW, "SHGetSpecialFolderPathW");
strcpy(str_RegOpenKeyExA, "RegOpenKeyExA");
strcpy(str_RegOpenKeyExW, "RegOpenKeyExW");
strcpy(str_RegSetValueExA, "RegSetValueExA");
strcpy(str_RegSetValueExW, "RegSetValueExW");
strcpy(str_RegQueryValueExA, "RegQueryValueExA");
strcpy(str_RegQueryValueExW, "RegQueryValueExW");
strcpy(str_RegCloseKey, "RegCloseKey");
strcpy(str_CreateDirectoryW, "CreateDirectoryW");
strcpy(str_ExitProcess, "ExitProcess");
strcpy(str_Sleep, "Sleep");
strcpy(str_GetFileTime, "GetFileTime");
strcpy(str_SetFileTime, "SetFileTime");
strcpy(str_CopyFileW, "CopyFileW");
strcpy(str_DeleteFileW, "DeleteFileW");
strcpy(str_VirtualAlloc, "VirtualAlloc");
strcpy(str_GetTickCount, "GetTickCount");
strcpy(str_IsWow64Process, "IsWow64Process");
strcpy(str_OpenProcess, "OpenProcess");
strcpy(str_DuplicateHandle, "DuplicateHandle");
strcpy(str_NtUnmapViewOfSection, "NtUnmapViewOfSection");
strcpy(str_VirtualAllocEx, "VirtualAllocEx");
strcpy(str_WriteProcessMemory, "WriteProcessMemory");
strcpy(str_GetThreadContext, "GetThreadContext");
strcpy(str_SetThreadContext, "SetThreadContext");
strcpy(str_ResumeThread, "ResumeThread");
strcpy(str_SuspendThread, "SuspendThread");
strcpy(str_TerminateProcess, "TerminateProcess");
strcpy(str_NtReadVirtualMemory, "NtReadVirtualMemory");
strcpy(str_GetCommandLineW, "GetCommandLineW");
strcpy(str_GetProcessMemoryInfo, "GetProcessMemoryInfo");
strcpy(str_WriteFile, "WriteFile");

初始化完毕后,根据参数值进行分支操作,由于第一个参数为1,这里从1开始。

document_image_rId29

首先进行了一些看不懂的文件操作。

document_image_rId30

然后开始解密新的shellcode

document_image_rId31

然后开始进行一下虚拟机检测之类的东西

document_image_rId32

document_image_rId33

document_image_rId34

然后是运行一个脚本,但是这个脚本在整个分析过程中没有碰到。

document_image_rId35

该shellcode的内容比较多,最后会执行到比较核心的内容。

document_image_rId36

首先是判断电脑是否存在浏览器。

document_image_rId37

如果IE存在,则启动IE浏览器,以IE浏览器为目标程序,解密一个资源文件并内存加载到IE中。反之自启动一份作为目标进程。

document_image_rId38

document_image_rId39

document_image_rId40

动态调试直接捕获到最终加载的**恶意样本(7396C43A6E8CCA2F811939EF1BE71B73)**。

ShellCode2

MD5 7396c43a6e8cca2f811939ef1be71b73
SHA1 a7dace43bcc5e7108a9827dd3a7e03c30acdeeba
SHA256 5548fec3bae254f7882d9b681080261ba588bc05cb63a81a28107ff49f71c513
File size 52.00 KB (53248 bytes)}

document_image_rId41

该样本首先创建一个互斥名作为单例启动。

document_image_rId42

随后删除了卷影文件,防止通过该文件进行文件恢复。

document_image_rId43

然后开始加密文件。

document_image_rId44

加密过程主要是遍历电脑磁盘和移动硬盘文件。

document_image_rId45

然后查看文件是否为需要加密的文件。

document_image_rId46

以下为该样本所要加密的文件后缀。

document_image_rId47

加密后的文件在文件的头部会存在一个CRC32的值,该值由原文件前128个字节计算来的。样本会判断前面这个CRC32的值来判断是否需要加密。

document_image_rId48

document_image_rId49

之后开始进行隐藏文件和创建快捷方式

document_image_rId50

隐藏文件。

document_image_rId51

创建快捷方式,并重定向为临时目录的样本文件。

document_image_rId52

然后进行疑似横向感染操作。

document_image_rId53

然后开始解密HTML数据,就是运行样本后弹出的那个网页。

document_image_rId54

document_image_rId55

该样本在运行之初会判断是否为管理员运行,如果不是管理员,会以管理员模式运行,并关闭当前进程。

document_image_rId56

该样本中还存在疑似公钥的东西,估计是可以用来解密,但是本人对加密这一块比较弱,就没去详细分析。

document_image_rId57

至于提供样本的那个老哥问怎么解决,我这边建议闲鱼5元包邮送出远方。

document_image_rId58