Session hijacking prevention?

Started by Eloi, May 24, 2012, 06:24:48 PM

Previous topic - Next topic

Eloi

Does SMF provide protection against session hijacking? If someone eavedrops the connection between user and forum server, can that attacker impersonate the user based on captured information, be it stored in a cookie or embedded in URL if cookies are blocked? If not, could you explain how is it achieved?

I know SMF uses JavaScript to hash a password on client side so attacker can't get a hold of it, but I still don't understand if and how it secures current session.

I put this thread in Feedback and Discussion board, not Support, because it's a general question regarding all current and future versions.

Arantor

The principle detail is stored in a cookie.

For all data changing events, the session ID is passed via the URL and must match the relevant parts of the cookie. This is done to prevent CSRF attacks, and applies to minor actions that can be triggered via the URL, e.g. logout.

For any cases where there is a form to be sent, the session ID is passed in the form itself, again it must match the session, again to prevent CSRF attacks.

Lastly, for major actions in the system, e.g. accessing the admin panel, changing account details in profiles, the user must re-entry their password, which sets a flag in the session.


Session IDs are not accepted for logged in users when supplied via URL to prevent session fixation. There are not checks against IP address (for the obvious reason) but I believe that there are circumstances where user agent is verified between requests.

The bottom line is that the session ID has to be provided per request, there is no way around that due to the stateless nature of HTTP, and doing it via a cookie is the only way that's possible.

If you're afraid of session hijacking, use HTTPS. There's no more that can be done than SMF does in an otherwise-unsecured connection.

Eloi

Thanks for the explanation Arantor.

I suspected there is no real protection against hijacking other than using SSL/TLS. The problem is that forums, including this one, usually don't employ it. This is not SMF specific.

Quote from: Arantor on May 24, 2012, 06:35:03 PM
Session IDs are not accepted for logged in users when supplied via URL to prevent session fixation.

Except when user has cookies blocked, when it has to be sent through URL.

Session fixation is still possible if someone listens to connection and intercepts a cookie, so in which cases does what you have described prevent it?


One question about password hashing. Does client-side JS use the same salt (username?) every time? In case it's fixed, if attacker intercepts that password, account access is granted as if it were a plain text because server compares hashes.

Arantor

QuoteExcept when user has cookies blocked, when it has to be sent through URL.

No, even then it's not permitted, as far as I remember, such that logins explicitly require cookies.

QuoteSession fixation is still possible if someone listens to connection and intercepts a cookie, so in which cases does what you have described prevent it?

There is nothing you CAN do, for any app of any kind anywhere that runs over HTTP without something like Websockets (and even then it's still... complicated).

HTTP is stateless, that means by definition you have to submit the authentication every single request. Either you do that blatantly obviously in the URL (which opens you up to session fixation and easy-insane hijacking) or you do it slightly less obviously in the cookie.

Either way, if you have something that can intercept and observe the cookie, sure it's possible to spoof it, and there's not a fat lot you can actually do about it. The session ID is regenerated periodically anyway, and it is always regenerated upon certain actions (admin, profile) but more than that you can't do.

Mind you, you seem to believe it's possible to secure these things, I'd love to hear what you think should be done.


The hash on the client side isn't done every time, incidentally. It's not done when you register (for obvious reasons) and if the password fails the first time, the second time it is not hashed at all. This is for cases where you have migrated from an old platform that hashes differently and the hashed password from the user won't work.

Off the top of my head I can't remember how it sends it, but IIRC it is much the same as the server-side. Thing is, it actually doesn't matter. If an attacker intercepts that request, it makes no difference whether it's hashed or not, the hacker gets in, and there's no way around that. On the other hand, hashing it does mean it isn't actually *known* to the attacker so even if one account is compromised, it means that any other accounts using the same username/password are still more secure than if the password is known.


I understand that you're paranoid about security. It's a fine mentality to have. Unfortunately, HTTP was not designed with this in mind, the only methods of password protection in HTTP itself are almost pointless (seeing that the username/password or username/unsalted MD5 (IIRC) are sent every request)

Eloi

Quote from: Arantor on May 25, 2012, 06:56:01 AM
No, even then it's not permitted, as far as I remember, such that logins explicitly require cookies.

I tried disabling cookies and login works that way too. Session ID is appended to URL, right after the question mark.


Quote from: Arantor on May 25, 2012, 06:56:01 AM
Mind you, you seem to believe it's possible to secure these things, I'd love to hear what you think should be done.

Actually, I wanted to understand how it works and your explanations helped. Thanks again.

Arantor

It actually works? That surprises me, I was under the impression that it didn't. The PHPSESSID cookie does get appended, but the full SMFCookie shouldn't be.

(Note that it does get put into the URL in some cases, like the logout URL, as indicated. I guess I need to go back and look at the code since I think it needs changing.)

xekon

#6
Quote from: Arantor on May 24, 2012, 06:35:03 PM
Session IDs are not accepted for logged in users when supplied via URL to prevent session fixation. There are not checks against IP address (for the obvious reason) but I believe that there are circumstances where user agent is verified between requests.

I have been reading about the different securities in place for various CMS and forum php web apps (smf, drupal, phpbb, mybb) regarding user authentication, and session/cookie security.

I have been reading about them to get a better understanding of good practices for an opensource php web app that I have been writing, primarily as a learning experience.

phpBB has "Session IP validation:" options in the Security settings. where you can match against part of or the entire IP address.

I would really like to know the reason there are not checks against IP address, it was not obvious to me, but I am still learning.

The other phpbb security checks were: "Validate X_FORWARDED_FOR header", "Validate Referer:",

and "validate browser" which is what I think you said smf does with the "user agent".

and mybb has this option:
"Do you want to check a user's IP address for HTTP_X_FORWARDED_FOR or HTTP_X_REAL_IP headers? If you're unsure, set this to no."

Arantor

QuotephpBB has "Session IP validation:" options in the Security settings. where you can match against part of or the entire IP address.

That can be viable if, and only if, you know the session will not bounce between too many IP addresses. There are still networks out there that will bounce users between very wide ranges of IP addresses, which means this could break things for users.

QuoteThe other phpbb security checks were: "Validate X_FORWARDED_FOR header", "Validate Referer:",

SMF does things with X-Forwarded-For (see below). Checking the referer is not necessarily wise since not every browser submits a referer (especially internet security software and proxies that strip the header) but if it is supplied, it should not be changing between requests. SMF will do some limited checks against this.

Quoteand mybb has this option:
"Do you want to check a user's IP address for HTTP_X_FORWARDED_FOR or HTTP_X_REAL_IP headers? If you're unsure, set this to no."

SMF already checks HTTP_X_FORWARDED_FOR and if you ban any IP addresses, it will apply the ban to both the 'IP address' and the 'X-Forwarded-For' IP address that a user has.


As for what X-Forwarded-For and X-Real-IP are, these are where there is a proxy between the user and the server, through whatever means (maybe it's a server proxy like CloudFlare) and the IP address that the user presents is actually the proxy's IP address, so the proxy adds the actual user's IP address to a header when it gets to the application.

xekon

Excellent! Thank you so much for the reply :)

Advertisement: