zoukankan      html  css  js  c++  java
  • 简单PE类代码

    三个文件分别是类定义文件pefile.h;类实现文件pefile.cpp;类调用文件petype.cpp.
    #ifndef PE_FILE_H
    #define PE_FILE_H
    #include "windows.h"
    
    #define ISMZHEADER            (*(WORD*)File_memory == 0x5a4d)
    #define ISPEHEADER            (*(WORD*)((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c)) == 0x4550)
    #define ISPE32MAGIC            (*(WORD*)((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c) + sizeof(IMAGE_FILE_HEADER) + 4) == 0x10b)
    #define ISPE64MAGIC            (*(WORD*)((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c) + sizeof(IMAGE_FILE_HEADER) + 4) == 0x20b)
    #define ISPEROMMAGIC        (*(WORD*)((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c) + sizeof(IMAGE_FILE_HEADER) + 4) == 0x107)
    
    
    #define X_PE_32                32
    #define X_PE_64                64
    
    #define    READ_ERRO            0x0
    #define    NOT_PE_FILE            0x200
    #define    PE_FILE                0x100
    #define    PE64_FILE            0x40
    #define    PE32_FILE            0x20
    #define    ROM_IMAGE            0x10
    #define    EXE_FILE            0x8
    #define    DLL_FILE            0x4
    #define    SYS_FILE            0x2
    #define    OTHER_FILE            0x1
    
    typedef struct X_IMAGE_NT_HEADERS32 {
        DWORD Signature;
        IMAGE_FILE_HEADER FileHeader;
        IMAGE_OPTIONAL_HEADER32 OptionalHeader;
    } MX_IMAGE_NT_HEADERS32;
    
    typedef struct X_IMAGE_NT_HEADERS64 {
        DWORD Signature;
        IMAGE_FILE_HEADER FileHeader;
        IMAGE_OPTIONAL_HEADER64 OptionalHeader;
    } MX_IMAGE_NT_HEADERS64;
    
    typedef struct X_IMAGE_NT_HEADERS {
        DWORD systembit;
        union {
            MX_IMAGE_NT_HEADERS32* Ntheader32;
            MX_IMAGE_NT_HEADERS64* Ntheader64;
        };
    } MX_IMAGE_NT_HEADERS;
    
    typedef struct X_IMPORT_FUNCTION {
        union{
            DWORD Flag32;
            UINT64 Flag64;
        }uf;
        union {
            DWORD* FunOrdinal32;
            UINT64* FunOrdinal64;
            char* FunName;
        }ud;
    } MX_IMPORT_FUNCTION;
    
    typedef struct X_EXPORT_FUNCTION {
        DWORD Flag;
        union {
            DWORD FunOrdinal;
            char* FunName;
        }ud;
    } MX_EXPORT_FUNCTION;
    
    typedef struct X_RESOURCE_TYPE {
        DWORD Flag;
        union {
            DWORD ResourceID;
            char* ResourceName;
        }u;
    } MX_RESOURCE_TYPE;
    
    
    class XPEFILE
    {
    public:
        XPEFILE(char* lpFileName);
        virtual ~XPEFILE();
        int GetType();
        int GetSize();
        IMAGE_DOS_HEADER* GetDosHeader();
        IMAGE_FILE_HEADER* GetFileHeader();
        VOID GetNTHeader(MX_IMAGE_NT_HEADERS* ntheader);
        IMAGE_SECTION_HEADER* GetSectionInfo();
        int Rva2Raw(DWORD* lpaddress);
        int Raw2Rva(DWORD* lpaddress);
        int CheckImportDll(char* dllname);
        int CheckImportFun(char* dllname, MX_IMPORT_FUNCTION* importfun);
        int CheckExportFun(MX_EXPORT_FUNCTION* exportfun);
        IMAGE_RESOURCE_DATA_ENTRY* GetFileResource(MX_RESOURCE_TYPE* resourcetype1, MX_RESOURCE_TYPE* resourcetype2);
        
    
    private:
        void* File_memory;
        int File_size;
        int File_type;
    };
    
    #endif
    pefile.h
    #include "stdafx.h"
    #include "windows.h"
    #include "pefile.h"
    #include "winnls.h"
    
    XPEFILE::XPEFILE(char* strFileName)
    {
        HANDLE hfile;
        unsigned long sizehigh;
        void* lpmemory;
    
        File_memory = NULL;
        File_type = READ_ERRO;
    
        hfile = CreateFile(strFileName, GENERIC_READ|GENERIC_WRITE,FILE_SHARE_READ|FILE_SHARE_WRITE,0,OPEN_EXISTING,FILE_FLAG_SEQUENTIAL_SCAN,0);
        if (hfile != INVALID_HANDLE_VALUE)
        {
            File_size = GetFileSize(hfile, &sizehigh);
            lpmemory = LocalAlloc(LPTR,File_size);
            if(ReadFile(hfile,lpmemory,File_size,&sizehigh,0) != NULL)
            {
                File_memory = lpmemory;
            }
            CloseHandle(hfile);
        }
    }
    
    XPEFILE::~XPEFILE()
    {
        if (File_memory == NULL)
        {
            LocalFree(File_memory);
        }
    }
    
    int XPEFILE::GetSize()
    {
        return File_size;
    }
    
    int XPEFILE::GetType()
    {
        MX_IMAGE_NT_HEADERS32* ntheader32;
        MX_IMAGE_NT_HEADERS64* ntheader64;
    
        File_type = READ_ERRO;
    
        if (File_memory == NULL)
        {
            return File_type;
        }
        File_type = NOT_PE_FILE;
        if(ISMZHEADER && ISPEHEADER)
        {
            File_type = PE_FILE;
        }
        if (File_type == PE_FILE)
        {
            if (ISPE32MAGIC)
            {
                File_type = File_type | PE32_FILE;
                ntheader32 = (MX_IMAGE_NT_HEADERS32*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
                if (ntheader32->FileHeader.Characteristics & IMAGE_FILE_DLL)
                {
                    File_type = File_type | DLL_FILE;
                }
                else if ((ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_WINDOWS_CUI)||(ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_WINDOWS_GUI))
                {
                    File_type = File_type | EXE_FILE;
                }
                else if ((ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_NATIVE)||(ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_NATIVE_WINDOWS))
                {
                    File_type = File_type | SYS_FILE;
                }
            }
            if (ISPE64MAGIC)
            {
                File_type = File_type | PE64_FILE;
                ntheader64 = (MX_IMAGE_NT_HEADERS64*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
                if (ntheader64->FileHeader.Characteristics & IMAGE_FILE_DLL)
                {
                    File_type = File_type | DLL_FILE;
                }
                else if ((ntheader64->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_WINDOWS_CUI)|(ntheader64->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_WINDOWS_GUI))
                {
                    File_type = File_type | EXE_FILE;
                }
                else if ((ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_NATIVE)||(ntheader32->OptionalHeader.Subsystem & IMAGE_SUBSYSTEM_NATIVE_WINDOWS))
                {
                    File_type = File_type | SYS_FILE;
                }
            }
            if (ISPEROMMAGIC)
            {
                File_type = File_type | ROM_IMAGE;
            }
        }
        return  File_type;
    }
    
    IMAGE_DOS_HEADER* XPEFILE::GetDosHeader()
    {
        IMAGE_DOS_HEADER* dosheader;
        if (ISMZHEADER && ISPEHEADER)
        {
            dosheader = (IMAGE_DOS_HEADER*) File_memory;
            return dosheader;
        }
        return NULL;
    }
    
    VOID XPEFILE::GetNTHeader(MX_IMAGE_NT_HEADERS* ntheader)
    {
        if (ISMZHEADER && ISPEHEADER && ISPE32MAGIC)
        {
            ntheader->systembit = X_PE_32;
            ntheader->Ntheader32 = (MX_IMAGE_NT_HEADERS32*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
        }
        else if (ISMZHEADER && ISPEHEADER && ISPE64MAGIC)
        {
            ntheader->systembit = X_PE_64;
            ntheader->Ntheader64 = (MX_IMAGE_NT_HEADERS64*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
        }
        else
        {
            ntheader->systembit = NULL;
        }
    }
    
    IMAGE_SECTION_HEADER* XPEFILE::GetSectionInfo()
    {
        IMAGE_SECTION_HEADER* sectioninfo;
        MX_IMAGE_NT_HEADERS32* ntheader32;
        MX_IMAGE_NT_HEADERS64* ntheader64;
    
        if (ISMZHEADER && ISPEHEADER && ISPE32MAGIC)
        {
            ntheader32 = (MX_IMAGE_NT_HEADERS32*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
            sectioninfo = (IMAGE_SECTION_HEADER*)((BYTE*)ntheader32 + sizeof(ntheader32->Signature) + ntheader32->FileHeader.SizeOfOptionalHeader + sizeof(ntheader32->FileHeader));
            return sectioninfo;
        }    
        if (ISMZHEADER && ISPEHEADER && ISPE64MAGIC)
        {
            ntheader64 = (MX_IMAGE_NT_HEADERS64*) ((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c));
            sectioninfo = (IMAGE_SECTION_HEADER*)((BYTE*)ntheader64 + sizeof(ntheader64->Signature) + ntheader64->FileHeader.SizeOfOptionalHeader + sizeof(ntheader64->FileHeader));
            return sectioninfo;
        }
        return NULL;
    }
    
    IMAGE_FILE_HEADER* XPEFILE::GetFileHeader()
    {
        if (ISMZHEADER && ISPEHEADER)
        {
            return (IMAGE_FILE_HEADER*)((BYTE*)File_memory + *(DWORD*)((BYTE*)File_memory + 0x3c) +4);
        }
        else
        {
            return NULL;
        }
    }
    
    int XPEFILE::Rva2Raw(DWORD* lpaddress)
    {
        IMAGE_FILE_HEADER* fileheader;
        IMAGE_SECTION_HEADER* sectionheader;
        int numberofsection, secnumber1, notinsection;
        
        notinsection = 1;
        secnumber1 = 0;
        sectionheader = GetSectionInfo();
        fileheader = GetFileHeader();
        numberofsection = fileheader->NumberOfSections;
        while (secnumber1 < numberofsection)
        {
            if((sectionheader[secnumber1].VirtualAddress <= *lpaddress) && ((sectionheader[secnumber1].VirtualAddress + sectionheader[secnumber1].Misc.VirtualSize) > *lpaddress))
            {
                *lpaddress = (*lpaddress - sectionheader[secnumber1].VirtualAddress + sectionheader[secnumber1].PointerToRawData);
                if ((sectionheader[secnumber1].PointerToRawData <= *lpaddress) && ((sectionheader[secnumber1].PointerToRawData + sectionheader[secnumber1].SizeOfRawData) > *lpaddress))
                {
                    notinsection = 0;
                    secnumber1 += numberofsection;
                }
            }
            secnumber1++;
        }
        if (notinsection)
        {
            return 0;
        }
        return (secnumber1 - numberofsection);
    }
    
    int XPEFILE::Raw2Rva(DWORD* lpaddress)
    {
        IMAGE_FILE_HEADER* fileheader;
        IMAGE_SECTION_HEADER* sectionheader;
        int numberofsection, secnumber1, notinsection;
        
        notinsection = 1;
        secnumber1 = 0;
        sectionheader = GetSectionInfo();
        fileheader = GetFileHeader();
        numberofsection = fileheader->NumberOfSections;
        while (secnumber1 < numberofsection)
        {
            if((sectionheader[secnumber1].PointerToRawData <= *lpaddress) && ((sectionheader[secnumber1].PointerToRawData + sectionheader[secnumber1].SizeOfRawData) > *lpaddress))
            {
                *lpaddress = (*lpaddress - sectionheader[secnumber1].PointerToRawData + sectionheader[secnumber1].VirtualAddress);
                if ((sectionheader[secnumber1].VirtualAddress <= *lpaddress) && ((sectionheader[secnumber1].VirtualAddress + sectionheader[secnumber1].Misc.VirtualSize) > *lpaddress))
                {
                    notinsection = 0;
                    secnumber1 += numberofsection;
                }
            }
            secnumber1++;
        }
        if (notinsection)
        {
            return 0;
        }
        return (secnumber1 - numberofsection);
    }
    
    int XPEFILE::CheckImportDll(char* dllname)
    {
        MX_IMAGE_NT_HEADERS* ntheader;
        ntheader = new MX_IMAGE_NT_HEADERS;
        DWORD importaddress;
        int sectionnumber;
        IMAGE_IMPORT_DESCRIPTOR* importdesc;
        int returnvalue;
    
        
        returnvalue = 0;
        GetNTHeader(ntheader);
        if (ntheader->systembit == X_PE_32)
        {
            importaddress = ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
            sectionnumber = Rva2Raw(&importaddress);
            if (sectionnumber)
            {
                importdesc = (IMAGE_IMPORT_DESCRIPTOR*) (importaddress + (BYTE*)File_memory);
                while(importdesc->Characteristics||importdesc->FirstThunk||importdesc->ForwarderChain||importdesc->Name||importdesc->TimeDateStamp)
                {
                    DWORD namerva = (importdesc->Name);
                    if (Rva2Raw(&namerva))
                    {
                        char* b = (char*)(namerva + (BYTE*)File_memory);
                        if (!(stricmp((char*)(namerva + (BYTE*)File_memory) , dllname)))
                        {
                            returnvalue = 1;
                            break;
                        }
                    }
                    importdesc += 1;                
                }
            }
        }
        else if (ntheader->systembit == X_PE_64)
        {
            importaddress = ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
            sectionnumber = Rva2Raw(&importaddress);
            if (sectionnumber)
            {
                importdesc = (IMAGE_IMPORT_DESCRIPTOR*) (importaddress + (BYTE*)File_memory);
                while(importdesc->Characteristics||importdesc->FirstThunk||importdesc->ForwarderChain||importdesc->Name||importdesc->TimeDateStamp)
                {
                    DWORD namerva = (importdesc->Name);
                    if (Rva2Raw(&namerva))
                    {
                        if (!(stricmp((char*)(namerva + (BYTE*)File_memory) , dllname)))
                        {
                            returnvalue = 1;
                            break;
                        }
                    }
                    importdesc += 1;                
                }
            }
    
        }
        return returnvalue;
    }
    
    
    int XPEFILE::CheckImportFun(char* dllname, MX_IMPORT_FUNCTION* importfun)
    {
        MX_IMAGE_NT_HEADERS* ntheader;
        ntheader = new MX_IMAGE_NT_HEADERS;
        DWORD importaddress;
        int sectionnumber;
        IMAGE_IMPORT_DESCRIPTOR* importdesc;
        IMAGE_THUNK_DATA32* data32;
        IMAGE_THUNK_DATA64* data64;
        IMAGE_IMPORT_BY_NAME* funname;
        DWORD funoridinal;
        UINT64 funoridinal64;
        int returnvalue;
        
        
        returnvalue = 0;
        GetNTHeader(ntheader);
        if (ntheader->systembit == X_PE_32)
        {
            importaddress = ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
            sectionnumber = Rva2Raw(&importaddress);
            if (sectionnumber)
            {
                importdesc = (IMAGE_IMPORT_DESCRIPTOR*) (importaddress + (BYTE*)File_memory);
                while(importdesc->Characteristics||importdesc->FirstThunk||importdesc->ForwarderChain||importdesc->Name||importdesc->TimeDateStamp)
                {
                    if (returnvalue == 1) break;
                    DWORD namerva = (importdesc->Name);
                    if (Rva2Raw(&namerva))
                    {
                        if (!(stricmp((char*)(namerva + (BYTE*)File_memory) , dllname)))
                        {
    //                        returnvalue = 2;
                            DWORD data32rva = importdesc->OriginalFirstThunk;
                            if (!Rva2Raw(&data32rva)) continue;
                            data32 = (IMAGE_THUNK_DATA32*)(data32rva + (BYTE*)File_memory);
                            while (data32->u1.Ordinal)
                            {    
                                funoridinal = data32->u1.Ordinal;
                                if ((funoridinal & 0x80000000) != importfun->uf.Flag32)
                                {
                                    data32 += 1;
                                    continue;
                                }
                                funoridinal = data32->u1.Ordinal;
                                if ((funoridinal & 0x80000000) == 0x80000000)
                                {
                                    funoridinal = data32->u1.Ordinal;
                                    funoridinal = funoridinal &0x7fffffff;                                
                                    if (funoridinal == *(DWORD*)importfun->ud.FunOrdinal32)
                                    {
                                        returnvalue = 1;
                                        break;
                                    }
                                    data32 += 1;
                                    continue;
                                }
                                else
                                {
                                    DWORD funnamerva =(DWORD) data32->u1.AddressOfData;
                                    if (Rva2Raw(&funnamerva))
                                    {
                                        funname = (IMAGE_IMPORT_BY_NAME*)(funnamerva + (BYTE*)File_memory);
                                        if (!(stricmp((char*)funname->Name , importfun->ud.FunName)))
                                        {
                                            returnvalue = 1;
                                            break;
                                        }
                                    }
                                    data32 += 1;
                                    continue;
                                }
                            }
                            break;
                        }
                    }
                    importdesc += 1;                
                }
            }
        }
        else if (ntheader->systembit == X_PE_64)
        {
            importaddress = ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
            sectionnumber = Rva2Raw(&importaddress);
            if (sectionnumber)
            {
                importdesc = (IMAGE_IMPORT_DESCRIPTOR*) (importaddress + (BYTE*)File_memory);
                while(importdesc->Characteristics||importdesc->FirstThunk||importdesc->ForwarderChain||importdesc->Name||importdesc->TimeDateStamp)
                {
                    if (returnvalue == 1) break;
                    DWORD namerva = (importdesc->Name);
                    if (Rva2Raw(&namerva))
                    {
                        char* aa = (char*)(namerva + (BYTE*)File_memory);
                        if (!(stricmp((char*)(namerva + (BYTE*)File_memory) , dllname)))
                        {
    //                        returnvalue = 2;
                            DWORD data64rva = importdesc->OriginalFirstThunk;
                            if (!Rva2Raw(&data64rva)) continue;
                            data64 = (IMAGE_THUNK_DATA64*)(data64rva + (BYTE*)File_memory);
                            while (data64->u1.Ordinal)
                            {    
                                funoridinal64 = data64->u1.Ordinal;
                                if ((funoridinal64 & 0x8000000000000000) != importfun->uf.Flag64)
                                {
                                    data64 += 1;
                                    continue;
                                }
                                funoridinal64 = data64->u1.Ordinal;
                                if ((funoridinal64 & 0x8000000000000000) == 0x8000000000000000)
                                {
                                    funoridinal64 = data64->u1.Ordinal;
                                    funoridinal64 = funoridinal64 &0x7fffffffffffffff;                                
                                    if (funoridinal64 == *(UINT64*)importfun->ud.FunOrdinal64)
                                    {
                                        returnvalue = 1;
                                        break;
                                    }
                                    data64 += 1;
                                    continue;
                                }
                                else
                                {
                                    DWORD funnamerva =(DWORD) data64->u1.AddressOfData;
                                    if (Rva2Raw(&funnamerva))
                                    {
                                        funname = (IMAGE_IMPORT_BY_NAME*)(funnamerva + (BYTE*)File_memory);
                                        if (!(stricmp((char*)funname->Name , importfun->ud.FunName)))
                                        {
                                            returnvalue = 1;
                                            break;
                                        }
                                    }
                                    data64 += 1;
                                    continue;
                                }
                            }
                            break;
                        }
                    }
                    importdesc += 1;                
                }
            }
    
        }
        return returnvalue;
    }
    
    
    int XPEFILE::CheckExportFun(MX_EXPORT_FUNCTION* exportfun)
    {
        MX_IMAGE_NT_HEADERS* ntheader;
        ntheader = new MX_IMAGE_NT_HEADERS;
        IMAGE_EXPORT_DIRECTORY* exportdir;
    
        GetNTHeader(ntheader);
        exportdir = NULL;
        if (ntheader->systembit == X_PE_32)
        {
            DWORD namerva = (ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
            DWORD namesize = (ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size);
            if ((namerva == 0)&&(namesize == 0)) return false;
            if (Rva2Raw(&namerva))
            {
                exportdir = (IMAGE_EXPORT_DIRECTORY*)(namerva + (BYTE*)File_memory);
            }
        }
        else if (ntheader->systembit == X_PE_64)
        {
            DWORD namerva = (ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress);
            DWORD namesize = (ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size);
            if ((namerva == 0) &&(namesize == 0)) return false;
            if (Rva2Raw(&namerva))
            {
                exportdir = (IMAGE_EXPORT_DIRECTORY*)(namerva + (BYTE*)File_memory);
            }
        }
        if (exportfun->Flag == 1)
        {
            if ((exportfun->ud.FunOrdinal >= exportdir->Base) && (exportfun->ud.FunOrdinal <= exportdir->NumberOfFunctions + exportdir->Base))
            {
                return true;
            }
            return false;
        }
        if (exportfun->Flag == 0)
        {
            
            DWORD funnamerva = exportdir->AddressOfNames;
            if (Rva2Raw(&funnamerva))
            {
                DWORD* funnamelistrva = (DWORD*)(funnamerva + (BYTE*)File_memory);
                for (UINT i = 0; i < exportdir->NumberOfFunctions ; i++)
                {
                    DWORD namerva = funnamelistrva[i];
                    if (Rva2Raw(&namerva))
                    {
                        char* funname = (char*)(namerva + (BYTE*)File_memory);
                        if (!(stricmp(funname , exportfun->ud.FunName)))
                        {
                            return true;
                        }
                    }
                }
            }
        }
        return false;
    }
    
    IMAGE_RESOURCE_DATA_ENTRY* XPEFILE::GetFileResource(MX_RESOURCE_TYPE* resourcetype1, MX_RESOURCE_TYPE* resourcetype2)
    {
        IMAGE_RESOURCE_DATA_ENTRY* resourcedata;
        MX_IMAGE_NT_HEADERS* ntheader;
        ntheader = new MX_IMAGE_NT_HEADERS;
        IMAGE_RESOURCE_DIRECTORY* resourcebase;
        IMAGE_RESOURCE_DIRECTORY* resourcedir;
        char str[256];
        char* funnamestr = str;
    
        GetNTHeader(ntheader);
        //获取文件的ntheader,需要对ntheader判断其是32位还是64位pe
        if (ntheader->systembit == X_PE_32)
        {
            DWORD resourcerva= (ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress);
            DWORD resourcesize = (ntheader->Ntheader32->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].Size);
            if ((resourcerva == 0)&&(resourcesize == 0)) return false;
            if (Rva2Raw(&resourcerva))
            {
                resourcebase = (IMAGE_RESOURCE_DIRECTORY*)(resourcerva + (BYTE*)File_memory);
            }
        }
        //计算32位pe文件的资源基址
        else if (ntheader->systembit == X_PE_64)
        {
            DWORD resourcerva = (ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress);
            DWORD resourcesize = (ntheader->Ntheader64->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].Size);
            if ((resourcerva == 0) &&(resourcesize == 0)) return false;
            if (Rva2Raw(&resourcerva))
            {
                resourcebase = (IMAGE_RESOURCE_DIRECTORY*)(resourcerva + (BYTE*)File_memory);
            }
        }
        //计算64位pe文件的资源基址
        resourcedir = resourcebase;
        if (!resourcedir) return NULL;
        //以上代码分win32和win64两种情况分别获取文件可选头中数据目录表中的资源项数据,判断其不为空。
        //返回的是资源数据的raw起始地址resourcebase
        
        DWORD resourcenum = resourcedir->NumberOfIdEntries + resourcedir->NumberOfNamedEntries;
        IMAGE_RESOURCE_DIRECTORY_ENTRY* resourcedirentry = (IMAGE_RESOURCE_DIRECTORY_ENTRY*)((BYTE*)resourcedir + sizeof(IMAGE_RESOURCE_DIRECTORY));
        DWORD dataoffset = 0;
        for (UINT i = 0; i < resourcenum; i++)
        {
            if (resourcetype1->Flag == (resourcedirentry->Name & 0x80000000))
            {
                if (resourcetype1->Flag == 0x0)
                {
                    //是通过id调用
                    if (resourcetype1->u.ResourceID == resourcedirentry->Name)
                    {
                        //是要获取的资源类型
                        dataoffset = resourcedirentry->OffsetToData;
                        break;
                    }
                }
                else if (resourcetype1->Flag == 0x80000000)
                {
                    //是通过名字调用
                    IMAGE_RESOURCE_DIR_STRING_U* resourcetypename = (IMAGE_RESOURCE_DIR_STRING_U*)((BYTE*)resourcedir + (resourcedirentry->Name & 0x7FFFFFFF));
                    memset(funnamestr,0x0,0x100);
                    WideCharToMultiByte(CP_ACP,NULL,resourcetypename->NameString,resourcetypename->Length,funnamestr,0x255,0,0);
                    if (!stricmp(resourcetype1->u.ResourceName, funnamestr))
                    {
                        //是要获取的资源类型
                        dataoffset = resourcedirentry->OffsetToData;
                        break;
                    }
                }
            }
            resourcedirentry += 1;
        }
        if (!dataoffset) return NULL;
        //以上部分是匹配资源的第一级目录中也就是资源的type是否为需要获取的type,返回的数据为资源目录项指针IMAGE_RESOURCE_DIRECTORY_ENTRY.OffsetToData
    
        if (!(dataoffset & 0x80000000)) return NULL;
        //如果二级目录就是数据,不符合资源的层级结构,目前也没有发现有此类资源结构,直接返回null。
        if (dataoffset & 0x80000000)
        {
            resourcedir = (IMAGE_RESOURCE_DIRECTORY*)((unsigned char*)resourcebase + (dataoffset & 0x7fffffff));
            resourcenum = resourcedir->NumberOfIdEntries + resourcedir->NumberOfNamedEntries;
            resourcedirentry = (IMAGE_RESOURCE_DIRECTORY_ENTRY*)((BYTE*)resourcedir + sizeof(IMAGE_RESOURCE_DIRECTORY));
            dataoffset = 0;
            for (UINT i = 0; i < resourcenum; i++)
            {
                if (resourcetype2->Flag == (resourcedirentry->Name & 0x80000000))
                {
                    if (resourcetype2->Flag == 0x0)
                    {
                        //是通过id调用
                        if (resourcetype2->u.ResourceID == resourcedirentry->Name)
                        {
                            //是要获取的资源id
                            dataoffset = resourcedirentry->OffsetToData;
                            break;
                        }
                    }
                    else if (resourcetype2->Flag == 0x80000000)
                    {
                        //是通过名字调用
                        IMAGE_RESOURCE_DIR_STRING_U* resourcetypename = (IMAGE_RESOURCE_DIR_STRING_U*)((BYTE*)resourcedir + (resourcedirentry->Name & 0x7FFFFFFF));
                        memset(funnamestr,0x0,0x100);
                        WideCharToMultiByte(CP_ACP,NULL,resourcetypename->NameString,resourcetypename->Length,funnamestr,0x255,0,0);
                        if (!stricmp(resourcetype2->u.ResourceName, funnamestr))
                        {
                            //是要获取的资源id
                            dataoffset = resourcedirentry->OffsetToData;
                            break;
                        }
                    }
                }
            resourcedirentry += 1;
            }
        }
        //以上部分是匹配资源的第二级目录中也就是资源的id是否为需要获取的id,返回的数据为资源目录项指针IMAGE_RESOURCE_DIRECTORY_ENTRY.OffsetToData
    
        if (!(dataoffset & 0x80000000)) return NULL;
        //如果三级目录就是数据,不符合资源的层级结构,目前也没有发现有此类资源结构,直接返回null。
        if (dataoffset & 0x80000000)
        {
            resourcedir = (IMAGE_RESOURCE_DIRECTORY*)((unsigned char*)resourcebase + (dataoffset & 0x7fffffff));
            resourcenum = resourcedir->NumberOfIdEntries + resourcedir->NumberOfNamedEntries;
            if (resourcenum != 1) return NULL;
            IMAGE_RESOURCE_DIRECTORY_ENTRY* resourcedirentry = (IMAGE_RESOURCE_DIRECTORY_ENTRY*)((BYTE*)resourcedir + sizeof(IMAGE_RESOURCE_DIRECTORY));
            dataoffset = resourcedirentry->OffsetToData;
        }
        //以上部分是从第三级目录中读取第四级结构的偏移
    
        if ((dataoffset & 0x80000000)) return NULL;
        //如果第四级不是数据,不符合资源的层级结构,目前也没有发现有此类资源结构,直接返回null。
        resourcedata = (IMAGE_RESOURCE_DATA_ENTRY*)((unsigned char*)resourcebase + dataoffset);
        return resourcedata;
        //返回要获取的资源数据的数据结构
    }
    pefile.cpp
    // TEST.cpp : Defines the entry point for the console application.
    //
    
    #include "stdafx.h"
    #include "pefile.h"
    #include <iostream>
     
    int main(int argc, char* argv[])
    {
        int filetype;
        IMAGE_DOS_HEADER* dosheader;
        MX_IMAGE_NT_HEADERS* ntheader;    
        IMAGE_SECTION_HEADER* sectioninfo;
        DWORD address;
        int a,b,c,d,e;
        
        ntheader = new MX_IMAGE_NT_HEADERS;
        address = 0x39000;
    
        char* file = "c:\64.exe";
        char* dllname = "kernel32.dll";
        char* funname = "CreateFileA";
        MX_IMPORT_FUNCTION* impfun;
        impfun = new MX_IMPORT_FUNCTION;
        impfun->uf.Flag64 = 0;
        impfun->ud.FunName = funname;
        MX_EXPORT_FUNCTION* expfun;
        expfun = new MX_EXPORT_FUNCTION;
        expfun->Flag = 0;
        expfun->ud.FunName = funname;
        MX_RESOURCE_TYPE* resourcetype1;
        MX_RESOURCE_TYPE* resourcetype2;
        char* rtypename = "KERNEL";
    
        IMAGE_RESOURCE_DATA_ENTRY* resoursedataentry;
        resourcetype1 = new MX_RESOURCE_TYPE;
        resourcetype2 = new MX_RESOURCE_TYPE;
    
        resourcetype1->Flag = 0x80000000;
        resourcetype1->u.ResourceName = rtypename;
    
        resourcetype2->Flag = 0x0;
        resourcetype2->u.ResourceID = 231;
    
        XPEFILE pefile1(file);
        
        filetype = pefile1.GetType();
        dosheader = pefile1.GetDosHeader();
        pefile1.GetNTHeader(ntheader);
        sectioninfo = pefile1.GetSectionInfo();
    
        a=pefile1.Raw2Rva(&address);
        b=pefile1.Rva2Raw(&address);
        c=pefile1.CheckImportDll(dllname);
        d=pefile1.CheckImportFun(dllname, impfun);
        e=pefile1.CheckExportFun(expfun);
    
        resoursedataentry = pefile1.GetFileResource(resourcetype1, resourcetype2);
    
        system("pause");
        return 0;
    }
    petype.cpp
  • 相关阅读:
    ReportingServices报表管理器实现订阅
    sharepoint部署
    在sharepoint工程中添加引用
    asp:DropDownList选择事件出错
    ETL项目
    javascript refresh page 刷新页面的几种方法(转)
    innerHtml 和 innerText用法:(转载)
    用JavaScript隐藏控件的方法(转)
    JS中onpropertychange事件和onchange事件区别
    Window 对象
  • 原文地址:https://www.cnblogs.com/Mikhail/p/4509113.html
Copyright © 2011-2022 走看看