代码之家  ›  专栏  ›  技术社区  ›  user15071

告诉给定二进制文件(exe或dll)是x86、x64还是IA64的win32 api

  •  5
  • user15071  · 技术社区  · 15 年前

    我试图找到一种程序化的方法来判断二进制文件是x86、x64还是IA64。

    平台:窗户。 语言:C/C++。

    背景:在尝试加载第三方DLL之前,我需要找出它的位。

    感谢任何指点。

    3 回复  |  直到 11 年前
        1
  •  12
  •   Community CDub    7 年前

    对于exes

    使用 GetBinaryType(...)

    Here is same question 对于成人EXE。

    对于dll(和exes)

    使用 ImageNtHeader(...) 要获取文件的PE数据,然后检查image_file_header.machine字段。

    Here is some code 我发现使用谷歌代码搜索

    没有清理和错误检查

    // map the file to our address space
    // first, create a file mapping object
    hMap = CreateFileMapping( 
      hFile, 
      NULL,           // security attrs
      PAGE_READONLY,  // protection flags
      0,              // max size - high DWORD
      0,              // max size - low DWORD      
      NULL );         // mapping name - not used
    
    // next, map the file to our address space
    void* mapAddr = MapViewOfFileEx( 
      hMap,             // mapping object
      FILE_MAP_READ,  // desired access
      0,              // loc to map - hi DWORD
      0,              // loc to map - lo DWORD
      0,              // #bytes to map - 0=all
      NULL );         // suggested map addr
    
    peHdr = ImageNtHeader( mapAddr );
    
        2
  •  2
  •   Aaronontheweb    11 年前

    我开放源码 a project on Github that checks for VC++ redistributable DLLs 具体来说,我根据Shay的答案中的函数创建了一个代码片段, successfully finds, loads, and inspects DLLs for x86 / x64 compatibility .

    完整代码段如下:

    /******************************************************************
    Function Name:  CheckProductUsingCurrentDirectory
    Description:    Queries the current working directory for a given binary.
    Inputs:         pszProductFolderToCheck - the product name to look up.
    pBinaryArchitecture - the desired processor architecture
    of the binary (x86, x64, etc..).
    Results:        true if the requested product is installed
    false otherwise
    ******************************************************************/
    bool CheckProductUsingCurrentDirectory(const LPCTSTR pszProductBinaryToCheck, Architecture pBinaryArchitecture){
            bool bFoundRequestedProduct = false;
    
            //Get the length of the buffer first
            TCHAR currentDirectory[MAX_PATH];
            DWORD currentDirectoryChars = GetCurrentDirectory(MAX_PATH, currentDirectory);
    
            //exit if couldn't get current directory
            if (currentDirectoryChars <= 0) return bFoundRequestedProduct;
    
            TCHAR searchPath[MAX_PATH];
            //exit if we couldn't combine the path to the requested binary
            if (PathCombine(searchPath, currentDirectory, pszProductBinaryToCheck) == NULL) return bFoundRequestedProduct;
    
            WIN32_FIND_DATA FindFileData;
            HANDLE hFind= FindFirstFile(searchPath, &FindFileData);
    
            //exit if the binary was not found
            if (hFind == INVALID_HANDLE_VALUE) return bFoundRequestedProduct;
    
            HANDLE hFile = CreateFile(searchPath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_READONLY, NULL);
            if (hFile == INVALID_HANDLE_VALUE) goto cleanup;
    
            HANDLE hMapping = CreateFileMapping(hFile, NULL, PAGE_READONLY | SEC_IMAGE, 0, 0, pszProductBinaryToCheck);
            if (hMapping == INVALID_HANDLE_VALUE) goto cleanup;
    
            LPVOID addrHeader = MapViewOfFile(hMapping, FILE_MAP_READ, 0, 0, 0);
            if (addrHeader == NULL) goto cleanup; //couldn't memory map the file
    
            PIMAGE_NT_HEADERS peHdr = ImageNtHeader(addrHeader);
            if (peHdr == NULL) goto cleanup; //couldn't read the header
    
            //Found the binary, AND its architecture matches. Success!
            if (peHdr->FileHeader.Machine == pBinaryArchitecture){
                    bFoundRequestedProduct = true;
            }
    
    cleanup: //release all of our handles
            FindClose(hFind);
            if (hFile != INVALID_HANDLE_VALUE)
                    CloseHandle(hFile);
            if (hMapping != INVALID_HANDLE_VALUE)
                    CloseHandle(hMapping);
            return bFoundRequestedProduct;
    }
    

    这个问题和Shay的回答在我创建这个项目的时候对我很有帮助,所以我想我会把这个项目发布到这里。

        3
  •  0
  •   Community CDub    7 年前

    您可以自己检查PE头来读取 IMAGE_FILE_MACHINE 字段。 Here's a C# implementation 这不应该太难适应C++。