判斷某exe尾碼的檔案是否為PE格式

來源:互聯網
上載者:User

如何判斷PE檔案合法,主要就是兩個地方,頭為"MZ"簽名,跟著DOS頭部的就是"PE"簽名,任何標準的PE檔案都會包含這兩個簽名。如下這段代碼所示,這是一個判斷是否為合法PE檔案的API。

通過檔案對應實現PE檔案內容的讀取。

BOOL IsValidPEFile( CString strPathName ){    if ( ! PathFileExists( strPathName ) )        return FALSE;    HANDLE hFile = CreateFile( strPathName,     GENERIC_READ,     FILE_SHARE_READ,     NULL,     OPEN_EXISTING,     FILE_ATTRIBUTE_NORMAL,     NULL );    if ( hFile == INVALID_HANDLE_VALUE ) {        TRACE1( "Failed To Open File %s !/n", strPathName );        return FALSE;    }    HANDLE hMMFile = CreateFileMapping( hFile, NULL, PAGE_READONLY, 0, 0, NULL );    if ( hMMFile == INVALID_HANDLE_VALUE ) {        CloseHandle( hFile );        return FALSE;    }    LPVOID pvMem = MapViewOfFile( hMMFile, FILE_MAP_READ, 0, 0, 0 );    if ( ! pvMem ) {        CloseHandle( hMMFile );        CloseHandle( hFile );        return FALSE;    }    if ( *( USHORT* ) pvMem != IMAGE_DOS_SIGNATURE ) {        UnmapViewOfFile( pvMem );        CloseHandle( hMMFile );        CloseHandle( hFile );        return FALSE;    }    if ( *( ( DWORD* ) ( ( PBYTE ) pvMem + ( ( PIMAGE_DOS_HEADER ) pvMem )->e_lfanew ) ) != IMAGE_NT_SIGNATURE ) {        UnmapViewOfFile( pvMem );        CloseHandle( hMMFile );        CloseHandle( hFile );        return FALSE;    }    UnmapViewOfFile( pvMem );    CloseHandle( hMMFile );    CloseHandle( hFile );    return TRUE;}

這段代碼實現了對PE檔案合法性的判斷。
  但是,我還希望對應用程式的類型作一個更加徹底的判斷,如何知道應用程式是基於視窗形式的還是基於命令列形式的程式呢?
其實PE檔案中早已經包含了這種程式類型的標誌!這個標誌包含在PE檔案的頭部IMAGE_NT_HEADER的結構中的 IMAGE_OPTIONAL_HEADER的Sybsystem記錄! 看看"winnt.h"中對Sybsystem的宏定義。

#define IMAGE_SUBSYSTEM_UNKNOWN 0 // Unknown subsystem.#define IMAGE_SUBSYSTEM_NATIVE 1 // Image doesn't require a subsystem.#define IMAGE_SUBSYSTEM_WINDOWS_GUI 2 // Image runs in the Windows GUI subsystem.#define IMAGE_SUBSYSTEM_WINDOWS_CUI 3 // Image runs in the Windows character System#define IMAGE_SUBSYSTEM_OS2_CUI 5 // image runs in the OS/2 character subsystem.#define IMAGE_SUBSYSTEM_POSIX_CUI 7 // image runs in the Posix character subsystem.#define IMAGE_SUBSYSTEM_NATIVE_WINDOWS 8 // image is a native Win9x driver.#define IMAGE_SUBSYSTEM_WINDOWS_CE_GUI 9 // Image runs in the Windows CE subsystem.

  通過這些定議則可以輕易的判斷應用程式是何種形式的,當Subsystem的值為IMAGE_SUBSYSTEM_WINDOWS_GUI的時候,則可以確定這個程式是基於圖形介面的,當它的值為IMAGE_SUBSYSTEM_WINDOWS_CUI的時候可以確定它為命令列的程式了。 核心的代碼如下:

BOOL IsWindowsApp( CString strPathName )
{
    if ( ! PathFileExists( strPathName ) )
        return FALSE;
    // 根據 PE 簽名判斷當前檔案是否合法的 可攜式執行檔
    HANDLE hFile = CreateFile( strPathName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL );
    if ( hFile == INVALID_HANDLE_VALUE ) {
        TRACE1( "Failed To Open File %s !/n", strPathName );
        return FALSE;
    }
    HANDLE hMMFile = CreateFileMapping( hFile, NULL, PAGE_READONLY, 0, 0, NULL );
    if ( hMMFile == INVALID_HANDLE_VALUE ) {
        CloseHandle( hFile );
        return FALSE;
    }
    LPVOID pvMem = MapViewOfFile( hMMFile, FILE_MAP_READ, 0, 0, 0 );
    if ( ! pvMem ) {
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    // 是否包含有 DOS 簽名
    if ( *( USHORT* ) pvMem != IMAGE_DOS_SIGNATURE ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    // 是否包含有 NT 簽名
    if ( *( ( DWORD* ) ( ( PBYTE ) pvMem + ( ( PIMAGE_DOS_HEADER ) pvMem )->e_lfanew ) ) != IMAGE_NT_SIGNATURE ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    LPVOID pvOptionalHeader =  ( PBYTE ) pvMem + ( ( PIMAGE_DOS_HEADER ) pvMem )->e_lfanew + sizeof( DWORD ) + sizeof( IMAGE_FILE_HEADER );
    IMAGE_OPTIONAL_HEADER ioh;
    CopyMemory( & ioh, pvOptionalHeader, sizeof( IMAGE_OPTIONAL_HEADER ) );
    if ( ioh.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_GUI ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );   
        return TRUE;
    }
    return FALSE;
}
BOOL IsCosoleApp( CString strPathName )
{
    if ( ! PathFileExists( strPathName ) )
        return FALSE;
    // 根據 PE 簽名判斷當前檔案是否合法的 可攜式執行檔
    HANDLE hFile = CreateFile( strPathName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL );
    if ( hFile == INVALID_HANDLE_VALUE ) {
        TRACE1( "Failed To Open File %s !/n", strPathName );
        return FALSE;
    }
    HANDLE hMMFile = CreateFileMapping( hFile, NULL, PAGE_READONLY, 0, 0, NULL );
    if ( hMMFile == INVALID_HANDLE_VALUE ) {
        CloseHandle( hFile );
        return FALSE;
    }
    LPVOID pvMem = MapViewOfFile( hMMFile, FILE_MAP_READ, 0, 0, 0 );
    if ( ! pvMem ) {
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    // 是否包含有 DOS 簽名
    if ( *( USHORT* ) pvMem != IMAGE_DOS_SIGNATURE ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    // 是否包含有 NT 簽名
    if ( *( ( DWORD* ) ( ( PBYTE ) pvMem + ( ( PIMAGE_DOS_HEADER ) pvMem )->e_lfanew ) ) != IMAGE_NT_SIGNATURE ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );
        return FALSE;
    }
    LPVOID pvOptionalHeader =  ( PBYTE ) pvMem + ( ( PIMAGE_DOS_HEADER ) pvMem )->e_lfanew + sizeof( DWORD ) + sizeof( IMAGE_FILE_HEADER );
    IMAGE_OPTIONAL_HEADER ioh;
    CopyMemory( & ioh, pvOptionalHeader, sizeof( IMAGE_OPTIONAL_HEADER ) );
    if ( ioh.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_CUI ) {
        UnmapViewOfFile( pvMem );
        CloseHandle( hMMFile );
        CloseHandle( hFile );   
        return TRUE;
    }
    return FALSE;
}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.