Here’s a C++ and Win32 class to read version information from the
resource section within EXE and DLL Windows binaries. The key functions are
GetFileVersionInfo and
VerQueryValue. The object will provide public pointers to the strings; these pointers should not be deleted, since they point straight into the allocated data block. If version information can’t be read – for example, if it’s a file with no version information – the load method will simply return
false
.
There’s room for more improvements, like tighter error checking, but it’s pretty usable:
#include <Windows.h>
#pragma comment(lib, "Version.lib")
class VersionInfo {
public:
const wchar_t *pComments, *pCompanyName, *pLegalCopyright, *pProductVersion;
VersionInfo() : _data(NULL),
pComments(NULL), pCompanyName(NULL),
pLegalCopyright(NULL), pProductVersion(NULL) { }
~VersionInfo() {
if(_data) free(_data);
}
bool load(const wchar_t *path) {
DWORD szVer = 0;
if(!(szVer = GetFileVersionInfoSize(path, &szVer)))
return false;
_data = (BYTE*)malloc(sizeof(BYTE) * szVer);
if(!GetFileVersionInfo(path, 0, szVer, _data))
return false;
UINT len = 0;
VerQueryValue(_data, L"\\StringFileInfo\\040904b0\\Comments",
(void**)&pComments, &len);
VerQueryValue(_data, L"\\StringFileInfo\\040904b0\\CompanyName",
(void**)&pCompanyName, &len);
VerQueryValue(_data, L"\\StringFileInfo\\040904b0\\LegalCopyright",
(void**)&pLegalCopyright, &len);
VerQueryValue(_data, L"\\StringFileInfo\\040904b0\\ProductVersion",
(void**)&pProductVersion, &len);
return true;
}
private:
BYTE *_data;
};
Usage example:
{
VersionInfo vi;
if(vi.load(L"C:\\Program.exe")) {
OutputDebugString(vi.pProductVersion);
OutputDebugString(vi.pComments);
}
}
Can’t be simpler than that.