Jump to content

PHP Sessions


Kovo
 Share

Recommended Posts

I have a security question about PHP session security. I have read up quite a bit on php session handling and would like some input from some of the experienced posters (or any poster of course).First of all, the information stored in the sessions is propagated over the entire visit of the user. (its an online text-based game). I store player info, statistics etc... into session variables so that I do not need to run dozens of queries per page. Then when a user makes an action that requires a value to change, I do so in the session and run an UPDATE in the database, but then do not need a subsequent SELECT to get the new information since I already updated the session info itself.Of course to avoid cheating, its important that the user cannot some how hack his/her own session data (it can cause bugs in the system if they do). So is there any way apart from a direct hacking attempt on the server to modify session info outside of the control I have placed?This is how I initiate every session (on script execution): (example code given)

session_set_cookie_params(0, '/', '.mydomain.com', false, true); 	session_start();	if(strlen(session_id()) != 32 || session_id() == '')	{		session_id(hash_session_id_function());	}

Also would anyone else have any security tips I could use to protect sessions from being hijacked, hacked or compromised?Thank you!

Link to comment
Share on other sites

Session data is stored on the server. Data you store using the $_SESSION array is not available to the client. The only thing that travels to the client, and from client to server, is a unique identifier that associates the client with the correct data. So there is no direct way for a user to hack the session data.I'm not sure what you think your hash routine does, but I doubt it improves security.As with most data, the biggest security risks are ones you create yourself. SQL injection, which you can Google, is the biggest threat to any system that uses a database. There are simple ways to protect against it.If your game depends on a user submitting accurate data to the server, then that of course can be spoofed. Unless you're going through something like FLASH, any user can modify a copy of the document in his browser and send back data to make it seem like something has happened that could not happen. So you'd need a way to validate incoming data before using it.

Link to comment
Share on other sites

Session data is stored on the server. Data you store using the $_SESSION array is not available to the client. The only thing that travels to the client, and from client to server, is a unique identifier that associates the client with the correct data. So there is no direct way for a user to hack the session data.I'm not sure what you think your hash routine does, but I doubt it improves security.As with most data, the biggest security risks are ones you create yourself. SQL injection, which you can Google, is the biggest threat to any system that uses a database. There are simple ways to protect against it.If your game depends on a user submitting accurate data to the server, then that of course can be spoofed. Unless you're going through something like FLASH, any user can modify a copy of the document in his browser and send back data to make it seem like something has happened that could not happen. So you'd need a way to validate incoming data before using it.
All queries are sanitized. All values expected to be integers are typecast. 9 out of 10 actions in the game are made via AJAX and all requests that should be AJAX are checked if they are being called via AJAX before executing (this way if someone wants to manually submit data to a processor script I have, they would need to send an AJAX request, and AJAX has cross domain restrictions that would negate that form of cheating/hacking)And again, if someone submits a form where they are theoretically limited to a number (ie 1000) and instead modify the form to send 2000, in all my scripts I always compare data stored in the session to what they are submitting. So I guess the best way to program is to assume everyone will try to cheat.As for my session init routine, I simply limit the session cookie to only being edited via php and not the client (for example javascript cannot access or modify the cookie) also I generate a md5 hash for actually naming the session itself (the id). Which make sit slightly harder for someone to hijack a session via redundant, bruteforce methods. I also place that session id name into the cookie itself and also run a check on that to make sure it matches the session id sent via php.
Link to comment
Share on other sites

I suppose someone could brute-force hack a session id. With only 16**32 possibilities, eventually they would hit the correct one. One attempt per second would require 10**31 years. One attempt per millisecond would require 10**28 years. One per microsecond would require 10**25 years, but I'm pretty sure most Internet connections would reject requests coming at such a rate. Compared to your processor's crunch-speed, the Internet travels at a snail's pace.But let's assume one request per microsecond anyway. Your hacker will require (the age of the universe) * (the age of the universe) * 100 years to guarantee a successful hijack.Unfortunately, since an MD5 hash results in the same kind of 32-character hexadecimal string used as a session ID, I don't think you improve security at all.Unless you want to pay for a SSL, server-side validation is all you really need, and it sounds like you're already doing what you can.

Link to comment
Share on other sites

9 out of 10 actions in the game are made via AJAX and all requests that should be AJAX are checked if they are being called via AJAX before executing (this way if someone wants to manually submit data to a processor script I have, they would need to send an AJAX request, and AJAX has cross domain restrictions that would negate that form of cheating/hacking)
I'm not sure I follow that one... AJAX or not, an HTTP request is an HTTP request. It can always be forged. No matter what you check for, it can be submitted in a wrong way. The only thing close to a secure thing is the session ID itself. If you deny AJAX requests when the session ID has expired or is invalid, you'll be requiring from hackers to make one very sophisticated bot if they want to cheat, and even then, they'd actually have to log in before activating the bot.
Link to comment
Share on other sites

I'm not sure I follow that one... AJAX or not, an HTTP request is an HTTP request. It can always be forged. No matter what you check for, it can be submitted in a wrong way. The only thing close to a secure thing is the session ID itself. If you deny AJAX requests when the session ID has expired or is invalid, you'll be requiring from hackers to make one very sophisticated bot if they want to cheat, and even then, they'd actually have to log in before activating the bot.
Well checking if its an AJAX call or not is not the only layer of protection I use. I do require a valid active session to have access to every page/script on every request anyways.What I do check for is if two special headers are sent to my scripts that would only be sent when using AJAX. It wont protect against everything, but it should deter the common hack that is just trying to screw around. I also protect all files that are included with a required variable check, if that variable does not exist or does not equal a certain value, the script simply exits. Of course it would be hard to guess file names that are only ever included, I have that check anyway.As for the brute force calculations. The server setup Im on will automatically ban an IP that makes too many requests over a short period of time. So I guess I shouldn't have to worry too much about rudimentary brute forcing techniques.
Link to comment
Share on other sites

Have a look around your whole application with Fiddler (see my signature). In particular, make sure you look at the "Raw" tab.There's no such thing as "special headers ... only sent when". Any header can be sent at any time. While yes, checking for those headers may stop people who just copy&paste the URL into the browser and refresh it repeatedly, it won't stop anyone who's willing to write a bot.The only way to reliably protect yourself from bots is that other thing you're already doing - automatically block IPs and/or accounts that make too many requests in a too short period of time. That way, on the very least, a bot will have to be made in a way that doesn't go beyond the allowed rate.

I do require a valid active session to have access to every page/script on every request anyways.
Including AJAX calls? If so, good.
Link to comment
Share on other sites

Have a look around your whole application with Fiddler (see my signature). In particular, make sure you look at the "Raw" tab.There's no such thing as "special headers ... only sent when". Any header can be sent at any time. While yes, checking for those headers may stop people who just copy&paste the URL into the browser and refresh it repeatedly, it won't stop anyone who's willing to write a bot.The only way to reliably protect yourself from bots is that other thing you're already doing - automatically block IPs and/or accounts that make too many requests in a too short period of time. That way, on the very least, a bot will have to be made in a way that doesn't go beyond the allowed rate.Including AJAX calls? If so, good.
Thanks, I will take a look at Fiddler.Yes, every request including AJAX calls requires a valid session ID, cookie and a few other checks.Thanks for the tips guys
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

×
×
  • Create New...