Posted on

Beginners guide to buffer overflow

Hello aspiring ethical hackers. In our previous blogpost, you learnt about remote code execution vulnerability. In this article, you will learn about buffer overflow vulnerability. This vulnerability is one of the most well known vulnerabilities but is also most common in software and apps. This vulnerability is also known as buffer overwrite vulnerability.

What is a buffer overflow?

To understand what is a buffer overflow, you have to first understand what is a buffer. So, first, let’s start with that. A buffer is a name given to an allocated memory space in programming. Programs and applications use memory space to store data temporarily and while transferring. This memory space is allocated while writing the program. This allocated memory space is called a buffer or memory buffer.

What is buffer overflow? For example, let’s say there is a program that takes input from you. Let’s say that input is username. So the programmer allocates 8 bytes of memory buffer to the data you enter. What happens if the data you enter as username is more than that allocated memory space, let’s say 10 bytes. The additional 2 bytes of memory overflows the allocated buffer space and and occupies the adjacent memory locations. This is known as buffer overflow. Depending on the circumstances, buffer overflow can be very dangerous sometimes even leading to execution of malicious code.

Types of buffer overflow vulnerabilities

Since buffer overflow is the overflow of data in memory buffers, there are prominently two types of buffer overflow depending on how a data is saved. They are,

1. Stack based buffer overflow:

In programming, a memory stack is used to store local variables, function arguments etc. If a overflow occurs in stack memory, it is known as stack overflow.

2. Heap based buffer overflow:

In programming, a memory heap is used for dynamic memory allocation allowing users to create and manage memory blocks while executing the program. An overflow in a heap is known as Heap buffer overflow.

Practical demonstration

Let’s see buffer overflow practically. For this, we will be writing a simple C program named “hc_wyn” with the code shown below. We are doing this on Kali Linux.

Let me explain the internal code of this program line by line. Let’s jump to the 4th and 5th line directly in which we are declaring two pointers “name” and “cmd”. In C, a pointer is a variable that holds the memory address of another variable. The asterisk symbol signifies a pointer to a char variable. In the 6th and 7th line of the program, we are using a C function named “malloc” which is used to dynamically allocate memory during runtime. As you can see, it allocates a memory of 8 and 128 bytes to ‘name’ and ‘cmd’ respectively. To put simply, we have created two buffers here, one of 8 bytes and other of 128 bytes.

In the 8th line, it will prompt users to enter their name. In the 9th line, we use a function gets() to read the line of input from stdin. Put simply, gets() reads the input the user has entered. This user input will be stored in memory buffer “name”. The code in 10th line will display the name anyone has entered as it is. In 11th line, we are using system() function. This function passes commands to the command processor of the operating system and returns output. Here, it will execute any command given to “cmd” variable. After we finish coding it, we compile the “hc_wyn.c” program using gcc as shown below.

The compilation should pop up many warnings. As long as there are no errors, ignore the warnings for now. Let’s execute the compiled program as shown below.


As it is intended to do, this program will output you back the name you typed. But when we enter a long name like “Cassandrius Thornston Gray mywills”, apart from returning back the name we entered, this program also returns what looks like output for Linux command “ls” as shown below.

Why did this happen? You might not have noticed but already a buffer overflow occurred here. To understand it clearly, let’s add three additional lines of code to our “hc_wyn” program as shown below.

The first line of code we added prints the memory address of the variable “name”. The second line of code prints the memory address of variable “cmd”. The third line of code we added gives the difference between two memory addresses. What the third line of code does is that it gives us the length of the memory buffer of variable “name”. Note that these two buffers are adjacent to each other.

Let’s recompile the program again and execute it. The result is as shown below.

As you can see, the size of the buffer of variable “name” is 32 characters. Now let’s see what went wrong with the program when we entered name “Cassandrius Thornston Gray mywills”. Let’s start with counting the number of characters in the name we just entered.
Cassandrius: 11 characters.
Thornston: 9 characters.
Gray: 4 characters
mywills: 7 characters
Three spaces: 3 characters
Total characters: 11+9+4+7+3=34

