Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-18 Пенетрантность Валентин Бартенев
On Tuesday 17 June 2014 18:05:15 S.A.N wrote:
 Валентин Бартенев Wrote:
 ---
  Как уже неоднократно в этой ветке говорилось, nginx в параметрах
  HTTP_* пишет
  ровно то, что от него требуется: заголовки, пришедшие от клиента, в
  том виде,
  в котором они получены.
 
 Nginx так и должен делать, если запрос валидный, а инвалидные запросы на
 бекенд передавать не имеет никакого смысла, они не несут в себе полезной
 нагрузки (payload) для бекенда.
[..]

Вы подменяете понятия.  Пока ещё никто из дискутирующих не смог привести
аргументов за то, что такие запросы не являются валидными.

Попытки ссылаться на требования к клиенту и склонять спецификацию так,
как того хочется - результата точно не принесут.

Это с точки зрения вашего конкретного бэкенда запрос не валиден, nginx
же вполне справляется с его обработкой, как в общем-то и многие другие
сервера.

Можете предложить исправить баг на ietf.org:

$ netcat ietf.org 80
HEAD http://www.ietf.org/ HTTP/1.1
Host: example.com
Host: example.org

HTTP/1.1 200 OK
Date: Wed, 18 Jun 2014 07:49:22 GMT
Server: Apache
Last-Modified: Thu, 05 Jun 2014 15:47:35 GMT
ETag: 884603a-49c4-4fb18a9ec37a4
Accept-Ranges: bytes
Content-Length: 18884
Vary: Accept-Encoding
Content-Type: text/html


или на apache.org:

$ netcat apache.org 80
HEAD http://www.apache.org/ HTTP/1.1
Host: example.com
Host: example.org

HTTP/1.1 200 OK
Date: Wed, 18 Jun 2014 07:49:57 GMT
Server: Apache/2.4.9 (Unix) mod_wsgi/3.4 Python/2.7.5 OpenSSL/1.0.1h
Last-Modified: Sun, 15 Jun 2014 09:10:45 GMT
ETag: a250-4fbdc492d0221
Accept-Ranges: bytes
Content-Length: 41552
Vary: Accept-Encoding
Cache-Control: max-age=3600
Expires: Wed, 18 Jun 2014 08:49:57 GMT
Content-Type: text/html; charset=utf-8


или на google.com в конце-концов:

$ netcat google.com 80
HEAD http://google.com/ HTTP/1.1
Host: example.com
Host: example.org

HTTP/1.1 302 Found
Cache-Control: private
Content-Type: text/html; charset=UTF-8
Location: http://www.google.ru/?gfe_rd=crei=wkShU4e1GM-A4AS4poHoDg
Content-Length: 258
Date: Wed, 18 Jun 2014 07:50:26 GMT
Server: GFE/2.0
Alternate-Protocol: 80:quic



 По этому, мы разработчики бекенда хотели бы чтобы Nginx не передавал нам
 инвалидные запросы, а отдавал 400 статус.
 
[..]

Список инвалидных запросов в студию.  Завтра придут просить запретить
запрос к /private/, поскольку с точки зрения некоторого бэкенда он не
валиден. 


--
Валентин Бартенев
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-18 Пенетрантность Валентин Бартенев
On Tuesday 17 June 2014 18:05:15 S.A.N wrote:
[..]
 Немного позволю себе лирики, надеюсь никто не обидеться.
 Слепое выполнения протокола CGI 1.1 для инвалидных запросов, напоминает
 анегдот:
 Когда маленькую девочку оставили одну дома и дали указания чужим людям двери
 не открывать.
 В квартире начался пожар, приехали пожарные стучат в двери, но девочка
 утверждает, что двери чужим людям нельзя открывать, потому что были такие
 указания )
 Самое удивительное что переубедить девочку нельзя, она уверена в своей
 правоте, вить указаний открывать двери пожарным не было, то что пожарным
 тушить пожар из окна улицы сложней и накладней, по мнению девочки это
 проблема пожарных, если они пожарные хреновые специалисты им уже не помочь.

Т.е. девочке сказали выдавать 400, а тут пришли пожарные, которые пользуются
теми самыми запросами, которые вы считаете инвалидными.

Ok.

[..]
 
 Мораль этой байки такова - при возникновении исключительной ситуации, когда
 нет указаний как поступать в этой ситуации, нужно руководствоватся общим
 правилом поведения в исключительных ситуациях, они гласят - нужно убегать,
 т.е выбрасывать эксепшин, в нашем случаи это выдать 400 статус и завершить
 запрос.
 

Ещё раз, для nginx это не является исключительной ситуацией, он знает
как обрабатывать такие запросы и успешно с этим справляется.

--
Валентин Бартенев
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-18 Пенетрантность Igor Sysoev
On 17 Jun 2014, at 20:03, Maxim Dounin mdou...@mdounin.ru wrote:

 В своё время, однако, nginx'у потребовалось от этой практики отказаться:
 
 http://hg.nginx.org/nginx/rev/b9de93d804ea
 
 Если мне не изменяет память, причина была всё та же - реальная
 жизнь заставила.
 
 Можно подробнее узнать про причину?
 
 Это вопрос к Игорю, может быть он помнит подробности.  

В переписке следов не нашёл, но помню строки из error_log’а с десятками
строк “Host” в одном запросе, по-моему от MSIE. Видел, скорее всего, в
рамблеровских логах.


--   
Igor Sysoev
http://nginx.com

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-18 Пенетрантность S.A.N
Валентин Бартенев Wrote:
---
 Вы подменяете понятия.  Пока ещё никто из дискутирующих не смог
 привести
 аргументов за то, что такие запросы не являются валидными.

Я никогда не утверждал, что инвалидность этих запросов определяется
стандартом CGI, даже привел метафору про девочку которой не дали указания на
случай пожара.

Причины по которым такие запросы необходимо считать инвалидными очень
прозаичны, легальных HTTP клиентов которые создают такие запросы НЕТ,
сервера которые подвержены данному эксплойту ЕСТЬ, этих серверов не единицы,
обсуждать профессионализм администраторов и разработчиков этих бекендов
можно но это не меняет картину, это просто нужно признать как данность.

Мне кажется хорошей аналогией являются браузеры, которые по таким же
прозаичным причинам, решили не выполнять JS код в странице, если такой код
содержится в URI запроса, вот пример:

http://localhost/?var=scriptalert(XSS)/script

?php

echo $_GET['var'];

?

По всем стандартам HTTP, данный запрос корректный (url encode я убрал для
читабельности).
JS код который находится в теле страницы тоже абсолютно корректный с точки
зрения JS, браузер обязан его выполнить, но браузер этот код не выполнит, по
соображениям безопасности и защиты от XSS атак.

К этому разработчики браузеров тоже пришли не сразу, много лет XSS атаки
было легко проводить на подверженных сайтах. 
Разработчики браузеров по праву считали что это проблема тех кто
разрабатывает сайт и это они должны на своей стороне закрыть XSS
уязвимости.
Но годы шли, а XSS уязвимостей находили все больше, они были даже в
инетбанкингах.
Тогда первым кто сделал мудрое решения был Chrome он реализовал защиты от
XSS атак и объявил себя самым безопасным браузером, потом так же сделал IE.

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


 Это с точки зрения вашего конкретного бэкенда запрос не валиден, nginx
 же вполне справляется с его обработкой, как в общем-то и многие другие
 сервера.

Да, вы правы ценость этого эксплойта я оценил на нескольких своих старых
серверах, ещё года два назад, у себя я закрыл эти уязвимости, закрывать это
на уровне веб-сервера решать вам, дело хозяйское, выше я изложил свои
аргументы и пожелания по закрытию на уровне веб-сервера

 Можете предложить исправить баг на ietf.org:
 
 или на apache.org:
 
 или на google.com в конце-концов:
 

Chrome и IE тоже не сразу создали защиту от XSS, прошли годы, вопрос кто это
сделает первым Nginx или Apache.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,251015#msg-251015

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Maxim Dounin
Hello!

On Mon, Jun 16, 2014 at 11:20:57PM +0300, Gena Makhomed wrote:

 On 16.06.2014 15:00, Maxim Dounin wrote:
 
 озвученные в RFC 7230 требования к клиенту:
 
 http://tools.ietf.org/html/rfc7230#section-5.4
 
 A client MUST send a Host header field in all HTTP/1.1 request
 messages.  If the target URI includes an authority component, then a
 client MUST send a field-value for Host that is identical to that
 authority component, excluding any userinfo subcomponent and its @
 delimiter (Section 2.7.1).
 
 - это ведь требования к синтаксису, которые обязательны для выполнения.
 
 Нет, это не требования к синтаксису, это требования к семантике.
 
 Запись target URI в виде valid request message - это разве не syntax?

Синтаксис - это то, что нарушает требования приведённых нормативных 
грамматик, см. http://tools.ietf.org/html/rfc7231#section-1.2 и 
далее.

