Был a партия из разговор о проблеме безопасности относительно cgi.fix_pathinfo
Опция PHP используется с Nginx (обычно PHP-FPM, быстрый CGI).
В результате значение по умолчанию nginx конфигурационный файл раньше говорило:
# NOTE: You should have "cgi.fix_pathinfo = 0;" in php.ini
Однако теперь, "официальный" Nginx, Wiki указывает, что PATH_INFO может быть обработан правильно, не отключая вышеупомянутую опцию PHP.И что?
cgi.fix_pathinfo
? (в официальном документе просто говорится: "Для получения дополнительной информации о PATH_INFO посмотрите спецификации CGI"),PATH_INFO
и SCRIPT_FILENAME
переменные? Я пытаюсь понять проблему на каждом шаге. Например, я не понимаю, почему использование php-fpm сокета Unix могло избежать этой проблемы.
Я постараюсь ответить на ваши конкретные вопросы, но ваше неправильное понимание того, что такое PATH_INFO, делает сами вопросы немного неправильными.
Первый вопрос должен быть "Что это за бизнес информации о пути?"
Информация о пути - это материал после скрипта в URI (должен начинаться с прямого слэша, но заканчиваться до аргументов запроса, который начинается с ?
). Последний абзац обзорной части статьи Википедии о CGI прекрасно её резюмирует. Ниже PATH_INFO
написано "/THIS/IS/PATH/INFO":
http://example.com/path/to/script.php/THIS/IS/PATH/INFO?query_args=foo
Ваш следующий вопрос должен был быть: "Как PHP определяет, что такое PATH_INFO
и SCRIPT_FILENAME
? "
PATH_INFO
, так что то, что должно было быть PATH_INFO
было заряжено на SCRIPT_FILENAME
, который, да, во многих случаях сломан. У меня нет достаточно старой версии PHP для тестирования, но я думаю, что она видела SCRIPT_FILENAME
как весь shebang: "/path/to/script.php/THIS/IS/PATH/INFO" в приведенном выше примере (как обычно, с префиксом docroot).PATH_INFO
и SCRIPT_FILENAME
получает только ту часть, которая указывает на запрашиваемый скрипт (конечно же, префикс с docroot). PATH_INFO
, они должны были добавить настройки конфигурации для новой функции, чтобы люди, выполняющие скрипты, которые зависели от старого поведения, могли запускать новые версии PHP. Поэтому для этого даже есть переключатель конфигурации. Он должен был быть встроен (с "опасным" поведением) с самого начала.Но откуда PHP знает, какая часть скрипта и каков его путь? Что если URI что-то вроде:
http://example.com/path/to/script.php/THIS/IS/PATH/INFO.php?q=foo
SCRIPT_FILENAME
определено, а PATH_INFO
получает остальное. SCRIPT_FILENAME
получает "/foo.jpg" (опять же, с префиксом docroot) и PATH_INFO
получает "/nexistent". php".Почему и как это может быть опасно теперь должно быть ясно:
Nginx и Apache могут быть собраны или сконфигурированы так, чтобы предотвратить запросы, использующие эту хитрость, и для этого есть множество примеров, в том числе в ответе user2372674. Эта статья в блоге хорошо объясняет проблему, но в ней отсутствует правильное решение.
Однако, лучшее решение - это просто убедиться, что PHP-FPM настроен правильно, чтобы он никогда не выполнял файл, если только он не заканчивается на ".php". Стоит отметить, что последние версии PHP-FPM (~5.3.9+?) имеют такую конфигурацию по умолчанию, так что эта опасность больше не является проблемой.
Если у вас есть последняя версия PHP-FPM (~5.3.9+? ), то вам ничего не нужно делать, так как приведенное ниже безопасное поведение уже по умолчанию.
Иначе найдите файл php-fpm's www.conf
(может быть /etc/php-fpm.d/www.conf
, зависит от вашей системы). Убедитесь, что у вас есть следующее:
security.limit_extensions = .php
Опять же, это во многих местах по умолчанию в наши дни.
Обратите внимание, что это не мешает злоумышленнику загрузить ".php" файл в папку WordPress и выполнить его, используя ту же самую технику. Вам все еще нужна хорошая безопасность для ваших приложений.
В сущности без этого вы можете загрузить файл с php кодом с именем 'foo.jpg' на веб-сервер; затем запросить его как http://domain.tld/foo.jpg/nonexistent.php и стек веб-сервера ошибочно скажет oh; это PHP; мне нужно обработать это, он не сможет найти foo.jpg/nexistent.php, так что он вернется к foo.jpg и обработает foo.jpg как php код. Это опасно, так как открывает систему для очень легкого вторжения; любое веб-приложение, позволяющее, например, загружать образы, становится инструментом для загрузки бэкдора.
Относительно использования php-fpm с unix-сокетом, чтобы избежать этого; IMO это не решит проблему.
.В вики Nginx в качестве меры безопасности
if (!-f $document_root$fastcgi_script_name) {
return 404;
}
включена в блок локации. В других учебниках используется
try_files $uri =404;
, которая должна сделать то же самое, но может дать проблемы в соответствии с вики Nginx. С этими опциями cgi.fix_pathinfo=1
больше не должно быть проблем. Больше информации можно найти здесь .