How to decode viewstate

asp.netViewstate

asp.net Problem Overview


I need to see the contents of the viewstate of an asp.net page. I looked for a viewstate decoder, found Fridz Onion's ViewState Decoder but it asks for the url of a page to get its viewstate. Since my viewstate is formed after a postback and comes as a result of an operation in an update panel, I cannot provide a url. I need to copy & paste the viewstate string and see what's inside. Is there a tool or a website exist that can help viewing the contents of viewstate?

asp.net Solutions


Solution 1 - asp.net

Here's an online ViewState decoder:

http://ignatu.co.uk/ViewStateDecoder.aspx</strike>

Edit: Unfortunatey, the above link is dead - here's another ViewState decoder (from the comments):

http://viewstatedecoder.azurewebsites.net/

Solution 2 - asp.net

Use Fiddler and grab the view state in the response and paste it into the bottom left text box then decode.

Solution 3 - asp.net

Here is the source code for a ViewState visualizer from Scott Mitchell's article on ViewState (25 pages)

using System;
using System.Collections;
using System.Text;
using System.IO;
using System.Web.UI;


namespace ViewStateArticle.ExtendedPageClasses
{
	/// <summary>
	/// Parses the view state, constructing a viaully-accessible object graph.
	/// </summary>
	public class ViewStateParser
	{
		// private member variables
		private TextWriter tw;
		private string indentString = "   ";

		#region Constructor
		/// <summary>
		/// Creates a new ViewStateParser instance, specifying the TextWriter to emit the output to.
		/// </summary>
		public ViewStateParser(TextWriter writer)
		{
			tw = writer;
		}
		#endregion

		#region Methods
		#region ParseViewStateGraph Methods
		/// <summary>
		/// Emits a readable version of the view state to the TextWriter passed into the object's constructor.
		/// </summary>
		/// <param name="viewState">The view state object to start parsing at.</param>
		public virtual void ParseViewStateGraph(object viewState)
		{
			ParseViewStateGraph(viewState, 0, string.Empty);	
		}

		/// <summary>
		/// Emits a readable version of the view state to the TextWriter passed into the object's constructor.
		/// </summary>
		/// <param name="viewStateAsString">A base-64 encoded representation of the view state to parse.</param>
		public virtual void ParseViewStateGraph(string viewStateAsString)
		{
			// First, deserialize the string into a Triplet
			LosFormatter los = new LosFormatter();
			object viewState = los.Deserialize(viewStateAsString);
			
			ParseViewStateGraph(viewState, 0, string.Empty);	
		}

		/// <summary>
		/// Recursively parses the view state.
		/// </summary>
		/// <param name="node">The current view state node.</param>
		/// <param name="depth">The "depth" of the view state tree.</param>
		/// <param name="label">A label to display in the emitted output next to the current node.</param>
		protected virtual void ParseViewStateGraph(object node, int depth, string label)
		{
			tw.Write(System.Environment.NewLine);

			if (node == null)
			{
				tw.Write(String.Concat(Indent(depth), label, "NODE IS NULL"));
			} 
			else if (node is Triplet)
			{
				tw.Write(String.Concat(Indent(depth), label, "TRIPLET"));
				ParseViewStateGraph(((Triplet) node).First, depth+1, "First: ");
				ParseViewStateGraph(((Triplet) node).Second, depth+1, "Second: ");
				ParseViewStateGraph(((Triplet) node).Third, depth+1, "Third: ");
			}
			else if (node is Pair)
			{
				tw.Write(String.Concat(Indent(depth), label, "PAIR"));
				ParseViewStateGraph(((Pair) node).First, depth+1, "First: ");
				ParseViewStateGraph(((Pair) node).Second, depth+1, "Second: ");
			}
			else if (node is ArrayList)
			{
				tw.Write(String.Concat(Indent(depth), label, "ARRAYLIST"));

				// display array values
				for (int i = 0; i < ((ArrayList) node).Count; i++)
					ParseViewStateGraph(((ArrayList) node)[i], depth+1, String.Format("({0}) ", i));
			}
			else if (node.GetType().IsArray)
			{
				tw.Write(String.Concat(Indent(depth), label, "ARRAY "));
				tw.Write(String.Concat("(", node.GetType().ToString(), ")"));
				IEnumerator e = ((Array) node).GetEnumerator();
				int count = 0;
				while (e.MoveNext())
					ParseViewStateGraph(e.Current, depth+1, String.Format("({0}) ", count++));
			}
			else if (node.GetType().IsPrimitive || node is string)
			{
				tw.Write(String.Concat(Indent(depth), label));
				tw.Write(node.ToString() + " (" + node.GetType().ToString() + ")");
			}
			else
			{
				tw.Write(String.Concat(Indent(depth), label, "OTHER - "));
				tw.Write(node.GetType().ToString());
			}
		}
		#endregion

		/// <summary>
		/// Returns a string containing the <see cref="IndentString"/> property value a specified number of times.
		/// </summary>
		/// <param name="depth">The number of times to repeat the <see cref="IndentString"/> property.</param>
		/// <returns>A string containing the <see cref="IndentString"/> property value a specified number of times.</returns>
		protected virtual string Indent(int depth)
		{
			StringBuilder sb = new StringBuilder(IndentString.Length * depth);
			for (int i = 0; i < depth; i++)
				sb.Append(IndentString);

			return sb.ToString();
		}
		#endregion
	
		#region Properties
		/// <summary>
		/// Specifies the indentation to use for each level when displaying the object graph.
		/// </summary>
		/// <value>A string value; the default is three blank spaces.</value>
		public string IndentString
		{
			get
			{
				return indentString;
			}
			set
			{
				indentString = value;
			}
		}
		#endregion
	}
}

