Dan Maharry

Debugging ViewState Errors & Visual Studio Debugging Options

by

(In which a problem with ViewState is solved by tweaking Visual Studio’s debugging options and using ViewState Decoder to locate the problem on the page)

When an error occurs in your code as you run it through the Visual Studio Debugger, you’ll know all too well that Visual Studio is given focus, opens the code file where the error has occurred and highlights the line it has occurred on. Recently, I came across the problem where as soon as I caused a page to postback, a ViewState error was instantly thrown before any of my code had run.

Failed to load viewstate. The control tree into which viewstate is being loaded must match the control tree that was used to save viewstate during the previous request. For example, when adding controls dynamically, the controls added during a post-back must match the type and position of the controls added during the initial request. 

Now typically if you see this error, you start searching your code for the phrase ‘Controls.Add’ because the error implies that you have changed the structure of the page after the state of the page has been saved into the StateBag. Statements like Page.Controls.Add(…) are the usual culprits as this is exactly what they do. However, there were no such statements in my entire site, let alone this particular page.

To discover the exact problem then, I told the debugger to show me every error that occurred, not just the ones in my code as follows

  1. In Visual Studio, select Tools > Options > Debugging > General
  2. Uncheck “Enable Just My Code (Managed only)” and hit OK.
    The VS2008 Debuggin Options Dialog
  3. Press Ctrl + Alt + E to bring up the Exceptions dialog. This allows you to specify which errors the debugger should break to code on encountering. Check ‘Common Language Runtime Exceptions’ to break on any .NET Exception. Drill down into the tree to be more specific – e.g. to break only those Exceptions in the System namespace. Hit OK.
    VS_Exception_Dialogs2

Debugging into the page again, the debugger quickly identified a System.InvalidCastException occurring with the message

{"Unable to cast object of type 'System.String[]' to type 'System.Collections.ArrayList'."}  when System.Web.UI.StateBag.LoadViewState(Object state)  is being called.

After clicking continue, the ‘Failed To Load Viewstate Error’ then appeared and we were back to the error we’d seen before. All the InvalidCastException message tells us is that as the server loaded the viewstate from the page back into the pipeline for processing, it expected an ArrayList and got a String array instead. By inspecting the page’s viewstate then, we could investigate where this clash might be occurring and try to map it to the page.

Enter Fritz Onion’s ViewState Decoder app, a really handy download which takes that encoded hidden field on your page and renders it into something more legible. Loading my erroring page into the decoder presented me with the following.

Screenshot of Viewstate Decoder displaying the viewstate from the erroring page. Highlighted is the only string array in the viewstate

As luck would have, it turned out there was only one string array in the entire viewstate tree (highlighted above) and that highlighted this line in the markup was the likely cause

<script type="text/javascript" 
src="<%# ResolveUrl("~/scripts/swfobject.js") %>">
</script>

and in the code-behind, this line in Page_Load, which ensured any javascript urls in the page header are resolved, was the malfeasant one.

Page.Header.DataBind();

Sure enough, commenting out the call to DataBind() stopped the ViewState error occuring on the page, but the location of the script in the header was not resolved. Rather than using an absolute URL, I ended up opting for a Literal control which generated the correct script tag instead and all was well.

Enabling SSL Certificates On Any Given Port

by

Following on from my travails with HttpListeners not working as a non-admin user, it turned out that the Cardspace samples (download them here if you’re interested) had one more sticking point up their sleeve before everything worked. The main example demonstrates how a simple Security Token Service is used to verify the managed card a user wants to send to a site. However, the service is accessible only through the HTTPS protocol on port 7001 and Cardspace was unable to access it. A little digging revealed that the setup scripts for the sample tried and failed to build a copy of httpcfg, a utility found on Windows Server 2003. I didn't have the necessary files to build httpcfg successfully, bit it turns out that the netsh utility that comes with Vista and helped me out previously could also help me out here to.

The command required to add the certificate to a port with netsh is

netsh http add sslcert ipport=0.0.0.0:7001 certhash=thumbprint appid=arbitrary_guid

And the corresponding one to remove it is

netsh http delete sslcert ipport=0.0.0.0:7001

More...

Enabling HttpListeners for Non-Admins

by