So this name has 34 characters in total but the buffer for “name” can hold only 32 characters. So in this case the last two characters “ls” in the name overflowed to the adjacent buffer belonging to variable “cmd”. We already know what this does. It submits the input to the command processor and returns output. The output for “ls” command. This is how buffer overflow occurs.

But how is it possible. Now, go back to something I told you ignore a while back. The warnings while compiling the program “hc_wyn.c”. Focus on the use of gets() function. At the end it says the usage of gets() is dangerous. That’s because gets() function doesn’t perform bounds checking. It copies all input from STDIN to the buffer without checking size. Exactly this happened when we entered the large name.

Posted on 1 Comment

Beginners guide to GNU debugger

Hello aspiring ethical hackers. In this article, you will learn about GNU debugger. A debugger is a computer program used to test the working of and debug other programs and applications. Debugging means breaking down the program piece by piece to see if it has any bugs or glitches while running. These bugs can also be vulnerabilities although most of the times they are random behavior or unexpected behavior of the program (like crashing).

A debugger does debugging by running the target program under controlled conditions. GNU debugger more popular as GDB, is one such debugger. Its features include inspecting present program state, controlling execution flow of programs, setting breakpoints at the stages we want, examining source code of the program, modifying program data etc. It is a portable debugger and runs on Windows, UNIX and Mac OS X. It can debug programs written in the following programming languages.

  • 1. Ada
  • 2. Assembly
  • 3. C
  • 4. C++
  • 5. D
  • 6. Fortran
  • 7. Go
  • 8. Objective-C
  • 9. OpenCL
  • 10. Modula-2
  • 11. Pascal
  • 12. Rust

Let’s see the working of this tool practically. We are doing this on Kali Linux OS (any version) as GNU debugger is available by default in its repositories. For this purpose, we code a simple C program named “first.c” as shown below.

Given below is the code of the C program we have written.

//Program to add two numbers and display their sum

#include<stdio.h>
int main()
{
int a,b,sum;
printf("Enter the first number: ");
scanf("%d",&a);
printf("Enter the second number: ");
scanf("%d",&b);
//Adding
sum=a+b;
printf("%d + %d = %d",a,b,sum);
return 0; 
}

As can be seen, “first.c” is a simple C program that adds two numbers given to it and display the result. Once the program is finished, save the file and compile the program using GCC compiler. This can be done using command shown below.

gcc first.c -g -o first

The “-g” option here enables debugging. Once it is in machine code, we can execute it and see if it is working. It can be done as shown below.

./first

As we execute it, the program first asks the user to enter the first number. Once it is over, it asks user to enter the second umber. When both numbers are entered, it will add them both and display the result as shown below.

For example, the sum of 7 and 19 is 26. The program is running smoothly as intended. Now, let’s load this in the gdb debugger. This can be done as shown below.

How to use GNU Debugger

Now let’s run the program once again inside the debugger. This can be done either using command r or run as shown below.

Now, in case you want to view the source code of the program you have no need to go out of the debugger. You can do this using “l” or “list” command will show the first 10 lines of the code as shown below.

Now let’s add a break point at a certain line of the program. What is a break point? Break points allow us to stop the execution of the program at a certain point we want. A break point can be added using command “break” or “b“. For example, let’s stop the execution of program at line 9. Run the program again to see if the program stops at the intended point.

As you can see in the above image, It stops exactly at line 9. We can remove the particular break point using the “disable” command.

Now, let’s set a break point at line 10. As the program stops at line 10, we can only enter one value that of variable “a”. We can use the “print” command to see the values of variables we have assigned.

While the value of “a” is something we set and it is getting displayed correctly, we did not yet set the value for variable “b”. But it is still showing some random value. We can change the values we already set using the “set” command as shown below.

We set another break point at line 15. All the breakpoints set to the program can be seen using command “info b“.

