As I’ve written in one of my previous posts, I found out that one gets a “Validation of viewstate MAC failed” exception when submitting a DNN login form and the login status has changed from “not logged in” to “logged in” after the login form initially was loaded (e.g. by using an addition browser tab to log in).
After contacting the DNN support team it turned out, that this is not a bug, but a security feature in DNN. In detail, DNN adds the username of the current session to the APS.NET ViewStateUserKey (see “Take Advantage of ASP.NET Built-in Features to Fend Off Web Attacks” on MSDN for more information).
In DNN profession knowledge base, two resolutions are described which both have their drawbacks:
- One could edit the Default.aspx.cs and remove the username from the ViewStateUserKey which has to be done after each DNN update because Default.aspx.cs will be overwritten when updating the framework.
- One could disable “ViewState MAC validation” entirely by setting enableViewStateMac to false in Web.config file which is not recommended due to security problems.
I finally came up with the following code snippet that I’ve added to the code behind file of the skin:
protected override void OnInit(EventArgs e)
{
// Catch "Validation of viewstate MAC failed" exceptions and redirect the user
// to the current page (i.e. force a redirect on the client)
Page.Error += (sender, args) =>
{
if (!(HttpContext.Current.Error is HttpException)) return;
if (!(HttpContext.Current.Error.InnerException is ViewStateException)) return;
HttpContext.Current.Response.Clear();
Response.Redirect(Request.UrlReferrer == null ? Request.Url.ToString() : Request.UrlReferrer.ToString());
};
base.OnInit(e);
}
In detail the code above adds an error handler that catches “Validation of viewstate MAC failed” exceptions and forces the client to reload the current page in case of such an excpetion (which updates the ViewStateUserKey according to the current session state). Since this error handler needs to be added on every page, the skin is the perfect place to put the code into.
11 responses to “DotNetNuke: Workaround for “Validation of viewstate MAC failed” exception when using the DNN 7 login form in multiple tabs”
[…] 2013-04-18 It turned out, that this is not a bug, but a security feature in DNN. I written an new blog post that describes a possible […]
Hello thank you very much for the Workaround! It saved me a lot of time!!
Hi Can you please provide the vb.net version of this function. I can include that in default.aspx.vb
Here is the equivalent Vb.net code in case someone else is looking for:
Protected Sub OnInit(ByVal sender As System.Object, ByVal e As System.EventArgs)
‘ Catch “Validation of viewstate MAC failed” exceptions and redirect the user
‘ to the current page (i.e. force a redirect on the client)
AddHandler Page.[Error], AddressOf [Error]
End Sub
Protected Sub [Error](ByVal sender As System.Object, ByVal e As System.EventArgs)
If Not (TypeOf HttpContext.Current.[Error] Is HttpException) Then
Return
End If
If Not (TypeOf HttpContext.Current.[Error].InnerException Is ViewStateException) Then
Return
End If
HttpContext.Current.Response.Clear()
Response.Redirect(If(Request.UrlReferrer Is Nothing, Request.Url.ToString(), Request.UrlReferrer.ToString()))
MyBase.OnInit(e)
End Sub
Thanks Shaun for the update.
Does this mean the DNN already sets the ViewStateUserKey for you? Would it be correct to set it to Session.SessionID on page init?
We started to get viewstate mac address error in some of our environments after they implemented this code “ViewStateUserKey = Session.SessionID” on page init and I was trying to figure out why.
Hi Alex,
Sorry for my late reply. Yes, by default DNN sets the ViewStateUserKey for you. As written in the blog post the code can be found in the Default.aspx.cs file (see here). As far as I understand the problem you could either directly change the Default.aspx.cs (which is not “upgrade-safe”) or use the workaround I’ve described above. Hope this helps…
very interesting…nuke strikes again…
Thanks Jan Jonas, this is very useful post and described nicely to understand well.
Great!
What do you mean by the code-behind of your skin file? The particular skin I am using does not have code-behind pages.they are ascx user controls.