[...]

 Разве ответить на такой запрос 400-м статусом не будет лучше?
 
 Это зависит от многих факторов.  Вот тут Валентин давеча
 напрограммировал возврат 400, если имя, указанное в SNI, не
 совпадало с именем, используемым в запросе, ибо RFC 6066 говорит:
 
 ... If the server_name is
 established in the TLS session handshake, the client SHOULD NOT
 attempt to request a different server name at the application layer.
 
 Так пришлось распрограмировать обратно - потому что Chrome
 использует a different server name at the application layer,
 когда считает нужным/возможным.
 
 SHOULD NOT - это не запрет, а только лишь рекомендация:
 http://tools.ietf.org/html/rfc2119#section-4
 так что формально и фактически Chrome ничего не нарушает.

Фактически - упомянутый SHOULD NOT на тот момент безусловно 
отклонялся Apache'ом, а противоречащие друг другу Host + 
Request-Line - формально вообще ничего не нарушали до выхода 
HTTPbis.  И что на самом деле происходит в реальной жизни - это 
отдельный интересный вопрос.

Среди прочего, например, HTTPbis явно требует возвращать 400, если 
запрос содержит несколько заголовков Host.  В своё время, однако, 
nginx'у потребовалось от этой практики отказаться:

http://hg.nginx.org/nginx/rev/b9de93d804ea

Если мне не изменяет память, причина была всё та же - реальная 
жизнь заставила.

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Илья Шипицин
а расскажите на примерах, как эту уязвимость можно эксплуатировать ?


бесконечный пинг-понг между Геннадием и Максимом утомляет ))

11 июня 2014 г., 16:30 пользователь Gena Makhomed g...@csdoc.com написал:
 On 10.01.2014 15:07, Валентин Бартенев wrote:

 http://habrahabr.ru/post/166855/


 Единственный правильный способ: пойти в IETF с предложением исправить
 соответствующие RFC, которые в том числе оговаривают, что следует делать
 при получении нескольких заголовков Host, ну а потом уже сюда.


 http://tools.ietf.org/html/rfc7230#section-5.4

When a proxy receives a request with an absolute-form of
request-target, the proxy MUST ignore the received Host header field
(if any) and instead replace it with the host information of the
request-target.  A proxy that forwards such a request MUST generate a
new Host field-value based on the received request-target rather than
forward the received Host field-value.

 Referer: http://www.opennet.ru/opennews/art.shtml?num=39956

 --
 Best regards,
  Gena

 ___
 nginx-ru mailing list
 nginx-ru@nginx.org
 http://mailman.nginx.org/mailman/listinfo/nginx-ru
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Maxim Dounin
Hello!

On Mon, Jun 16, 2014 at 03:36:38PM -0400, S.A.N wrote:

   Maxim Dounin Wrote:
   ---
Какая-либо проблема появляется тогда и только 
тогда, когда администратор начинает писать в конфиге $http_host, 
не думая о последствиях.  Есть мнение, что совсем простое решение 
этой проблемы - не делать так (c) анекдот.
   
   Вся проблема в том что сами программисты Nginx в модуле FastCGI
  используют
   переменную $http_host для HTTP_HOST, вместо нормализованной
  переменой $host,
   администраторам на оборот приходится исправлять это своими руками и
  писать в
   конфиге
   fastcgi_param  HTTP_HOST  $host;
   Если следовать вашей логике, надо изменить код модуля FastCGI, чтобы
  по
   умолчанию Nginx был вполне себе безопасный.
  
  По умолчанию в fastcgi http-заголовки передаются как есть, в виде 
  параметров HTTP_*.  Каноническое же имя сервера доступно в 
  параметре SERVER_NAME.  Что из этого и как использовать - это 
  вопрос к приложению, а не к nginx'у.
 
 Я знаю, и уже выше объяснял почему бекенд-приложениям нужно использовать
 HTTP_HOST вместо SERVER_NAME.
 Значения SERVER_NAME не может использоваться, если в директиве server_name
 используется маска или бекенд обрабатывает запросы для default_server.

Если SERVER_NAME нельзя использовать - значит, необходимо передать 
дополнительный параметр, который и использовать.

Использовать HTTP_* поля для чего-то, что позволяет получить 
доступ - это неправильно.

 Ещё раз приведу пример, в котором мы легко можем получить доступ, к закрытым
 на уровне Nginx ресурсам.
 
 server
 {
   server_name *.example.com;
   ...
   fastcgi_pass php;
 }
 
 server
 {
   server_name private.example.com;
 
   location / {
   allow 192.168.1.0/24;
   deny all;
 
   fastcgi_pass php;
 
   auth_request /auth;
 }
 ...
  }
 
 Как видно два хоста используют один upstream, на котором бекенд приложения
 даёт расширенные привилегии юзерам private.example.com, в расчете на то что
 Nginx предварительно сделал проверку по IP и успешно провел аунтификацию,
 всё вроде логично и удобно сделано, но такая схема легко ломается таким
 запросом.
 
 GET http://example.com/SecureData/ HTTP/1.1
 Host: private.example.com
 
 Бекенд получает HTTP_HOST=private.example.com, даёт юзеру привилегии, но
 Nginx не проводил проверки по IP и не делал запрос аунтификацию, потому что
 отработал хост конфигурации для example.com вместо private.example.com

Проблема в том, что приложение некорректно предполагает, что 
HTTP_HOST=private.example.com чем-то отличается от других.  Как 
показывает пример запроса выше - это не так.  И не так - не 
только в nginx'е, но и в других серверах.

Не надо себя обманывать и пытаться закрыть nginx'ом небезопасную 
логику приложения - это не работает и рано или поздно выстрелит.

Правильное решение - передавать информацию о произошедшей 
авторизации явно и отдельно (или пользоваться параметром 
SERVER_NAME, который уже передаётся и предназначен специально для 
идентификации сервера).

 В данном случаи можно было бы использовать переменную SERVER_NAME, но я выше
 писал почему это не всегда возможно.
 
 Если мы оба понимаем, что ситуация когда authority component и значения Host
 разные, это исключительная ситуация и её нужно обрабатывать как Exception, в
 этом случаи есть три варианта поведения, выбросить Exception (отдать 400
 статус), исправить ошибку (использовать переменую $host), и самый плохой
 вариант (антишаблон) ничего не делать и не обрабатывать эту исключительную
 ситуацию и оставить все как есть.

Возможно, когда-нибудь мы и придём к тому, что в таких ситуациях 
будет возвращаться 400.  Но это ни коим образом не избавляет от 
необходимости исправить приложение.

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Gena Makhomed

On 17.06.2014 9:30, Maxim Dounin wrote:


http://tools.ietf.org/html/rfc7230#section-5.4

A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).

- это ведь требования к синтаксису, которые обязательны для выполнения.


Нет, это не требования к синтаксису, это требования к семантике.


Запись target URI в виде valid request message - это разве не syntax?


Синтаксис - это то, что нарушает требования приведённых нормативных
грамматик, см. http://tools.ietf.org/html/rfc7231#section-1.2 и
далее.


Не все требования к синтаксису выражены в виде нормативных грамматик.
Например, требование отправлять первой строкой запроса request-line
- это тоже требование к синтаксису валидной HTTP request message.
Но это требование не выражено в виде Augmented Backus-Naur Form.


SHOULD NOT - это не запрет, а только лишь рекомендация:
http://tools.ietf.org/html/rfc2119#section-4
так что формально и фактически Chrome ничего не нарушает.


Фактически - упомянутый SHOULD NOT на тот момент безусловно
отклонялся Apache'ом,


И это безусловный BUG апача, копировать его в nginx - нет смысла.
Apache ведь не является reference implementation протокола HTTP/1.1


а противоречащие друг другу Host +
Request-Line - формально вообще ничего не нарушали


Вообще-то в RFC 2616 написано в точности то же самое что и в RFC 7230:

http://tools.ietf.org/html/rfc2616#section-14.23

   The Host request-header field specifies the Internet host and port
   number of the resource being requested, as obtained from the original
   URI given by the user or referring resource (generally an HTTP URL,
   as described in section 3.2.2). The Host field value MUST represent
   the naming authority of the origin server or gateway given by the
   original URL. This allows the origin server or gateway to
   differentiate between internally-ambiguous URLs, such as the root /
   URL of a server for multiple host names on a single IP address.

Здесь точно так же присутствует требование MUST,
то есть клиент, который не выполнил это требование -
прислал на сервер невалидный запрос и сервер имеет
полное право ответить на такой запрос статусом 400.


до выхода HTTPbis.


Выход HTTPbis так и не состоялся. Вместо этого - решили
уточнить спецификацию протокола HTTP/1.1 и сконцентировать
свои усилия в работе над протоколом HTTP/2.0 на базе SPDY,
насколько мне известно.


И что на самом деле происходит в реальной жизни
- это отдельный интересный вопрос.


В реальной жизни я не встречал софта, который бы создавал запросы

GET http://apple.com/ HTTP/1.1
Host: samsung.com

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


Среди прочего, например, HTTPbis явно требует возвращать 400,
если запрос содержит несколько заголовков Host.


Нет смысла отправлять несколько одинаковых заголовков
с одинаковым значением. А разных значений там быть не должно.

Единственное что добавилось в RFC 7230 - это более явное требование,
чтобы такой заголовок был всего один. В RFC 2616 это было между строк.


В своё время, однако, nginx'у потребовалось от этой практики отказаться:

