Почему моя структура Fiddle заполнена мусором?
Я пытаюсь преобразовать очень простой вызов C Win32 API в Ruby с использованием Fiddle, и я не добиваюсь большого успеха.
Первые два вызова метода работают безупречно, хотя, когда я добираюсь до вызова, который заполняет структуру, у меня возникают некоторые трудности, так как кажется, что структура заполняется данными мусора:
Вот соответствующий код C:
DWORD dwHandle, dwLen;
LPVOID lpData;
UINT BufLen;
VS_FIXEDFILEINFO *pFileInfo;
LPTSTR LibName = L"C:\\windows\\notepad.exe";
dwLen = GetFileVersionInfoSize(LibName, &dwHandle);
if(dwLen != 0)
{
lpData = malloc(dwLen);
if (GetFileVersionInfo(LibName, NULL, &dwLen, lpData))
{
if (VerQueryValue(lpData, L"\\", (LPVOID)&pFileInfo, (PUINT)&BufLen))
{
printf("ProductVersion: %d.%d.%d.%d\n", HIWORD(pFileInfo->dwProductVersionMS), LOWORD(pFileInfo->dwProductVersionLS), HIWORD(pFileInfo->dwFileVersionLS), LOWORD(pFileInfo->dwFileVersionLS));
printf("FileVersion: %d.%d.%d.%d\n", HIWORD(pFileInfo->dwFileVersionMS), LOWORD(pFileInfo->dwFileVersionMS), HIWORD(pFileInfo->dwFileVersionLS), LOWORD(pFileInfo->dwFileVersionLS));
}
}
}
И вот моя попытка конвертировать C в Ruby:
require 'fiddle/import'
module Version
extend Fiddle::Importer
dlload 'version'
typealias 'HANDLE', 'void*'
typealias 'LPVOID', 'void*'
typealias 'LPCVOID', 'const void*'
typealias 'LPDWORD', 'int*'
typealias 'HWND', 'HANDLE'
typealias 'LPCSTR', 'const char*'
typealias 'LPCWSTR', 'const wchar_t*'
typealias 'UINT', 'unsigned int'
typealias 'PUINT', 'unsigned int*'
typealias 'DWORD', 'unsigned long'
typealias 'BOOL', 'int'
extern 'DWORD GetFileVersionInfoSize(LPCSTR, LPDWORD)'
extern 'BOOL GetFileVersionInfo(LPCSTR, DWORD, DWORD, LPVOID)'
extern 'BOOL VerQueryValue(LPCVOID, LPCSTR, LPVOID, PUINT)'
VS_FIXEDFILEINFO = struct [
'DWORD dwSignature',
'DWORD dwStrucVersion',
'DWORD dwFileVersionMS',
'DWORD dwFileVersionLS',
'DWORD dwProductVersionMS',
'DWORD dwProductVersionLS',
'DWORD dwFileFlagsMask',
'DWORD dwFileFlags',
'DWORD dwFileOS',
'DWORD dwFileType',
'DWORD dwFileSubtype',
'DWORD dwFileDateMS',
'DWORD dwFileDateLS'
]
end
dwHandle = Fiddle::NULL
dwLen = Version::GetFileVersionInfoSize "C:\\windows\\system32\\notepad.exe", dwHandle
lpData = Fiddle::Pointer.malloc(dwLen)
Version::GetFileVersionInfo "C:\\windows\\notepad.exe", 0, dwLen, lpData
BufLen = Fiddle::NULL
pFileInfo = Version::VS_FIXEDFILEINFO.malloc()
success = Version::VerQueryValue lpData, "\\", pFileInfo, BufLen.ref
puts "pFileInfo: #{pFileInfo.dwSignature}"
К несчастью, pFileInfo.dwSignature
кажется, меняется каждый раз, указывая, что он заполняется мусорными данными (как ни странно, он равен нулю до VerQueryValue
вызов). pFileInfo.dwSignature
значение всегда должно быть 0xFEEF04BD
или в десятичном виде 4277077181
,
Есть мысли о том, что здесь происходит?
Спасибо!