How to secure the ASP.NET_SessionId cookie?

C#asp.netSession Cookies

C# Problem Overview


I have set the .ASPXAUTH cookie to be https only but I am not sure how to effectively do the same with the ASP.NET_SessionId.

The entire site uses HTTPS so there is no need for the cookie to work with both http and https.

C# Solutions


Solution 1 - C#

To add the ; secure suffix to the Set-Cookie http header I simply used the <httpCookies> element in the web.config:

<system.web>
  <httpCookies httpOnlyCookies="true" requireSSL="true" />
</system.web>

IMHO much more handy than writing code as in the article of Anubhav Goyal.

See: http://msdn.microsoft.com/en-us/library/ms228262(v=vs.100).aspx

Solution 2 - C#

Here is a code snippet taken from a blog article written by Anubhav Goyal:

// this code will mark the forms authentication cookie and the
// session cookie as Secure.
if (Response.Cookies.Count > 0)
{
    foreach (string s in Response.Cookies.AllKeys)
    {
        if (s == FormsAuthentication.FormsCookieName || "asp.net_sessionid".Equals(s, StringComparison.InvariantCultureIgnoreCase))
        {
             Response.Cookies[s].Secure = true;
        }
    }
}

Adding this to the EndRequest event handler in the global.asax should make this happen for all page calls.

Note: An edit was proposed to add a break; statement inside a successful "secure" assignment. I've rejected this edit based on the idea that it would only allow 1 of the cookies to be forced to secure and the second would be ignored. It is not inconceivable to add a counter or some other metric to determine that both have been secured and to break at that point.

Solution 3 - C#

Going with Marcel's solution above to secure Forms Authentication cookie you should also update "authentication" config element to use SSL

<authentication mode="Forms">
   <forms ...  requireSSL="true" />
</authentication>

Other wise authentication cookie will not be https

See: http://msdn.microsoft.com/en-us/library/vstudio/1d3t3c61(v=vs.100).aspx

Solution 4 - C#

Found that setting the secure property in Session_Start is sufficient, as recommended in MSDN blog "Securing Session ID: ASP/ASP.NET" with some augmentation.

    protected void Session_Start(Object sender, EventArgs e)
    {
        SessionStateSection sessionState = 
 (SessionStateSection)ConfigurationManager.GetSection("system.web/sessionState");
        string sidCookieName = sessionState.CookieName;

        if (Request.Cookies[sidCookieName] != null)
        {
            HttpCookie sidCookie = Response.Cookies[sidCookieName];
            sidCookie.Value = Session.SessionID;
            sidCookie.HttpOnly = true;
            sidCookie.Secure = true;
            sidCookie.Path = "/";
        }
    }

Solution 5 - C#

Adding onto @JoelEtherton's solution to fix a newly found security vulnerability. This vulnerability happens if users request HTTP and are redirected to HTTPS, but the sessionid cookie is set as secure on the first request to HTTP. That is now a security vulnerability, according to McAfee Secure.

This code will only secure cookies if request is using HTTPS. It will expire the sessionid cookie, if not HTTPS.

    // this code will mark the forms authentication cookie and the
    // session cookie as Secure.
    if (Request.IsSecureConnection)
    {
        if (Response.Cookies.Count > 0)
        {
            foreach (string s in Response.Cookies.AllKeys)
            {
                if (s == FormsAuthentication.FormsCookieName || s.ToLower() == "asp.net_sessionid")
                {
                    Response.Cookies[s].Secure = true;
                }
            }
        }
    }
    else
    {
        //if not secure, then don't set session cookie
        Response.Cookies["asp.net_sessionid"].Value = string.Empty;
        Response.Cookies["asp.net_sessionid"].Expires = new DateTime(2018, 01, 01);
    }

Solution 6 - C#

It is also worth considering:

__Secure-, which signals to the browser that the Secure attribute is required.
__Host-, which signals to the browser that both the Path=/ and Secure attributes are required, and at the same time, that the Domain attribute must not be present.

A good article on why this helps

https://check-your-website.server-daten.de/prefix-cookies.html


Renaming your cookies

Instead of using names that clearly identify programming language.

e.g

ASP.NET_SessionId = __Secure-SID


Using samesite settings

sameSite="Lax"

https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Set-Cookie/SameSite


requireSSL="true"


SECURE EXAMPLE

<sessionState cookieless="false" cookieName="__Secure-SID" cookieSameSite="Lax" />
<httpCookies httpOnlyCookies="true" sameSite="Lax" requireSSL="true" />

Solution 7 - C#

If the entire site uses HTTPS, your sessionId cookie is as secure as the HTTPS encryption at the very least. This is because cookies are sent as HTTP headers, and when using SSL, the HTTP headers are encrypted using the SSL when being transmitted.

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
QuestionPeteView Question on Stackoverflow
Solution 1 - C#Marcel HoyerView Answer on Stackoverflow
Solution 2 - C#Joel EthertonView Answer on Stackoverflow
Solution 3 - C#Raghu AView Answer on Stackoverflow
Solution 4 - C#Doug DomenyView Answer on Stackoverflow
Solution 5 - C#Jonathan HarrisView Answer on Stackoverflow
Solution 6 - C#DreamTeKView Answer on Stackoverflow
Solution 7 - C#Nick BerardiView Answer on Stackoverflow