http://hg.nginx.org/nginx/rev/b9de93d804ea

Если мне не изменяет память, причина была всё та же - реальная
жизнь заставила.


Можно подробнее узнать про причину?

--
Best regards,
 Gena

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Gena Makhomed

On 17.06.2014 10:00, Maxim Dounin wrote:

 Значения SERVER_NAME не может использоваться,
 если в директиве server_name используется маска
 или бекенд обрабатывает запросы для default_server.

 Если SERVER_NAME нельзя использовать - значит, необходимо
 передать дополнительный параметр, который и использовать.

Именно для этого и существует HTTP_HOST - передать
значение заголовка Host из валидного клиентского запроса.

 Использовать HTTP_* поля для чего-то, что позволяет
 получить доступ - это неправильно.

Если nginx не будет отправлять на backend невалидные клиентские запросы
- проблем с заголовком HTTP_HOST не будет никаких, - он будет валидным.

 Проблема в том, что приложение некорректно предполагает, что
 HTTP_HOST=private.example.com чем-то отличается от других.  Как
 показывает пример запроса выше - это не так.  И не так - не
 только в nginx'е, но и в других серверах.

А мы никаких других веб-серверов кроме nginx и не используем.
В IIS например, багов еще больше, чем в Apache, и что с того?

 Не надо себя обманывать и пытаться закрыть nginx'ом небезопасную
 логику приложения - это не работает и рано или поздно выстрелит.

Приложение было написано в соответствии со стандартами HTTP/1.1
и ожидало, что nginx не пропустит на backend невалидный запрос.

 Правильное решение - передавать информацию о произошедшей
 авторизации явно и отдельно (или пользоваться параметром
 SERVER_NAME, который уже передаётся и предназначен специально для
 идентификации сервера).

server {
  server_name www.example.com example.com;
  // ...
}

на backend в переменной SERVER_NAME уйдет всегда www.example.com
вне зависимости от того, к какому именно вирт. хосту был запрос.

переменную HTTP_HOST использовать нельзя.
неужели надо всем делать workaround

fastcgi_param  X_REAL_HTTP_HOST  $host;

и потом использовать переменную X_REAL_HTTP_HOST вместо HTTP_HOST ?

 Возможно, когда-нибудь мы и придём к тому,
 что в таких ситуациях будет возвращаться 400.

Что мешает сделать это прямо сейчас?

 Но это ни коим образом не избавляет
 от необходимости исправить приложение.

Сейчас - приходится имена виртуальных хостов прописывать
в двух местах - в настройках nginx и в настройках самого
приложения. И дополнительно валидировать HTTP_HOST, проверяя
входит ли это имя в список имен, которые были указаны в директиве
server_name, и были повторно прописаны в настройках приложения.
И если нет - то явно возвращать клиенту статус 400 Bad Request.

Есть стойкое ощущение, что это может и даже должен делать nginx.
Тогда имена хостов надо будет настраивать всего в одном конфиге.

