Protecting passwords is important, but do you take the same care with your SESSIONIDs? You should. Here's how they work: When you log into a web application, you exchange your credentials for a SESSIONID cookie. This cookie gets sent with every subsequent request from your browser until you log out or the session times out. …
Easily read by anyone with access to the network?
Which isn't that easy at all, really. If you are using home broadband, you'd need access to telco infrastructure. Unsecured WiFi or a work/college network shared with dodgy people makes this more likely, but it isn't like an easy expolit to do systematically.
It's all a matter of appropriateness. For banking, or an email system that transfers passwords, always-on SSL is a good idea. For an ordinary info site where the worst case is that someone finds out a users login and posts silly messages, not really.
You forgot some stuff
For additional security you can tie the Useragent and IP to a session so the attacker would have to be physically close to the person and use the same browser version.
It foils XSS attacks which try to steal the session.
Er, displaying a page from site A that references an image from site B will not transmit cookies destined for A to B. So the final point of this article is incorrect (unless the site you're viewing happens to be *.example.com).
If you were using URL rewriting instead of cookies to pass around the session ID, then you'd be correct - the session ID would be transferred to example.com as part of the Referer header.
ZOMG! SESSIONIDs are EVIL!!!!!111one
"Back in the early days of the web, the US Government (wrongly) concluded that cookies were evil and they banned them."
This is because experts -- like yourself -- panicked over them and told everyone that used a Netscape branded web browser that the privacy sky was falling. I still have accountants telling me that my expert opinion on cookies is invalid when faced with "conventional wisdom" today.
Now you're panicking over session IDs?!
Let's all switch back to Mosaic already. And while we're at it, IE is never safe from malware, Windows will always be insecure, Macs are safe to use, Mozilla is secure, anti-virus vendors pay virus writers, September 11th was an inside job, etc.
Nothing new here BUT it's about time
That's been around for some time now. It's quite impractical to exploit this vuln on a large scale because you have to be here listening when the guys start talking, so it won't be used much untill most system are relatively safe from asynchronous attacks. But I bet the time will come. Better fix that now. Unfortunately, as always, the crowd won't move until they get hit hard in the face. There's still a hope though: if MS survives the crunch (and the "missing" $700 bn), there will ALWAYS be a large supply of systems vulnerable to asynchronous attacks.
I'll just post my MS-bashing crap as Anon, today.
Good basic overview of common authentication pitfalls.
Informative, concise and well-written. Bit low on the swearing but you can't have everything!
On your server, tie the sessionid to the requesting IP address.
A few other suggestions
This is a nice, and worthy, article - here are a few other things to watch for, some more and some less esoteric - that commonly crop up even in some otherwise well-written web applications.
Disable HTTP TRACE on your webserver. HTTP TRACE returns the headers sent by the client in the request made to the webserver, and can be used in conjunction with XMLHttpRequest to obtain cookies even when httponly is enabled
Make sure you annul on the webserver *and* in the client the cookie when the user logs out. The same cookie (and sessionID) should never be used for more than one actual session, and the client should forget about it when it logs off. It's quite common to encounter web applications that don't do this, leading to the same session being recycled over and over and over again for successive logins from the same client. Stolen the user's session? Great. You've stolen seven.
Always ensure you only accept cookies issued by your application (ie. cookies marked as issued within whatever internal array or database table you use to store your list of valid sessions), and not cookies used before - some web applications accept anything with a valid number/pattern of characters, leading to an attack known as 'session fixation' if an attacker can set another user's cookie to a value known to him/her (eg. via XSS) who then subsequently logs in (giving the attacker a free session to use)
If your web framework requires you to incorporate code into each page you write to perform authorization and entitlement checks, MAKE SURE YOU DO, and centralise it wherever possible. Ensure you check both for a valid session and correct level of entitlement before you do any processing, particularly with POST requests. it's quite common to encounter applications that won't let limited users see the administrator parts of a site, but which accept correctly-formed administrative POST requests from limited users.
Use session management frameworks wherever you can, but /do/ be careful. Certain session management frameworks (like classic ASP) are antiquated and vulnerable (in ASP's instance to the session fixation attack mentioned above).
Ensure you use some form of transient authentication (eg. hidden form fields containing random values) on form posts to protect against CSRF attacks in which a third party submits a request (eg. a GET request in an img tag, or a POST request using XMLHttpRequest) to your website which automatically has cookies sent by the client - if a third party can do this (and in particular if your forms are submittable via GET and POST), an attacker may be able to ride your users sessions in a type of attack known as CSRF (or Cross-Site Request Forgery).
Lastly, but probably-should-come-firstly, make sure you educate your developers well. It's scarily common to encounter developers with big titles in important places who write fantastic functional code that's riddled with security holes. Get a good book on web application security (the web app hacker's handbook is my choice) and buy each of your devs a copy. Give them some time to read it - any developer worth their salt will be writing code that's miles more secure in no time.
Here endeth the lesson.
Just to clarify
I was a bit confused by this section:
"Even if your application always uses SSL, attackers may try to trick the browser into exposing the SESSIONID over a non-SSL connection by getting victims to view a page including the following type of tag:
When the browser sees this tag (even in the attacker's page), it will generate a non-SSL request and send it to www.example.com. The request will include the SESSIONID, and the attacker can sidejack the user's session."
The author seems to be assuming the user has a session on the .example.com domain - the "trick" is then getting a non-SSL request sent to this domain rather than some cross-domain leakage of the SESSIONID. Or have I misunderstood the way session cookies work somehow?
Could somebody clarify ...
The session ID used by IIS is an incrementing integer. It starts as a random number but if yours is 234777668 you know there's a high probability that somebody is active on sessions 234777669 and 234777670.
However, its my understanding that the session ID is *NOT* the actual cookie, which is surely the very much longer string such as JIBNECJCCPLOONHGOJIFHAGH which seems much less guessable.
Equally, it seems to me that each domain visited generates its OWN cookie. Thus the cookie sent to the host of an image served by a third party site *ought* to be different from the cookie sent to the main site. In which case, the cookie given to example.com by embedding that "img src=example.com" would be its own cookie, not that of the site which links to the image.
To be blunt...
Any paid web developer should resign if they don't know this stuff already.
My very simple method:
Generate a GUID, store the GUID in the session cookie. Store the GUID coupled with the requesting IP address on the server.
Get the IP and the GUID from the cookie for each request, compare it to what is stored on the server, and give/deny access based on that.
Session ID vs Authentication.
"When you log into a web application, you exchange your credentials for a SESSIONID cookie. "
That may be true in some cases, but certainly not all. Session management should ideally be kept separate from authentication, and authentication cookies should be encrypted and validated.
re: tie to IP
But be aware of proxying ISPs like AOL that will make a user use several IPs, giving false positives in your logs, and users getting chucked out.
Session's *must* be transmitted over SSL
Why do you send login details over SSL? To prevent them being sniffed and your account being accessed. If you don't send the session ID over SSL too, there's no point in sending the login details over SSL either, as you're account will end up compromised anyway.
If you're sat in a web cafe using facebook, that geek in the corner has sniffed your session ID, is logged in to your account and is in the process of stealing your identity. If you're not using the SSL option with gmail, he's reading your email too and emailing your boss. if you're logged into your favourite DVD rental site, he's logged in as well, adding dubious titles to your list.
*All* of my network traffic goes over a VPN to a trusted server when I'm using a public wifi network. This isn't paranoia, it's just so damn easy for people to sniff plain text traffic in a web cafe and hijack sessions.
Bleh - back to school
Two tier auth - it's all about balance. You should have 2 sessions - one "non-sensitive" and another "sensitive".
The non-sensitive one has access to nothing useful, sort of like when you visit Amazon and it comes up with "Hi Chris... if you're not Chris click here". It doesn't matter too much if people see this session id (e.g. it's URI passed) as having access to this session doesn't allow the user access to anything sensitive. Just register a useragent/ip address hash value with the session and if there's a mis-match, respawn... no biggy.
The sensitive session should be cookies only and those cookies should be SSL only. This session can incorporate data from the non-senstive session, but never the other way around. The sensitive session should only be created upon a successful login (under an SSL domain) and must contain some verification hashes - user agent, IP address, session start time and so on.
You should also store a second SSL cookie containing a user verification string which can be used to check the user against the database (once they're logged in of course).
If either the session hashes or the user verification fails then nerf the session.
None of this is rocket science - it's just a healthy (from an intertubes point of view) "trust no-one" mentality... I don't even trust my own objects and even strings that are passed around internally are "sanitised".
AC - it's that "trust no-one" mentality again. :P
I've not yet encountered AOL generating new IP addresses mid-session for anyone... but that might be because I don't deal with many AOL users thankfully.
A session is just a session
"During that window, if an attacker steals your SESSIONID, they have full access to your account."
Purely depends what you use a session for.
They *should* only have access to your session state at that point, and better still will find they can't proceed further with it without having the relevant mash/hash of keys and elements that define a session ID (which should never be static during the actual "session").
A session is just a session. All it should ever identify is a session between browser and server. Never solely provide the identity of the user or access to their account.
Throw up enough security doors and a hijacker will find to get anything useful from the session they'll need to know a lot more, including passwords.
And yes, it goes without saying that actual secure information should go over SSL. Of course you do use SSL certs from trusted authorities and keep them up to date? ;) (yes, a huge amount of sites just spin their own or fail to update the certs!!).
Surprised noone's mentioned
one-time sessionids. As they're one-time, they can't be hijacked.
What the author is saying with <img src=www.example.com> is that the attacker on site www.attacker.com sets up the img src tag to steal the SESSIONID of www.example.com but forcing it to relay it in plain text rather than SSL encrypted. This would work if normally all links on www.example.com are SSL encrypted.
The SESSIONID would still have to be sidejacked or rerouted though.
I despair at the quality of posts in response to this article: I sincerely hope most of these people are not developing supposedly secure sites I'll be using.
The original article is OK, but its surprising it does not mention session fixation - which is the easiest way to compromise a session (even over SSL).
...WAP gateways have this annoying default set-up of stripping cookies of any kind from your request. Meaning that for mobile development you HAVE to embed the SESSIONID in the URI.
Unless anyone has a decent solution to that one!
Re: Surprised noone's mentioned
And me thinking that every sensible framework used one-time sessionid's. At least Java's JSESSIONID is only used once.
Heh, it may be expensive, but Tivoli Access Manager WebSEAL does this and more: it can keep all the backend cookies on its side, and only send its own session cookie. This cookie keeps tabs on session id, IP address, and *bytes sent/received*. So it is pretty hard to tamper with these cookies, even if they aren't going through SSL, and the session's active. If you have this well configured, it doesn't even matter if your backend's running broken PHP sessions, as the actual session management is done by this "reverse proxy". Nice stuff.