続 暗号化ZIPの復号

昨日のバージョンではInfo-ZIPで暗号化したZIPが読めなかったので修正しました。
raw_zip_file.hppの差分
zip_file.hppの差分
Info-ZIPがZIP仕様書と違う出力をするのには訳があります。
ZIP仕様書では、

  1. 32ビット×3個の鍵を用意(固定値)
  2. パスワードの各文字で鍵を更新
  3. 10バイトの乱数とファイルのCRC32値の上位2バイトで鍵を更新しながら暗号化
  4. ファイルイメージ(圧縮済み)の各バイトで鍵を更新しながら暗号化

という手順を踏みます。
この方法では、CRCを暗号に使っているため、暗号化に先立ってファイルのCRCを調べる必要があります。
これでは同じファイルを2度スキャンすることになり非効率的です。
そこでInfo-ZIPでは、id:y-hamigaki:20061023 で話題にしたdata descriptorのフラグがオンの場合、CRC32の代わりに最終更新時間を使うようになっています。
(おそらくPK-ZIPでは暗号化とdata descriptorが同時に使われることがないのでしょう。)
最終更新時間ならファイルを読まずに取得できるので、二度手間になりません。


逆に、Info-ZIPで作成した暗号化ZIPをPK-ZIPで読めないと困る訳ですが、(多分)そのためにzipcloakという暗号化専用のプログラムが用意されています。
このプログラムは暗号化されていないZIPをPK-ZIP仕様の暗号化ZIPに変換します。
ZIPを作った時点でCRCは記録されていますから、今度はそれを使うわけです。
Windowsの圧縮フォルダでいきなり暗号化ZIPを作成できず、アーカイブを作成してから別途暗号化を行うのも同じ理由からなのではないかと思います。
なお、7-ZIPはPK-ZIP形式で出力しますが、ファイルを二度読んでいるようです。
(しかもFilemonで見る限り、なぜか1バイトずつWriteFileしている!)


これで暗号化ZIPの作成に関しても目処が立ちました。
Info-ZIPに倣い、zip_file_sinkはInfo-ZIP形式の暗号化のみをサポートし、PK-ZIP形式の暗号化は別クラスで行うことにします。