What are the implementation details and rationale of ASP.NET MVC3's AntiForgeryToken? - asp.net-mvc-3

The AntiForgeryToken is used to prevent CSRF attacks, however the links on MSDN don't give me much insight to what exactly the AntiForgeryToken does, or how it works, or why things are done the way they are.
From what I gather, it creates a hash inside a web page and a cookie. One or both of them use the hashed IPrincipal.Name, and use symmetric encryption.
Can anyone shed light as to:
How the AntiForgeryToken works internally
What should it be used to protect
What should it NOT be used to protect
What is the reasoning behind the implementation choices for #1 above?
Example:
is the implementation safe from "DoubleSubmit" cookies and other common vulnerability
Are there implementation issues if the user opens multiple tabs
What makes MSFT's implementation different from the one available at SANS

Okay, here is my best shot.
1) Internally, mvc uses RNG crypto methods to create a 128 bit string to act as the XSRF token. This string is stored in a cookie as well as in a hidden field somewhere on the form. The cookie name seems to be in the form of __RequestVerificationToken + a base 64 encoded version of the application path(server side). The html part of this uses the AntiForgeryDataSerializer to serialize the following pieces of data
- salt
- value(the token string)
- the ticks of the creation date
- the username (seems like Context.User)
The validate method basically deserializes the values out of the cookie and that of the form and compares them based on the values (salt/value/ticks/username).
2/3) I would think this discussion is more for when to use XSRF tokens and when not to. In my mind, you should use this on every form (I mean why not). The only thing I can think of that this doesn't protect is if you have actually hit the form in question or not. Knowing the base64 encoding of the app name will allow the attacker to be able to view the cookie during the XSRF attack. Maybe my interpretation of that is incorrect.
4) Not sure exactly what you are looking for here? I guess I would have built a mechanism where I would try and store the XSRF token in the session (if one was already available) and if not, then try the cookie approach. As for type of crypto used, I found this SO artcile.
Pros and cons of RNGCryptoServiceProvider

Related

how AntiForgeryToken() works in MVC and how to retrieve value at server action method from AntiForgeryToken?

i was reading about AntiForgeryToken but do not understand the actual use or importance. i saw people wrote a code like in their form as
#using (Html.BeginForm("Create", "Register"))
{
#Html.AntiForgeryToken()
}
so what it does....it will generate a unique token and when form will post then this unique toke will pass and as well as a cookie will pass with same unique token value and two unique data will compare at server end that both are equal or not. if not then some tamper occur.
i just do not understand if other form field value change or tamper then how that tampering can be determine. suppose we often store valuable data inside hidden fields. if i need to secure that hidden fields value then how AntiForgeryToken can help us?
can we use AntiForgeryToken to wrap up those valuable data inside it and later compare at server end.
can anyone give me bit of sample code by which i can put 3 valuable data in my page and if tamper then a friendly message will be show to user. guide me how to do it. thanks
The idea behind the AntiForgeryToken is to prevent data being posted from a "fake" source. An attacker using a fake (forged) form can trick the user to submit any kind of data using their current session context. As you can imagine this can do quite a lot of damage.
A way to prevent this is to have a hidden field on your forms containing user specific data(something random) that is stored in the session, so that the bad guys can't forge it. In this case when a user posts the data, but doesn't have the user specific token, you can treat is as being malicious.
I think you have a misconception that the anti forgery token is about detecting whether the data posted has been "tempered" with, which it is not.
Here is more on this.

rails how to give data to ajax in a secure way?

In order to use some AJAX calls, we use often some input type="hidden". But these values can be easily changed. So, is it a builtin rails feature than permit to send date to AJAX, withouth being usable by user, or than can't be changed by user ?
In my current rails apps, i'm using filters for discard all malicious actions on my controllers. I am not building a public API, so i don't really need more powerful checks.
But for examples, i have an apotomo widget displaying some data, using some input hidden. But if you change it, you can access to another data set. In my case, it's not really an issue, cause all these users have the right to access these data sets anyway.
But is it some manner to give datas to ajax call, in a secure way ? Or the only security, is about rights management ?
All input that comes from the user is insecure as you do not have control over it! Users even do not need a webbrowser but can use some other program (like curl or wget) to send manipulated data.
As you state, using a whitelist (not a blacklist as you can never be sure of all bad, but of all good!) is a good way to start.
To make sure the hidden fields have not been changed you can use some kind of checksum that is calculated on server side using a fixed secret. This secret must never be exposed to your visitors!
hash = md5(field_1 + field_2 + field_3 + my_secret)
When these four hidden fields (field_1..3, hash) arrive in your form you can recalculate the hash and compare it with the params[:hash] in order to be sure the field_1 to field_3 have not been changed.