Добавить этот workaround во все backend`ы, которые есть в мире -
это нереально, гораздо проще добавить валидацию запроса в nginx.

--
Best regards,
 Gena

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Валентин Бартенев
On Tuesday 17 June 2014 13:31:16 Gena Makhomed wrote:
[..]
  SHOULD NOT - это не запрет, а только лишь рекомендация:
  http://tools.ietf.org/html/rfc2119#section-4
  так что формально и фактически Chrome ничего не нарушает.
 
  Фактически - упомянутый SHOULD NOT на тот момент безусловно
  отклонялся Apache'ом,
 
 И это безусловный BUG апача, копировать его в nginx - нет смысла.
 Apache ведь не является reference implementation протокола HTTP/1.1
 
[..]

Там было и другое:

11.1.  Security Considerations for server_name

   If a single server hosts several domains, then clearly it is
   necessary for the owners of each domain to ensure that this satisfies
   their security needs.  Apart from this, server_name does not appear
   to introduce significant security issues.

   Since it is possible for a client to present a different server_name
   in the application protocol, application server implementations that
   rely upon these names being the same MUST check to make sure the
   client did not present a different name in the application protocol.

http://tools.ietf.org/html/rfc6066#section-11.1

В частности, клиент может запросить по SNI один виртуальный хост,
и исходя из этого будет проверен его клиентский сертификат, а
также выбраны настройки шифрования, а затем на уровне HTTP,
запрашивать совсем другие виртуальные хосты, тем самым обходя
настройки TLS для этих хостов.

--
Валентин Бартенев
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Maxim Dounin
Hello!

On Tue, Jun 17, 2014 at 01:31:16PM +0300, Gena Makhomed wrote:

 On 17.06.2014 9:30, Maxim Dounin wrote:
 
 http://tools.ietf.org/html/rfc7230#section-5.4
 
 A client MUST send a Host header field in all HTTP/1.1 request
 messages.  If the target URI includes an authority component, then a
 client MUST send a field-value for Host that is identical to that
 authority component, excluding any userinfo subcomponent and its @
 delimiter (Section 2.7.1).
 
 - это ведь требования к синтаксису, которые обязательны для выполнения.
 
 Нет, это не требования к синтаксису, это требования к семантике.
 
 Запись target URI в виде valid request message - это разве не syntax?
 
 Синтаксис - это то, что нарушает требования приведённых нормативных
 грамматик, см. http://tools.ietf.org/html/rfc7231#section-1.2 и
 далее.
 
 Не все требования к синтаксису выражены в виде нормативных грамматик.
 Например, требование отправлять первой строкой запроса request-line
 - это тоже требование к синтаксису валидной HTTP request message.
 Но это требование не выражено в виде Augmented Backus-Naur Form.

http://tools.ietf.org/html/rfc7230#appendix-B

HTTP-message = start-line *( header-field CRLF ) CRLF [ message-body
]
status-line = HTTP-version SP status-code SP reason-phrase CRLF

 SHOULD NOT - это не запрет, а только лишь рекомендация:
 http://tools.ietf.org/html/rfc2119#section-4
 так что формально и фактически Chrome ничего не нарушает.
 
 Фактически - упомянутый SHOULD NOT на тот момент безусловно
 отклонялся Apache'ом,
 
 И это безусловный BUG апача, копировать его в nginx - нет смысла.
 Apache ведь не является reference implementation протокола HTTP/1.1

Это не баг - как уже говорилось выше, вернуть 400 сервер может в 
любой момент.

Это ровно такое же решение авторов апача, как и предлагаемый 
возврат 400 в случае несовпадения Host и host'а из request line.

 а противоречащие друг другу Host +
 Request-Line - формально вообще ничего не нарушали
 
 Вообще-то в RFC 2616 написано в точности то же самое что и в RFC 7230:
 
 http://tools.ietf.org/html/rfc2616#section-14.23
 
The Host request-header field specifies the Internet host and port
number of the resource being requested, as obtained from the original
URI given by the user or referring resource (generally an HTTP URL,
as described in section 3.2.2). The Host field value MUST represent
the naming authority of the origin server or gateway given by the
original URL. This allows the origin server or gateway to
differentiate between internally-ambiguous URLs, such as the root /
URL of a server for multiple host names on a single IP address.
 
 Здесь точно так же присутствует требование MUST,
 то есть клиент, который не выполнил это требование -
 прислал на сервер невалидный запрос и сервер имеет
 полное право ответить на такой запрос статусом 400.

Здесь нет каких-либо явных требований о совпадении Host и host'а 
из request-line.

Что касается имеет полное право, то руководствующийся RFC 2616 
сервер не имеет права ответить на такой запрос 400, так как MUST 
ignore.  Этот вопрос, мне помнится, Валентин уже прояснял.

 до выхода HTTPbis.
 
 Выход HTTPbis так и не состоялся. Вместо этого - решили
 уточнить спецификацию протокола HTTP/1.1 и сконцентировать
 свои усилия в работе над протоколом HTTP/2.0 на базе SPDY,
 насколько мне известно.

HTTPbis - рабочая группа, созданная для уточнения HTTP/1.1.  И 
именно набор RFC 7230 .. 7237 - основной результат её работы, aka 
HTTPbis.

http://trac.tools.ietf.org/wg/httpbis/trac/wiki

 И что на самом деле происходит в реальной жизни
 - это отдельный интересный вопрос.
 
 В реальной жизни я не встречал софта, который бы создавал запросы
 
 GET http://apple.com/ HTTP/1.1
 Host: samsung.com
 
 и ожидал бы, что такой запрос будет нормально обработан сервером.

Такой софт, безусловно, встретить сложно.  Проблема в том, что 
зачастую разный странный софт занимается модификацией запросов, и 
результаты могут быть малопредсказуемы.

 Среди прочего, например, HTTPbis явно требует возвращать 400,
 если запрос содержит несколько заголовков Host.
 
 Нет смысла отправлять несколько одинаковых заголовков
 с одинаковым значением. А разных значений там быть не должно.
 
 Единственное что добавилось в RFC 7230 - это более явное требование,
 чтобы такой заголовок был всего один. В RFC 2616 это было между строк.

Угу, и именно так поступал nginx до упомянутого коммита.  Только 
не работает.

Из совсем свежих примеров - Opera при работе по SPDY присылает два 
заголовка Content-Length.  Ну и кто они после этого?

 В своё время, однако, nginx'у потребовалось от этой практики отказаться:
 
 http://hg.nginx.org/nginx/rev/b9de93d804ea
 
 Если мне не изменяет память, причина была всё та же - реальная
 жизнь заставила.
 
 Можно подробнее узнать про причину?

Это вопрос к Игорю, может быть он помнит подробности.  

-- 
Maxim Dounin
http://nginx.org/

___

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Валентин Бартенев
On Tuesday 17 June 2014 15:03:18 Maxim Dounin wrote:
[..]
  Среди прочего, например, HTTPbis явно требует возвращать 400,
  если запрос содержит несколько заголовков Host.
  
  Нет смысла отправлять несколько одинаковых заголовков
  с одинаковым значением. А разных значений там быть не должно.
  
  Единственное что добавилось в RFC 7230 - это более явное требование,
  чтобы такой заголовок был всего один. В RFC 2616 это было между строк.
 
 Угу, и именно так поступал nginx до упомянутого коммита.  Только 
 не работает.
 
 Из совсем свежих примеров - Opera при работе по SPDY присылает два 
 заголовка Content-Length.  Ну и кто они после этого?
[..]

Если бы два заголовка... они там посылают один заголовок, но со значением, 
содержащим два одинаковых числа через запятую, и похоже, что само число при 
этом не соответствует реальному размеру тела.

--
Валентин Бартенев
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность S.A.N
Илья Шипицин Wrote:
---
 а расскажите на примерах, как эту уязвимость можно эксплуатировать?

Вариантов эксплойтов очень много:

1. SQL иньекции, когда содержимое HTTP_HOST без экранирования используется в
SQL запросах.
2. Хаки в include path, например в некоторых фрейворках имена конфиг файлов
строится из имени хоста и загружаются таким образом
include(configs/$_SERVER[HTTP_HOST].php)
3. Обход конфигураций веб сервера, Nginx будет выполнять директивы хоста
указанного в absolute uri, но на бекенд отправит HTTP_HOST указанный в
заголовке Host
4. И всевозможные обходы логики приложений которая строится на HTTP_HOST,
например система логирования, добавляет запись в таблицу поле host является
связующем для определения на каком сайте юзер выполнил определенное
действия, если вы будите высылать произвольный заголовок Host, нарушится
целостной данных и просмотреть ваши действия на реальном сайте будет не
возможно, потому что ваши действия логировались для сайта (host) которого не
существует или на оборот выполнять действия на одном сайте отправлять
заголовок Host другого сайта, тогда ваши действия будут логироватся для
другого сайта.

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

Пункты 1, 2, 4 полностью на совести разработчиков бекенд-приложений, это их
зона ответственности, но третий пункт (обход конфигураций веб сервера) на
мой взгляд остаётся на совести разработчиков веб-сервера.
Если закрыть эту уязвимость на уровне веб-сервера, сразу закроются все
варианты её эксплойта.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250942#msg-250942

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Илья Шипицин
а чем опасен пункт 3) ?
мне почему-то кажется, что масштаб бедствия в районе нуля, шум из-за ничего.

ну ок, в nginx сработал конфиг для одного значения Host, на бекенд
улетело другое, что в этом случае может произойти страшного ?
в интернет-банке деньги спишутся со счета ?

или это какие-то абстрактные угрозы и именно так к ним и надо относиться ?


17 июня 2014 г., 20:46 пользователь S.A.N nginx-fo...@nginx.us написал:
 Илья Шипицин Wrote:
 ---
 а расскажите на примерах, как эту уязвимость можно эксплуатировать?

 Вариантов эксплойтов очень много:

 1. SQL иньекции, когда содержимое HTTP_HOST без экранирования используется в
 SQL запросах.
 2. Хаки в include path, например в некоторых фрейворках имена конфиг файлов
 строится из имени хоста и загружаются таким образом
 include(configs/$_SERVER[HTTP_HOST].php)
 3. Обход конфигураций веб сервера, Nginx будет выполнять директивы хоста
 указанного в absolute uri, но на бекенд отправит HTTP_HOST указанный в
 заголовке Host
 4. И всевозможные обходы логики приложений которая строится на HTTP_HOST,
 например система логирования, добавляет запись в таблицу поле host является
 связующем для определения на каком сайте юзер выполнил определенное
 действия, если вы будите высылать произвольный заголовок Host, нарушится
 целостной данных и просмотреть ваши действия на реальном сайте будет не
 возможно, потому что ваши действия логировались для сайта (host) которого не
 существует или на оборот выполнять действия на одном сайте отправлять
 заголовок Host другого сайта, тогда ваши действия будут логироватся для
 другого сайта.

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

 Пункты 1, 2, 4 полностью на совести разработчиков бекенд-приложений, это их
 зона ответственности, но третий пункт (обход конфигураций веб сервера) на
 мой взгляд остаётся на совести разработчиков веб-сервера.
 Если закрыть эту уязвимость на уровне веб-сервера, сразу закроются все
 варианты её эксплойта.

 Posted at Nginx Forum: 
 http://forum.nginx.org/read.php?21,246086,250942#msg-250942

 ___
 nginx-ru mailing list
 nginx-ru@nginx.org
 http://mailman.nginx.org/mailman/listinfo/nginx-ru
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Валентин Бартенев
On Tuesday 17 June 2014 10:46:01 S.A.N wrote:
[..]
 3. Обход конфигураций веб сервера, Nginx будет выполнять директивы хоста
 указанного в absolute uri, но на бекенд отправит HTTP_HOST указанный в
 заголовке Host
[..]

Как уже неоднократно в этой ветке говорилось, nginx в параметрах HTTP_* пишет
ровно то, что от него требуется: заголовки, пришедшие от клиента, в том виде,
в котором они получены.

Это не имеет ни какого отношения к выбору виртуального сервера, который,
к слову, может быть осуществлен множеством других способов, в том числе,
не связанных с HTTP вовсе.

Пытаться проводить тут какую-либо параллель - бессмысленно.  Нет никакого
обхода конфигурации.  То, что значение в HTTP_HOST должно каким-то образом
соответствовать выбранному блоку server - не более чем чья-то фантазия.

HTTP_* - данные пришедшие от клиента.  И если разработчик приложения не знает 
о том, что входные данные необходимо надлежавшим образом фильтровать, то тут
уже ничем не поможешь.


 
 Пункты 1, 2, 4 полностью на совести разработчиков бекенд-приложений, это их
 зона ответственности, но третий пункт (обход конфигураций веб сервера) на
 мой взгляд остаётся на совести разработчиков веб-сервера.
 Если закрыть эту уязвимость на уровне веб-сервера, сразу закроются все
 варианты её эксплойта.
 

Недавно на глаза попался замечательная цитата из интервью с Клинтом Иствудом:

I remember going to a huge waterfall on a glacier in Iceland. People were 
there on a rock-platform overlook to see it. They had their kids. There was a 
place that wasn't sealed off, but it had a cable that stopped anybody from 
going past a certain point. I said to myself, You know, in the States they'd 
have that hurricane-fenced off, because they're afraid somebody's gonna fall 
and some lawyer's going to appear. There, the mentality was like it was in 
America in the old days: If you fall, you're stupid.

--
Валентин Бартенев
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность S.A.N
Илья Шипицин Wrote:
---
 а чем опасен пункт 3) ?
 мне почему-то кажется, что масштаб бедствия в районе нуля, шум из-за
 ничего.
 
 ну ок, в nginx сработал конфиг для одного значения Host, на бекенд
 улетело другое, что в этом случае может произойти страшного ?
 в интернет-банке деньги спишутся со счета ?
 
 или это какие-то абстрактные угрозы и именно так к ним и надо
 относиться ?

Угрозы от третьего пункта, зависят от отличий конфигурации хостов, который
исполняет Nginx и который уходит в значении HTTP_HOST на бекенд.
Отличий может быть масса, ограничения по IP, ограничения по кол-ву
одновременных запросов с IP, ограничения по размеру тела запросов и методов
запроса, наличия и отсутствия кеширования, не выполнения директив internal
для location потому что Nginx выполняет директивы другого хоста где нет
таких location и самое забавное это безусловное доверия бекенд-приложения
что юзер прошел аутентификация на уровне веб-сервера потому что эта
аутентификация прописана для хоста который пришел на бекенд в HTTP_HOST.

Но даже если у вас все хосты сконфигурированы одинаково и вы на сервере
используете SERVER_NAME вместо HTTP_HOST, у вас остается риск что где-то в
конфиге используется переменная $http_host вместо $host, расскажу ситуацию
которая возникла у моих знакомых.

Все хосты использовали единый fastcgi_cache_path, ключ для файл кеша
создавался как-то так: fastcgi_cache_key $http_host$uri$args;
Теперь делаем запрос

GET http://apple.com/ HTTP/1.1
Host: samsung.com

Nginx обрабатывает директивы для хоста apple.com, бекенд правильно
генерирует страницу для apple.com, но в ключ кеша идет значения $http_host
т.е samsung.com и при следующем запросе http://samsung.com/ мы увидим
страницу для apple.com.
Это легко исправляется, в ключ кеша поставить $host вместо $http_host или
для каждого хоста использовать свой собственный fastcgi_cache_path.

Никогда нельзя доверять значению $http_host, но как показывает практика,
программисты бекенд-приложений доверяют HTTP_HOST, пологая что Nginx
безопасный и не пропустит инвалидный запросы. Но вот не задача разработчики
Nginx так же считают что бекенд разработчики умные и всегда пишут безопасный
код обрабатывая инвалидные заголовки Host.
К сожалению это не так.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250956#msg-250956

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Илья Шипицин
пока что все озвученные сценарии для пользователя приведут к
400/404/200, ну то есть назло маме отморожу уши.
ну ок, пользователь специально сконструировал такой запрос, чтобы он
попал в другой хост. ему там ответили 400 (в моих случаях обычно 404 в
силу особенностей майкрософтовского http.sys)

мне как администратору сервера это чем грозит ?
ну увеличится доля 404-х. посмотрю, удивлюсь, разведу руками. надоест,
отключу access_log.


18 июня 2014 г., 1:31 пользователь S.A.N nginx-fo...@nginx.us написал:
 Илья Шипицин Wrote:
 ---
 а чем опасен пункт 3) ?
 мне почему-то кажется, что масштаб бедствия в районе нуля, шум из-за
 ничего.

 ну ок, в nginx сработал конфиг для одного значения Host, на бекенд
 улетело другое, что в этом случае может произойти страшного ?
 в интернет-банке деньги спишутся со счета ?

 или это какие-то абстрактные угрозы и именно так к ним и надо
 относиться ?

 Угрозы от третьего пункта, зависят от отличий конфигурации хостов, который
 исполняет Nginx и который уходит в значении HTTP_HOST на бекенд.
 Отличий может быть масса, ограничения по IP, ограничения по кол-ву
 одновременных запросов с IP, ограничения по размеру тела запросов и методов
 запроса, наличия и отсутствия кеширования, не выполнения директив internal
 для location потому что Nginx выполняет директивы другого хоста где нет
 таких location и самое забавное это безусловное доверия бекенд-приложения
 что юзер прошел аутентификация на уровне веб-сервера потому что эта
 аутентификация прописана для хоста который пришел на бекенд в HTTP_HOST.

 Но даже если у вас все хосты сконфигурированы одинаково и вы на сервере
 используете SERVER_NAME вместо HTTP_HOST, у вас остается риск что где-то в
 конфиге используется переменная $http_host вместо $host, расскажу ситуацию
 которая возникла у моих знакомых.

 Все хосты использовали единый fastcgi_cache_path, ключ для файл кеша
 создавался как-то так: fastcgi_cache_key $http_host$uri$args;
 Теперь делаем запрос

 GET http://apple.com/ HTTP/1.1
 Host: samsung.com

 Nginx обрабатывает директивы для хоста apple.com, бекенд правильно
 генерирует страницу для apple.com, но в ключ кеша идет значения $http_host
 т.е samsung.com и при следующем запросе http://samsung.com/ мы увидим
 страницу для apple.com.
 Это легко исправляется, в ключ кеша поставить $host вместо $http_host или
 для каждого хоста использовать свой собственный fastcgi_cache_path.

 Никогда нельзя доверять значению $http_host, но как показывает практика,
 программисты бекенд-приложений доверяют HTTP_HOST, пологая что Nginx
 безопасный и не пропустит инвалидный запросы. Но вот не задача разработчики
 Nginx так же считают что бекенд разработчики умные и всегда пишут безопасный
 код обрабатывая инвалидные заголовки Host.
 К сожалению это не так.

 Posted at Nginx Forum: 
 http://forum.nginx.org/read.php?21,246086,250956#msg-250956

 ___
 nginx-ru mailing list
 nginx-ru@nginx.org
 http://mailman.nginx.org/mailman/listinfo/nginx-ru
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность S.A.N
Maxim Dounin Wrote:
---
 Возможно, когда-нибудь мы и придём к тому, что в таких ситуациях 
 будет возвращаться 400.  Но это ни коим образом не избавляет от 
 необходимости исправить приложение.

Приведенный мной пример немного утрирован, но взят из реальной жизни, это
внутренний портал довольно большой компании, на private.example.com работает
PHP сайт который ничего про аунтификацию юзеров не знает, этим занимается
локальный ASP сервер, на который отправляется подзапрос для аунтификации
локального юзера, создания общей сессии или токена который передается в
куках, для подтверждения что юзер прошел аутентификация сделано не было,
всем казалось что такая схема более чем надежна и главное что минимальные
трудозатраты.

Правильно что вы её критикуете, но вить поломалась эта схема благодаря тому
что Nginx не отдал 400 ошибку и выполнил этот заведомо инвалидный запрос.
Целью данного примера, было показать насколько важно для бекенд-приложения
исполнения всех директив Nginx конфига.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250958#msg-250958

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность Илья Шипицин
расскажу вам тоже одну байку.
читал как-то по Linux.

поставили линукс, настроили ssh, зашли удаленно.
один слушатель сильно занервничал.

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


18 июня 2014 г., 1:31 пользователь S.A.N nginx-fo...@nginx.us написал:
 Илья Шипицин Wrote:
 ---
 а чем опасен пункт 3) ?
 мне почему-то кажется, что масштаб бедствия в районе нуля, шум из-за
 ничего.

 ну ок, в nginx сработал конфиг для одного значения Host, на бекенд
 улетело другое, что в этом случае может произойти страшного ?
 в интернет-банке деньги спишутся со счета ?

 или это какие-то абстрактные угрозы и именно так к ним и надо
 относиться ?

 Угрозы от третьего пункта, зависят от отличий конфигурации хостов, который
 исполняет Nginx и который уходит в значении HTTP_HOST на бекенд.
 Отличий может быть масса, ограничения по IP, ограничения по кол-ву
 одновременных запросов с IP, ограничения по размеру тела запросов и методов
 запроса, наличия и отсутствия кеширования, не выполнения директив internal
 для location потому что Nginx выполняет директивы другого хоста где нет
 таких location и самое забавное это безусловное доверия бекенд-приложения
 что юзер прошел аутентификация на уровне веб-сервера потому что эта
 аутентификация прописана для хоста который пришел на бекенд в HTTP_HOST.

 Но даже если у вас все хосты сконфигурированы одинаково и вы на сервере
 используете SERVER_NAME вместо HTTP_HOST, у вас остается риск что где-то в
 конфиге используется переменная $http_host вместо $host, расскажу ситуацию
 которая возникла у моих знакомых.

 Все хосты использовали единый fastcgi_cache_path, ключ для файл кеша
 создавался как-то так: fastcgi_cache_key $http_host$uri$args;
 Теперь делаем запрос

 GET http://apple.com/ HTTP/1.1
 Host: samsung.com

 Nginx обрабатывает директивы для хоста apple.com, бекенд правильно
 генерирует страницу для apple.com, но в ключ кеша идет значения $http_host
 т.е samsung.com и при следующем запросе http://samsung.com/ мы увидим
 страницу для apple.com.
 Это легко исправляется, в ключ кеша поставить $host вместо $http_host или
 для каждого хоста использовать свой собственный fastcgi_cache_path.

 Никогда нельзя доверять значению $http_host, но как показывает практика,
 программисты бекенд-приложений доверяют HTTP_HOST, пологая что Nginx
 безопасный и не пропустит инвалидный запросы. Но вот не задача разработчики
 Nginx так же считают что бекенд разработчики умные и всегда пишут безопасный
 код обрабатывая инвалидные заголовки Host.
 К сожалению это не так.

 Posted at Nginx Forum: 
 http://forum.nginx.org/read.php?21,246086,250956#msg-250956

 ___
 nginx-ru mailing list
 nginx-ru@nginx.org
 http://mailman.nginx.org/mailman/listinfo/nginx-ru
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность S.A.N
Илья Шипицин Wrote:
---
 пока что все озвученные сценарии для пользователя приведут к
 400/404/200, ну то есть назло маме отморожу уши.
 ну ок, пользователь специально сконструировал такой запрос, чтобы он
 попал в другой хост. ему там ответили 400 (в моих случаях обычно 404
 в
 силу особенностей майкрософтовского http.sys)
 
 мне как администратору сервера это чем грозит ?
 ну увеличится доля 404-х. посмотрю, удивлюсь, разведу руками.
 надоест,
 отключу access_log.
 

Так это и есть наша цель, чтобы веб-сервер отдавал 400 ошибку на такие
запросы, вместо передачи их на бекенд.
Я так понимаю, что у вас происходит HTTP проксирования и бекендом выступает
другой веб сервер который и отдает 400 ошибку?
Мы здесь обсуждаем проблемы связанные с FastCGI где бекендом выступает
приложения которое в своей внутренней логике использует HTTP_HOST и
подразумевает что Nginx выполнил все директивы для этого хоста.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250961#msg-250961

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-17 Пенетрантность S.A.N
Валентин Бартенев Wrote:
---
 Как уже неоднократно в этой ветке говорилось, nginx в параметрах
 HTTP_* пишет
 ровно то, что от него требуется: заголовки, пришедшие от клиента, в
 том виде,
 в котором они получены.

Nginx так и должен делать, если запрос валидный, а инвалидные запросы на
бекенд передавать не имеет никакого смысла, они не несут в себе полезной
нагрузки (payload) для бекенда.
По этому, мы разработчики бекенда хотели бы чтобы Nginx не передавал нам
инвалидные запросы, а отдавал 400 статус.

Немного позволю себе лирики, надеюсь никто не обидеться.
Слепое выполнения протокола CGI 1.1 для инвалидных запросов, напоминает
анегдот:
Когда маленькую девочку оставили одну дома и дали указания чужим людям двери
не открывать.
В квартире начался пожар, приехали пожарные стучат в двери, но девочка
утверждает, что двери чужим людям нельзя открывать, потому что были такие
указания )
Самое удивительное что переубедить девочку нельзя, она уверена в своей
правоте, вить указаний открывать двери пожарным не было, то что пожарным
тушить пожар из окна улицы сложней и накладней, по мнению девочки это
проблема пожарных, если они пожарные хреновые специалисты им уже не помочь.
Даже не знаю кто виноват, родители девочки что не дали указания что делать
при пожаре (нет указаний в CGI 1.1 при не соответствии host и absolute uri)
или пожарные не умеют быстро переубеждать.

Мораль этой байки такова - при возникновении исключительной ситуации, когда
нет указаний как поступать в этой ситуации, нужно руководствоватся общим
правилом поведения в исключительных ситуациях, они гласят - нужно убегать,
т.е выбрасывать эксепшин, в нашем случаи это выдать 400 статус и завершить
запрос.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250962#msg-250962

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-16 Пенетрантность Maxim Dounin
Hello!

On Sun, Jun 15, 2014 at 11:07:58PM +0300, Gena Makhomed wrote:

 On 14.06.2014 21:14, Maxim Dounin wrote:
 
 http://habrahabr.ru/post/166855/
 ...
 Прокси-сервер, помимо всего прочего, является сервером, и
 процитированное требование вернуть 400 в ответ на Host header
 field with an invalid field-value - к нему тоже относится.
 Соответственно, если трактовать термин invalid field-value как
 включающий проверку не только синтаксиса, но и требований,
 предъявляемых к формированию заголовка Host клиентом, то
 требование ignore the received Host header теряет смысл.
 
 Максим, теперь я понял, в чем была моя ошибка, спасибо!
 
 Теримн field-value расшифровывается в 3.2.  Header Fields,
 http://tools.ietf.org/html/rfc7230#section-3.2:
 
  field-value= *( field-content / obs-fold )
 
 Соответственно invalid - это то, что не соответствует указанному
 синтаксису.
 
 Понял, спасибо!
 
 Но есть один не совсем понятный нюанс -
 озвученные в RFC 7230 требования к клиенту:
 
 http://tools.ietf.org/html/rfc7230#section-5.4
 
A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).
 
 - это ведь требования к синтаксису, которые обязательны для выполнения.

Нет, это не требования к синтаксису, это требования к семантике.  
И они обязательны для клиента, но не для сервера.  Соответственно, 
что делать в случае, если клиент их не выполнил - на совести 
сервера.

 А вот что есть в RFC 7231:
 
 http://tools.ietf.org/html/rfc7231#section-6.5.1
 
 6.5.1. 400 Bad Request
 
The 400 (Bad Request) status code indicates that the server cannot or
will not process the request due to something that is perceived to be
a client error (e.g., malformed request syntax, invalid request
message framing, or deceptive request routing).
 
 Следовательно, сервер имеет право вернуть 400 статус,
 если получит запрос с разными authority component
 в заголовке Host и в absolute Request URI ?

Сервер имеет право вернуть 400 более или менее в любой момент.

 Кроме того, в разделе 5.5. Effective Request URI
 http://tools.ietf.org/html/rfc7230#section-5.5
 
 даже прямо говорят, что запрос может быть misdirected,
 deliberately or accidentally, и что origin server должен
 сам решить, обрабатывать такой запрос или нет, потому что
 it might indicate an attempt to bypass security filters,
 trick the server into delivering non-public content,
 or poison a cache.
 
 именно это ведь и происходит в случае запроса
 
 GET http://apple.com/ HTTP/1.1
 Host: samsung.com
 
 Разве ответить на такой запрос 400-м статусом не будет лучше?

Это зависит от многих факторов.  Вот тут Валентин давеча 
напрограммировал возврат 400, если имя, указанное в SNI, не 
совпадало с именем, используемым в запросе, ибо RFC 6066 говорит:

   ... If the server_name is
   established in the TLS session handshake, the client SHOULD NOT
   attempt to request a different server name at the application layer.

Так пришлось распрограмировать обратно - потому что Chrome 
использует a different server name at the application layer, 
когда считает нужным/возможным.

То, как ведёт себя nginx по умолчанию - вполне себе безопасно, и 
проблемы нет.  Какая-либо проблема появляется тогда и только 
тогда, когда администратор начинает писать в конфиге $http_host, 
не думая о последствиях.  Есть мнение, что совсем простое решение 
этой проблемы - не делать так (c) анекдот.

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-16 Пенетрантность S.A.N
Maxim Dounin Wrote:
---
 Какая-либо проблема появляется тогда и только 
 тогда, когда администратор начинает писать в конфиге $http_host, 
 не думая о последствиях.  Есть мнение, что совсем простое решение 
 этой проблемы - не делать так (c) анекдот.

Вся проблема в том что сами программисты Nginx в модуле FastCGI используют
переменную $http_host для HTTP_HOST, вместо нормализованной переменой $host,
администраторам на оборот приходится исправлять это своими руками и писать в
конфиге
fastcgi_param  HTTP_HOST  $host;
Если следовать вашей логике, надо изменить код модуля FastCGI, чтобы по
умолчанию Nginx был вполне себе безопасный.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250890#msg-250890

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-16 Пенетрантность Maxim Dounin
Hello!

On Mon, Jun 16, 2014 at 11:19:57AM -0400, S.A.N wrote:

 Maxim Dounin Wrote:
 ---
  Какая-либо проблема появляется тогда и только 
  тогда, когда администратор начинает писать в конфиге $http_host, 
  не думая о последствиях.  Есть мнение, что совсем простое решение 
  этой проблемы - не делать так (c) анекдот.
 
 Вся проблема в том что сами программисты Nginx в модуле FastCGI используют
 переменную $http_host для HTTP_HOST, вместо нормализованной переменой $host,
 администраторам на оборот приходится исправлять это своими руками и писать в
 конфиге
 fastcgi_param  HTTP_HOST  $host;
 Если следовать вашей логике, надо изменить код модуля FastCGI, чтобы по
 умолчанию Nginx был вполне себе безопасный.

По умолчанию в fastcgi http-заголовки передаются как есть, в виде 
параметров HTTP_*.  Каноническое же имя сервера доступно в 
параметре SERVER_NAME.  Что из этого и как использовать - это 
вопрос к приложению, а не к nginx'у.

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-16 Пенетрантность S.A.N
  Maxim Dounin Wrote:
  ---
   Какая-либо проблема появляется тогда и только 
   тогда, когда администратор начинает писать в конфиге $http_host, 
   не думая о последствиях.  Есть мнение, что совсем простое решение 
   этой проблемы - не делать так (c) анекдот.
  
  Вся проблема в том что сами программисты Nginx в модуле FastCGI
 используют
  переменную $http_host для HTTP_HOST, вместо нормализованной
 переменой $host,
  администраторам на оборот приходится исправлять это своими руками и
 писать в
  конфиге
  fastcgi_param  HTTP_HOST  $host;
  Если следовать вашей логике, надо изменить код модуля FastCGI, чтобы
 по
  умолчанию Nginx был вполне себе безопасный.
 
 По умолчанию в fastcgi http-заголовки передаются как есть, в виде 
 параметров HTTP_*.  Каноническое же имя сервера доступно в 
 параметре SERVER_NAME.  Что из этого и как использовать - это 
 вопрос к приложению, а не к nginx'у.

Я знаю, и уже выше объяснял почему бекенд-приложениям нужно использовать
HTTP_HOST вместо SERVER_NAME.
Значения SERVER_NAME не может использоваться, если в директиве server_name
используется маска или бекенд обрабатывает запросы для default_server.

Ещё раз приведу пример, в котором мы легко можем получить доступ, к закрытым
на уровне Nginx ресурсам.

server
{
  server_name *.example.com;
  ...
  fastcgi_pass php;
}

server
{
  server_name private.example.com;

  location / {
  allow 192.168.1.0/24;
  deny all;

  fastcgi_pass php;

  auth_request /auth;
}
...
 }

Как видно два хоста используют один upstream, на котором бекенд приложения
даёт расширенные привилегии юзерам private.example.com, в расчете на то что
Nginx предварительно сделал проверку по IP и успешно провел аунтификацию,
всё вроде логично и удобно сделано, но такая схема легко ломается таким
запросом.

GET http://example.com/SecureData/ HTTP/1.1
Host: private.example.com

Бекенд получает HTTP_HOST=private.example.com, даёт юзеру привилегии, но
Nginx не проводил проверки по IP и не делал запрос аунтификацию, потому что
отработал хост конфигурации для example.com вместо private.example.com

В данном случаи можно было бы использовать переменную SERVER_NAME, но я выше
писал почему это не всегда возможно.

Если мы оба понимаем, что ситуация когда authority component и значения Host
разные, это исключительная ситуация и её нужно обрабатывать как Exception, в
этом случаи есть три варианта поведения, выбросить Exception (отдать 400
статус), исправить ошибку (использовать переменую $host), и самый плохой
вариант (антишаблон) ничего не делать и не обрабатывать эту исключительную
ситуацию и оставить все как есть.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250896#msg-250896

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-16 Пенетрантность Gena Makhomed

On 16.06.2014 15:00, Maxim Dounin wrote:


озвученные в RFC 7230 требования к клиенту:

http://tools.ietf.org/html/rfc7230#section-5.4

A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).

- это ведь требования к синтаксису, которые обязательны для выполнения.


Нет, это не требования к синтаксису, это требования к семантике.


Запись target URI в виде valid request message - это разве не syntax?

http://tools.ietf.org/html/rfc7231#section-2

   When a client constructs an HTTP/1.1 request message, it sends the
   target URI in one of various forms, as defined in (Section 5.3 of
   [RFC7230]).  When a request is received, the server reconstructs an
   effective request URI for the target resource (Section 5.5 of
   [RFC7230]).

   One design goal of HTTP is to separate resource identification from
   request semantics, which is made possible by vesting the request
   semantics in the request method (Section 4) and a few
   request-modifying header fields (Section 5).

effective request URI - это именно что resource identification.

Они ведь разнесли syntax и semantics по двум отдельным документам:

RFC 7230: Message Syntax and Routing
RFC 7231: Semantics and Content


http://tools.ietf.org/html/rfc7231#section-6.5.1

6.5.1. 400 Bad Request

The 400 (Bad Request) status code indicates that the server cannot or
will not process the request due to something that is perceived to be
a client error (e.g., malformed request syntax, invalid request
message framing, or deceptive request routing).

Следовательно, сервер имеет право вернуть 400 статус,
если получит запрос с разными authority component
в заголовке Host и в absolute Request URI ?


Сервер имеет право вернуть 400 более или менее в любой момент.


Да, но здесь явно указывается, когда сервер возвращает 400:
в случае client error, например, malformed request syntax
или deceptive request routing - эти две причины подходят.


Кроме того, в разделе 5.5. Effective Request URI
http://tools.ietf.org/html/rfc7230#section-5.5

даже прямо говорят, что запрос может быть misdirected,
deliberately or accidentally, и что origin server должен
сам решить, обрабатывать такой запрос или нет, потому что
it might indicate an attempt to bypass security filters,
trick the server into delivering non-public content,
or poison a cache.

именно это ведь и происходит в случае запроса

GET http://apple.com/ HTTP/1.1
Host: samsung.com

Разве ответить на такой запрос 400-м статусом не будет лучше?


Это зависит от многих факторов.  Вот тут Валентин давеча
напрограммировал возврат 400, если имя, указанное в SNI, не
совпадало с именем, используемым в запросе, ибо RFC 6066 говорит:

... If the server_name is
established in the TLS session handshake, the client SHOULD NOT
attempt to request a different server name at the application layer.

Так пришлось распрограмировать обратно - потому что Chrome
использует a different server name at the application layer,
когда считает нужным/возможным.


SHOULD NOT - это не запрет, а только лишь рекомендация:
http://tools.ietf.org/html/rfc2119#section-4
так что формально и фактически Chrome ничего не нарушает.

В обсуждаемой выше ситуации написано совсем иначе: MUST.
http://tools.ietf.org/html/rfc2119#section-1
и если клиент этого не сделал - он сам прислал невалидный запрос,
так что ответить 400-м статусом на такой запрос - вполне разумно.

да и в RFC 7230 об этом тоже есть (про поведение хрома):

http://tools.ietf.org/html/rfc7230#section-2.3

   server MUST NOT assume that two requests on the same connection are
   from the same user agent unless the connection is secured and
   specific to that agent.  Some non-standard HTTP extensions (e.g.,
   [RFC4559]) have been known to violate this requirement, resulting in
   security and interoperability problems.


То, как ведёт себя nginx по умолчанию - вполне себе безопасно,
и проблемы нет.  Какая-либо проблема появляется тогда и только
тогда, когда администратор начинает писать в конфиге $http_host,
не думая о последствиях.  Есть мнение, что совсем простое решение
этой проблемы - не делать так (c) анекдот.


Когда nginx выполняет роль origin server или HTTP reverse proxy
- тогда проблем действительно нет, но когда он выполняет роль
gateway и communicates с backend`ом по протоколу FastCGI -
тогда получаются очень неприятные проблемы.