And here's a simple page to read the viewstate from a textbox and graph it using the above code

private void btnParse_Click(object sender, System.EventArgs e)
		{
			// parse the viewState
			StringWriter writer = new StringWriter();
			ViewStateParser p = new ViewStateParser(writer);

			p.ParseViewStateGraph(txtViewState.Text);
			ltlViewState.Text = writer.ToString();
		}

Solution 4 - asp.net

As another person just mentioned, it's a base64 encoded string. In the past, I've used this website to decode it:

http://www.motobit.com/util/base64-decoder-encoder.asp

Solution 5 - asp.net

Here's another decoder that works well as of 2014: http://viewstatedecoder.azurewebsites.net/

This worked on an input on which the Ignatu decoder failed with "The serialized data is invalid" (although it leaves the BinaryFormatter-serialized data undecoded, showing only its length).

Solution 6 - asp.net

JavaScript-ViewState-Parser:

> The parser should work with most non-encrypted ViewStates. It doesn’t > handle the serialization format used by .NET version 1 because that > version is sorely outdated and therefore too unlikely to be > encountered in any real situation.

http://deadliestwebattacks.com/2011/05/29/javascript-viewstate-parser/


Parsing .NET ViewState


Solution 7 - asp.net

This is somewhat "native" .NET way of converting ViewState from string into StateBag Code is below:

public static StateBag LoadViewState(string viewState)
    {
        System.Web.UI.Page converterPage = new System.Web.UI.Page();
        HiddenFieldPageStatePersister persister = new HiddenFieldPageStatePersister(new Page());
        Type utilClass = typeof(System.Web.UI.BaseParser).Assembly.GetType("System.Web.UI.Util");
        if (utilClass != null && persister != null)
        {
            MethodInfo method = utilClass.GetMethod("DeserializeWithAssert", BindingFlags.NonPublic | BindingFlags.Static);
            if (method != null)
            {
                PropertyInfo formatterProperty = persister.GetType().GetProperty("StateFormatter", BindingFlags.NonPublic | BindingFlags.Instance);
                if (formatterProperty != null)
                {
                    IStateFormatter formatter = (IStateFormatter)formatterProperty.GetValue(persister, null);
                    if (formatter != null)
                    {
                        FieldInfo pageField = formatter.GetType().GetField("_page", BindingFlags.NonPublic | BindingFlags.Instance);
                        if (pageField != null)
                        {
                            pageField.SetValue(formatter, null);
                            try
                            {
                                Pair pair = (Pair)method.Invoke(null, new object[] { formatter, viewState });
                                if (pair != null)
                                {
                                    MethodInfo loadViewState = converterPage.GetType().GetMethod("LoadViewStateRecursive", BindingFlags.Instance | BindingFlags.NonPublic);
                                    if (loadViewState != null)
                                    {
                                        FieldInfo postback = converterPage.GetType().GetField("_isCrossPagePostBack", BindingFlags.NonPublic | BindingFlags.Instance);
                                        if (postback != null)
                                        {
                                            postback.SetValue(converterPage, true);
                                        }
                                        FieldInfo namevalue = converterPage.GetType().GetField("_requestValueCollection", BindingFlags.NonPublic | BindingFlags.Instance);
                                        if (namevalue != null)
                                        {
                                            namevalue.SetValue(converterPage, new NameValueCollection());
                                        }
                                        loadViewState.Invoke(converterPage, new object[] { ((Pair)((Pair)pair.First).Second) });
                                        FieldInfo viewStateField = typeof(Control).GetField("_viewState", BindingFlags.NonPublic | BindingFlags.Instance);
                                        if (viewStateField != null)
                                        {
                                            return (StateBag)viewStateField.GetValue(converterPage);
                                        }
                                    }
                                }
                            }
                            catch (Exception ex)
                            {
                                if (ex != null)
                                {

                                }
                            }
                        }
                    }
                }
            }
        }
        return null;
    }

Solution 8 - asp.net

You can ignore the URL field and simply paste the viewstate into the Viewstate string box.

It does look like you have an old version; the serialisation methods changed in ASP.NET 2.0, so grab the [2.0 version][1]

[1]: http://www.pluralsight.com/community/media/p/51688.aspx "2.x version"

Solution 9 - asp.net

Best way in python is use this link.

A small Python 3.5+ library for decoding ASP.NET viewstate.

First install that: pip install viewstate

>>> from viewstate import ViewState
>>> base64_encoded_viewstate = '/wEPBQVhYmNkZQ9nAgE='
>>> vs = ViewState(base64_encoded_viewstate)
>>> vs.decode()
('abcde', (True, 1))

Solution 10 - asp.net

Solution 11 - asp.net

Normally, ViewState should be decryptable if you have the machine-key, right? After all, ASP.net needs to decrypt it, and that is certainly not a black box.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionSerhat OzgelView Question on Stackoverflow
Solution 1 - asp.netJamesView Answer on Stackoverflow
Solution 2 - asp.netDarren KoppView Answer on Stackoverflow
Solution 3 - asp.netSameer AlibhaiView Answer on Stackoverflow
Solution 4 - asp.netJosh HinmanView Answer on Stackoverflow
Solution 5 - asp.netRoman StarkovView Answer on Stackoverflow
Solution 6 - asp.netXP1View Answer on Stackoverflow
Solution 7 - asp.netBasilView Answer on Stackoverflow
Solution 8 - asp.netblowdartView Answer on Stackoverflow
Solution 9 - asp.nethenrryView Answer on Stackoverflow
Solution 10 - asp.netXP1View Answer on Stackoverflow
Solution 11 - asp.netMichael StumView Answer on Stackoverflow