php - 如何保护 PHP 图片上传脚本免受攻击?

标签 php security

我创建了(使用 a script 和来自 Stack 的一些帮助以及来自 friend 的一些帮助;我对 PHP 知之甚少)一个本地非营利出版物的简单页面,人们可以在其中上传照片。

我不太擅长安全(出于无知,而非故意疏忽),但我已采取以下步骤来保护此页面:

• PHP 脚本设置为仅接受 .jpg、.png 和 .tif 文件上传;
• 保存表单内容的子文件夹权限设置为700,保存上传照片的子文件夹权限设置为700;
• 根据文档,我的主机具有以下配置以确保只有 .php 文件作为 .php 运行:

<FilesMatch \.php$>
    SetHandler php52-fcgi
</FilesMatch>

• 我已将 .htaccess 文件放入相关(主内容和已保存内容)文件夹中:

RemoveHandler .php
RemoveHandler .inc
RemoveHandler .pl
RemoveHandler .cgi
RemoveHandler .py
RemoveHandler .fcgi

然而,一夜之间,有人找到了这个测试页面并提交了一个看起来完全无害的测试消息和小的 .jpg。这是一个带有非直观 URL 的私有(private)测试页面,只有我和其他三个人知道;其他人都没有发送此测试。

这显然让我担心发生了一些奇怪的事情,而且我担心我对安全性的了解不够,无法确保此页面的安全。

有什么明显的我遗漏的东西吗?

最佳答案

在处理上传时,您应该记住,您可以在 $_FILES 数组中找到的所有数据都可以伪造。它通过 HTTP 传输,因此很容易将 image/jpg mime 提供给可执行文件,例如。

1- 检查真实的 mime

PHP 带有一些函数来检查文件的真实 mime。为此你应该使用 fileinfo

$finfo = new finfo(FILEINFO_MIME, "/usr/share/misc/magic");
$filename = "/var/tmp/afile.jpg";
echo $finfo->file($filename);

2- 检查图像的属性

你显然只想上传图片,所以接收到的文件必须有宽度和高度:

使用getImageSize()获取有关图像的所有必需信息。如果它返回 false ,则该文件可能不是图像,您可以将其删除。 getImageSize 也可以给你一个 mime 类型,但我不知道它是否可信。

2.5- 重新处理图像

根据 user628405 的建议,使用 GD 重新处理图像可能是更安全的做法。

$img = imagecreatefrompng('vulnerable.png'); 
imagepng($img, 'safe.png');

显然它必须根据图像类型进行调整。查看 php 文档中的所有 imagecreatefrom*。

3- 上传文件夹 除了您已经完成的工作之外:

确保您的上传文件夹无法从网络上获得。验证上传的文件,然后根据需要将其移动到其他文件夹并重命名该文件。 它将阻止黑客执行恶意文件(如果无法通过 url 访问则无法执行)。

进一步阅读:https://www.owasp.org/index.php/Unrestricted_File_Upload

关于php - 如何保护 PHP 图片上传脚本免受攻击?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12318907/

相关文章:

java - Java Web Start 的过期证书

security - 基本身份验证不适用于 AngularJS 客户端和 Java Jersey 后端(未附加 header )

php - 执行成功但 num_rows 返回 0 [PHP-MySQL]

php - 如何通过 Postman 以 JSON 格式发送请求正文中的对象数组?

php - Laravel 在保存前生成 slug

java - Websphere 应用程序服务器安全 REST API

php - Symfony VichUploaderBundle : File name could not be generated

php - 在 PHP 中比较日期

android - 当应用程序在android中处于 Activity 状态时获取电话锁定事件

java - java 网络应用程序中用于身份验证的任何库?