Причина проблем: malformed request syntax,
который не получается корректным образом передать на backend.

Что мешает в этой ситуации вернуть 400 статус? Вместо того,
чтобы отсылать на backend невалидный запрос, интерпретируя
клиентский запрос не по спецификации HTTP/1.1 а по спецификации
CGI/1.1, которая не согласуется со спецификацией протокола HTTP/1.1.

Ничего ведь не сломается и на 

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-15 Пенетрантность Gena Makhomed

On 14.06.2014 21:14, Maxim Dounin wrote:


http://habrahabr.ru/post/166855/

...

Прокси-сервер, помимо всего прочего, является сервером, и
процитированное требование вернуть 400 в ответ на Host header
field with an invalid field-value - к нему тоже относится.
Соответственно, если трактовать термин invalid field-value как
включающий проверку не только синтаксиса, но и требований,
предъявляемых к формированию заголовка Host клиентом, то
требование ignore the received Host header теряет смысл.


Максим, теперь я понял, в чем была моя ошибка, спасибо!


Теримн field-value расшифровывается в 3.2.  Header Fields,
http://tools.ietf.org/html/rfc7230#section-3.2:

 field-value= *( field-content / obs-fold )

Соответственно invalid - это то, что не соответствует указанному
синтаксису.


Понял, спасибо!