Although, there are three breakpoints, see that only two of them are active as we disabled one already. Let’s run the program again.

It stops at the break point which is at line 10. To completely remove the breakpoint use command “clear“.

Now, there are only two breakpoints. To continue running the program from this point, use command “continue“. This will run the program from the exact point where it stopped. The program exited normally. “clear” command can be used to delete break points using their line number as shown below.

Let’s run the program again after removing all the break points.

Now, let’s set three new break points again on lines 9, 11 and 16. We will assign the values as the program gets executed.

At the first break point, we set the value of variable “a” to 19.5 and continue the program. I use the print command to see the value of variable “a”.

As you can see, it is printed as 19 and not 19.5. Our first bug. Similarly the “b” variable is 17 whereas we gave it the value of 17.6.

When we continue the program as it is, the answer we got is 32786 which is definitely wrong. Here we detected that the program is behaving abnormally when decimal numbers are given as input.

Here’ s another example.

Seeing this we can conclude that this program is only suitable for non decimal numbers and result goes wrong even if one of them is a decimal number. Using gdb, we found out our first bug in a program. We can even see the assembly code of this program using the “disass” command.

The program is sent to the testers to find out what the bug can do. The testers load the program using GNU Debugger about which our readers have learnt in our previous article.

Now, you are the tester. Check the assembly code of the program.

In the assembly code, you can see that there’s a command “gets” that collects data from standard input. Introduce a breakpoint at the point shown below and run the program . With the breakpoint, the program stops running exactly at the point where you give input to the program. After giving input, you can continue the program as shown below.

If you have observed in the above image, I have given 16 C’s as input. This process is known as fuzzing. Fuzzing is a process where we provide strings of varying length as input to find out where the buffer overflow occurs.
This strings of different lengths can be created in various ways. Here’s a method to create C’s of varied lengths using python.

We can also directly provide this random text created to the program as shown below instead of copying and pasting it.

Here is the program running in the debugger.

buffer overflow

As an input of 35 characters is provided, a overflow occurred. Three C’s overflowed over their buffer onto the next buffer.

So the size of the first buffer is 35-3 = 32 characters. Anything that jumps over this 32 characters onto next buffer is being executed as a command due to “system” function there. So next, give 32 C’s and then append a command “ls” to it as shown below.

As you can see, the “ls” command got executed. If it is not a command, the program says “not found” .

Try some other commands as shown below.

You can even pop a raw shell to another machine as shown below.

That’s all for now. To add more fun, go to your “second.c” program and add some additional lines as highlighted below. These are print commands.

Compile again and now run the program. You should see something as shown below. Observed the difference?

Posted on

Shellcode injection for beginners

Hello aspiring ethical hackers. In our previous blogpost, you learnt what is shellcode from a hacker’s perspective and different types of shellcode. In this article, you will learn about shellcode injection.

What is shellcode injection?

Shellcode injection is the process in which we inject our own shellcode into vulnerable programs to be executed. Basically, shellcode injection consists of three steps. They are,

  1. Creating the shellcode
  2. Finding the vulnerable program and injecting the shellcode
  3. Modifying the execution flow of this vulnerable program to execute our shellcode.

Let’s see shellcode injection practically. Metasploit has a shellcode injection module which can be used to inject shellcode into Windows processes in memory. Let’ s see how this module works. This works after gaining access to a Windows system and grabbing a meterpreter session on it. Background the current session and load the windows shellcode inject module as shown below.

For this tutorial, we will use Donut tool create a shellcode of the mimikatz program.

Set the SESSION ID and other options given below.

Set the interactive option to TRUE . We need to do this so that we are not taken directly to the mimikatz shell. We also need to set the correct target architecture.

After all the options are set, we need to just execute the module as shown below.

shellcode injection with Metasploit

As you can see in the above image, we are directly into mimikatz shell.

