Basic Linux Exploit – Buffer Overflow – Part 1

Tram Ho

Hi everyone, this is my first post to start a series of binary exploits on linux. My first article will focus on introducing the structure of the stack, buffer overflow errors and basic exploitation. From the following articles will gradually increase the difficulty, bypass anti-exploit methods on linux.

1. Stack and steps when a function call is made

This series I will not go into the stack, or the concept and functions of the registers, but this knowledge currently on google has a lot of articles, everyone can learn to read more before reading the article. mine. In this article, I introduce and exploit on 32 bit system.

First, when a function call is made, there are 3 steps to be taken:

  • Put the function parameters on the stack in reverse order. For example void func(int a, int b) is placed on the stack in order b then a.
  • Put the EIP pointer on the stack, this is considered the return address so that when the function is done, the program will know the next instruction to execute.
  • Call function is called (call function)

After the function is called, it is responsible for performing the following tasks in turn:

  • Stores the current EBP register on the stack
  • Save ESP to EBP
  • Reduce EBP to make space for storing function local variables on the stack

=> This process is called function prolog

Example of function prolog: (assembly in intel structure)

After the function is done, esp increments to ebp to clear the stack (delete the initial memory area created), the saved eip is removed to execute the next instruction.

=> this process is called function epilog Example:

In it, the leave command has the following form:

The ret command is to get the eip value in the stack. Here is an example of a stack frame when making a function call func(int value1, int value2)

With the steps taken when the function call executes, and ends, the esp and ebp pointers are always returned to their original values ​​and the program always knows the next instruction to execute after the function ends.

2. Debug with gdb (gef) and a simple buffer overflow exploit

I have a simple victim.c file as follows:

After reading through the program, I realized that the program uses the strcpy function (copy string), a flaw of this function is that it does not specify the number of characters to copy, so if the array array contains at most 64 characters, that argv[1] is larger than 64 characters, the function will still execute, thereby causing an error in the stack.

After the main function call is called, the stack will look like this:

I proceed to compile the program using gcc with the following options:

gcc -m32 -z execstack -mpreferred-stack-boundary=2 -fno-stack-protector victim.c -o victim

In there:

  • -m32: compile 32 bit program
  • -z execstack: allows execution in the stack
  • -mpreferred-stack-boundary=2 : Use DWORD size stack
  • fno-stack-protector: disable stack canary

Here I have turned off all stack protection mechanisms, later in the series to bypass these mechanisms I will talk in more detail.

Debugging with gdb (gef) (github gef link: https://github.com/hugsy/gef )

Create breakpoint at main

Run the program with the argument: “test”:

This is the information before the program runs into the main function, pay attention to the assembly part, we get the function prolog, as follows:

This is why in the illustration above, I have 4 more bytes of the ebx bar. So according to the calculation, to override the eip register, to redirect to the shell code after the main function is done, we need the number of bytes:

Run the program with input 76 bytes:

The results obtained are as follows:

Where 0x42 corresponds to B in ascii. So our calculation is correct. Thanks to eip pointer control, it is now possible to redirect the program as you like. I will do a redirect to a shellcode in the next post.

Share the news now

Source : Viblo