Но есть один не совсем понятный нюанс -
озвученные в RFC 7230 требования к клиенту:

http://tools.ietf.org/html/rfc7230#section-5.4

   A client MUST send a Host header field in all HTTP/1.1 request
   messages.  If the target URI includes an authority component, then a
   client MUST send a field-value for Host that is identical to that
   authority component, excluding any userinfo subcomponent and its @
   delimiter (Section 2.7.1).

- это ведь требования к синтаксису, которые обязательны для выполнения.
А вот что есть в RFC 7231:

http://tools.ietf.org/html/rfc7231#section-6.5.1

6.5.1. 400 Bad Request

   The 400 (Bad Request) status code indicates that the server cannot or
   will not process the request due to something that is perceived to be
   a client error (e.g., malformed request syntax, invalid request
   message framing, or deceptive request routing).

Следовательно, сервер имеет право вернуть 400 статус,
если получит запрос с разными authority component
в заголовке Host и в absolute Request URI ?

Кроме того, в разделе 5.5. Effective Request URI
http://tools.ietf.org/html/rfc7230#section-5.5

даже прямо говорят, что запрос может быть misdirected,
deliberately or accidentally, и что origin server должен
сам решить, обрабатывать такой запрос или нет, потому что
it might indicate an attempt to bypass security filters,
trick the server into delivering non-public content,
or poison a cache.

