读书人

!很高的手才可以进的一个从内存中加

发布时间: 2012-03-30 17:32:10 作者: rapoo

!!很高的手才可以进的,一个从内存中加载并启动一个exe的问题?
#include <stdio.h>
#include <string.h>
#include <windows.h>
#include <tlhelp32.h>
//#include <psapi.h>

struct PE_Header
{
unsigned long signature;
unsigned short machine;
unsigned short numSections;
unsigned long timeDateStamp;
unsigned long pointerToSymbolTable;
unsigned long numOfSymbols;
unsigned short sizeOfOptionHeader;
unsigned short characteristics;
};

struct PE_ExtHeader
{
unsigned short magic;
unsigned char majorLinkerVersion;
unsigned char minorLinkerVersion;
unsigned long sizeOfCode;
unsigned long sizeOfInitializedData;
unsigned long sizeOfUninitializedData;
unsigned long addressOfEntryPoint;
unsigned long baseOfCode;
unsigned long baseOfData;
unsigned long imageBase;
unsigned long sectionAlignment;
unsigned long fileAlignment;
unsigned short majorOSVersion;
unsigned short minorOSVersion;
unsigned short majorImageVersion;
unsigned short minorImageVersion;
unsigned short majorSubsystemVersion;
unsigned short minorSubsystemVersion;
unsigned long reserved1;
unsigned long sizeOfImage;
unsigned long sizeOfHeaders;
unsigned long checksum;
unsigned short subsystem;
unsigned short DLLCharacteristics;
unsigned long sizeOfStackReserve;
unsigned long sizeOfStackCommit;
unsigned long sizeOfHeapReserve;
unsigned long sizeOfHeapCommit;
unsigned long loaderFlags;
unsigned long numberOfRVAAndSizes;
unsigned long exportTableAddress;
unsigned long exportTableSize;
unsigned long importTableAddress;
unsigned long importTableSize;
unsigned long resourceTableAddress;
unsigned long resourceTableSize;
unsigned long exceptionTableAddress;
unsigned long exceptionTableSize;
unsigned long certFilePointer;
unsigned long certTableSize;
unsigned long relocationTableAddress;
unsigned long relocationTableSize;
unsigned long debugDataAddress;
unsigned long debugDataSize;
unsigned long archDataAddress;
unsigned long archDataSize;
unsigned long globalPtrAddress;
unsigned long globalPtrSize;
unsigned long TLSTableAddress;
unsigned long TLSTableSize;
unsigned long loadConfigTableAddress;
unsigned long loadConfigTableSize;
unsigned long boundImportTableAddress;
unsigned long boundImportTableSize;
unsigned long importAddressTableAddress;
unsigned long importAddressTableSize;
unsigned long delayImportDescAddress;
unsigned long delayImportDescSize;
unsigned long COMHeaderAddress;
unsigned long COMHeaderSize;
unsigned long reserved2;
unsigned long reserved3;
};


struct SectionHeader
{
unsigned char sectionName[8];
unsigned long virtualSize;
unsigned long virtualAddress;
unsigned long sizeOfRawData;
unsigned long pointerToRawData;
unsigned long pointerToRelocations;
unsigned long pointerToLineNumbers;
unsigned short numberOfRelocations;
unsigned short numberOfLineNumbers;
unsigned long characteristics;
};

struct MZHeader
{
unsigned short signature;
unsigned short partPag;
unsigned short pageCnt;
unsigned short reloCnt;
unsigned short hdrSize;
unsigned short minMem;
unsigned short maxMem;


unsigned short reloSS;
unsigned short exeSP;
unsigned short chksum;
unsigned short exeIP;
unsigned short reloCS;
unsigned short tablOff;
unsigned short overlay;
unsigned char reserved[32];
unsigned long offsetToPE;
};


struct ImportDirEntry
{
DWORD importLookupTable;
DWORD timeDateStamp;
DWORD fowarderChain;
DWORD nameRVA;
DWORD importAddressTable;
};

/
WINBASEAPI
LPVOID
WINAPI
VirtualAllocEx(
HANDLE hProcess,
LPVOID lpAddress,
SIZE_T dwSize,
DWORD flAllocationType,
DWORD flProtect
);





[解决办法]
咕~~()b
我就是来接分的。。。
[解决办法]
struct MZHeader mzH;
struct PE_Header peH;
struct PE_ExtHeader peXH;
struct SectionHeader *secHdr;

