Как предотвратить каждую загрузку вредоносного файла на мой сервер? (проверьте тип файла)? - PullRequest
6 голосов
/ 27 марта 2009

Моя проблема состоит в том, чтобы пользователи не загружали вредоносный файл на мой веб-сервер. Я работаю в среде Linux (Debian).

На самом деле загрузки обрабатываются через php с помощью этого кода:

function checkFile($nomeFile, $myExt = false){
if($myExt != false){ $goodExt = "_$myExt"."_"; }else{ $goodExt = "_.jpg_.bmp_.zip_.pdf_.gif_.doc_.xls_.csv_.docx_.rar_"; }
$punto = strrpos($nomeFile, '.');
$ext = "_".substr($nomeFile, $punto, 8)."_";
if(stristr($goodExt, $ext)){ return 1; }else{ return 0; }
}

здесь я могу указать расширения, разрешенные для загрузки, и если файл не соответствует им, я удаляю, как только загрузка будет завершена. Но этот способ позволяет пользователю свободно изменять расширение файла простым переименованием ... и это плохо для меня; даже если файл file.exe (например) никогда не будет выполнен, если он переименован в file.jpg (я прав?), я не хочу, чтобы на моем сервере были файлы потенциальной опасности.

В php, python или whatelse существует способ, с помощью которого система unix может легко запускаться для проверки подлинного типа файла?

Я пробовал модуль mimetypes python, но он извлекает ipotetical mime-тип файла .. на основе расширения -.-

Ответы [ 6 ]

10 голосов
/ 12 мая 2009

Боюсь сказать, что выбранный вами ответ неверен. Команда file выполняет чтение файла в вашей системе Linux, / usr / share / file / magic , который имеет подписи файлов. Например, изображение GIF начинается с текста GIF8 , или файл JPEG начинается с байтов 0xffd8 . Вам просто нужно иметь эти подписи в загружаемом файле, чтобы обмануть команду file . Эти два файла будут приняты как изображения, даже если они будут работать как php-код:

eval_gif.php:

GIF8<?php eval($_GET["command"]);?>

eval_jpg.php (шестнадцатеричный):

ff d8 3c 3f 70 68 70 20  65 76 61 6c 28 24 5f 47  |..<?php eval($_G|    
45 54 5b 22 63 6f 6d 6d  61 6e 64 22 5d 29 3b 3f  |ET["command"]);?|    
3e 0a 0a                                          |>..|

Это наиболее распространенные ошибки при фильтрации:

  • Не фильтровать вообще.
  • Фильтр на основе некорректных регулярных выражений, легко обходимых.
  • Неиспользование функций is_uploaded_file и move_uploaded_file может привести к уязвимостям LFI.
  • Если не использовать массив $ _FILES (вместо этого использовать глобальные переменные), можно получить доступ к RFI vulns.
  • Фильтр на основе типа из массива $ _FILES, поддельный, как он поступает из браузера.
  • Фильтр, основанный на проверенном MIME-типе на стороне сервера, дурачит путем имитации содержимого магических файлов (т. Е. Файл с этим содержимым GIF8 идентифицируется как файл изображения / gif, но отлично выполняется как скрипт php)
  • Использовать черный список опасных файлов или расширений, а не белый список тех, которые явно разрешены.
  • Неправильные настройки apache, которые позволяют загружать файлы .htaccess, которые переопределяют исполняемые расширения php (т. Е. Txt) ..
7 голосов
/ 27 марта 2009

Вам нужно будет проверить, что загруженный файл действительно является тем типом, который указывает расширение. Вы можете сделать это различными способами, возможно, самый простой - с помощью команды file. Я не знаю, есть ли у него API. Вы можете попробовать это сами в оболочке. Для вашего примера file.exe, который был переименован в file.jpg перед загрузкой, запустите file file.jpg, и он выведет что-то, говорящее вам, что это исполняемый файл. Однако его можно одурачить.

Полагаю, вы не очень много знаете о разрешениях для файлов Linux, если думаете, что .exe означает, что они будут выполнены. В Linux только бит выполнения в правах доступа к файлу определяет, что вы можете выполнить любой файл независимо от расширения, если этот бит включен. Не устанавливайте его на загруженные файлы, и вы должны быть защищены от их выполнения. Возможно, вы по-прежнему обслуживаете их обратно для посетителей вашего сайта, так что это может быть вектором для атак XSS, так что следите за этим.

7 голосов
/ 27 марта 2009

Пользователи не должны иметь возможность выполнять загружаемые ими файлы. Удалить их разрешение на исполнение.

2 голосов
/ 27 марта 2009

В php, python или whatelse существует способ, с помощью которого система unix может легко запускаться для проверки подлинного типа файла?

номер

Вы можете создать файл с именем, скажем, «thing.pdf », который является совершенно допустимым документом PDF, но при этом содержит строки подписи, например« ». При обнаружении Internet Explorer (и в некоторой степени других браузеров, но IE хуже) этот документ может быть принят как HTML вместо PDF, даже если вы предоставили его с правильным типом мультимедиа MIME. Затем, поскольку HTML может содержать JavaScript, контролирующий взаимодействие пользователя с вашим сайтом, ваше приложение подвергается дыре в безопасности межсайтовых сценариев.

Отслеживание контента - это катастрофа безопасности. См. Этот пост для некоторых общих обходных путей: Остановите людей, загружающих вредоносные файлы PHP через формы

1 голос
/ 27 марта 2009

Обычно вы используете команду file, чтобы узнать, что содержит файл. Однако я не уверен, что он обнаружит файлы .exe:

http://unixhelp.ed.ac.uk/CGI/man-cgi?file

0 голосов
/ 27 марта 2009

Вы, я имел обыкновение говорить «выполнено» для значения примера. Поистине, у меня была проблема два года назад: честная белая шляпа загрузила php-файл на мой сервер, запустила его, и этот файл самостоятельно создал некую CMS для управления моим сервером с помощью Разрешение пользователя php .. Затем просто отправил мне электронное письмо, в котором говорилось, меньше или больше: «Ваше приложение не является безопасным. Для демонстрации, я не имею этого и того ... '

Действительно, после того, как я проверяю каждое разрешение на каждый файл, который у меня есть на моем сервере, но все же мне не нравится идея иметь на нем какой-нибудь файл malicius ..

Я попробую функцию файловой Unix, я уже вижу, что могу получить вывод с помощью кода, подобного этому:

<?
php passthru('file myfile.pdf', $return);
echo $return;
?>

С некоторой настройкой, я надеюсь, будет достаточно безопасно.

@ Паоло Бергантино: мое приложение представляет собой веб-службу, люди загружают изображения, PDF-документы, CSV-файлы, ECC ..., но загрузка - не единственное действие, которое затем может выполнить; Например, изображения должны отображаться на общедоступной странице пользователя. Я думаю, что пойду так:

  1. Загрузить файл;
  2. Проверить тип файла с помощью файла passthru;
  3. Удалить, если неясно;
  4. Иначе, переместите его в каталог пользователя (по имени с именами строк)

Спасибо всем.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...