|Perl Monk, Perl Meditation|
This is about a kind of XSS security hole betterworld and I detected recently.
It's described at http://en.wikipedia.org/wiki/Cross-site_request_forgery.
ExampleYou have a webapp at yourdomain.example. Let's say you have a profile settings site where you can set your realname, for example (harmless example though).
The user is authenticated by a session cookie.
The code looks like:
Looks fine, doesn't it?
Missed something?The form-method is POST. Why is it POST and why don't you care in the script if it really was sent by POST?
Consider some bad hacker creates a website on http://somewhere.example/bad.html:
An easy solution for this is to check for POST in your application.
Use TokensA lot of websites do this already; create a token (that expires like a session-id), and that must be a parameter in the form:
<input type="hidden" name="t" value="123abc...">
So every action of the script that changes data should require such a token. That makes your script pretty safe.
Couldn't browsers help me to surf more secure?Well, if the scripts are programmed badly, why should browser vendors care?
Because they can.
In Opera you can say that you just want get cookies from the current site.
Unfortunatley Opera still sends cookies from domain A to an embedded image
of domain B.
Also, there is no possibility to say "Warn me before a site does a form.submit() to a different domain". All these things could be implemented.
So, while you can do some things to make your own scripts safe, do you also think, browsers should take care of these issues? Here is a posting on Bugzilla https://bugzilla.mozilla.org/show_bug.cgi?id=375238 about this.
Update 2008-04-17: In Opera 9.5 the option "only send cookies to the site I visit" works reliably. In Firefox, the extension CookieSafe (and the option originalOnly) doesn't work reliably. So if you wanna be safe from CSRF, try Opera 9.5. But make sure you deactivate this option for OpenID sites.