1
mirror of https://github.com/rapid7/metasploit-payloads synced 2025-03-24 18:16:24 +01:00

Revert "fix free() process.execute wchars"

This reverts commit be443779ff492b73eac988f77a42f71ece6ff277.
This commit is contained in:
Ashley Donaldson 2023-06-15 08:13:44 +10:00
parent 1ead8a024d
commit 830b4f801a

@ -29,6 +29,12 @@ typedef BOOL (WINAPI* INITIALIZEPROCTHREADATTRIBUTELIST) (
PSIZE_T lpSize
);
typedef struct _STARTUPINFOEXA
{
STARTUPINFOA StartupInfo;
LPPROC_THREAD_ATTRIBUTE_LIST lpAttributeList;
} STARTUPINFOEXA, *LPSTARTUPINFOEXA;
const int PROC_THREAD_ATTRIBUTE_PARENT_PROCESS = 0x00020000;
/*
@ -114,16 +120,13 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
Tlv inMemoryData;
BOOL doInMemory = FALSE;
PROCESS_INFORMATION pi;
STARTUPINFOW si;
LPPROC_THREAD_ATTRIBUTE_LIST lpAttributeList;
STARTUPINFOEXA si;
HANDLE in[2], out[2];
PCHAR path, arguments, commandLine = NULL;
wchar_t *commandLine_w = NULL;
PCHAR cpDesktop = NULL;
wchar_t *cpDesktop_w = NULL;
DWORD flags = 0, createFlags = 0, ppid = 0;
BOOL inherit = FALSE;
HANDLE token, pToken;
char * cpDesktop = NULL;
DWORD session = 0;
LPVOID pEnvironment = NULL;
LPFNCREATEENVIRONMENTBLOCK lpfnCreateEnvironmentBlock = NULL;
@ -135,9 +138,10 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
// Initialize the startup information
memset( &pi, 0, sizeof(PROCESS_INFORMATION) );
memset( &si, 0, sizeof(STARTUPINFOW) );
si.cb = sizeof(STARTUPINFOW);
lpAttributeList = NULL;
memset( &si, 0, sizeof(STARTUPINFOEXA) );
si.StartupInfo.cb = sizeof(STARTUPINFO);
si.lpAttributeList = NULL;
// Initialize pipe handles
in[0] = NULL;
@ -167,25 +171,23 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
if (flags & PROCESS_EXECUTE_FLAG_DESKTOP)
{
cpDesktop = (char *)malloc(512);
if (!cpDesktop)
do
{
result = ERROR_NOT_ENOUGH_MEMORY;
break;
}
memset(cpDesktop, 0, 512);
met_api->lock.acquire(remote->lock);
cpDesktop = (char *)malloc(512);
if (!cpDesktop)
break;
_snprintf(cpDesktop, 512, "%s\\%s", remote->curr_station_name, remote->curr_desktop_name);
memset(cpDesktop, 0, 512);
met_api->lock.release(remote->lock);
met_api->lock.acquire(remote->lock);
if (!(cpDesktop_w = met_api->string.utf8_to_wchar(cpDesktop)))
{
result = ERROR_NOT_ENOUGH_MEMORY;
break;
}
si.lpDesktop = cpDesktop_w;
_snprintf(cpDesktop, 512, "%s\\%s", remote->curr_station_name, remote->curr_desktop_name);
met_api->lock.release(remote->lock);
si.StartupInfo.lpDesktop = cpDesktop;
} while (0);
}
// If the remote endpoint provided arguments, combine them with the
@ -211,11 +213,6 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
result = ERROR_INVALID_PARAMETER;
break;
}
if (!(commandLine_w = met_api->string.utf8_to_wchar(commandLine)))
{
result = ERROR_NOT_ENOUGH_MEMORY;
break;
}
// If the channelized flag is set, create a pipe for stdin/stdout/stderr
// such that input can be directed to and from the remote endpoint
@ -266,10 +263,10 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
}
// Initialize the startup info to use the pipe handles
si.dwFlags |= STARTF_USESTDHANDLES;
si.hStdInput = in[0];
si.hStdOutput = out[1];
si.hStdError = out[1];
si.StartupInfo.dwFlags |= STARTF_USESTDHANDLES;
si.StartupInfo.hStdInput = in[0];
si.StartupInfo.hStdOutput = out[1];
si.StartupInfo.hStdError = out[1];
inherit = TRUE;
createFlags |= CREATE_NEW_CONSOLE;
@ -285,8 +282,8 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
// If the hidden flag is set, create the process hidden
if (flags & PROCESS_EXECUTE_FLAG_HIDDEN)
{
si.dwFlags |= STARTF_USESHOWWINDOW;
si.wShowWindow = SW_HIDE;
si.StartupInfo.dwFlags |= STARTF_USESHOWWINDOW;
si.StartupInfo.wShowWindow = SW_HIDE;
createFlags |= CREATE_NO_WINDOW;
}
@ -312,8 +309,8 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
) {
size_t len = 0;
InitializeProcThreadAttributeList(NULL, 1, 0, &len);
lpAttributeList = malloc(len);
if (!InitializeProcThreadAttributeList(lpAttributeList, 1, 0, &len)) {
si.lpAttributeList = malloc(len);
if (!InitializeProcThreadAttributeList(si.lpAttributeList, 1, 0, &len)) {
printf("[execute] InitializeProcThreadAttributeList: [%d]\n", GetLastError());
result = GetLastError();
break;
@ -321,7 +318,7 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
dprintf("[execute] InitializeProcThreadAttributeList\n");
if (!UpdateProcThreadAttribute(lpAttributeList, 0, PROC_THREAD_ATTRIBUTE_PARENT_PROCESS, &handle, sizeof(HANDLE), 0, 0)) {
if (!UpdateProcThreadAttribute(si.lpAttributeList, 0, PROC_THREAD_ATTRIBUTE_PARENT_PROCESS, &handle, sizeof(HANDLE), 0, 0)) {
printf("[execute] UpdateProcThreadAttribute: [%d]\n", GetLastError());
result = GetLastError();
break;
@ -330,6 +327,7 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
dprintf("[execute] UpdateProcThreadAttribute\n");
createFlags |= EXTENDED_STARTUPINFO_PRESENT;
si.StartupInfo.cb = sizeof(STARTUPINFOEXA);
FreeLibrary(hKernel32Lib);
}
@ -383,10 +381,15 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
}
// Try to execute the process with duplicated token
if (!CreateProcessAsUserW(pToken, NULL, commandLine_w, NULL, NULL, inherit, createFlags, pEnvironment, NULL, &si, &pi))
wchar_t *commandLine_w = met_api->string.utf8_to_wchar(commandLine);
if (!CreateProcessAsUserW(pToken, NULL, commandLine_w, NULL, NULL, inherit, createFlags, pEnvironment, NULL, (LPSTARTUPINFOW)&si, &pi))
{
LPCREATEPROCESSWITHTOKENW pCreateProcessWithTokenW = NULL;
HANDLE hAdvapi32 = NULL;
wchar_t * wcmdline = NULL;
wchar_t * wdesktop = NULL;
size_t size = 0;
free(commandLine_w);
result = GetLastError();
// sf: If we hit an ERROR_PRIVILEGE_NOT_HELD failure we can fall back to CreateProcessWithTokenW but this is only
@ -400,12 +403,35 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
{
break;
}
pCreateProcessWithTokenW = (LPCREATEPROCESSWITHTOKENW)GetProcAddress(hAdvapi32, "CreateProcessWithTokenW");
if (!pCreateProcessWithTokenW)
{
break;
}
if (!pCreateProcessWithTokenW(pToken, LOGON_NETCREDENTIALS_ONLY, NULL, commandLine_w, createFlags, pEnvironment, NULL, &si, &pi))
// convert the multibyte inputs to wide strings (No CreateProcessWithTokenA available unfortunatly)...
size = mbstowcs(NULL, commandLine, 0);
if (size == (size_t)-1)
{
break;
}
wcmdline = (wchar_t *)malloc((size + 1) * sizeof(wchar_t));
mbstowcs(wcmdline, commandLine, size);
if (si.StartupInfo.lpDesktop)
{
size = mbstowcs(NULL, (char *)si.StartupInfo.lpDesktop, 0);
if (size != (size_t)-1)
{
wdesktop = (wchar_t *)malloc((size + 1) * sizeof(wchar_t));
mbstowcs(wdesktop, (char *)si.StartupInfo.lpDesktop, size);
si.StartupInfo.lpDesktop = (LPSTR)wdesktop;
}
}
if (!pCreateProcessWithTokenW(pToken, LOGON_NETCREDENTIALS_ONLY, NULL, wcmdline, createFlags, pEnvironment, NULL, (LPSTARTUPINFOW)&si, &pi))
{
result = GetLastError();
dprintf("[execute] failed to create the new process via CreateProcessWithTokenW 0x%.8x", result);
@ -420,6 +446,9 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
{
FreeLibrary(hAdvapi32);
}
SAFE_FREE(wdesktop);
SAFE_FREE(wcmdline);
}
else
{
@ -456,8 +485,10 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
if (session_id(GetCurrentProcessId()) == session || !hWtsapi32)
{
if (!CreateProcessW(NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, &si, &pi))
wchar_t *commandLine_w = met_api->string.utf8_to_wchar(commandLine);
if (!CreateProcessW(NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, (LPSTARTUPINFOW)&si, &pi))
{
free(commandLine_w);
BREAK_ON_ERROR("[PROCESS] execute in self session: CreateProcessW failed");
}
}
@ -473,8 +504,10 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
{
BREAK_ON_ERROR("[PROCESS] execute in session: WTSQueryUserToken failed");
}
if (!CreateProcessAsUserW(hToken, NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, &si, &pi))
wchar_t *commandLine_w = met_api->string.utf8_to_wchar(commandLine);
if (!CreateProcessAsUserW(hToken, NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, (LPSTARTUPINFOW)&si, &pi))
{
free(commandLine_w);
BREAK_ON_ERROR("[PROCESS] execute in session: CreateProcessAsUser failed");
}
}
@ -501,9 +534,11 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
else
{
// Try to execute the process
if (!CreateProcessW(NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, &si, &pi))
wchar_t *commandLine_w = met_api->string.utf8_to_wchar(commandLine);
if (!CreateProcessW(NULL, commandLine_w, NULL, NULL, inherit, createFlags, NULL, NULL, (LPSTARTUPINFOW)&si, &pi))
{
result = GetLastError();
free(commandLine_w);
break;
}
}
@ -574,24 +609,14 @@ DWORD request_sys_process_execute(Remote *remote, Packet *packet)
free(commandLine);
}
if (commandLine_w)
{
free(commandLine_w);
}
if (cpDesktop)
{
free(cpDesktop);
}
if (cpDesktop_w)
if (si.lpAttributeList)
{
free(cpDesktop_w);
}
if (lpAttributeList)
{
free(lpAttributeList);
free(si.lpAttributeList);
}
met_api->packet.transmit_response(result, remote, response);