www.pudn.com > PEMonitor_0.10_src.zip > PEServ.c


/////////////////////////////////////////////////////////////////////////////// 
// 
//  FileName    :   PEServ.c 
//  Version     :   0.10 
//  Author      :   Luo Cong 
//  Date        :   2004-09-02 (yyyy-mm-dd) 
//  Comment     : 
// 
/////////////////////////////////////////////////////////////////////////////// 
 
#include  
#include  
#include "Misc.h" 
#include "PEServ.h" 
#include "MemServ.h" 
#include "disasm.h" 
 
int IsPEFile( 
    /* [in] */ const char *szFileName 
) 
{ 
    int nRetResult = 0; 
 
    FILE *fp_in = NULL; 
 
    unsigned long   ulPEHeaderOffset    = 0; 
    unsigned short  usMagic             = 0;    // should be "MZ", 0x5a4d 
    unsigned long   ulPESignature       = 0;    // should be "PE", 0x4550 
 
    fp_in = fopen(szFileName, "rb"); 
    if (NULL == fp_in) 
    { 
        printf(ErrMsg[ERR_OPEN_FILE], szFileName); 
        goto Exit0; 
    } 
 
    fread(&usMagic, 1, 2, fp_in); 
    if (0x5a4d != usMagic) 
    { 
        printf(ErrMsg[ERR_NOT_A_PE_FILE], szFileName); 
        goto Exit0; 
    } 
 
    fseek(fp_in, 0x3c, SEEK_SET); 
    fread(&ulPEHeaderOffset, 1, 4, fp_in); 
 
    fseek(fp_in, ulPEHeaderOffset, SEEK_SET); 
    fread(&ulPESignature, 1, 4, fp_in); 
    if (0x4550 != ulPESignature) 
    { 
        printf(ErrMsg[ERR_NOT_A_PE_FILE], szFileName); 
        goto Exit0; 
    } 
 
    nRetResult = 1; 
Exit0: 
    if (fp_in) 
    { 
        fclose(fp_in); 
        fp_in = NULL; 
    } 
    return nRetResult; 
} 
 
unsigned long RVAToFileOffset( 
    /* [in] */ const unsigned long RVA 
) 
{ 
    unsigned long ulOffset = 0; 
    const int nSizeOfImageNtHeaders = 0xf8; 
    const int nSizeOfSectionHeader = 0x28; 
    const long ulPEHeaderOffset = *(unsigned long *)&g_FileContents[0x3c]; 
    const int nNumberOfSections =  
        *(unsigned short *)&g_FileContents[ulPEHeaderOffset + 0x06]; 
    unsigned long ulVirtualAddress; 
    unsigned long ulSizeOfRawData; 
    unsigned long ulPointerToRawData; 
    int i; 
 
    for (i = 0; i < nNumberOfSections; ++i) 
    { 
        // 0x0c is the offset of VirtualAddress in IMAGE_SECTION_HEADER: 
        ulVirtualAddress =  
            *(unsigned int *)&g_FileContents[ 
            ulPEHeaderOffset + 
            nSizeOfImageNtHeaders + 
            nSizeOfSectionHeader * i + 0x0c 
        ]; 
        // 0x10 is the offset of SizeOfRawData in IMAGE_SECTION_HEADER: 
        ulSizeOfRawData = 
            *(unsigned int *)&g_FileContents[ 
            ulPEHeaderOffset + 
            nSizeOfImageNtHeaders + 
            nSizeOfSectionHeader * i + 
            0x10 
        ]; 
        if (RVA >= ulVirtualAddress) 
        { 
            if ((ulVirtualAddress + ulSizeOfRawData) > RVA) 
            { 
                // 0x14 is the offset of 
                // PointerToRawData in IMAGE_SECTION_HEADER: 
                ulPointerToRawData = 
                    *(unsigned int *)&g_FileContents[ 
                    ulPEHeaderOffset + 
                    nSizeOfImageNtHeaders + 
                    nSizeOfSectionHeader * i + 
                    0x14 
                ]; 
                ulOffset = RVA - ulVirtualAddress + ulPointerToRawData; 
                break; 
            } 
        } 
    } 
 
    return ulOffset; 
} 
 
/** 
 * Must call IsPEFile() & Initialize() first! 
 */ 
int GetNTHeader( 
    /* [out] */ IMAGE_NT_HEADERS *nt_header 
) 
{ 
    int nRetResult = 0; 
    unsigned long ulPEHeaderOffset = 0; 
 
    MY_PROCESS_ERROR(nt_header); 
 
    ulPEHeaderOffset = *(unsigned long *)&g_FileContents[0x3c]; 
 
    *nt_header = *(IMAGE_NT_HEADERS *)&g_FileContents[ulPEHeaderOffset]; 
 
    nRetResult = 1; 
Exit0: 
    return nRetResult; 
} 
 
int GetImportFunctionName( 
    /* [in] */ const unsigned long ip, 
    /* [out] */ char *szFuncName 
) 
{ 
    int nRetResult = 0; 
    int nRetCode; 
    unsigned long ulFileOffset; 
    char cmd[MAXCMDSIZE]; 
    t_disasm da; 
 
    MY_PROCESS_ERROR(szFuncName); 
 
    szFuncName[0] = '\0'; 
 
    nRetCode = ReadCommand(ip, MAXCMDSIZE, cmd); 
    MY_PROCESS_ERROR(nRetCode); 
    Disasm(cmd, MAXCMDSIZE, ip, &da, DISASM_CODE); 
 
    if (C_CAL != da.cmdtype) 
        goto Exit1; 
 
    if (0 != da.jmpconst) 
    { 
        nRetCode = ReadCommand(da.jmpconst, MAXCMDSIZE, cmd); 
        MY_PROCESS_ERROR(nRetCode); 
        Disasm(cmd, da.jmpconst, da.jmpconst, &da, DISASM_CODE); 
    } 
    if (0 == da.adrconst) 
        goto Exit1; 
 
    nRetCode = ReadCommand(da.adrconst, 4, cmd); 
    MY_PROCESS_ERROR(nRetCode); 
 
    ulFileOffset = RVAToFileOffset(*(unsigned long *)&cmd); 
    MY_PROCESS_ERROR(nRetCode); 
 
    ulFileOffset += 2; 
 
    strcpy(szFuncName, &g_FileContents[ulFileOffset]); 
 
Exit1: 
    nRetResult = 1; 
Exit0: 
    return nRetResult; 
}