Win32API and GetFileVersionInfo

J

jim.peak

Hi all,

I searched the whole web in order to find answers to my questions
without much success.

I'm writing a script that extract the version of executable files. I
use the Win32API and the following functions:

GetFileVersionInfoSize
GetFileVersionInfo
VerQueryValue

in this order. For GetFileVersionInfoSize and GettFileVersionInfo,
everything is working fine. But I'm totally lost at using
VerQueryValue.

Here's what I'm doing:

apiGetInfoFromVersion = Win32API.new("version", "VerQueryValue",
['p','p','p','p'], 'v')
msgp = DL.malloc(DL.sizeof('P'))
infoBufferLength = DL.malloc(DL.sizeof('P'))
apiGetInfoFromVersion.call(infoVersion, "\\", msgp, infoBufferLength)


where infoVersion is the result of a previous call to
GetFileVersionInfo.

How do I retrieve the information in msgp? I've tried many ways,
without any success.
(Information about VerQueryValue:
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/w
inui/windowsuserinterface/resources/versioninformation/versioninformationreference/versioninformationfunctions/verqueryvalue.asp
)

Thank you in advance.
 
P

Park Heesob

Hi,
----- Original Message -----
From: <[email protected]>
Newsgroups: comp.lang.ruby
To: "ruby-talk ML" <[email protected]>
Sent: Tuesday, October 18, 2005 9:26 PM
Subject: Win32API and GetFileVersionInfo

Hi all,

I searched the whole web in order to find answers to my questions
without much success.

I'm writing a script that extract the version of executable files. I
use the Win32API and the following functions:

GetFileVersionInfoSize
GetFileVersionInfo
VerQueryValue

in this order. For GetFileVersionInfoSize and GettFileVersionInfo,
everything is working fine. But I'm totally lost at using
VerQueryValue.

Here's what I'm doing:

apiGetInfoFromVersion = Win32API.new("version", "VerQueryValue",
['p','p','p','p'], 'v')
msgp = DL.malloc(DL.sizeof('P'))
infoBufferLength = DL.malloc(DL.sizeof('P'))
apiGetInfoFromVersion.call(infoVersion, "\\", msgp, infoBufferLength)


where infoVersion is the result of a previous call to
GetFileVersionInfo.

How do I retrieve the information in msgp? I've tried many ways,
without any success.
You can use memcpy.
Thank you in advance.

Here is my version without dl

require 'Win32API'

VS_FIXEDFILEINFO = Struct.new("VS_FIXEDFILEINFO",
:Signature,
:StrucVersion,
:FileVersionMS,
:FileVersionLS,
:productVersionMS,
:productVersionLS,
:FileFlagsMask,
:FileFlags,
:FileOS,
:FileType,
:FileSubtype,
:FileDateMS,
:FileDateLS)

file = "c:\\work\\xxx.dll"

apiGetFileVersionInfo = Win32API.new("version",
"GetFileVersionInfo",['P','L','L','P'], 'L')
apiGetFileVersionInfoSize = Win32API.new("version",
"GetFileVersionInfoSize",['P','P'], 'L')
apiGetInfoFromVersion = Win32API.new("version",
"VerQueryValue",['P','P','P','P'], 'L')
memcpy = Win32API.new('msvcrt','memcpy','PPL','P')

size = apiGetFileVersionInfoSize.call(file,nil)
infoVersion = "\0" * size
apiGetFileVersionInfo.call(file,0,size,infoVersion)
lplpBuffer = "\0" * 4
pLen = "\0" * 4
apiGetInfoFromVersion.call(infoVersion,"\\",lplpBuffer,pLen)
lpBuffer = lplpBuffer.unpack("L")[0]
bufSize = pLen.unpack("L*")[0]
rbuf = "\0" * bufSize
memcpy.call(rbuf,lpBuffer,bufSize)
vs_fixedfileinfo = VS_FIXEDFILEINFO.new(*rbuf.unpack("L*"))


HTH,

Park Heesob
 
J

jim.peak

Wow, thanks a lot, that'll be very useful!

Jim.
jim.peak... said:
VerQueryValue.

This may be similar to Park Heesob's solution since I learned
the memcpy trick from him a while ago.
(It prints the version number of the 'fname')

#----------------------------
require 'Win32API'

fname = 'D:\ruby\bin\ruby.exe' # <------- CHANGE --- ###

GetFileVersionInfoSize = Win32API.new('Version', 'GetFileVersionInfoSize', 'PP', 'L')
GetFileVersionInfo = Win32API.new('Version', 'GetFileVersionInfo', 'PLLP', 'L')
VerQueryValue = Win32API.new('Version', 'VerQueryValue', 'PPPP', 'I')
memcpy = Win32API.new('msvcrt', 'memcpy', 'PLL', 'L')

addr = "\0"*4
v_info_sz = GetFileVersionInfoSize.call(fname, addr)

raise 'GFVIS failed' if v_info_sz == 0

v_info = "\0"*v_info_sz
GetFileVersionInfo.call(fname, 0, v_info_sz, v_info)

v_val_sz = "\0"*4
VerQueryValue.call(v_info, '\\', addr, v_val_sz)

v_bufsz = v_val_sz.unpack('L')[0]
v_buf = "\0" * v_bufsz
v_src = addr.unpack('L')[0]
ret = memcpy.call(v_buf, v_src, v_bufsz)
raise 'memcpy failed' if ret == 0

raise 'Oops' unless v_buf[0, 4].unpack('L')[0] == 0xFEEF04BD

p v_buf[0x08, 8].unpack('S*').values_at(1,0,3,2) #-> [1, 8, 2, 0]
p v_buf[0x10, 8].unpack('S*').values_at(1,0,3,2) #-> [1, 8, 2, 0]
#----------------------------


daz
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,537
Members
45,021
Latest member
AkilahJaim

Latest Threads

Top