diff --git a/RE102/images/Section6_40bytes.png b/RE102/images/Section6_40bytes.png new file mode 100644 index 0000000..5096bd0 Binary files /dev/null and b/RE102/images/Section6_40bytes.png differ diff --git a/RE102/images/Section6_RC4Decrypt.png b/RE102/images/Section6_RC4Decrypt.png new file mode 100644 index 0000000..fec6f1d Binary files /dev/null and b/RE102/images/Section6_RC4Decrypt.png differ diff --git a/RE102/images/Section6_VirtualAlloc.png b/RE102/images/Section6_VirtualAlloc.png new file mode 100644 index 0000000..5ec01ee Binary files /dev/null and b/RE102/images/Section6_VirtualAlloc.png differ diff --git a/RE102/images/Section6_addingMZ.png b/RE102/images/Section6_addingMZ.png new file mode 100644 index 0000000..8d4ecbd Binary files /dev/null and b/RE102/images/Section6_addingMZ.png differ diff --git a/RE102/images/Section6_compress.png b/RE102/images/Section6_compress.png new file mode 100644 index 0000000..7118f59 Binary files /dev/null and b/RE102/images/Section6_compress.png differ diff --git a/RE102/images/Section6_compressroutine.gif b/RE102/images/Section6_compressroutine.gif new file mode 100644 index 0000000..5109535 Binary files /dev/null and b/RE102/images/Section6_compressroutine.gif differ diff --git a/RE102/images/Section6_createprocess.png b/RE102/images/Section6_createprocess.png new file mode 100644 index 0000000..d46d6e6 Binary files /dev/null and b/RE102/images/Section6_createprocess.png differ diff --git a/RE102/images/Section6_decrypted.png b/RE102/images/Section6_decrypted.png new file mode 100644 index 0000000..376e5b2 Binary files /dev/null and b/RE102/images/Section6_decrypted.png differ diff --git a/RE102/images/Section6_offsets.png b/RE102/images/Section6_offsets.png new file mode 100644 index 0000000..a1b4b49 Binary files /dev/null and b/RE102/images/Section6_offsets.png differ diff --git a/RE102/images/Section6_output.png b/RE102/images/Section6_output.png new file mode 100644 index 0000000..7917cb7 Binary files /dev/null and b/RE102/images/Section6_output.png differ diff --git a/RE102/images/Section6_paths.png b/RE102/images/Section6_paths.png new file mode 100644 index 0000000..7bc1c66 Binary files /dev/null and b/RE102/images/Section6_paths.png differ diff --git a/RE102/images/Section6_script.png b/RE102/images/Section6_script.png new file mode 100644 index 0000000..04a93cf Binary files /dev/null and b/RE102/images/Section6_script.png differ diff --git a/RE102/re102_section5.1.md b/RE102/re102_section5.1.md index 8c27c31..6afe969 100644 --- a/RE102/re102_section5.1.md +++ b/RE102/re102_section5.1.md @@ -7,13 +7,16 @@ title: Setup # Section 5.1: Debugging # -Debugging should be your last resort because it can be time consuming. The purpose of doing static analysis is to know where you are. Be sure to take a VM snapshot before you begin debugging. This snapshot will come in handy when you accidently run the malware sample. Frequent snapshots save your debugging work so you won’t lose your place. +Debugging should be your last resort, as it can be time consuming. However, for the sake of teaching, I will go over it anyway. Be sure to take a snapshot of your VM before you begin debugging. This snapshot will come in handy when you accidently run the malware sample. + +**Tip:** Take frequent snapshots to save your debugging work, this way you won’t lose your place. ## Create the Breakpoints ## Open decrypted_shellcode.exe in x32dbg. -At this point you should have recorded the following functions and locations: +At this point you should have recorded the following functions along with their corresponding locations: + 1. `sub_402B1C` @ `00401D9B` - The function the loads the libraries 2. `sub_4014AA` @ `0040560B` - The function that checks for sample, sandbox, and virus 3. `jz loc_405272` @ `004019E4` - The jump to modify the EFlags if necessary @@ -29,17 +32,17 @@ Now press **F9** to run the program to breakpoints until you reach `004019E4`. ![alt text](https://securedorg.github.io/RE102/images/Section5.1_4019E4.png "Section5.1_4019E4") -Scroll down to check out offset `00405272`. Looks like the [esp+1C] is using Path Windows APIs to check the strings against sample, sandbox, and virus. Since your exe name is and path does not contain these words, it will not jump. So you won’t need to force the jump. Keep pressing F8 (step over) until you reach offset `00405277`. +Scroll down to check out offset `00405272`. Looks like the `[esp+1C]` is using Path Windows APIs to check the strings against sample, sandbox, and virus. Since your exe name is and path does not contain these words, it will not take the jump. Thus, no need to change the flags or patch the instruction. Keep pressing **F8** (to step over the instruction) until you reach the offset `00405277`. ![alt text](https://securedorg.github.io/RE102/images/Section5.1_405272.png "Section5.1_405272") -Congrats! This was the first evasion technique you worked through. Now that you know what these API calls are, you should be filling in your IDA comments with these APIs. +**Congrats!** You bypassed the first evasion technique deployed by this malware . Now that you know what these API calls are, you should be renaming the subroutines in your IDA with appropriate labels. --- ## Adding Resources ## -Step **F7** the program until you reach the next function `sub_40487D`. Be sure to record the arguments pushed onto the stack. Step Into **F7** function `sub_40487D`. Next step until you reach `00401632` and look down to `00401645`. The calls to GetModuleHandle and FindResource means it’s about to access a resource in the exe. +Step **F7** the program until you reach the next function `sub_40487D`. Be sure to record the arguments pushed onto the stack. Step Into **F7** function `sub_40487D`. Next step until you reach `00401632` and look down to `00401645`. The calls to GetModuleHandle and FindResource indicate that the malware is about to access a resource. This is typically how you get a resource from an exe: @@ -51,7 +54,7 @@ DWORD dwSize = SizeofResource(hModule, hResource); LPVOID lpAddress = LockResource(hMemory); ``` -When you turned the shellcode into an exe it did not include any resources. Remember that the original exe is where this shellcode gets executed. So you will need to get the resource from the original exe and import them into shellcode exe. The argument passed to the function `sub_40487D` was 0xE38 which is 1000 in decimal. If you keep stepping through function `sub_40487D` you will see the routine above and notice that the argument to find the resource is 1000. +When you turned the shellcode into an exe it did not include any resources. Remember that the original exe is where this shellcode gets executed. So, you will need to get the resource from the original exe and import them into shellcode exe. The argument passed to the function `sub_40487D` was 0xE38 which is 1000 in decimal. If you keep stepping through function `sub_40487D` you will see the routine above, and notice that the argument to find the resource is 1000. ``` HRSRC WINAPI FindResource( @@ -75,7 +78,7 @@ Once you exported the resource 1000, open the decrypted_shellcode.exe with CFF e ## Saving Junk and Chunks in Memory ## -Keep stepping until you reach `0040416F` where you will see that the resource is being placed into a new memory allocation. Remember that VirtualAlloc is typically followed by a Move function. After the VirtualAlloc function is returned make sure you note the address of the newly allocated memory. This function will return that memory address value in the `eax` register. +Keep stepping until you reach `0040416F` where you will see that the resource is being placed into a new memory allocation. Remember that VirtualAlloc is typically followed by a ‘mov instruction’. After the VirtualAlloc function is returned make sure you note the address of the newly allocated memory. As before, this function will put the address of the allocated memory in the `eax` register (the returned value). ![alt text](https://securedorg.github.io/RE102/images/Section5.1_savingresource.png "Section5.1_savingresource") @@ -83,7 +86,7 @@ Once you are done stepping through function `sub_40487D` step until you reach `l ![alt text](https://securedorg.github.io/RE102/images/Section5.1_allocate318.png "Section5.1_allocate318") -The size 0x318 is a common theme for the next couple of function calls. This is where you will see another routine of VirtualAlloc and Move. It will store the first 0x318 bytes into the newly allocated memory. +The size 0x318 is a common theme for the next couple of function calls. This is where you will see another combo of VirtualAlloc and `mov`. It will store the first 0x318 bytes into the newly allocated memory. ![alt text](https://securedorg.github.io/RE102/images/Section5.1_Virtualloc318.png "Section5.1_Virtualloc318") @@ -114,9 +117,10 @@ In IDA, glance through function `sub_403BC2`. There are 3 hints that give away w * Multiple loops * The use of XOR -If you remember from the previous Section 4, multiple loops and the use XOR is indicative of being some kind of crypto algorithm. There is a theme of crypto here but there just a slight difference. The use of anding a value with `800000FFh` is also a form of modulo for `X mod 256`. Earlier you saw that the modified RC4 algorithm was using a delphi mod function instead. +If you remember from the previous Section 4, multiple loops and the use XOR is indicative of being some kind of crypto algorithm. There is a theme of crypto here, but there is just a slight difference. The use of anding a value with `800000FFh` is also a form of modulo for `X mod 256`. Earlier we saw that the modified RC4 algorithm was using a delphi mod function instead. + +As you might have guessed, it looks like the malware is using RC4 again, but you might want to step through the algorithm to confirm if it’s the correct RC4 or the modified RC4 like from Section 4. Once you have, you will notice that the first 32 bytes (0x20) decrypted the rest of the CopiedData 760 bytes (0x2F8). Be sure to save the address of this memory in your notes, and rename the functions in IDA as you will need to go back to them for Section 6. -Looks like the is using RC4 again, but you might want to step through the algorithm to confirm if it’s true RC4 or modified RC4 like from Section 4. Once you have you will notice that the first 32 bytes (0x20) decrypted the rest of the CopiedData 760 bytes (0x2F8). Be sure to save the address of this memory in your notes and renaming functions in IDA because you will need it for Section 6. Step through until you reach `loc_401CCA` and continue to the next page. diff --git a/RE102/re102_section5.2.md b/RE102/re102_section5.2.md index fc24831..a821c78 100644 --- a/RE102/re102_section5.2.md +++ b/RE102/re102_section5.2.md @@ -9,7 +9,7 @@ title: Setup ## Anti-Automation ## -Before you continue to `loc_401CCA`, there were some Anti-Automation behaviors that were not discussed from Section 3.1. There calls to GetForegroundWindow, Sleep, then GetForegroundWindow is an anti-automation technique to ensure that there is an actual user changing the state of the foreground window. Typically in automated sandbox testing there is no user interaction unless they accounted to build that into their VM. +Before you continue to `loc_401CCA`, there were some Anti-Automation behaviors that were not discussed from Section 3.1. The calls to GetForegroundWindow, Sleep, and GetForegroundWindow indicate that the malware is deploying various anti-automation techniques to ensure that there is an actual user changing the state of the foreground window. Typically in automated sandbox testing there is no user interaction unless they accounted to build that into their VM. ![alt text](https://securedorg.github.io/RE102/images/Section3.1_record_interesting.png "Section3.1_record_interesting") @@ -17,7 +17,7 @@ Before you continue to `loc_401CCA`, there were some Anti-Automation behaviors t ## Anti-Debugging ## -If you remember from Section 3.1 and 3.2, there were many calls to OutputDebugString. Instead of directly calling for IsDebuggerPresent, calling to OutputDebugString and checking the success or failure is another technique to check if there is a debugger running. It’s a simple tactic to avoid reverse engineering. +If you remember from Section 3.1 and 3.2, there were many calls to OutputDebugString. Instead of directly calling for IsDebuggerPresent, calling to OutputDebugString and checking the success or failure is another technique to check if there is a debugger running. It’s a simple tactic to make reverse engineering and debugging the malware harder. --- @@ -25,7 +25,7 @@ If you remember from Section 3.1 and 3.2, there were many calls to OutputDebugSt There are many resources for a developer to identify if the process is running in a Virtual Machine. Paranoid Fish or pafish is one of the more well-known automated VM identification scripts available. You can view the code here: [https://github.com/a0rtega/pafish](https://github.com/a0rtega/pafish). -Every VM distro has their own filesystem and registry indicators. Products such as VMware and Vbox often have software installed to help with host to guest sharing. Hardware simulation will contain strings and naming related to the VM product. Some malware will check if it is running inside a VM and change its behavior. +Every VM distro has their own filesystem and registry indicators. Products such as VMware and VirtualBox often have software installed to help with host to guest sharing. Hardware simulation will contain strings and naming related to the VM product. Some malware will change their behavior if they find out they are running inside a VM. In IDA, start back at `loc_401CCA` where you will be able to identify some VM Evasion techniques. @@ -33,7 +33,7 @@ In IDA, start back at `loc_401CCA` where you will be able to identify some VM Ev ### Checking Hardware Device ### -Earlier in this section, there was an anti-analysis technique of pushing strings to the stack. In function `sub_4029E7` until you are in function `sub_402274`, you can see it’s pushing **H** and **A** in the the screenshot below. +Earlier in this section, there was an anti-analysis technique of pushing strings to the stack. In function `sub_4029E7` until you are in function `sub_402274`, you can see that it is pushing **H** and **A** in the the screenshot below. *Click to Enlarge* [![alt text](https://securedorg.github.io/RE102/images/Section5.2_hardware.gif "Section5.2_hardware")](https://securedorg.github.io/RE102/images/Section5.2_hardware.gif) @@ -44,7 +44,7 @@ Go ahead and go through all the strings that are being pushed to the stack. It s HARDWARE\DEVICEMAP\Scsi\Scsi Port 0\Scsi Bus 0\Target Id 0\ Logical Unit Id 0\Identifier ``` -At the very end of the function it jumps to `loc_404777` where it calls `sub_403F73`. This is where the shellcode pushes strings **vmware, qemu,** and **vbox**. In the debugger, set a breakpoint and run/step to 00406AB6 within function `sub_4037FD`. This is where the call to RegKeyOpenEx happens. +At the very end of the function it jumps to `loc_404777` where it calls `sub_403F73`. This is where the shellcode pushes strings **vmware, qemu,** and **vbox**. The malware is checking for registry artifacts to see if it’s running inside a VM. In the debugger, set a breakpoint and run/step into 00406AB6 within function `sub_4037FD`. This is where the call to RegOpenKeyEx happens. ![alt text](https://securedorg.github.io/RE102/images/Section5.2_checkregistry.png "Section5.2_checkregistry") @@ -52,11 +52,11 @@ If you follow the stack argument DWORD in the dump you can see the full strings. ![alt text](https://securedorg.github.io/RE102/images/Section5.2_hardwarestrings.png "Section5.2_hardwarestrings") -Open regedit.exe in Windows and verify that this registry key exists under HKEY_LOCAL_MACHINE. If this key exists RegKeyOpenEx will return 0, if not 2. In the debugger, Step over **F8** this function call. Fortunately this VM was built with an IDE instead of scsi hardware. You can verify this by looking at Virtualbox’s storage settings. +Open regedit.exe in Windows and verify that this registry key exists under HKEY_LOCAL_MACHINE. If this key exists RegOpenKeyEx will return 0, if not 2. In the debugger, Step over **F8** this function call. Fortunately this VM was built with an IDE instead of scsi hardware. You can verify this by looking at Virtualbox’s storage settings. ![alt text](https://securedorg.github.io/RE102/images/Section5.2_vboxstoragesettings.png "Section5.2_vboxstoragesettings") -If the VM you are working in does happen to have this registry key, you can always bypass the check. Put a breakpoint at 00404977 so that you won’t miss this next jump. When you are debugging you can modify the **ZF flag** so that `jz loc_404D01` will fail and continue onto the next check. +If the VM you are working in does happen to have this registry key, you can always bypass the check. You can either get rid of the artifacts themselves or patch the binary. Put a breakpoint at 00404977 so that you won’t miss this next jump. When you are debugging you can modify the **ZF flag** so that `jz loc_404D01` will fail and continue onto the next check. ![alt text](https://securedorg.github.io/RE102/images/Section5.2_checkbypass.png "Section5.2_checkbypass") @@ -89,7 +89,7 @@ There are 2 places where you can choose to modify the jump: ![alt text](https://securedorg.github.io/RE102/images/Section5.2_biosjump2.png "Section5.2_biosjump2") -If you modified either of the jump calls above while debugging you should have reached `loc_4010FE` and `sub_4029F1`. Below how you modify the second jump. +If you modified either of the jump calls above while debugging you should have reached `loc_4010FE` and `sub_4029F1`. Below, you can see how to modify the second jump. *Click to Enlarge* [![alt text](https://securedorg.github.io/RE102/images/Section5.2_ModifyFlags.gif "Section5.2_ModifyFlags")](https://securedorg.github.io/RE102/images/Section5.2_ModifyFlags.gif) @@ -114,11 +114,11 @@ Keep stepping through function `sub_4029F1` until you get back to `0040110B` whe ### Check for VM DLLs ### -Keep stepping into `sub_401117` until you reach some interesting immediate values. Go ahead and convert the immediate values at `00405884` into strings. +Step into`sub_401117` and keep going through instructions until you reach some interesting immediate values. Go ahead and convert the immediate values at `00405884` into strings. ![alt text](https://securedorg.github.io/RE102/images/Section5.2_sandboxiedll.png "Section5.2_sandboxiedll") -This function is checking for sbiedll.dll which is a DLL used by the Sandboxie sandbox. If you are working with Vbox, this DLL will not exist so you won’t need to bypass a jump. Keep working your way through this function because it’s not done with all the checks. +This function is checking for sbiedll.dll which is a DLL used by the Sandboxie sandbox. If you are working with Vbox, this DLL will not exist so you won’t need to bypass the jump. Keep working your way through this function because it’s not done with all the checks. --- @@ -162,6 +162,6 @@ After DeviceIOControl is called do not take the jump after at `00405778` or `loc ![alt text](https://securedorg.github.io/RE102/images/Section5.2_deviceIOcontroljump.png "Section5.2_deviceIOcontroljump") -This jump should land you at `loc_402192` or `00402192`. **Congratulations!** You have made it past several VM evasion techniques. The next Section 6 will go over identifying a packer. +This jump should land you at `loc_402192` or `00402192`. **Congratulations!** You have made it past several VM evasion techniques. The next section will go over identifying a packer. [Section 5.1 <- Back](https://securedorg.github.io/RE102/section5.1) | [Next -> Section 6](https://securedorg.github.io/RE102/section6) \ No newline at end of file diff --git a/RE102/re102_section5.md b/RE102/re102_section5.md index 183047b..bf64ca9 100644 --- a/RE102/re102_section5.md +++ b/RE102/re102_section5.md @@ -9,25 +9,25 @@ title: Setup ![alt text](https://securedorg.github.io/RE102/images/Section5_intro.gif "intro") -This section will focus on identifying various Evasion Techniques as well as working around them during the debugging phase. Now that you will be working with an new executable, you will need to create another road map. +This section will focus on identifying various evasion techniques as well as working around them during the debugging phase. Now that you will be working with an new executable, you will need to create another road map. ## Control Flow Obfuscation ## -You will notice that the shellcode is broken up into extraneous and unnecessary jumps. This is meant to throw off malware analysis with these anti-disassembly techniques. Malware that has this kind of useless instructions is usually processed with some kind of obfuscation kit. Malware authors rarely write new shellcode and will sell, share, or reuse this code. +You will notice that the shellcode is broken up into extraneous and unnecessary jumps. This is meant to throw off malware analysts. Malware that has this kind of useless instructions is usually processed with some kind of obfuscation kit (e.g., cryptors). Malware authors rarely write new shellcode and will sell, share, or reuse this code. -Going forward, you should be viewing the disassembly in graph mode. It will be easier to read the control flow. Below is an example of the Flow-chart mode of the useless jumps. +Going forward, you should be viewing the disassembly in graph mode, as it makes it easier to understand the control flow. Below is an example of the flow-chart mode of these jumps. ![alt text](https://securedorg.github.io/RE102/images/Section5_ControlFlowObfuscation.png "Section5_ControlFlowObfuscation") ## Where to Start? ## -There are no strings for us to investigate and there are no functions parsed by IDA. Tip: The professional version of IDA does a great job at parsing functions. So you need to start exploring each function one by one finding interesting code to look at. If this is too daunting, then manual debugging is your next option. The goal is to make a road map of shellcode by working backwards. +There are no strings for us to investigate and there are no functions parsed by IDA.. So, you need to start exploring each function one by one finding an interesting piece of code to analyze. This comes with experience. If this seems too daunting, then manual debugging is your next option. The goal is to make a road map of shellcode by working backwards. ## String Obfuscation ## The first function call sub_404C1E doesn’t look like something interesting, so move on to the next function call to `sub_402B1C`. This function is a jump-wrapper for the function `sub_4059A3`. -Notice anything strange about the immediate values being placed onto the stack? These are actually strings. By breaking up the string and pushing it onto the stack is a common way to hide strings from malware analysts. Go ahead right-click these numbers and convert it to a string (R). +Notice anything strange about the immediate values being placed onto the stack? These are actually strings. Breaking up strings and pushing them onto the stack is a common of hiding strings from malware analysts. Go ahead right-click these numbers and convert it to a string (R). ![alt text](https://securedorg.github.io/RE102/images/Section5_FunkyStrings.png "Section5_FunkyStrings") @@ -47,7 +47,7 @@ With shellcode or position independent code (PIC), the code needs to load resour ## Access to the Process Environment Block (PEB) ## After the advapi32 string gets loaded onto the stack, enter the function `sub_405421`. -This function is accessing the FS segment register `fs:[0x30]` which is the pointing to the Process Environment Block. This is a common shellcode tactic to get handles to loaded windows libraries a.k.a. Modules, specifically the base of kernel32 from the PEB. +This function is accessing the FS segment register at offset 30. This register is commonly used by OS kernels to access thread-specific memory. This specific offset (i.e., `fs:[0x30]`) points to the Process Environment Block. This is a common shellcode tactic to get handles to loaded windows libraries a.k.a. Modules, specifically the base address of kernel32 from the PEB. ``` mov eax, 30h @@ -60,7 +60,7 @@ mov eax, [eax+18h] ; get Kernel32 ![alt text](https://securedorg.github.io/RE102/images/Section5_PEB.gif "Section5_PEB") -The second instruction `mov eax, [eax+0Ch]` gets the address of the PEB Loader Data from the [PEB](https://msdn.microsoft.com/en-us/library/windows/desktop/aa813706%28v=vs.85%29.aspx) struct. The [PEB_LDR_DATA](https://msdn.microsoft.com/en-us/library/windows/desktop/aa813708(v=vs.85).aspx) contains the struct for the InMemoryOrderModuleList which is where it gets the pointer for Kernel32. Note: there are many great Shellcode resources available that explain this technique. I just want you to recognize the instruction `fs:[0x30]`. +The second instruction `mov eax, [eax+0Ch]` gets the address of the PEB Loader Data from the [PEB](https://msdn.microsoft.com/en-us/library/windows/desktop/aa813706%28v=vs.85%29.aspx) struct. The [PEB_LDR_DATA](https://msdn.microsoft.com/en-us/library/windows/desktop/aa813708(v=vs.85).aspx) contains the struct for the InMemoryOrderModuleList which is where it gets the pointer for Kernel32. **Note:** there are many great shellcode resources available that explain this technique. I just want you to recognize the instruction `fs:[0x30]`. ``` struct PEB_LDR_DATA { diff --git a/RE102/re102_section6.md b/RE102/re102_section6.md new file mode 100644 index 0000000..680cf8e --- /dev/null +++ b/RE102/re102_section6.md @@ -0,0 +1,116 @@ +--- +layout: default +permalink: /RE102/section6/ +title: Setup +--- +[Go Back to Reverse Engineering Malware 102](https://securedorg.github.io/RE102/) + +# Section 6: Identifying Packing # + +This section will focus on identifying a custom packing routine. Believe it or not this whole shellcode executable is a packer itself. The next several functions will reveal its algorithm, and you will be able to create a simple unpacking script. + +## The Bat and Vbs Scripts ## + +Before you actually get to the unpacking routine, navigate your way to `loc_4050A0`. There is a function call you might miss. When you are debugging the jump instruction `jz loc_40196B` at 004050A0 will jump over `sub_405463`. If you want to debug this function just modify the jump here. + +![alt text](https://securedorg.github.io/RE102/images/Section6_script.png "Section6_script") + +Here is a summary of `sub_405463`: + +1. This function allocates memory to store the current filename and %APPDATA% location to determine if the executable already exists there. The giveaways are: +* VirtualAlloc +* SHGetFolderPath +* GetModuleHandleA +* GetModuleFileNameW +* PathRemoveFileSpec +2. It will then try to create a process from the file stored in %APPDATA%, by calling CreateProcess +3. Create a .bat file in %APPDATA% where the contents are pushed onto the stack. This file contains the following: +``` +start /d "C:\Users\victim\AppData\" +``` + +4. Where it will write the hidden .vbs script in the location: +``` +C:\\Users\\victim\\AppData\\Roaming\\Microsoft\\Windows\\Start Menu\\Programs\\Startup\\.vbs +``` + +This vbs script contains the following: +``` +Set WshShell = CreateObject("WScript.Shell") +WshShell.Run chr(34) & "C:\\Users\\victim\\AppData\\Roaming\\.bat" & Chr(34), 0 +Set WshShell = Nothing +``` +To see the bat and vbs script get created, force these jump locations to not take the jump branch! This can be done like before, by simply changing the zero flag. +* 00403089 +* 00404652 +* 004048A7 +* 004048B0 +* 00403349 +* 0040507A + +## The Unpacker ## + +In IDA, after the call to `sub_405463`, all paths lead to `loc_4057BC`. In the debugger, set a breakpoint at `004057BC` and run to this location. + +![alt text](https://securedorg.github.io/RE102/images/Section6_paths.png "Section6_paths") + +The next routine should look familiar to you. There are multiple values being pushed to the stack before the call to `sub_40651A`. + +![alt text](https://securedorg.github.io/RE102/images/Section6_compress.png "Section6_compress") + +1. The first pushed value is `[esi+60]` which is the location where the first 0x318 bytes of Resource 1000 was decrypted. +2. The second value is 0x1. +3. The third pushed value is one dword at the relative offset 0x64 of that 0x318 bytes. +4. The fourth pushed value is one dword at the relative offset 0xA8 of that 0x318 bytes. +5. The fifth pushed value is the original resource stored in memory. + +![alt text](https://securedorg.github.io/RE102/images/Section6_offsets.png "Section6_offsets") + +The values for 0x0A (10 decimal) and 0x21 (33 decimal) will become important within function `sub_40651A`. Step into **F7** function `sub_40651A`. The first part of the function allocates some memory where it will store the output of the next routine. In the debugger, step over **F8** the VirtualAlloc call and dump the memory location that it returns so that you can monitor the changes. + +![alt text](https://securedorg.github.io/RE102/images/Section6_VirtualAlloc.png "Section6_VirtualAlloc") + +In the debugger, step **F7** through this loop and keep track how values 10 and 33 are used against the resource bytes. + +![alt text](https://securedorg.github.io/RE102/images/Section6_looping.png "Section6_looping") + +The 2 dumps below shows what this routine is actually doing: compression. After the initial byte 0x1, it is removing every 10 bytes, displayed as 0xFF below. The routine will then store the next 33 bytes. + +![alt text](https://securedorg.github.io/RE102/images/Section6_compressroutine.gif "Section6_compressroutine") + +Below is an example of what the first loop through the data looks like. All 10 instances of 0xFF were removed. + +![alt text](https://securedorg.github.io/RE102/images/Section6_output.png "Section6_output") + +After you run through the whole function it will return this new compressed code for the next function call. Be sure to dump this section of memory as a .bin file and name it *compressed.bin*. You should have correctly renamed the RC4 function from earlier in IDA. After function `sub_40651A`, there should be a call to the RC4 decrypt function at `00407165`. + +![alt text](https://securedorg.github.io/RE102/images/Section6_RC4Decrypt.png "Section6_RC4Decrypt") + +If you remember from section 5.1, the key size was 0x20. For this call to RC4Decrypt, the key size is 0x40h at offset 0x2D0 of the decrypted 0x318 bytes. Below is the RC4 key: + +![alt text](https://securedorg.github.io/RE102/images/Section6_40bytes.png "Section6_40bytes") + +``` +6F 49 04 00 35 06 03 00 63 49 03 00 89 10 04 00 A2 6C 03 00 F4 D1 02 00 59 88 03 00 25 D4 03 00 74 EF 03 00 0B 6C 03 00 A8 95 03 00 E0 EC 02 00 75 52 04 00 2B FB 02 00 22 C4 03 00 B5 FF 02 00 +``` + +Export this key as a binary file and use the decrypt_shellcode.py script against the compressed.bin and the key.bin. + +``` +c:\Python27\python.exe \decrypt_shellcode.py 0x40key.bin \compressed.bin +``` +In the debugger, you can step over **F8** the RC4Decrypt function and watch the compressed code change to the output below: + +![alt text](https://securedorg.github.io/RE102/images/Section6_decrypted.png "Section6_decrypted") + +Notice that the output looks like the header of a PE executable. The only difference is that it is missing the MZ header. If you scroll down after the RC4Decrypt function you will see the immediate value 0x544D which is MZ. This is where it will add the MZ header. + +![alt text](https://securedorg.github.io/RE102/images/Section6_addingMZ.png "Section6_addingMZ") + +Step through the rest until you reach a call to `sub_4031A9` at `00404C81`. You will find that it uses CreateProcess to spawn a new process of the newly created PE without dropping it to disk. After you step over the call to CreateProcess, you can open Process Explorer to view the newly created child process. + +![alt text](https://securedorg.github.io/RE102/images/Section6_createprocess.png "Section6_createprocess") + +Now that you know the algorithm, you can create a unpacking script for the resource. The next page will go over the script. + +[Section 5.2 <- Back](https://securedorg.github.io/RE102/section5.1) | [Next -> Section 6.1](https://securedorg.github.io/RE102/section6.1) \ No newline at end of file