web-dev-qa-db-ja.com

PHP=を使用して、アップロードされた画像ファイルにマルウェアがないか確認しますか?

ユーザーが写真をアップロードできるようにしたい。現在、アップロードされた写真に問題がないか確認していませんが、サイズを32kに制限しています。アップロードされた画像ファイルにマルウェアがないか確認する方法はありますか?たとえば、PHPからアクセスできるClamAVを実行しているサーバーはありますか?ありがとう。

2
Frank E
9
D.W.

PHPは、イメージを再作成することです。例えば:

$src_file = '/your/tmp/image.tmp';
$dest_file = '/desired/file/location/img.jpg';
$img_quality = 70;

$im = imagecreatefromstring(file_get_contents($src_file));
$im_w = imagesx($im);
$im_h = imagesy($im);
$tn = imagecreatetruecolor($im_w, $im_h);
imagecopyresampled ( $tn , $im, 0, 0, 0, 0, $im_w, $im_h, $im_w, $im_h );
imagejpeg($tn,$dest_file,$img_quality);

次に、最初にアップロードした画像を削除し、サイズを変更したコピーを保持します。

3
Timo Huovinen

最善のアプローチは、組み合わせたソリューションを使用することだと思います。

  • ウイルス対策を使用してファイルをスキャンする
  • ファイルのMIMEタイプを確認する
  • Cristiがここで説明したファイルサイズチェックを実行します。
  • アップロードしたファイルを画像ライブラリにロードして、もう一度保存します(画像のサイズを変更している場合は、すでにこれを行っている可能性があります)

これらのチェックをすべて使用することにより、攻撃が成功する可能性は大幅に小さくなります。

2
Dinu

アップロードされた画像が本当に画像であり、他のものではないかどうかを確認することは、よく使用される方法です。画像の検証は、ウイルス対策でスキャンするよりも安全です。

getimagesize() 関数は、指定された画像ファイルのサイズを決定し、通常のHTML IMGタグおよび対応するHTTP内で使用されるファイルタイプと高さ/幅のテキスト文字列とともに寸法を返しますコンテンツタイプ。この関数は多くの画像フォーマットをサポートしています。

getimagesize()を使用して、一度に複数のことを実行できます。

  • ファイルが画像であることを検証する
  • 一部の画像タイプのみを許可する
  • 必要なサイズのみを許可する
  • 正しいHTTP MIME typeヘッダーで画像を配信するために使用できる画像のContent-typeを決定します

    function is_image($path)
        {
        $a = getimagesize($path);
        $image_type = $a[2];
    
        if (in_array($image_type , array(IMAGETYPE_GIF , IMAGETYPE_JPEG ,IMAGETYPE_PNG , IMAGETYPE_BMP)))
        {
            return true;
        }
        return false;
    }
    
  • $array[0]および$array[1]は、画像の幅と高さです。

  • $array[2]には画像タイプがあります。

MPEGビデオはIMAGETYPE_ICOとして検出されることに注意してください。

1
Cristian Dobre

クリスチャンが言うように、最善の解決策は、ファイルタイプをホワイトリストに登録して確認することです。ただし、メタデータが圧縮されていないファイルは Webサーバーを攻撃する手段 になる可能性があります。メタデータを取り除きます。

Webリクエストからウイルスチェッカーを同期的に呼び出すことは、パフォーマンス、安定性、および可用性の点で非常に悪い考えです。 PHP=のデフォルトのアップロードハンドラーは、賢明にファイルを邪魔にならないように配置し、リクエストが完了する前にそれらを移動するように強制します。つまり、ウイルスの後でもう一度ファイルをコピーする必要がありますそれをスキャンします。

1
symcbean

完全な答え*ではありませんが、不要なコンテンツを除外する1つの方法は、アップロードされたデータではなく、PHPの画像操作関数を使用して、アップロードされた画像を新しい画像に置き換えて保存することです。写真を直接保存するだけでなく、写真のスクリーンショットを撮るようなものです。

* =または、最良のソリューション、または最も簡単な...

1
John U