问题很简单。如何使用php制作100%安全的照片上传脚本?是否有任何教程可以显示所有可能的安全性差距?
不要让我看this question,因为他们只谈论大小。但我想确定,没有人可以上传shell和其他内容。因为这是一个需要100%安全照片上传脚本的大型网站。
编辑:或者我应该允许会员将图片上传到imageshack等插座并将其链接复制到我的网站?我想它是100%安全的,对吧?
答案 0 :(得分:4)
这真的很简单。通过已知安全的图像过滤器运行所有上传的图像。如果它以“不是图像错误”回击,那么你就有了恶作剧。 (一个简单的例子是身份变换,或JPEG质量规范化技术。)重要的一点,即,实际使用过滤器的输出,而不是原始文件。
答案 1 :(得分:4)
您需要考虑和注意的事项:
文件扩展名:Web服务器使用文件扩展名来确定发送给客户端的MIME类型。您应该使用允许的扩展名列入白名单。在您的情况下,这将是图像扩展。
LFI:正如Matchu已经提到的,本地文件包含可能是一个问题。如果您的应用程序具有允许您包含任意文件的动态包含,例如。 include($_GET['myfile']);
它可能导致任意PHP执行。因此,您需要使用basename()来保护此类包含。这甚至可以在图像中发生,因为它们可以包含嵌入的注释。
MIME-Type-Detection:这实际上并不是很有名,而且关于它的信息也不多。 IE&lt; 8具有称为MIME类型检测的特征,如果Content-Type与内容不匹配,则尝试通过查看前256个字节来猜测类型。这意味着,如果你有一个名为image.gif的PNG文件,其顶部的注释为<script>alert('hello');</script>
,则IE&lt; 8将认为它是HTML并执行JavaScript,导致XSS攻击。
要防止图像出现此问题,您可以使用Williham Totland提到的方法。我建议使用getimagesize()来检测图像是否有效并确保扩展名与类型匹配。
$image_filename = 'uploaded_image.gif';
$image_extension = substr(strrchr($image_filename, '.'), 1);
$mime_mapping = array('png' => 'image/png', 'gif' => 'image/gif', 'jpg' => 'image/jpeg', 'jpeg' => 'image/jpeg');
$info = getimagesize($image_filename);
if (!$info) {
exit('not an image');
}
if ($info['mime'] != $mime_mapping[$image_extension]) {
exit('wrong extension given');
}
// all checks passed
// image can be saved now
有一篇关于此问题的文章here。
答案 2 :(得分:2)
如你所说,there's another question that addresses the issue。作者指出,只要他只接受真正的图像文件并保持文件大小,他应该是安全的,这是你唯一可以做的事情。检查扩展名和MIME类型,并拒绝任何与您想要的格式不匹配的内容。还有RFI(好吧,更像是LFI),但只要你没有进行健全性检查就不会偶然包含文件,你应该好好去。