I’ve just started working through the Cardspace samples to learn some more about online identity layers (download them here if you're interested). The first example demonstrates a web service running on http://localhost:4123 requesting a certificate from a client. However, as a non-admin, I get the following error from Visual Studio when running the sample.

AddressAccessDeniedException was unhandled
HTTP could not register URL http://+:4123/HelloService/. Your process does not have access rights to this namespace

Coincidentally, the error is totally analogous to a similar problem I’ve had while trying out the CR_Documentor plug-in that Travis Illig has created and it’s Travis and co that figured out both problems in hindsight. To paraphrase,

By default, only local admins have permission to listen to http prefixes. Other accounts require explicit grant using either httpcfg.exe for WinXp/2003 users or netsh for Vista/2008 users. This isn’t a .net permission, it goes right to the windows urlacl level.

Just as this cardspace demo relies on port 4123 being accessible, so too does CR_Documentor rely on port 11235. The full commands to call either can be found here, explaining the various options.

Thus, to solve my cardspace problem, I needed to open a command prompt as an admin and run the following command to match the URL given in the error dialog.

netsh http add urlacl url=http://+:4123/ user=cweb\dan

And hey presto, I can continue debugging my web services as a standard user.

Thanks again to Travis and the CR_Documentor guys for figuring this one out and explaining it here. I’m just passing on the info.

Learning that WAPs on IIS are for Admins Only The Hard Way

by

(Or rather “How a fixed bug and a rubbish COMException error dialog ended up making me take four months to learn that Web Application Projects running on IIS rather than Cassini can only be edited in VS when running with Administrative privileges” but that seems slightly long for a blog title post)

I’ve been happily running VS2008 as a standard user since it came out. And with TestDriven.NET and VisualSVN, I’m motoring along quite well. Yesterday, I decided to upgrade VisualSVN to the latest version v1.5.1. And then bang!! I loaded up my current work and got this dialog.

The COMException Dialog

And my Web Application Projects have failed to load in VS2008. After mild panic has finished setting in, I try regressing to my previous version v1.3.2 and the project loads fine. Which is mildly inconvenient as v1.3.2 doesn’t work with TortoiseSVN 1.5 which is something I also updated on my machine.

Looking on the intarwub, it’s mildly amusing to see that Google’s best match to this situation as I search for it is a forum thread that I started on VisualSVN’s forums when I got the same error trying out v1.4. However, one response in there since I last read it suggests removing the <FlavorProperties> element from the wap’s .csproj file. Which I do and it works. But having loaded the project back in again and reset it back up to run on IIS, the dialog appears again.

A bit more googling for Web Application Projects and COMExceptions yields this page from Martin Kulov bemoaning the same useless dialog but with the following golden nugget of information.

In order to load the Web Application Project ... if you are running Vista, you should run in elevated privileges as well.

Which is a bit of a shock as I’ve been happily running Vista and developing this project as a standard user for four months. Furthermore, it turns out that that useless dialog is a VS2008 bug that will be fixed in Service Pack 1.

So apologies to VisualSVN for doubting you. I’m never a fan of running Visual Studio as an admin, but I guess I have no choice. But whatever bug was present in v1.3.2 so I could develop WAPs on IIS as a standard user, maybe you could put it back? :)

.NET Source Code Available For Xmas

by

It has taken a few years but Microsoft has announced that it will make the source code for the majority of its .NET framework libraries available for download with the release of Visual Studio 2008 and .NET 3.5 later this year.

Initially the release will include the source code (with source file comments included) for the .NET Base Class Libraries (System, System.IO, System.Collections, System.Configuration, System.Threading, System.Net, System.Security, System.Runtime, System.Text, etc), ASP.NET (System.Web), Windows Forms (System.Windows.Forms), ADO.NET (System.Data), XML (System.Xml), and WPF (System.Windows). Source code for more libraries such as WCF, Workflow, and LINQ will be added in later releases. The source code will be released under the Microsoft Reference License (MS-RL), which in a nutshell says “You can look at this, but don’t change anything”.

The full announcement from Scott Guthrie can be found on his blog here. From a developer’s point of view, this can only be good. Rather than relying on newsgroups for those buggy itches that can’t be scratched, developers should now be able to use the source code to trace exactly why their problems are occurring and make changes accordingly. Of course, by releasing the source code, the b0rg will open themselves up to criticism from some for their actual coding. Indeed, the first such comment from the ‘not my code, I could write better’ camp has already been posted based on the contents of the screenshots in Scott’s post.

As agilists and design pattern specialists ready their knives and posts for their release, it’s worth remembering that this is a huge step for Microsoft. Read only or not, for them to start opening up their code takes a lot of guts. Reactions from the open source world and podcasts are already appearing in reaction to the announcement.