//从文件取得Exe信息(MZ,PE,PEEXT,Sections)
if(readPEInfo(fp, &mzH, &peH, &peXH, &secHdr))
{
//按exe头的信息计算所需空间
int imageSize = calcTotalImageSize(&mzH, &peH, &peXH, secHdr);
//printf("Image Size = %X\n", imageSize);

LPVOID ptrLoc = VirtualAlloc(NULL, imageSize, MEM_COMMIT, PAGE_EXECUTE_READWRITE);//分配空间
if(ptrLoc)
{
//printf("Memory allocated at %X\n", ptrLoc);
loadPE(fp, &mzH, &peH, &peXH, secHdr, ptrLoc);//装载exe文件数据到分配空间

doFork(&mzH, &peH, &peXH, secHdr, ptrLoc, imageSize);//模拟目标Exe运行环境跑Exe代码
[解决办法]
各个函数基本都注释了,需要的知识点比较多,尤其是PE格式是一定要熟悉的,没什么好说的,lz还是要自己加强学习。

C/C++ code
BOOL readPEInfo(FILE *fp, struct MZHeader *outMZ, struct PE_Header *outPE, struct PE_ExtHeader *outpeXH, struct SectionHeader **outSecHdr){    //获取要执行的exe文件的长度     fseek(fp, 0, SEEK_END);    long fileSize = ftell(fp);    fseek(fp, 0, SEEK_SET);        //判断长度是否小于PE文件中DOS Stub的大小,如果小于,则说明不是合法的PE格式文件    if(fileSize < sizeof(struct MZHeader))    {        printf("File size too small\n");           return FALSE;    }        //读取DOS Stub到mzH    // read MZ Header    struct MZHeader mzH;    fread(&mzH, sizeof(struct MZHeader), 1, fp);        //判断DOS Stub的标志是否是"MZ",如果不是则说明不是合法的PE格式文件    if(mzH.signature != 0x5a4d) // MZ    {        printf("File does not have MZ header\n");        return FALSE;    }        //printf("Offset to PE Header = %X\n", mzH.offsetToPE);    //检查文件的大小是否小于PE文件头中指明的大小。如果小于,则说明不是合法的PE格式文件    //通常这两个值应该相等,但是实际上fileSize大于后面的和是有可能的,呵呵。    if((unsigned long)fileSize < mzH.offsetToPE + sizeof(struct PE_Header))    {        printf("File size too small\n");           return FALSE;    }        //接下来是读取PE头,PE头的起始位置在DOS Stub中会指明,通常不是和Dos Stub连在一块的,    //所以这里需要先SEEK一下文件指针的位置,然后读取    // read PE Header    fseek(fp, mzH.offsetToPE, SEEK_SET);    struct PE_Header peH;    fread(&peH, sizeof(struct PE_Header), 1, fp);        //printf("Size of option header = %d\n", peH.sizeOfOptionHeader);    //printf("Number of sections = %d\n", peH.numSections);    //又是一个判断,检查文件中的可选头的大小和实际大小一致    if(peH.sizeOfOptionHeader != sizeof(struct PE_ExtHeader))    {        printf("Unexpected option header size.\n");                return FALSE;    }        //接着读取PE的可选头    // read PE Ext Header    //struct PE_ExtHeader peXH;    struct PE_ExtHeader peXH;        fread(&peXH, sizeof(struct PE_ExtHeader), 1, fp);        //printf("Import table address = %X\n", peXH.importTableAddress);    //printf("Import table size = %X\n", peXH.importTableSize);    //printf("Import address table address = %X\n", peXH.importAddressTableAddress);    //printf("Import address table size = %X\n", peXH.importAddressTableSize);            // read the sections    //SectionHeader *secHdr = new SectionHeader[peH.numSections]; // VC++    //根据PE头中指明的section个数来分配内存,记录所有的section数据    struct SectionHeader *secHdr = (struct SectionHeader*)malloc(sizeof(struct SectionHeader) * peH.numSections);        fread(secHdr, sizeof(struct SectionHeader) * peH.numSections, 1, fp);        *outMZ = mzH;    *outPE = peH;    *outpeXH = peXH;    *outSecHdr = secHdr;        return TRUE;} 


[解决办法]

读书人网 >C++

热点推荐