windows – ruby win32apistructs(VerQueryValue)

我试图使用 win32-api library调用标准的Win32 API函数来获取文件版本信息. 3 version.dll函数是GetFileVersionInfoSize,GetFileVersionInfo和VerQueryValue.然后我调用kernel32.dll中的RtlMoveMemory来获取VS_FIXEDFILEINFO结构的副本(请参阅Microsoft文档:

我试图使用
win32-api library调用标准的Win32 API函数来获取文件版本信息.

3 version.dll函数是GetFileVersionInfoSize,GetFileVersionInfo和VerQueryValue.然后我调用kernel32.dll中的RtlMoveMemory来获取VS_FIXEDFILEINFO结构的副本(请参阅Microsoft文档:http://msdn.microsoft.com/en-us/library/ms646997(VS.85).aspx).

我从使用VB看到的一个例子中得出:http://support.microsoft.com/kb/139491.

我的问题是最终返回的数据似乎与预期的结构不匹配,实际上它甚至没有返回一致的值.我怀疑数据在某些时候会被破坏,可能是在VerQueryValue或RtlMoveMemory中.

这是代码:

GetFileVersionInfoSize = Win32::API.new('GetFileVersionInfoSize','PP','I','version.dll')
GetFileVersionInfo = Win32::API.new('GetFileVersionInfo','PIIP','version.dll')
VerQueryValue = Win32::API.new('VerQueryValue','PPPP','version.dll')
RtlMoveMemory = Win32::API.new('RtlMoveMemory','PPI','V','kernel32.dll')

buf = [0].pack('L')
version_size = GetFileVersionInfoSize.call(myfile + "\0",buf)
raise Exception.new  if version_size == 0 #TODO

version_info = 0.chr * version_size
version_ok = GetFileVersionInfo.call(file,version_size,version_info)
raise Exception.new if version_ok == 0   #TODO

addr = [0].pack('L')
size = [0].pack('L')
query_ok = VerQueryValue.call(version_info,"\\\0",addr,size)
raise Exception.new if query_ok == 0        #TODO

# note that at this point,size == 4 -- is that right?

fixed_info = Array.new(13,0).pack('L*')
RtlMoveMemory.call(fixed_info,fixed_info.length)

# fixed_info.unpack('L*')  #=> seemingly random data,usually only the first two dwords' worth and the rest 0.

这是我工作的完整代码,以防其他人正在寻找这样的功能.

返回一个包含四个产品/文件版本号部分的数组(即,在dll文件属性窗口中称为“文件版本”):

def file_version ref,options = {}
  options = {:path => LIBDIR,:extension => 'dll'}.merge(options)
  begin
      file = File.join(ROOT,options[:path],"#{ref}.#{options[:extension]}").gsub(/\//,"\\")
      buf = [0].pack('L')
      version_size = GetFileVersionInfoSize.call(file + "\0",buf)
      raise Exception.new    if version_size == 0 #TODO

      version_info = 0.chr * version_size
      version_ok = GetFileVersionInfo.call(file,version_info)
      raise Exception.new if version_ok == 0        #TODO

      addr = [0].pack('L')
      size = [0].pack('L')
      query_ok = VerQueryValue.call(version_info,size)
      raise Exception.new if query_ok == 0        #TODO

      fixed_info = Array.new(18,0).pack('LSSSSSSSSSSLLLLLLL')
      RtlMoveMemory.call(fixed_info,addr.unpack('L')[0],fixed_info.length)

      fixed_info.unpack('LSSSSSSSSSSLLLLLLL')[5..8].reverse

  rescue
        []
  end
end

作者: dawei

【声明】:永州站长网内容转载自互联网,其相关言论仅代表作者个人观点绝非权威,不代表本站立场。如您发现内容存在版权问题,请提交相关链接至邮箱:bqsm@foxmail.com,我们将及时予以处理。

为您推荐

联系我们

联系我们

0577-28828765

在线咨询: QQ交谈

邮箱: xwei067@foxmail.com

工作时间:周一至周五,9:00-17:30,节假日休息

返回顶部