Let’s see another example. This time we will show you how to perform shellcode injection into Windows executables. Windows  binaries are those binaries that are already present by default on a Windows system. Just imagine you are pen testing a Windows machine and you want to gain access to it without bringing any third party malware to the target system. How about using the files already present on the target system to execute your payload. This is also known as file less malware.

Windows by default has some genuine binaries for its own functions. However, these can be utilized by malicious actors to execute their own payload which is not benign. Examples of these binaries are regsrvr32.exe, notepad.exe, calc.exe and rundll32.exe etc. Rundll32.exe is a binary used in Windows to link library for other Windows applications. Of course, readers know about Notepad and Calculator.

For this tutorial, we will be using a tool named CactusTorch. CactusTorch  is a shellcode launcher tool that can be used to launch 32 bit shellcode which can then be injected into any Windows binaries. CactusTorch can be cloned from GitHub as shown below from here.

Once the repository is cloned successfully, we need to create shellcode. Cactus torch is compatible with Metasploit and Cobalt strike. So let’s use msfvenom to create 32 bit shellcode.

The shellcode is successfully created and is stored in payload.bin file.

Next, encode this payload using base64 encoding as shown below.

shellcode injection

This shellcode can be hosted in different formats as shown below. These formats are already provided by Cactustorch.

Let’s see the example of HTA file. Open the cactustorch.hta file using any text editor.

We can specify the binary you want to inject this shellcode into. For example, here we want to inject shellcode into rundll32.exe. Copy the base64 encoded shellcode at  “Dim code”. Save the file. Start a Metasploit listener as shown below.

Next, all we have to do is make the user on target system execute the cactus torch.hta file. This can be done using social engineering. As soon as this file is executed, we will get a successful meterpreter session as shown below.

Similarly, this shellcode can be hosted in JavaScript and also VB script and VBA files to be injected.

Posted on 1 Comment

Donut shellcode generator: Beginners guide

Hello, aspiring ethical hackers. In our previous blogpost, you learnt what shellcode is and why pen testers use it. In this blogpost, you will learn about Donut, a shellcode generator. Although there are many tools that can generate shellcode, Donut does this with position independent code that enables in-memory execution of the compiled assemblies. This compiled shellcode assembly can either be staged from a HTTP server or embedded directly in the file itself. After the compiled shellcode is loaded and executed in memory, the original reference is erased immediately to avoid memory scanners.

The features supported by the Donut shellcode generator are,

  1. Compression of the generated files with aPLib and LZNT1, Xpress, Xpress Huffman.
  2. Using entropy for generation of strings 128-bit symmetric encryption of files.
  3. Patching Antimalware Scan Interface (AMSI) and Windows Lockdown Policy (WLDP).
  4. Patching command line for EXE files.
  5. Patching exit-related API to avoid termination of host process.
  6. Multiple output formats: C, Ruby, Python, PowerShell, Base64, C#, Hexadecimal.

    Donut can be installed in Kali Linux by cloning it from GitHub as shown below. This will create a new directory named “Donut”.
donut1

Navigate into the newly created directory. Let’s create the shellcode for mimikatz.exe as shown.

How to use donut shellcode generator

Mimikatz.exe is a simple tool that is used to play with windows security. If you take this executable of Mimikatz into a Windows system, any antivirus or Windows Defender will detect this as malware. Just try it on your machine first before turning it into shellcode. It is found in Kali Linux. Here we copied it into the Donut folder.
When we run above command, shellcode is created as a file named “loader.bin” in the same directory of Donut.

By default, Donut creates shellcode for both x86 (32bit) and amd64 (64bit). To create only x86 shellcode, the command is as shown below.

The “-b” option is used to set the shellcode’s behavior when faced with AMSI/WLDP. Anti Malware Scan Interface (AMSI) and Windows Lock Down Policy (WLDP) are security features. Both these features protect the Windows system from malware.

By default, Donut sets the shellcode to bypass AMSI/WLDP. By setting the “-b” option to “2” as shown in the above image, it can be set to ABORT once it encounters AMSI/WLDP. Setting “1 ” will do nothing.

