Wednesday, September 23, 2009

Session Denial: session id contains illegal characters

This morning I woke up, went over to StackOverflow (Yes I admit lately I've been quite active answering questions on SO) and I saw this question: Session hijacking or attack?

The asker, Toto, saw these in his error logs:
[22-Sep-2009 21:13:52] PHP Warning: session_start() [function.session-start]: The session id contains illegal characters, valid characters are a-z, A-Z, 0-9 and '-,' in /var/my_files/class.session.php on line 67 
[22-Sep-2009 21:13:52] PHP Warning: Unknown: The session id contains illegal characters, valid characters are a-z, A-Z, 0-9 and '-,' in Unknown on line 0
[22-Sep-2009 21:13:52] PHP Warning: Unknown: Failed to write session data (files). Please verify that the current setting of session.save_path is correct () in Unknown on line 0


The first thing I thought before answering question was that obviously the user had tampered with the PHP session cookie (The cookie name is "PHPSESSID" by default).

So what we can do to prevent these errors is to simply reset the ID whenever the session fails to start:

<?php

$ok = @session_start();
if(!$ok){
session_regenerate_id(true); // replace the Session ID
session_start(); // restart the session (since previous start failed)
}

?>

Note that users tampering/changing the PHPSESSID to generate this error does not affect your server or read/write files on your server. It may be an attempt to generate great amount of log entries into your error logging file and so on. Thus with this solution, you can prevent such things from happening, yet allowing smooth load for normal users.

this piece of security protection has been added to Samstyle PHP Framework (after v1.2.11).

Friday, September 4, 2009

PHP speed up: Quote your strings

I've wanted to post this earlier, but i've been busy lately. So yeah, here's a tip off on how to speed things up for new or beginner php developers.

You might have noticed, PHP error level by default is set to E_ALL & ~E_NOTICE, which means all errors except notices are reported.

Take a look at the following snippet:
<?php

$test = cool;
echo $test;

?>


You might have noticed that it works fine. The output is still "cool".

But when you set the error level to E_ALL, you get to see an additional line like this one:
Notice: Use of undefined constant cool - assumed 'cool' in /public_html/quotestring.php on line 3

This means what when the line "$test = cool;" is parsed, PHP actually look up whether a constant "cool" exists. If not, it will assume that it is the string "cool". This means that extra time is taken to find the constant.

We ran a test to compare between quotes and no-quotes for a string, and also compared between double quotes and single quotes. the result was amazing (the output on browser):

Notice: Use of undefined constant cool - assumed 'cool' in /public_html/quotestring.php on line 4
cool
0.000458002090454 s
cool
9.05990600586E-6 s
cool
8.10623168945E-6 s

The first one is without quotes (look up constants then decide that it is a string). The 2nd one is using double quotes (look if there are variables or control characters to parse then output) and the last one is using single quotes (just output).

The full PHP code for the test results can be found on Pastebin at the following link:
http://thephpcode.pastebin.com/f7bb6a1f9

So remember to quote your strings with single quotes and occasionally use double quotes to speed things up. I am Sam Yong, signing off.