Javaを使用してファイルバージョン(exe、dll)を取得する

私はそのような問題に遭遇しました-Javaでファイルバージョン(exeとdll)を取得する方法。 実際、標準の標準的な方法でこれを決定することはできませんが、サイズ、最終変更の日付、およびファイルの他のプロパティのみを見つけることができます。 これはここで説明されます

フォーラムをざっと調べてすべてをうまく調べた後、そのような2つのソリューション、 JNIJNAを見つけました。 C ++では特別なdllを作成したくなかったため、javaですべてを解決し、version.dll(C:\ WINDOWS \ system32)に直接アクセスしたかったため、2番目のオプションで停止しました。

その結果、ソリューションはそのようなバンドルGetFileVersionInfo - GetFileVersionInfoSize - VerQueryValueに要約されます。 VerQueryValue関数を理解するのに長い時間がかかりました-難しさは、ファイルのバージョンが言語依存であり、LANGANDCODEPAGEをトリッキーな方法で取得する必要があることでした。 結果はこのクラスです:







package upload;



import com.sun.jna.Native;

import com.sun.jna.Pointer;

import com.sun.jna.ptr.IntByReference;

import com.sun.jna.ptr.PointerByReference;

import com.sun.jna.win32.StdCallLibrary;

import java.io.IOException;



/**

*

* @author samozvanka

*/

public class Win32GetFileInformation

{

//+ declare before using

private static byte [] Hexhars = "«0123456789abcdef" .getBytes();



public String FileVersion;

private String LanguageCodePage;

private PointerByReference InfoData;



public interface Win32VersionDLL extends StdCallLibrary

{

Win32VersionDLL INSTANCE = (Win32VersionDLL) Native.loadLibrary(

"Version" , Win32VersionDLL. class );



Integer GetFileVersionInfoSizeA( String FilePath, IntByReference Handle);



Boolean GetFileVersionInfoA( String FilePath, int Handle, int InfoSize,

PointerByReference InfoData);



Boolean VerQueryValueA(PointerByReference InfoData,

String VersionInformation, PointerByReference VersionData,

IntByReference DataSize);

}



public void Win32GetFileInformation( String FilePath) throws IOException

{

IntByReference unusedParam = new IntByReference();



int infoSize = Win32VersionDLL.INSTANCE.GetFileVersionInfoSizeA(FilePath, unusedParam);

if (infoSize == 0)

{

throw new IOException( "File does not exist or has no information." );

}



this .InfoData = new PointerByReference();



Boolean success = Win32VersionDLL.INSTANCE.GetFileVersionInfoA

(

FilePath,

unusedParam.getValue(),

infoSize,

this .InfoData

);



//+ Assert(success, "GetFileVersionInfoA in Win32GetFileInformation is failed")



PointerByReference versionDataByRef = new PointerByReference();

IntByReference dataSize = new IntByReference();

Pointer versionDataPointer = null ;



// Retrieve the language information

success = Win32VersionDLL.INSTANCE.VerQueryValueA

(

this .InfoData,

"\\VarFileInfo\\Translation" ,

versionDataByRef,

dataSize

);



//+ Assert(success, "VerQueryValueA in Win32GetFileInformation is failed")



System. out .println( "DataSize.getValue() = " + dataSize.getValue());



versionDataPointer = versionDataByRef.getValue();

byte [] codePageBytes = versionDataPointer.getByteArray(0, dataSize.getValue());

byte BSwap;

// swap 0<->1 and 2<->3

BSwap = codePageBytes[1];

codePageBytes[1] = codePageBytes[0];

codePageBytes[0] = BSwap;

BSwap = codePageBytes[3];

codePageBytes[3] = codePageBytes[2];

codePageBytes[2] = BSwap;

// got 1,0,3,2



this .LanguageCodePage = decode(codePageBytes).toUpperCase();



//// Retrieve file information

this .FileVersion = QueryValue( "FileVersion" );



System. out .println( "FileVersion = " + this .FileVersion);



}



private String QueryValue( String ValueName)

{

IntByReference dataSize = new IntByReference();

PointerByReference versionDataByRef = new PointerByReference();

Pointer versionDataPointer = null ;

Boolean success = Win32VersionDLL.INSTANCE.VerQueryValueA

(

this .InfoData,

"\\StringFileInfo\\" + this.LanguageCodePage + " \\ " + ValueName, //"

versionDataByRef,

dataSize

);



//+ Assert(success, "VerQueryValueA in Win32GetFileInformation is failed")



versionDataPointer = versionDataByRef.getValue();

if (versionDataPointer == null )

{

return "" ;

}

else

{

versionDataPointer = versionDataByRef.getValue();

return versionDataPointer.getString();

}

}



private static String decode( byte [] encodedString)

{

StringBuilder result = new StringBuilder (2 * encodedString.length);



for ( int i = 0; i < encodedString.length; i++)

{

int v = encodedString[i] & 0xff;



result.append(( char ) Hexhars[v >> 4]);

result.append(( char ) Hexhars[v & 0xf]);

}



return result.toString();

}

}



* This source code was highlighted with Source Code Highlighter .








突然誰かが重宝します。 そして、これの他の単純な実装がある場合、私はそれらを知りたいです。



All Articles