Outputcaching not working with cookies - asp.net

There was a weird issue yesterday about asp.net's outputcaching (webforms). We were using page-level caching (not partial caching) for a multi-lingual site (language is determined via querystring key) and for some purpose, caching stopped working for some languages. I kept track of GetVaryByCustomString method of Global.asax file but, it didnt worked. I will give more details in answer...

Perhaps you need to set the Shareable attribute on your cookies to true?
If a given HttpResponse contains one or more outbound cookies with
Shareable is set to false (the default value), output caching will be
suppressed for the response. This prevents cookies that contain
potentially sensitive information from being cached in the response
and sent to multiple clients. To allow a response containing cookies
to be cached, configure caching normally for the response, such as
using the OutputCache directive or MVC's [OutputCache] attribute, and
set all outbound cookies to have Shareable set to true.
https://msdn.microsoft.com/en-us/library/system.web.httpcookie.shareable(v=vs.110).aspx

Thanks to subversion, i kept track of recent commits. We made a mechanism allowing specific users to view some languages that have not been published yet, using cookies instead of session variables. This was the cause of problem. If a request comes to a language which is not the default language, this mechanism checks whether it should allow user to view page. And IMHO if you modify response's cookie collection, asp.net disables outputcache for that request. I tested it and it really disables cache if you add a cookie to response.

Related

Forcing browser to consider cookie value in cacheing response

I maintain a website where the front page is in a different language based on the value of a language cookie. However, when the browser caches this page, it does not consider that sending along a different value for this lang cookie could give a different page back, leading to it caching and present the old language value even after the user has indicated a preference for a different language. Can I tell the browser that this cookie should influence caching decisions, and if so how?
Found a solution myself in the HTTP Vary header. Adding
Vary: Cookie
will cause the browser to consider requests different if any of their cookie headers differ, which is sufficient for the use case I am having (although it can be inefficient when there are multiple cookies only some of which affect the outcome of the request)

Checkmarx XSRF issue

Checkmarx is complaining about an XSRF issue in our web application. We are using ASP.NET web forms with framework 4.0 (not MVC)
Checkmarx said: Method btnSubmit_Click at line 1760 of \ABC.aspx.vb gets a parameter from a user request URL from element text. This parameter value flows through the code and is eventually used to modify database contents. The application does not require renewed user authentication for the request. This may enable Cross-Site Request Forgery (XSRF).
Any idea of how to prevent XSRF from ASP.NET Webform application?
We have tried a lot of solutions but none of them pass Checkmarx:
Here are some things we tried:
https://software-security.sans.org/developer-how-to/developer-guide-csrf
or
http://willseitz-code.blogspot.com/2013/06/cross-site-request-forgery-for-web-forms.html?m=1
or
https://security.stackexchange.com/questions/187740/two-solutions-for-csrf-on-owasp-for-asp-net-webforms
I think the solutions above should work and protect/prevent our web form from CSRF/XSRF risks, but why can Checkmarx not detect it? Is this a false positive?
It is recommend to check the CxQL queries from Checkmarx Portal (Settings/Scan Settings/Query Viewer) to understand how Checkmarx find a vulnerability, including what kind of protection that Checkmarx is able to detect.
For your case, check the logic in CSharp/Cx/CSharp_Medium_Threat/XSRF.
For Web Form Applications, the query CSharp/Cx/General/Find_XSRF_Sanitize is used to find if you have done any protection in your application.
As the comment of Find_XSRF_Sanitize said:
For ASP Web Forms, the main solution to prevent XSRF attacks is to
assign a unique token to the ViewStateUserKey property of the page.
Also
AntiXsrfTokenKey
is also considered a protection.
If you use ViewStateUserKey or AntiXsrfTokenKey, all the http interactive requests that are defined in the same method as the ViewStateUserKey or AntiXsrfTokenKey will be considered as sanitized request, and will be removed for the potential tainted request list.
Note that in the CxDOM tree, ViewStateUserKey and the sanitized request have common ancestor, which is the method declaration.

What is AspxAutoDetectCookieSupport

Recently, I noticed about having AspxAutoDetectCookieSupport=1 in the URL when I clear browser cookies. Upon doing a short research, I found out that it is result of cookieless attribute set to "AutoDetetct" in web.config.
The parameter 'AspxAutoDetectCookieSupport' goes away when I visit the URL again. What does 'AspxAutoDetectCookieSupport=1' mean?
The AspxAutoDetectCookieSupport=1 querystring is added automatically by ASP.NET during the cookie support detection phase. Since cookieless attribute in the web.config file is set to "AutoDetect", the ASP.NET runtime tries to detect whether the user's browser supports cookies, and the querystring parameter is added during that process. If cookies are supported, the Session ID is kept in a cookie, and if not the Session ID is sent in the Url of all future requests by that user.
More information can be found at: https://captcha.com/doc/aspnet/faq/captcha-persistence-faq.html#persistence-querystring