именно это ведь и происходит в случае запроса

GET http://apple.com/ HTTP/1.1
Host: samsung.com

Разве ответить на такой запрос 400-м статусом не будет лучше?

--
Best regards,
 Gena

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-14 Пенетрантность Maxim Dounin
Hello!

On Thu, Jun 12, 2014 at 03:40:21PM +0300, Gena Makhomed wrote:

 On 11.06.2014 22:53, Maxim Dounin wrote:
 
 http://habrahabr.ru/post/166855/
 ...
 Единственный правильный способ: пойти в IETF с предложением исправить
 соответствующие RFC, которые в том числе оговаривают, что следует делать
 при получении нескольких заголовков Host, ну а потом уже сюда.
 ...
 http://tools.ietf.org/html/rfc7230#section-5.4
 
 A server MUST respond with a 400 (Bad Request) status code to any
 HTTP/1.1 request message that lacks a Host header field and to any
 request message that contains more than one Host header field or a
 Host header field with an invalid field-value.
 
 invalid field-value - это в том числе, когда клиент не выполняет
 требований, которые изложены выше в этом же документе:
 
 A client MUST send a Host header field in all HTTP/1.1 request
 messages.  If the target URI includes an authority component, then a
 client MUST send a field-value for Host that is identical to that
 authority component, excluding any userinfo subcomponent and its @
 delimiter (Section 2.7.1).
 
 Если исходить из такой трактовки термина invalid field-value, то
 ранее процитированное требование про the proxy MUST ignore the
 received Host header... и далее по тексту - не имеет смысла.
 
 В стандарте дается однозначное определение, что такое proxy:
 
 A proxy is a message-forwarding agent that is selected
 by the client, usually via local configuration rules.
 
 nginx - это reverse proxy / gateway, и все те требования,
 которые там предъявляются к proxy, - к nginx не применимы.

