7-Zip 16.00で特定のexeファイルを開くとクラッシュする件について調べた

7-Zip

記事をご覧の方へ

現在vivibit.netは旧システムからの移行に伴い修正作業を行っています。
表示上の問題や軽微なエラーが発生する可能性がありますが、ご利用に問題はありません。
また、現在一部ファイルのダウンロードができなくなっています。
順次対応予定ですが、お急ぎの場合や問題を発見された場合はコメント欄でご指摘いただけると助かります。


7-Zip 16.00で特定のexeファイルを展開しようとした際にクラッシュするという情報がsourceforgeのフォーラムで報告されていたので気になって調べてみた。

7-Zip / Discussion / Open Discussion:7-zip 16.00 64-bit crash

現象

https://downloadmirror.intel.com/10884/a08/INF_allOS_9.1.2.1008_PV.exeを開くと16.00の64-bit版のみEXCEPTION_ACCESS_VIOLATION (c0000005) の例外が発生する。
[code]
アプリケーション名: 7zFM.exe
アプリケーションのバージョン: 16.0.0.0
アプリケーションのタイムスタンプ: 5731aa47
障害モジュールの名前: 7z.dll
障害モジュールのバージョン: 16.0.0.0
障害モジュールのタイムスタンプ: 5731aba0
例外コード: c0000005
例外オフセット: 0000000000040713
[/code]

一つ前のバージョンである15.04の64-bit版ではクラッシュせずに展開できる。

32-bit版では「要求された量のメモリを割り当てることができません」というメッセージが表示されて開くことができないが、クラッシュはしない。

原因

CPP/7zip/Archive/PeHandler.cppの変更が原因であることがわかった。

PEファイルのリソースセクションの処理で、
セクションのVirtualSize(VSize)とSizeOfRawData(PSize)の小さいほうのサイズで確保されたバッファに対して、バッファの走査を行う際の境界判定の箇所のみSizeOfRawData(PSize)に変えたことが原因。

これによって、VirtualSize(VSize)よりSizeOfRawData(PSize)が大きいリソースセクションを持つPEファイル(exe)を開いた際にクラッシュする場合がある。

該当行は以下の画像を参照。

7zip_pe_bug

修正

バッファの領域外の参照が原因であり、特に危険な脆弱性ということはないと思われるので本家の修正を待てばよいと思う。
ただし、16.00には2件の脆弱性修正も含まれているため古いバージョンを使用するべきではない。

一応、以下のパッチを当て、ビルドするとクラッシュしなくなることは確認できた。

[code]
— PeHandler.cpp 2016-01-14 16:49:31.000000000 +0900
+++ PeHandler_fix.cpp 2016-05-16 01:50:01.000000000 +0900
@@ -1898,7 +1898,7 @@ static bool ParseVersion(const Byte *p,
HRESULT CHandler::OpenResources(unsigned sectionIndex, IInStream *stream, IArchiveOpenCallback *callback)
{
const CSection &sect = _sections[sectionIndex];
– const size_t fileSize = sect.GetSizeMin();
+ const size_t fileSize = sect.GetSizeExtract();

if (fileSize > kFileSizeMax)
return S_FALSE;
[/code]

※ 上記パッチの使用は自己責任でお願いします。パッチ自体のライセンスはパブリックドメイン扱いで。

コメント

タイトルとURLをコピーしました