Я пытаюсь закодировать безопасный и легкий белый-основанный на основе HTML очиститель, который будет использовать DOMDocument. Чтобы избежать ненужной сложности, я готов сделать следующие компромиссы:
script
и style
разделяются вместе body
Я много читал об атаках и предотвращении XSS, и я надеюсь, что я не слишком наивна (если да, то сообщите мне!) В предположении, что если я последую всем правилам, упомянутым выше, я буду безопасно от XSS.
Проблема в том, что я не уверен, что другие теги и атрибуты (в любой версии [X] HTML и / или версии / реализации браузера) могут инициировать события Javascript, помимо атрибутов события Javascript по умолчанию :
onAbort
onBlur
onChange
onClick
onDblClick
onDragDrop
onError
onFocus
onKeyDown
onKeyPress
onKeyUp
onLoad
onMouseDown
onMouseMove
onMouseOut
onMouseOver
onMouseUp
onMove
onReset
onResize
onSelect
onSubmit
onUnload
Существуют ли какие-либо другие атрибуты событий, не относящиеся к умолчанию или запатентованные, которые могут запускать события Javascript (или VBScript и т. Д.) Или выполнение кода? Я могу думать о href
, style
и action
, например:
<a href="javascript:alert(document.location);">XSS</a> // or <b style="width: expression(alert(document.location));">XSS</b> // or <form action="javascript:alert(document.location);"><input type="submit" /></form>
Я, вероятно, просто удалю любые атрибуты style
в тегах HTML, атрибуты action
и href
представляют собой большую проблему, но я думаю, что следующий код достаточно, чтобы убедиться, что их значение является относительным или абсолютным URL-адресом, а не каким-то неприятным кодом Javascript:
$value = $attribute->value; if ((strpos($value, ':') !== false) && (preg_match('~^(?:(?:s?f|ht)tps?|mailto):~i', $value) == 0)) { $node->removeAttributeNode($attribute); }
Итак, мои два очевидных вопроса:
После многих испытаний, размышлений и исследований я придумал следующую (довольно простую) реализацию, которая, по-видимому, невосприимчива к любому вектору атаки XSS, который я мог бы бросить на него.
Спасибо, я благодарен всем вашим ценным ответам.
Вы href
и action
как места javascript:
могут появляться URL-адреса, но вы не src
атрибут src
среди множества других атрибутов загрузки URL-адреса.
Строка 399 OWASP Java HTMLPolicyBuilder – это определение атрибутов URL в дезинфицирующем средстве HTML с белым листингом.
private static final Set<String> URL_ATTRIBUTE_NAMES = ImmutableSet.of( "action", "archive", "background", "cite", "classid", "codebase", "data", "dsync", "formaction", "href", "icon", "longdesc", "manifest", "poster", "profile", "src", "usemap");
Индекс HTML5 содержит сводку типов атрибутов. Он не упоминает некоторые условные вещи, такие как <input type=URL value=...>
но если вы просматриваете этот список для действительного URL-адреса и друзей, вы должны получить приличное представление о том, что добавляет HTML5. Набор атрибутов HTML 4 с типом %URI
также информативен.
Белый список ваших протоколов очень похож на дезинфицирующее средство OWASP . Добавление ftp
и sftp
выглядит достаточно безобидным.
Хорошим источником информации о схеме, связанной с безопасностью для элемента HTML и атрибутов, являются белые списки Caja JSON, которые используются дезинфицирующим средством Caja JS HTML .
Как вы планируете рендерить итоговую DOM? Если вы не будете осторожны, то даже если вы удалите все элементы <script>
, злоумышленник может получить багги-рендерер для создания контента, который браузер интерпретирует как содержащий элемент <script>
. Рассмотрим допустимый HTML, который не содержит элемент сценария.
<textarea></textarea><script>alert(1337)</script></textarea>
Багги-рендерер может выводить содержимое этого как:
<textarea></textarea><script>alert(1337)</script></textarea>
который содержит элемент сценария.
(Полное раскрытие: я написал фрагменты обоих дезинфицирующих средств HTML, упомянутых выше).
Гаруда уже дал то, что я считаю «правильным», и его ссылки очень полезны, но он избил меня до удара!
Я даю свой ответ только для усиления.
В этот день и возраст возрастающих функций в спецификациях html и ecmascript, избегая инъекции скриптов и других подобных уязвимостей в html становится все труднее. С каждым новым дополнением вводится целый мир возможных инъекций. Это связано с тем, что у разных браузеров, вероятно, есть разные идеи о том, как они собираются реализовать эти спецификации, поэтому вы получаете еще более возможные уязвимости.
Взгляните на короткий список векторов, введенный html 5
Лучшее решение – выбрать то, что вы позволите, а не то, что вы отрицаете. Гораздо проще сказать: «Эти теги и эти атрибуты только для тех, которые указаны в тегах, разрешены. Все остальное будет дезинфицировано соответствующим образом или выброшено».
Для меня было бы очень безответственно составить список и сказать «хорошо, вот вам: вот список всех вложенных векторов, которые вы пропустили. Вы можете спать спокойно». На самом деле, вероятно, существует множество инъекционных векторов, которые даже не известны черными шляпами или белыми шляпами. Как говорится на веб-сайте ha.ckers, инъекция скрипта действительно ограничена только умом.
Я хотел бы ответить на ваш конкретный вопрос, по крайней мере, немного, так что вот некоторые вопиющие упущения из вашего черного списка:
img
src
. Я думаю, что важно отметить, что src
является допустимым атрибутом для других элементов и может быть потенциально опасным. img
также dynsrc
и lowsrc
, может быть, даже больше. type
и атрибуты language
CDATA
в дополнение к просто комментариям html. head
и html
элементы внутри body
, а большинство элементов head
only внутри body
любом случае, поэтому это, вероятно, мало поможет. frame
s и iframe
s embed
и, вероятно, object
и applet
Кстати, я уверен, что это не имеет значения, но атрибуты camelCased недействительны xhtml и должны быть ниже. Я уверен, что это не повлияет на вас.
Вы можете проверить эти 2 ссылки для дополнительной справки:
http://adamcecc.blogspot.com/2011/01/javascript.html (это применимо только в том случае, если вы «отфильтрованный» вход всегда будет находиться между тегами сценария на странице)
http://ha.ckers.org/xss.html (в котором перечислены триггеры событий, специфичных для браузера)
Я использую HTML Purifier, как вы это делаете, по этой причине тоже в сочетании с wysiwyg-редактором. То, что я делал иначе, использует очень строгий белый список с несколькими основными метками разметки и атрибутами, доступными и расширяющими его, когда возникла необходимость. Это мешает вам атаковать очень неясные векторы (например, первое звено выше), и вы можете копаться в новом теге / атрибуте по одному.
Просто мои 2 цента.
Не забывайте обработчики событий HTML5 JavaScript
http://www.w3schools.com/html5/html5_ref_eventattributes.asp