Я нигде не говорил, что требование - применимо к nginx'у.  Я 
говорил, что упомянутое требование - не имеет смысла, если 
пользоваться предлагаемой интерпретацией термина invalid 
field-value.

Прокси-сервер, помимо всего прочего, является сервером, и 
процитированное требование вернуть 400 в ответ на Host header 
field with an invalid field-value - к нему тоже относится.  
Соответственно, если трактовать термин invalid field-value как 
включающий проверку не только синтаксиса, но и требований, 
предъявляемых к формированию заголовка Host клиентом, то 
требование ignore the received Host header теряет смысл.

Впрочем, сама идея о том, что требования к клиенту как-либо 
опосредованно могут влиять на интерпретацию требований к серверу - 
она странная, если не сказать грубее.

 Как подходить к трактовке термина invalid field-value
 в RFC 7230 тоже написано: http://tools.ietf.org/html/rfc7230#section-1.1

Приведённая ссылка не имеет никакого отношения к термину invalid 
field-value.

Теримн field-value расшифровывается в 3.2.  Header Fields, 
http://tools.ietf.org/html/rfc7230#section-3.2:

field-value= *( field-content / obs-fold )

Соответственно invalid - это то, что не соответствует указанному 
синтаксису.

На этом, наверно, и завершим нашу дискуссию, т.к. конструктивной 
она явно не получается.

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-12 Пенетрантность Gena Makhomed

On 11.06.2014 22:53, Maxim Dounin wrote:


http://habrahabr.ru/post/166855/

...

Единственный правильный способ: пойти в IETF с предложением исправить
соответствующие RFC, которые в том числе оговаривают, что следует делать
при получении нескольких заголовков Host, ну а потом уже сюда.

...

http://tools.ietf.org/html/rfc7230#section-5.4

A server MUST respond with a 400 (Bad Request) status code to any
HTTP/1.1 request message that lacks a Host header field and to any
request message that contains more than one Host header field or a
Host header field with an invalid field-value.

invalid field-value - это в том числе, когда клиент не выполняет
требований, которые изложены выше в этом же документе:

A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).


Если исходить из такой трактовки термина invalid field-value, то
ранее процитированное требование про the proxy MUST ignore the
received Host header... и далее по тексту - не имеет смысла.


В стандарте дается однозначное определение, что такое proxy:

A proxy is a message-forwarding agent that is selected
by the client, usually via local configuration rules.

nginx - это reverse proxy / gateway, и все те требования,
которые там предъявляются к proxy, - к nginx не применимы.

Как подходить к трактовке термина invalid field-value
в RFC 7230 тоже написано: http://tools.ietf.org/html/rfc7230#section-1.1

Сейчас nginx этим требованиям стандарта HTTP/1.1 не соответствует,
и пытается обрабатывать те запросы, на которые он на самом деле
MUST respond with a 400 (Bad Request) status code.

И это создает security проблемы с backend`ами, которые работают
по протоколу FastCGI и расчитывают на то, что nginx соответствует
требованиям стандарта HTTP/1.1 и не пропустит на backend запрос
с невалидным значением в заголовке Host. (RFC 2616 или RFC 7230)

Более правильно в этой ситуации наверное будет все-таки
привести nginx в соответствие с требованиями RFC 7230,
вместо того чтобы добавлять workaround`ы для этого бага
на стороне каждого backend`а, который работает с nginx.

===

Вопрос: признают ли разработчики nginx эту ошибку
и будет ли она исправлена в новых версиях сервера?

Второй вопрос: признается ли эта ошибка в nginx
проблемой с безопасностью (security vulnerability)
и будет ли по этому поводу выпущено CVE / advisorу
на http://nginx.org/en/security_advisories.html ?

--
Best regards,
 Gena

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-12 Пенетрантность S.A.N
Gena Makhomed Wrote:
---
 
 и да, отвечать с 400 статусом тут даже более логично,
 потому что если authority component в строке запроса
 и в заголовке Host: разные - это явно попытка взлома.
 

Я так же считаю, что 400 статус в этом случаи должен быть.
Если Nginx реализует эту логику, думаю проблем с обратной совместимостью не
будет, вот если не реализует выдачу 400 статуса и оставить все как есть
проблемы возможны на стороне бекенда.

Не понятная позиция Nginx в нежелании реализовать данную логику.

Posted at Nginx Forum: 
http://forum.nginx.org/read.php?21,246086,250821#msg-250821

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-11 Пенетрантность Maxim Dounin
Hello!

On Wed, Jun 11, 2014 at 02:25:38PM +0300, Gena Makhomed wrote:

 On 11.06.2014 13:42, Валентин Бартенев wrote:
 
 http://habrahabr.ru/post/166855/
 
 Единственный правильный способ: пойти в IETF с предложением исправить
 соответствующие RFC, которые в том числе оговаривают, что следует делать
 при получении нескольких заголовков Host, ну а потом уже сюда.
 
 http://tools.ietf.org/html/rfc7230#section-5.4
 
  When a proxy receives a request with an absolute-form of
  request-target, the proxy MUST ignore the received Host header field
  (if any) and instead replace it with the host information of the
  request-target.  A proxy that forwards such a request MUST generate a
  new Host field-value based on the received request-target rather than
  forward the received Host field-value.
 
 Referer: http://www.opennet.ru/opennews/art.shtml?num=39956
 
 Не очень понятно, а что хотели сказать этой цитатой?
 
 Так, на всякий случай, nginx не является proxy согласно терминологии того
 же RFC 7230.
 
 Ok.
 
 http://tools.ietf.org/html/rfc7230#section-5.4
 
A server MUST respond with a 400 (Bad Request) status code to any
HTTP/1.1 request message that lacks a Host header field and to any
request message that contains more than one Host header field or a
Host header field with an invalid field-value.
 
 invalid field-value - это в том числе, когда клиент не выполняет
 требований, которые изложены выше в этом же документе:
 
A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).

Если исходить из такой трактовки термина invalid field-value, то 
ранее процитированное требование про the proxy MUST ignore the 
received Host header... и далее по тексту - не имеет смысла.

Я просто оставлю эту ссылку здесь:

http://lurkmore.to/Взаимоисключающие_параграфы

-- 
Maxim Dounin
http://nginx.org/

___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru

Re: Об одной малоизвестной уязвимости в веб сайтах

2014-06-11 Пенетрантность Dmitry
Не понял в чем проблема, чисто наитием использую давно:

# Add default fake server
include //default_server.conf;

где default_server.conf:
=

server {
listen *:80 default_server;
server_name _;
return 403;
}



2014-06-11 15:25 GMT+04:00 Gena Makhomed g...@csdoc.com:

 On 11.06.2014 13:42, Валентин Бартенев wrote:

  http://habrahabr.ru/post/166855/


 Единственный правильный способ: пойти в IETF с предложением исправить
 соответствующие RFC, которые в том числе оговаривают, что следует делать
 при получении нескольких заголовков Host, ну а потом уже сюда.


 http://tools.ietf.org/html/rfc7230#section-5.4

  When a proxy receives a request with an absolute-form of
  request-target, the proxy MUST ignore the received Host header field
  (if any) and instead replace it with the host information of the
  request-target.  A proxy that forwards such a request MUST generate
 a
  new Host field-value based on the received request-target rather
 than
  forward the received Host field-value.

 Referer: http://www.opennet.ru/opennews/art.shtml?num=39956


 Не очень понятно, а что хотели сказать этой цитатой?

 Так, на всякий случай, nginx не является proxy согласно терминологии
 того
 же RFC 7230.


 Ok.

 http://tools.ietf.org/html/rfc7230#section-5.4

A server MUST respond with a 400 (Bad Request) status code to any
HTTP/1.1 request message that lacks a Host header field and to any
request message that contains more than one Host header field or a
Host header field with an invalid field-value.

 invalid field-value - это в том числе, когда клиент не выполняет
 требований, которые изложены выше в этом же документе:

A client MUST send a Host header field in all HTTP/1.1 request
messages.  If the target URI includes an authority component, then a
client MUST send a field-value for Host that is identical to that
authority component, excluding any userinfo subcomponent and its @
delimiter (Section 2.7.1).

 следовательно, если приходит запрос

 GET http://example.com/ HTTP/1.1
 Host: example.org

 - это Host header field with an invalid field-value
 и nginx MUST respond with a 400 (Bad Request) status code.

 Если такой запрос приходит по HTTP/1.0 - в этой версии
 протокола нет absolute-form и тоже надо отвечать 400 статусом.

 текущее поведение nginx не соответствует требованиям RFC 7230 ?

 P.S.

 и да, отвечать с 400 статусом тут даже более логично,
 потому что если authority component в строке запроса
 и в заголовке Host: разные - это явно попытка взлома.

 --
 Best regards,
  Gena


 ___
 nginx-ru mailing list
 nginx-ru@nginx.org
 http://mailman.nginx.org/mailman/listinfo/nginx-ru




-- 
Dmitry Goryainov
___
nginx-ru mailing list
nginx-ru@nginx.org
http://mailman.nginx.org/mailman/listinfo/nginx-ru