CryptographicException: заполнение является недопустимым и не может быть удалено, а проверка состояния представления MAC не выполнена
Отслеживая мои глобальные журналы исключений, эту ошибку, кажется, невозможно удалить независимо от того, что я делаю, я думал, что наконец избавился от нее, но она вернулась снова Вы можете увидеть след ошибки на подобном посте здесь.
Примечания об окружающей среде:
Приложение IIS 6.0, .NET 3.5 SP1 для одного сервера ASP.NET
Шаги уже приняты:
<system.web>
<machineKey validationKey="big encryption key"
decryptionKey="big decryption key"
validation="SHA1" decryption="AES" />
В моей базе страниц для всех моих страниц
protected override void OnInit(EventArgs e)
{
const string viewStateKey = "big key value";
Page.ViewStateUserKey = viewStateKey;
}
Также в исходном коде страницы видно, что все сгенерированные в ASP.NET скрытые поля правильно находятся в верхней части страницы.
3 ответа
Прежде всего, давайте начнем с того, что эта ошибка состояния просмотра происходит на PostBack.
Также я должен сказать, что я сделал все, что каждый предлагает сделать, чтобы избежать этой проблемы. И у меня есть одна машина, но 2 пула, которые работают на тех же страницах.
Итак, кто-то совершает действие, ищет человека, другой поисковой машины, "нажимая" на ваши страницы, или какой-то хакер пытается проверить вашу систему на наличие проблем...
У меня есть похожие проблемы (редкие, но уже существующие), и я наконец обнаружил, что люди пытаются взломать мои страницы. (с того же IP у меня и дос атакует)
Я изменяю функцию LoadPageStateFromPersistenceMedium(), которая переводит состояние просмотра, и вижу, регистрируя, что именно было входом, и с каких IP-адресов... затем я начал отслеживать эти результаты и вижу, что состояние просмотра было изменено вручную - или было полностью пустым,
При ошибке я просто перенаправляю его на ту же страницу...
Вот что я сделал...
public abstract class BasePage : System.Web.UI.Page
{
protected override object LoadPageStateFromPersistenceMedium()
{
try
{
.. return the base, or make here your decompress, or what ever...
return base.LoadPageStateFromPersistenceMedium();
}
catch (Exception x)
{
string vsString = Request.Form[__VIEWSTATE];
string cThePage = Request.RawUrl;
...log the x.ToString() error...
...log the vsString...
...log the ip coming from...
...log the cThePage...
// check by your self for local errors
Debug.Fail("Fail to load view state ! Reason:" + x.ToString());
}
// if reach here, then have fail, so I reload the page - maybe here you
// can place somthing like ?rnd=RandomNumber&ErrorId=1 and show a message
Responce.Redirect(Request.RawUrl, true);
// the return is not used after the redirect
return string.Empty;
}
}
Вторая причина
Теперь есть еще одна причина, по которой это может произойти, и причина в том, что кто-то одним щелчком мыши на вашей странице загружает __EVENTVALIDATION.
Это EventValidation помещается на последнюю кнопку, даже если asp.net нашел, и если у вас есть некоторые из них на многих местах на странице, или рядом с кнопкой, то это перейти к концу страницы.
Так что, даже если вы видите viewstate в верхней части страницы, где проверка? Может быть, это никогда не загружается - страница повреждена? Слишком быстрый пользователь нажимает на страницу?
<input type="hidden" name="__EVENTVALIDATION" id="__EVENTVALIDATION" ... >
Чтобы избежать такой проблемы, я сделал простой javascript, который не позволяет нажимать кнопку, если этот вход не был загружен!!!.
Еще один комментарий, __EVENTVALIDATION не всегда представляет! так что, может быть, безопаснее не искать это поле, если вы принимаете общее решение, но сделать трюк JavaScript, чтобы просто проверить, загружена ли полная страница, или что-то еще, что вы думаете.
Вот мое окончательное решение с jQuery: (обратите внимание, что я проверяю на PageLoad, если существует проверка события!). Я разместил это на своих мастер-страницах.
<script language="javascript" type="text/javascript">
function AllowFormToRun()
{
var MyEventValidation = $("#__EVENTVALIDATION");
if(MyEventValidation.length == 0 || MyEventValidation.val() == ""){
alert("Please wait for the page to fully loaded.");
return false;
}
return true;
}
</script>
protected void Page_Load(object sender, EventArgs e)
{
// I do not know if Page can be null - just in case I place it.
if (Page != null && Page.EnableEventValidation)
{
Form.Attributes["onsubmit"] = "return AllowFormToRun();";
}
}
Вы можете проверить, разместив возле кнопки вашей страницы задержку.
<% System.Threading.Thread.Sleep(5000); %>
Обновить
Сегодня я снова вижу в журнале это сообщение для WebResource, и обнаруживаю, что бот получает страницы и делает все символы в ссылках в нижнем регистре, включая параметры, так что это была еще одна причина, чтобы не получить правильную закодированную строку и выбросить сообщение типа Padding недопустимо и не может быть удалено.
Надеюсь, это поможет вам больше.
Обследование веб-страниц с несколькими ключевыми словами из сообщения об ошибке показывает, что этот тип ошибки является относительно распространенным, обычно случайным (по крайней мере, по внешнему виду) и, к сожалению, редко включающим явный обходной путь или объяснение...
Существование многих похожих, но разных ситуаций, вероятно, связано с очень многими различными архитектурами и базовыми конфигурациями, которые могут каким-то образом привести к неспособности криптоуровня утверждать подлинность MAC (кодов аутентификации сообщений) на страницах запросов:
- Настройка фермы серверов
- Междоменные / синдицированные страницы
- сторонние библиотеки виджетов и тому подобное
- Фактическая логика программы ASP (конечно)
Одним из довольно частых "маркеров" вокруг этих отчетов об ошибках является упоминание запросов ресурсов (например, WebResource.axd).
Обратите внимание, что такие запросы часто не регистрируются (чтобы они не увеличивали размер файлов журналов с помощью события, представляющего небольшой интерес). Это отсутствие в файле журнала и тот факт, что они часто кэшируются (и, следовательно, относительное случайное и нечастое возникновение ошибки), могут объяснить, как это возможное происхождение ошибки идет "под радаром". Это также говорит о том, что при попытке воссоздать ошибку (при отслеживании в журналах, в режиме реального времени и т. Д.) Может быть полезно предотвратить кеширование веб-браузера (или, по крайней мере, сначала очистить его кеш).
Вкратце, вот несколько идей и вещей для поиска:
- начать запись запросов *.axd
- попытаться связать такие запросы Axd с событиями ошибок в журнале исключений
- искать страницы со ссылками на ресурсы
- если в настройке фермы убедитесь, что все экземпляры используют один и тот же ключ (очевидно, фрагмент, приведенный в подсказке к вопросу на нескольких серверах IIS)
- С подозрением относитесь к страницам со сторонними привязками (поисковые сервисы, партнерские программы...)
Надеюсь это поможет;-)
Вы уверены, что ваша проблема связана с криптографией, а не вызвана слишком большим ViewState? Если ViewState является проблемой, вы можете разделить ее на части - измените значение pages / MaxPageStateFieldLength в web.config