Подтвердить что ты не робот

Может ли Python string.format() быть безопасным для ненадежных строк формата?

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

Я хотел бы использовать синтаксис формата PEP 3101(), и я рассматриваю возможность переопределения методов в Formatter, чтобы сделать его защищенным для ненадежного ввода.

Ниже приведены риски, которые я вижу с помощью .format():

  • Padding позволяет указать произвольные длины, поэтому '{: > 9999999999}'. format (..) может запустить сервер из памяти и быть DOS. Мне нужно отключить это.
  • Формат позволяет вам получить доступ к полям внутри объектов, что полезно, но это жутко, что вы можете получить доступ к dunder-переменным и начать сверление в биты стандартной библиотеки. Там не сказано, где может быть getattr(), который имеет побочные эффекты или возвращает что-то секретное. Я бы выделил атрибут/индекс доступа, переопределив get_field().
  • Естественно, мне нужно будет заполучить некоторые исключения.

Мои предположения:

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

Каковы ваши мысли? Возможное? Невозможно? Просто неразумно?


Edit: Armin Ronacher описывает неприятную утечку информации, если вы не отфильтровываете доступ к переменной dunder, но, по-видимому, считаете, что формат защиты() возможен:

{local_foo.__init__.__globals__[secret_global]}

http://lucumr.pocoo.org/2016/12/29/careful-with-str-format/

(Лично я на самом деле не отправил маршрут ненадежного формата() в свой продукт, но обновляюсь для полноты)

4b9b3361

Ответ 1

Хороший инстинкт. Да, злоумышленник, способный поставлять произвольную строку формата, является уязвимостью под python.
  • Отказ в обслуживании, вероятно, наиболее прост в обращении. В этот случай, ограничивающий размер строки или количество операторов в пределах строки будет устранена эта проблема. Должно быть где разумному пользователю не потребуется генерировать строку с больше переменных, чем X, и эта сумма вычислений не подвержена риску из-за использования в DoS-атаке.
  • Возможность доступа к атрибутам внутри объекта может быть опасной. Тем не менее, я не думаю, что родительский класс Object имеет полезный Информация. Объект, предоставленный в формат, должен содержать что-то чувствительное. В любом случае этот тип обозначений может быть ограничен с регулярным выражением.
  • Если строки формата предоставляются пользователю, пользователю может потребоваться знать сообщение об ошибке для отладки. Однако сообщения об ошибках могут содержат информацию о сенсибилизации, такую ​​как локальные пути или имена классов. Делать обязательно ограничьте информацию, которую может получить злоумышленник.

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