Entropy in general terms means the degree of randomness. It is used by malware to make detection of its code harder by Anti malware. This is called obfuscation. The more the entropy the least chances of detection of malware. Donut, by default sets random names and also encrypts the shellcode to obfuscate the code from anti malware. It can be changed using the “-e” option. Setting it to “2” just sets random names to the payload and setting it to “1” does nothing.

Not just binaries, we can create different output formats with Donut though by default it creates a binary payload. The “-f” option is used to set different output formats. For example, set -ting “-f” option to “2” gives a base64 format. 3 creates C, 4 creates Ruby, 5 creates Python, 6 creates PowerShell, 7 creates C# and 8 creates Hexadecimal shellcodes respectively.

The “-z” option is used to set packing and compressing engines. Donut doesn’t use any compression by default. However it supports four compression engines. 2=aPLib, 3=LZNT1, 4=Xpress, 5=Xpress Huffman. Only the aPlib compressor works in Linux. Rest of them work on Windows. Compression reduces the size of the payload whereas packing is used to avoid detection by anti malware.

We have seen that by default, Donut saves the payloads it creates in the same directory. The location as to where the payload is saved can be changed with the “-o” option.

That’s all about the Donut shellcode generator. Next, learn how to inject shellcode using Metasploit.

Posted on

How to install Parrot OS in VirtualBox

Hello aspiring ethical hackers. In this article, you will learn how to install Parrot OS in VirtualBox. Parrot Security OS, also popularly known as Parrot OS is an operating system specifically designed for pen testing similar to Kali Linux. It is a free and open source GNU/Linux distribution based on Debian designed for security experts, developers and privacy aware people. It includes a full portable arsenal for IT security and digital forensics operations.

In this article, we will show you two methods to install Parrot OS in VirtualBox. They are,

  • 1. Using a OVA file
  • 2. Using an ISO file

1. Using a OVA file

The makers of Parrot OS are providing pre-built images for hypervisors like VMware and VirtualBox. You can download the OVA file of Parrot Security OS from here. Once the OVA file is finished downloading, Open VirtualBox and click on “Import”.

Naviagte to the OVA file we just downloaded and click on “Next”.

All the settings applied to the virtual machine are displayed. Change any settings if necessary and click on “Import”.

When Software License Agreement is displayed, Click on “Agree”.

VirtualBox will start importing the Parrot Security OS virtual appliance as shown below.

After the import is complete, it will be displayed in the list of virtual machines as shown below.

We just need to power it up and the our Parrot OS is ready for pen testing.

2. Using iso file

Now, readers will see how to install Parrot  Security OS in VirtualBox using ISO file. Download the Parrot security ISO file from here. Once ISO file is finished downloading, open VirtualBox, go to Machine > New or hit CTRL+N.

A  new window will open as shown below.

Click on “Expert mode”.

How to install parrot os virtualbox

Fill up the details. Configure the machine folder, type of OS, version etc and allocate the RAM (RAM should be minimum 2GB). Once everything is configured, Click on “Create”.

Allocate the hard-disk size (minimum 16 GB is the minimum requirement but keep it at least 20 GB). Set the other options as shown below. Click on “Create”.

The virtual machine is created. Start the newly created virtual machine. It should start as shown below.

     Browse to the ISO file we downloaded earlier and add it as shown below. Then, click on “Start”.

  The interface changes as shown below. Click on “Install”.

Once you are at the OS interface, click on “Install Parrot “. The Calamares Installer opens.

Click on “Next “.  Select Location and click on “Next”.

Select the keyboard mode and click on “Next”.

Set the partition. Select “Erase disk” and click on “Next”.

Create a user and set credentials to the newly created user.

Review all the settings and click on “Install”.

Click on “Install Now.”

The system starts installing as shown below.

Once the system has finished installing as shown below, click on “Done” .

This will restart the system and will take you to the Login screen. Login using credentials of the newly created user and you are good to go. Happy ethical hacking. Next, see how to install Parrot OS in VMware.