My question is about this summary on session fixation:
Alice has an account at the bank http://unsafe.com/. Unfortunately, Alice is not very security savvy.
Question 1) If your application needs a session, you will have to send some kind of session id. If your application doesn't use sessions, then there is no need to call session_start()
, and ids (whether sent by URL or cookie) are simply not used.
Question 2) You can configure PHP, to accept session ids exclusively from cookies, and to ignore ids from the URL (see session.use_only_cookies). If you do that, you should also check, that the option session.use_trans_sid is set to 0 (this is the default).
You could set the options martinstoeckli mentioned in his answer, but this won't prevent session fixation. It makes session fixation a little harder to attack, but it doesn't prevent it.
As ServerBloke mentioned, you prevent session fixation by using session_regenerate_id() immediately after verifying the user's login information and before you show the first page that requires authentication.
Making it harder for the attacker to exploit session fixation does not prevent session fixation. You must generate a new session ID.
More and more, people are using public unsecured untrusted wi-fi hot spots. Sessions can be sniffed from the air. On a physical network, they can be sniffed off the wire. They can also force you to visit any URL by employing a man-in-the-middle attack. So, session fixation is still a problem, even if the attacker can't send you URLs.
Knowing that sessions (and passwords) can be sniffed, there is another step that is required to prevent session hijacking. That is HTTPS (TLS/SSL).
All protected pages that require authentication should be accessed only over HTTPS. So, the login page (the one where the user sends their username and password) should be accessed via HTTPs. In that same script, you must regenerate a new sessionID. All pages for the remainder of the session must then be accessed via HTTPs to protect the new session ID.
Here's an example pseudocode login.php script:
// Force SSL
if($_SERVER["HTTPS"] != "on") {
die('Must login via HTTPS');
}
// Load the current sessionID
session_start();
// Validate the login information, being sure to escape the input
...
if (! $valid) {
die('Invalid login');
}
// Start the new session ID to prevent session fixation
session_regenerate_id();
// Clear the old session
$_SESSION=array();
// Log them in
$_SESSION['user_id'] = $userID;
I don't fully understand, is this a really problem?
Q1. I think you need to check is there are a SID recieved from GET of COOKIE in you Session storage already (for example, in database). If YES - its'okay, if no, create a new one on server side and do http redirect with new SID.
Q2. I don't use a php 5.4 but i think the following code will help:
unset($_GET['sid'])
Update: I think the common fix is than only the backend-server can generate a SID identifiers. No user posibilites for this!
If you use session_regenerate_id() everytime a user logs in you will prevent session fixation. As the user logs in, their fixated session ID will be regenerated and thus stopping the attack.