[Adapted Version] smashing the stack for fun and profit part1

Source: Internet
Author: User

Introduction

For example, syslog, splitvt, sendmail 8.7.5, linux mount command, xtlibrary, and many other software have problems such as Buffer Overflow (bo ).

This article explains how to use bo attacks. Read: Assembly, virtual memory, and gdb usage. The environment used in this article is x86 + linux

First, we define what buffer is, and buffer is the memory space of several instances of the same data type (I still don't understand it ...) in C language, it is usually associated with the word buffer array (still do not understand ...)

The buffer can be understood as a memory block.

The array can be declared static or dynamic, and static variables are allocated to data segments when the program is loaded. Dynamically Loaded into the stack when the program is running

Overflow refers to outbound traffic to the top, edge, or border. This article only discusses the dynamic buffer, that is, stack-based buffer overflow.

 

Process Memory Organization

To understand the stack buffer, we must first learn how the process manages the memory zone.

A process is divided into three areas: Text, data, and stack. We mainly focus on the stack area, but we still look at other areas.

Partition: used to place code or read-only data. This area is equivalent to the text part of the running program. This area is generally marked as read-only. Any write operation on this area will cause a segment error.

Data zone: Contains initialization and uninitialized data, and static variables are stored here. This part is the data-bss part when the program is running...

/---------------- \ Low memory address
|
| Text |
|
| ---------------- |
| (Initialized) |
| Data |
| (Not initialized) |
| ---------------- |
|
| Stack |
|
\ ----------------/High memory address

What Is A Stack?

A stack is an abstract data structure. Its attribute is "post-in-first-out LIFO", which defines the PUSH and POP operations on the stack.

Why Do We Use A Stack?

Modern computers need the support of advanced languages. The most important component of advanced languages is functions. Function reference can change the control flow of the Program (that is, the change of function call)

However, after the execution body of the function is completed, the function returns the execution permission to the subsequent program (the execution command after the function call Statement)

To put it bluntly, it is not the use of the Call Stack. The stack LIFO attribute is used to save the local variables, function parameters, and return values in the function.

 

The Stack Region

A stack is a continuous storage area. The sp pointer in the register points to the top of the stack. The bottom of the stack is usually a fixed address. The size of the entire stack can be dynamically changed through the kernel.

CPU to implement the PUSH and POP operations of commands

A stack is composed of a series of logical stack frames. This ghost function is pushed when called and pop when returned.

Well, now we will introduce what Stack frames are. Stack frames include function input parameters, local variables, and stack frames for resuming upper-level calls. They include command pointers for higher-level calls.

Depending on the system, the stack implementation method is also very different. This article introduces the stack growth from high address to low address, where the sp pointer executes the last stack address used

Here we introduce the second pointer bp, which is used to represent local variables in the range of this function (this ghost bp is used to indicate the starting address of these local variables. Note that, the starting address does not include sfp and ret)

Bp and sp are based on the following operating mechanisms:

1. The called function first defines the original bp push as sfp (bp is interpreted as the symbol of the function stack frame, so it is also called fp)

2. Assign the sp value to bp (as you can imagine, the function stack frame is continuous across the memory. Each function stack frame can be regarded as an input parameter consisting of four parts; ret; sfp; for local variables between esp and ebp, see)

3 sp reset to deduct the space of local variables

 

Now it's time to really do the work. Study the real code. My local environment is ubuntu + gcc 4.4.3.

Example1.c:
------------------------------------------------------------------------------
Void function (int a, int B, int c ){
Char buffer1 [5];
Char buffer2 [10];
}

Void main (){
Function (1, 2, 3 );
}
------------------------------------------------------------------------------
Compilation process: gcc-S-o example1.s-fno-stack-protector example1.c

The generated assembly code is as follows:

Main:
Pushl % ebp
Movl % esp, % ebp
Subl $12, % esp
Movl $3, 8 (% esp)
Movl $2, 4 (% esp)
Movl $1, (% esp)

These three statements are different from the original one, but they are essentially push operations. I do not know why they are written like this.
Call function
Movl $0, % eax
Leave
Ret


Function:
Pushl % ebp
Movl % esp, % ebp
Subl $16, % esp

The bytes are not aligned. The original value is 20.
Leave
Ret

 

Shows the generated function memory space.


At the climax, the Buffer Overflow (in fact, it can be considered a function stack frame to try to rewrite the ret content)

The example in the original article is as follows: it is nothing more than overwriting a small string with a large string, resulting in ret writing failure.

Example2.c
------------------------------------------------------------------------------
Void function (char * str ){
Char buffer [16];
Strcpy (buffer, str );
}

Void main (){
Char large_string [256];
Int I;
For (I = 0; I <255; I ++)
Large_string [I] = 'a ';
Function (large_string );
}
------------------------------------------------------------------------------

Let's rewrite our example Code as follows:

Example3.c:
------------------------------------------------------------------------------
Void function (int a, int B, int c ){
Char buffer1 [5];
Char buffer2 [10];
Int * ret;
Ret = buffer1 + 13;

/*

The current version of gcc has been optimized, but I have not figured out the optimization, but at least the definition sequence and byte pairs of local variables have changed.

For this example, the ebp-4 defines the variable as ret; The ebp-9 since no byte alignment defines the variable as buffer1

13 = 5 (buffer1) + 4 (ret) + 4 (sfp)

*/
(* Ret) + = 8;

/*

Why is it the compilation behind + 8?

*/
}

Void main (){
Int x;
X = 0;
Function (1, 2, 3 );
X = 1;/* make this statement unexecutable */
Printf ("% d \ n", x );
}
------------------------------------------------------------------------------

The following is the assembler of the above Code.

(Gdb) disassemble main
Dump of worker er code for function main:
0x08048402 <+ 0>: push % ebp
0x08048403 <+ 1>: mov % esp, % ebp
0x08048405 <+ 3>: and $0xfffffff0, % esp
0x08048408 <+ 6>: sub $0x20, % esp
0x0804840b <+ 9>: movl $0x0, 0x1c (% esp)
0x08048413 <+ 17>: movl $0x8 (% esp)
0x0804841b <+ 25>: movl $0x2,0x4 (% esp)
0x08048423 <+ 33>: movl $0x1, (% esp)
0x0804842a <+ 40>: call 0x80483e4 <function>

This call occupies 5 bytes.
0x0804842f <+ 45>: movl $0x1, 0x1c (% esp)

The movl occupies 8 bytes.
0x08048437 <+ 53>: mov $0x8048520, % eax
0x0804843c <+ 58>: mov 0x1c (% esp), % edx
0x08048440 <+ 62>: mov % edx, 0x4 (% esp)
0x08048444 <+ 66>: mov % eax, (% esp)
0x08048447 <+ 69>: call 0x804831c <printf @ plt>
0x0804844c <+ 74>: mov $0x0, % eax
0x08048451 <+ 79>: leave
0x08048452 <+ 80>: ret

(Gdb) disassemble function
Dump of worker er code for function:
0x080483e4 <+ 0>: push % ebp
0x080483e5 <+ 1>: mov % esp, % ebp
0x080483e7 <+ 3>: sub $0x20, % esp
0x080483ea <+ 6>: lea-0x9 (% ebp), % eax

/* The new lea syntax obtains the valid value of the Offset and assigns it to eax */
0x080483ed <+ 9>: add $ 0xd, % eax
0x080483f0 <+ 12>: mov % eax,-0x4 (% ebp)
0x080483f3 <+ 15>: mov-0x4 (% ebp), % eax
0x080483f6 <+ 18>: mov (% eax), % eax
0x080483f8 <+ 20>: lea 0x8 (% eax), % edx
0x080483fb <+ 23>: mov-0x4 (% ebp), % eax
0x080483fe <+ 26>: mov % edx, (% eax)
0x08048400 <+ 28>: leave
0x08048401 <+ 29>: ret

The above small trick only makes the main execution change through a simple overflow.

The above is just an overflow, with no actual harm. What we see below is destructive.

 

Shell code

It is understood as a program pointed to by overflow. This program can obtain the shell or upgrade the root

Here we propose a general buffer overflow attack method: place the code in the buffer to which we will overflow, and then rewrite ret to point it to this buffer. For details, see:


Write the buffer (whether it has a deeper understanding of the buffer, it is an array for you to write and use) into your command, and then rewrite the ret to execute the buffer, this is B. o attack

The following analysis shows how to write a shell code, that is, what should be filled in the buffer?

Next time, break it down.

 

Angle:

An understanding of a computer system is not only an analysis of program code, but also an understanding of the running mechanism and environment of the program in the system.

Silky:

If it doesn't work, it slows down to the slowest speed.

Article completed: Create local get root shell

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.