Cross domain cookie access (or session)

While I realise that this is usually related to cross site scripting attacks, what I'm wondering is how can a session remain valid throughout multiple subdomains belonging to a single domain (example: a user logging in only once, and being able to access both subdomain1.domain.com and subdomain2.domain.com with the same session). I guess I first need to understand how it works, but so far I haven't been able to find much that would be of any relevance.
But then again, maybe I wasn't asking the right question.
Thanks in advance :)
Inproc sessions cannot remain valid, however you can code your web application to allow cookies across multiple subdomains. You will need to set the domain equal to:
Response.Cookies("CookieName").Domain = ".mydomain.com"
Remember the period.
There are quite a few ways to share session data or cookie data across domains. The simplest is to share it on the server side through a shared data store. But you would not be asking this question if it were that easy.
The other way to do this is equally simple. The domain one.com contains some session data say name=aleem and id=123 and wishes to pass this along to two.com. It will follow these steps:
Make a call to two.com/api/?name=aleem&id=123
When two.com gets the data via query parameters, it creates a cookie with the data. This cookie will be stored under the two.com domain.
two.com will then redirect back to the REFERER which in this case happens to be one.com
This is a simplified scenario. The domain two.com needs to be able to trust one.com and not only that but it needs to know that the request is authentic and not just crafted by the user so you need to use public/private keys to mitigate this.
By default, all cookies for a site are stored together on the client, and all cookies are sent to the server with any request to that site. In other words, every page in a site gets all of the cookies for that site. However, you can set the scope of cookies in two ways:
Limit the scope of cookies to a folder on the server, which allows you to limit cookies to an application on the site.
Set scope to a domain, which allows you to specify which subdomains in a domain can access a cookie.
You can learn more here.
The comments about the cookie being set for the domain to allow subdomains to receive that cookie give you that side but what's missing is the consistency of session.
I think this is very much like the problem of maintaining state across servers in a farm and the solution is probably to ensure that your session store is consistent across both sites (if they are not server from the same 'web site' in IIS). You can move the Session store into SQL Server (HOW TO: Configure SQL Server to Store ASP.NET Session State) which would probably serve the purpose as each site would query the same store when looking for the session data related to the cookie they've been presented with.
I hope that gets you on the right track.
If you have the ability to set up a common subdomain, you can do this:
In your subdomain html files, include a javascript file at the top like this:
<script src="http: //common.domain.com/check.asp"></script>
In check.asp, look for your logged_in cookie and if not present, show a page say, http://common.domain.com/login.asp using something like
<%
if (cookie_not_found){
%>
location.href = "http: //common.domain.com/login.asp";
<%
}
%>
Once a person submits username password, submit it back to the same login.asp and set the session cookie, (which will be set in common.domain.com domain) and then redirect to http://subdomain1.domain.com.
What will happen now is, a call will be made to the embedded "common.domain.com/check.asp", and cookies for common.domain.com will be sent by the browser along with the request. So you will know whether your session is valid or not, even when you are in subdomain1.domain.com.
You can set a cookie for a specific domain.
In php, the setCookie() method contains a parameter in which you can specify the top-level domain, so the cookie is valid for all subdomains. Based on your tags, I see you are working in asp.net. Probably this also exists for asp...
after a little search for asp:
try this:
Response.Cookies("CookieName").Domain = ".mydomain.com"
or read this
Here is a solution which works:
http://anantgarg.com/2010/02/18/cross-domain-cookies-in-safari/

Remove Cookie Support

My site has the following url format: www.mysite.com/Display.aspx?ID=128
However most users see the url as
www.mysite.com/Display.aspx?ID=128&AspxAutoDetectCookieSupport=1
How can I avoid &AspxAutoDetectCookieSupport=1 from appearing in the url.
Is it to do something with cookie in web.config, but where? And what would be the implications if I remove that. How to remove?
Session State and Forms Authentication can both be set up in the web.config file to operate without cookies - this is called "cookieless configuration". When this happens, ASP.Net can be set to try to compensate for lack of cookies by using the query string as a cookie substitute. This is what is causing your unwanted querystring parameters.
You should look in your web.config for "cookieless = AutoDetect" or "cookieless = UseUri".
Changing the setting to "cookieless = UseCookies" will ensure that the cookieless feature will not be used, and hence it won't be appending the AspxAutoDetectCookieSupport to your URL.
The implications of this is that users who browse with cookies turned off will not be able to have Session data or use Forms Authentication. This may or may not affect your target audience, you'll have to judge that for yourself.
Edit: Here's the MSDN link for the cookieless feature: http://msdn.microsoft.com/en-us/library/aa479315.aspx

Resources