Идентификатор сеанса недостаточно случайный - ASP.NET - PullRequest
10 голосов
/ 01 августа 2011

UPDATE

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

@ Vasile Bujac, поскольку ваш ответ был единственным и упоминался с использованием стандартного решения ASP.NET, я принял это как ответ, но всем спасибо за вашу помощь.


Мы используем сканер Retina Acunetix на работе для проверки безопасности наших приложений. Это говорит нам о том, что наши идентификаторы сессий не являются достаточно случайными и слишком предсказуемыми. Я не совсем уверен, как ASP.NET генерирует идентификатор сеанса по умолчанию (я думал, что это GUID в любом случае?), Но я продолжил и реализовал метод расширения класса SessionIDManager и переопределения методов CreateSessionID и Validate для использования Guid как объяснено в этой статье MSDN .

Хотя это делает его немного более случайным, он все равно не дает «желаемого» эффекта в соответствии с Acunetix. Я даже добавил свойство regenerateExpiredSessionId="true" в web.config, и это не имело никакого эффекта. У меня есть ощущение, что мне может понадобиться сознательно позвонить Session.Abandon(), чтобы действительно очистить сеанс и получить новый идентификатор. Проблема в том, что мне нужно позвонить прямо перед входом пользователя, поскольку это единственный надежный способ узнать, что пользователь начинает новый сеанс. Поэтому я ничего не мог установить в сеансе, пока следующая страница не будет загружена с использованием метода Abandon, и это будет означать промежуточную страницу, которая не очень идеальна, но сработает.

Кто-нибудь когда-либо испытывал это или успешно внедрил исправление?

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


Отчет от Acunetix:

КВО-330 ЦАТЭК-59 * 1 031 * OWASP2007-A7

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

Жетоны сессий должны быть созданы с помощью сильного генератора случайных чисел и собраны из большого числа чисел. Например, функции rand () операционной системы обычно может быть достаточно, если она может генерировать 32-битные значения, которые являются статистически однородным распределением. Плохие маркеры сеансов являются инкрементными, зависят от идентификатора учетной записи пользователя, используют только метки времени или имеют другую детерминированную информацию. Другие способы защиты безопасности токена сеанса - это всегда передавать их по SSL, автоматически истекать токен через определенный промежуток времени и явно истекать токен всякий раз, когда пользователь выходит из приложения.

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

  • Убедитесь, что значения токенов имеют размер не менее 32 бит, особенно для приложений с большим количеством одновременных пользователей и большим количеством ежедневных запросов страниц.
  • Размер бита источника энтропии (случайные значения) важнее, чем размер бита фактического токена сеанса. Например, хеш MD5 создает 128-битное значение. Однако хэш MD5 инкрементальных значений, временной метки или 8-битных случайных чисел каждый небезопасен, поскольку источник случайных значений можно легко предсказать. Следовательно, 128-битный размер не представляет точную меру маркера сеанса. Минимальный размер источника энтропии составляет 32 бита, хотя большие пулы (48 или 64 бита) могут быть необходимы для сайтов с более чем 10 000 одновременных пользователей в час.
  • В большинстве случаев сгенерированные приложением токены (например, ASP.NET_SessionId, ASPSESSIONID, JSPSESSIONID, PHPSESSIONID) предоставляют достаточно большие случайные значения для предотвращения атак с предсказанием сеанса. Приложение должно использовать эти алгоритмы управления сеансом, если пользовательский механизм сеанса не был тщательно рассмотрен и протестирован.
  • Отслеживание пользовательских атрибутов, связанных с маркером сеанса, с объектами на стороне сервера для предотвращения атак на персонификацию пользователя. Если приложение строго не связывает маркер сеанса пользователя с информацией профиля этого пользователя, то злоумышленник может просматривать произвольную информацию, манипулируя значениями на стороне клиента. Например, если приложение устанавливает сильный токен сеанса, но выполняет запросы SQL на основе файла cookie «UserId», то злоумышленнику нужно только изменить файл «UserId», чтобы выдать себя за кого-то другого. Приложение было бы более безопасным, если бы оно связывало значение «UserId» с объектом сеанса на стороне сервера, поскольку злоумышленник не сможет изменить значение.
  • Истекают маркеры сеанса, когда пользователь выходит из приложения или после заданного периода бездействия. Мы рекомендуем использовать 20-минутный тайм-аут для токена сеанса, хотя это в значительной степени зависит от типа приложения и ожидаемого использования.

1 Ответ

9 голосов
/ 01 августа 2011

Как я помню, генератор идентификаторов сеансов ASP.NET обеспечивает хорошую защиту от прогнозирования сеансов.Идентификатор сеанса состоит из 24 символов с использованием символов [az] и цифр [0-5] (всего 32 возможных символа, что составляет 2 ^ 5), что дает в общей сложности 2 ^ (5 * 24) = 2 ^ 120 возможных значений.Однако вы можете реализовать SessionIDManager для добавления некоторой информации (такой как адрес пользователя, пользовательский агент, токен проверки с использованием алгоритма HMAC) для еще лучшей защиты - так, чтобы идентификатор сеанса, передаваемый с другого IP-адреса или другого браузера, не проходилпроверка.Если у вас реализована проверка подлинности с помощью форм, в этом нет необходимости, поскольку билет проверки подлинности уже обеспечивает такие виды защиты.

Если вы хотите получить лучший случайный идентификатор сеанса, вы можете использовать RandomNumberGenerator, такой как RNGCryptoServiceProvider, в своем SessionIDManager и заполнить группу байтов (скажем, 32, которая составляет 256 бит), а затем кодировать их с помощью Base64

byte[] random = new byte[100];
//RNGCryptoServiceProvider is an implementation of a random number generator.
RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider();
rng.GetBytes(random); // The array is now filled with cryptographically strong random bytes.
return Convert.ToBase64String(random) 

Однако в этой статье говорится, что максимальная длина идентификатора сеанса равна 80, поэтому для его работы необходимо также переопределить метод Validate.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...