What does a Ajax call response like 'for (;;); { json data }' mean? [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Why do people put code like “throw 1; <dont be evil>” and “for(;;);” in front of json responses?
I found this kind of syntax being used on Facebook for Ajax calls. I'm confused on the for (;;); part in the beginning of response. What is it used for?
This is the call and response:
GET http://0.131.channel.facebook.com/x/1476579705/51033089/false/p_1524926084=0
Response:
for (;;);{"t":"continue"}
I suspect the primary reason it's there is control. It forces you to retrieve the data via Ajax, not via JSON-P or similar (which uses script tags, and so would fail because that for loop is infinite), and thus ensures that the Same Origin Policy kicks in. This lets them control what documents can issue calls to the API — specifically, only documents that have the same origin as that API call, or ones that Facebook specifically grants access to via CORS (on browsers that support CORS). So you have to request the data via a mechanism where the browser will enforce the SOP, and you have to know about that preface and remove it before deserializing the data.
So yeah, it's about controlling (useful) access to that data.
Facebook has a ton of developers working internally on a lot of projects, and it is very common for someone to make a minor mistake; whether it be something as simple and serious as failing to escape data inserted into an HTML or SQL template or something as intricate and subtle as using eval (sometimes inefficient and arguably insecure) or JSON.parse (a compliant but not universally implemented extension) instead of a "known good" JSON decoder, it is important to figure out ways to easily enforce best practices on this developer population.
To face this challenge, Facebook has recently been going "all out" with internal projects designed to gracefully enforce these best practices, and to be honest the only explanation that truly makes sense for this specific case is just that: someone internally decided that all JSON parsing should go through a single implementation in their core library, and the best way to enforce that is for every single API response to get for(;;); automatically tacked on the front.
In so doing, a developer can't be "lazy": they will notice immediately if they use eval(), wonder what is up, and then realize their mistake and use the approved JSON API.
The other answers being provided seem to all fall into one of two categories:
misunderstanding JSONP, or
misunderstanding "JSON hijacking".
Those in the first category rely on the idea that an attacker can somehow make a request "using JSONP" to an API that doesn't support it. JSONP is a protocol that must be supported on both the server and the client: it requires the server to return something akin to myFunction({"t":"continue"}) such that the result is passed to a local function. You can't just "use JSONP" by accident.
Those in the second category are citing a very real vulnerability that has been described allowing a cross-site request forgery via tags to APIs that do not use JSONP (such as this one), allowing a form of "JSON hijacking". This is done by changing the Array/Object constructor, which allows one to access the information being returned from the server without a wrapping function.
However, that is simply not possible in this case: the reason it works at all is that a bare array (one possible result of many JSON APIs, such as the famous Gmail example) is a valid expression statement, which is not true of a bare object.
In fact, the syntax for objects defined by JSON (which includes quotation marks around the field names, as seen in this example) conflicts with the syntax for blocks, and therefore cannot be used at the top-level of a script.
js> {"t":"continue"}
typein:2: SyntaxError: invalid label:
typein:2: {"t":"continue"}
typein:2: ....^
For this example to be exploitable by way of Object() constructor remapping, it would require the API to have instead returned the object inside of a set of parentheses, making it valid JavaScript (but then not valid JSON).
js> ({"t":"continue"})
[object Object]
Now, it could be that this for(;;); prefix trick is only "accidentally" showing up in this example, and is in fact being returned by other internal Facebook APIs that are returning arrays; but in this case that should really be noted, as that would then be the "real" cause for why for(;;); is appearing in this specific snippet.
Well the for(;;); is an infinite loop (you can use Chrome's JavaScript console to run that code in a tab if you want, and then watch the CPU-usage in the task manager go through the roof until the browser kills the tab).
So I suspect that maybe it is being put there to frustrate anyone attempting to parse the response using eval or any other technique that executes the returned data.
To explain further, it used to be fairly commonplace to parse a bit of JSON-formatted data using JavaScript's eval() function, by doing something like:
var parsedJson = eval('(' + jsonString + ')');
...this is considered unsafe, however, as if for some reason your JSON-formatted data contains executable JavaScript code instead of (or in addition to) JSON-formatted data then that code will be executed by the eval(). This means that if you are talking with an untrusted server, or if someone compromises a trusted server, then they can run arbitrary code on your page.
Because of this, using things like eval() to parse JSON-formatted data is generally frowned upon, and the for(;;); statement in the Facebook JSON will prevent people from parsing the data that way. Anyone that tries will get an infinite loop. So essentially, it's like Facebook is trying to enforce that people work with its API in a way that doesn't leave them vulnerable to future exploits that try to hijack the Facebook API to use as a vector.
I'm a bit late and T.J. has basically solved the mystery, but I thought I'd share a great paper on this particular topic that has good examples and provides deeper insight into this mechanism.
These infinite loops are a countermeasure against "Javascript hijacking", a type of attack that gained public attention with an attack on Gmail that was published by Jeremiah Grossman.
The idea is as simple as beautiful: A lot of users tend to be logged in permanently in Gmail or Facebook. So what you do is you set up a site and in your malicious site's Javascript you override the object or array constructor:
function Object() {
//Make an Ajax request to your malicious site exposing the object data
}
then you include a <script> tag in that site such as
<script src="http://www.example.com/object.json"></script>
And finally you can read all about the JSON objects in your malicious server's logs.
As promised, the link to the paper.
This looks like a hack to prevent a CSRF attack. There are browser-specific ways to hook into object creation, so a malicious website could use do that first, and then have the following:
<script src="http://0.131.channel.facebook.com/x/1476579705/51033089/false/p_1524926084=0" />
If there weren't an infinite loop before the JSON, an object would be created, since JSON can be eval()ed as javascript, and the hooks would detect it and sniff the object members.
Now if you visit that site from a browser, while logged into Facebook, it can get at your data as if it were you, and then send it back to its own server via e.g., an AJAX or javascript post.

Should hidden field information always be encrypted?

A question based on a comment made here:
storing user detail ... session vs cache !
Summary: I mentioned a technique I've used where I populate a model and use hidden fields to keep and pass back that information; Viewstate on the cheap. Simon Halsey said that the information should be encrypted or hashed so it is not tampered with. I'm thinking the added complexity of hashing it is just a form of YAGNI.
I can see that for sensitive information, definitely, but is this a good rule of thumb in general? What am I missing?
I actually have an attribute to do this (something similar) and speak about this exact thing in a security presentation. Yes - you should hash a copy of the value... encrypting it is up to you. if you encrypt it you get no model binding but is more open to attack, although a hash check helps. I'll post the code shortly for it and update this post. Who would ever think Viewstate helped with security : )
but to answer your question - you can encrypt it, but you need a way to at least validate it on the server side, so I hash a value and hash the posted value and then compare hashes in the attribute. encrypting can help - but then you need to implement either your own model binder or manually handle those values
The rule of thumb would be generally for any values that could be maliciously overwritten to attack your data - then you want some protection/validation on those fields. you could compare server side against what you know is a valid option for them (a form of whitelisting) but then you have the same form of rules duplicated on loading the data and on saving the data and that gets a bit messy at times, unless its as simple as limiting a user's get/update to a single userId.
What I mean is.. if you are updating say a user's record. Generally the main thing that matters for security is that the userId is not changed by the user to update a record that isn't theirs. The logic on get/save is easy "where o.UserId == userId"
However in complex role based security the logic becomes trickier and is not as clean to limit record updates like this. In those cases you can really take advantage of encrypted/hashed fields. I always hash the specific fields uses for update. Sure - they can be forged with other valid hashed fields from a previous request, but the scope of potential damage is significantly more limited this way.

Ajax and filenames - Best practices

I am using jQuery to call PHP files via the $.get method
function fetchDepartment(company_id)
{
$.get("ajax/fetchDepartment.php?sec=departments&company_id="+company_id, function(data){
$("#department_id").html(data);
});
}
What I am thinking is can I secure the filename even further?
Currently I have a global access check within the .php file that check if the user is logged in, if he can access this data etc.
But I am wondering if there are further steps I can take so a user couldn't see this filename, or what other steps you recommend to take.
Encoded requests
You could make the request details effectively invisible to the casual miscreant by encoding almost all of the URL and then decoding the request details server-side.
The request details would include the action you wish to perform plus the parameters relevant to that action.
All requests would be sent to a single URL, where a server-side process would decode the request details and perform the relevant action as required.
Example Original URL:
/ajax/delete.php?parameter1=foo&parameter2=bar
Request details:
action=delete&parameter1=foo&parameter2=bar
Encoded request details (encoded using base64):
YWN0aW9uPWRlbGV0ZSZwYXJhbWV0ZXIxPWZvbyZwYXJhbWV0ZXIyPWJhcg==
Encoded URL:
/ajax/?request=YWN0aW9uPWRlbGV0ZSZwYXJhbWV0ZXIxPWZvbyZwYXJhbWV0ZXIyPWJhcg==
I don't believe there is native functionality to encode to base64 in JavaScript, but it's far from impossible to find a suitable method or to write your own.
With obfuscated/minified client-side JavaScript it would be quite tricky for someone to determine how to make a request 'by hand'.
Hide implementation details
There are a number of practices you can follow to make your application less susceptible to attack through URL misuse.
Let's start with a URL of: ajax/fetchDepartment.php?sec=departments&company_id=99
There's no need to reveal what server-side technology you're using (PHP) nor, through the query string (sec, company_id), what the query string values actually mean.
Masking the server-side technology
Assuming you have index.php defined as a default, the following URLs are equivalent:
ajax/fetchDepartment.php?sec=departments&company_id=99
ajax/fetchDepartment/index.php?sec=departments&company_id=99
ajax/fetchDepartment/?sec=departments&company_id=99
The third URL does not reveal the server-side technology you're using. This limits the range of possible attacks. It also makes it easier for you to switch over to a different server-side technology without changing your URLs.
Hiding the meaning of request parameters
ajax/fetchDepartment/?sec=departments&company_id=99
ajax/99/departments/
The latter URL still conveys enough information to perform the request without revealing what the information means.
Whilst someone could still change the values, they won't know what they're changing. This will make it more difficult for an attacker to evaluate and understand the result of any URL changes they make.
Pretty much the only way you can obscure the URL for a certain piece of information from the user is by not loading it in through http. Maybe you can load a set of data on the calling page, or another page with a more generic url.

Resources