2013年8月27日火曜日

Windows OSが 64bit かどうか判定する。

64bit の Windows で実行中のアプリケーションから OS が 64bit かどうか判定する。

手順は

 http://msdn.microsoft.com/en-us/library/windows/desktop/ms684139(v=vs.85).aspx



 http://www.delphigroups.info/2/5/795988.html

等が見つかります。

が、これは 32bit アプリケーションが Windows の WOW64 上で実行されているかどうかの判定しかできません。

実行中のアプリケーションが64bitの場合 kernel32 の IsWow64Process は False を返します。

当然と言えば当然なのだけどしばらく悩みました。

Lazarus に移植した古臭い起動環境判定のユニットの一部の関数が 32bit としか返さないので、なぜなのかと読み返したらそういうことでした。

ということで、IsWow64Process に頼って OS が 64bit かどうか判定しているような場合は問題となります。

Lazarus,FPC みたいにクロスプラットフォーム対応で、Windows でも 32bit 版と64bit版が用意されているような開発環境では配慮したほうが良さそうです。

で、 64bit かどうか判定するには SizeOf で pointer 等のサイズを求めればOKのようです。
コンパイラオプションでサイズが変わる可能性がある型は避けたほうが良いように思います。

case SizeOf(pointer) of
 4: Result:='32bit';
 8: Result:='64bit';
end;

ちなみに各環境での結果は以下の通りです。

アプリ, OS, SizeOf結果, IsWOW64Process
32bit アプリケーション, 32bit Windows OS : SizeOf(pointer)=4, IsWow64Process=False
32bit アプリケーション, 64bit Windows OS : SizeOf(pointer)=4, IsWow64Process=True
64bit アプリケーション, 32bit Windows OS : ダイアログでエラー表示。起動しない。
64bit アプリケーション, 64bit Windows OS : SizeOf(pointer)=8, IsWow64Process=False

普段から SizeOf で型のサイズを使ってバッファのサイズを計算する習慣というのが Pascalの世界ではあちこちで推奨されていたはずなので判定の意味はないかもしれません。

判定などせずともコンパイラを変えればそのまま動くはずです。
リソースから32bit用、64bit用、それぞれのデータファイルを環境に応じて出力するような場合とか、API切り替えたり、OS環境そのものを表示する場合ぐらいにしか困ることは無いのかもしれません。


旧式からの移植は危険かもしれません。
たまたま動いているだけな気がします。
こんなのは氷山の一角なのでしょうね。


0 件のコメント:

コメントを投稿