March 9, 2007 - 17:23 UTC - Tags: ASP.NET security cookie session
I just read an
article on cookies in regular ASP, which explains some of the concerns related to session cookies. In this post I'll explain how this works in ASP.NET.
Session related cookies in .NETWhen a user connects to an ASP.NET application, a unique session ID will be affiliated with the user. If nothing is put in the session however, no cookie will be sent to the browser. This means that the user will get a new session ID the next time a new url is open or the page is refreshed. If something is put on the session (HttpContext.Current.Session["Hello] = "hello") however, ASP.NET will issue a cookie called ASP.NET_SessionId. This cookie contains the user's session ID and the cookie will expire at the end of the session (when you close your browser).
If the user logs in, a second cookie will be issued. This cookie is usually called .ASPXAUTH, and states that the user is logged in. It's encrypted, but probably contains some information about who the user is etc. This cookie sets ASP.NET apart from other web applications, because login-information is usually affiliated with the session ID.
Read only?In the article linked above, session ID is described as read-only. While this is normally true, it is not the case for ASP.NET. If you try to change your session ID in another type of web application, you will usually be logged out because the session does not exist. If the session does exist however, you will be logged in as the user having that session. This is called session stealing, and this is why session IDs must be hard to guess (many characters and not sequential).
If you pass an ASP.NET application a session ID of a session that does not exist, ASP.NET will create a session with that session ID. If you want to try this, open an ASP.NET application in your browser. Next, type the following in your browser address bar:
javascript:void(document.cookie="ASP.NET_SessionId=WhyDidTheChickenCrossThe;path=/")
In the code above I set the session ID to be the beginning of a familiar joke. If you want to set it to a value of your own, use the same length and only letters or numbers.
Session ID expiryThe ASP.NET_SessionId is set to be deleted when you close the browser. If you, however, modify the cookie to have an expiry date at some point ahead in time, you will get the same session ID every time you visit the ASP.NET application untill the expiry date set for the cookie. You can test this by writing something like this in your browser address bar:
javascript:void(document.cookie="ASP.NET_SessionId=WhyDidTheChickenCrossThe;path=/;expires=Mon, 19 Mar 2007 18:25:19 GMT");
Session ID and loginASP.NET does not create a new session ID for the user on login.
So what does this mean?ASP.NET does not tie login information to the session, which makes this a much smaller problem than in other web applications. It does however mean that an XSS problem might allow a hacker to set a session ID for a user, and then potentially get access to information from the session whenever the user logs in.
How do I protect my ASP.NET application from this?Make sure you always delete the ASP.NET_SessionId cookie when the user logs in. This way you'll avoid user's having permanent session IDs. I use the following code in Page_Load() on my ASP.NET .aspx login page:
if (!Page.User.Identity.IsAuthenticated)
{
if (Page.Request.Cookies["ASP.NET_SessionId"] != null)
{
Response.Cookies["ASP.NET_SessionId"].Expires = DateTime.Now.AddYears(-30);
}
Session.Abandon();
}
Another idea could be store the value of the .ASPXAUTH cookie in the session on login and checking it on every subsequent request. If it has changed, delete the session and session cookie.
IE and HTTP-Only cookiesBoth the ASP.NET_SessionId and .ASPXAUTH cookies are
HTTP Only, which means they cannot be read from javascript in Internet Explorer. They can, however, be changed by javascript using the javascript code presented early in this post.