About the Author

Chris Shiflett

Hi, I’m Chris: entrepreneur, community leader, husband, and father. I live and work in Boulder, CO.

Session Hijacking

  • Published in PHP Architect on 26 Aug 2004
  • Last Updated 26 Aug 2004

Welcome to another edition of Security Corner. This month's topic is session hijacking, often referred to as an impersonation attack. Session hijacking describes all methods by which an attacker can access another user's session. A successful session hijack attack exploits a flaw in the application; as PHP developers, the safeguard is our responsibility.

In an earlier column, I discussed session fixation, a method by which an attacker can gain a valid session identifier. The purpose of such an attack is to use this identifier to attempt to hijack a session. Thus, defending against session fixation helps to defend against session hijacking, but it only addresses a small part of the problem.

Capturing a Session Identifier

A more popular method of obtaining a valid session identifier is to capture it. There are many methods of capture, and these can be categorized according to the method used to propagate the session identifier. For example, if the session identifier is propagated as GET data, attacks focus on obtaining GET data, not specifically the session identifier.

This type of propagation is less secure than using a cookie, because GET data is more exposed. When possible, use a cookie to store the session identifier. Of course, this is just a defense in depth mechanism and should not be considered the primary safeguard.

It's a good practice to anticipate the worst case scenario. Thus, in this article, I demonstrate how to complicate impersonation under the assumption that the session identifier has already been captured. Of course, this is not a desirable situation, but every bit of complication for an attacker increases the security of the application.

Complicating Impersonation

If your session implementation consists of nothing but session_start(), it is very susceptible to session hijacking. In order to discover a method that can help to prevent simple exploits, first consider a typical HTTP request:

GET / HTTP/1.1
Host: example.org
User-Agent: Mozilla/5.0
Accept: text/xml, image/png, image/jpeg, image/gif, */*
Cookie: PHPSESSID=1234

A cookie named PHPSESSID is used to propagate the session identifier in this example.

Of the HTTP headers given in this example, only Host is required, and it certainly isn't very unique. So, it may seem at first glance that nothing within the request can help to identify the user with any more assurance than with the session identifier alone. While this isn't entirely false, any consistency that can be found in each request from the same client can be used to complicate impersonation, and there are steps that can be taken to provide some of this consistency. To further illustrate this concept, consider the following request sent soon after the previous one:

GET /profile.php HTTP/1.1
Host: example.org
User-Agent: Mozilla/5.0 (compatible; MSIE)
Accept: text/xml, image/jpeg, image/png, image/gif, */*
Cookie: PHPSESSID=1234

If every previous request from client 1234 used a different User-Agent header, should this request not be treated with some suspicion? It's possible that this request is an impersonation attempt, and asking the user to verify the password is a good safeguard. The legitimate user will be able to provide the correct password and continue, but an attacker cannot.

The following example shows how you can add a simple check for this:

if (isset($_SESSION['HTTP_USER_AGENT']) &&
    /* Prompt for Password */
} else {

Does this provide enough protection against impersonation? Not really. If the session identifier is being propagated in a cookie, consider that most cookie exploits involve the victim visiting the attacker's site. Thus, if the session identifier has been captured, it is reasonable to assume that the attacker also has access to the HTTP headers that the victim's client includes in a typical request. An impersonation attack simply has to reproduce all of these headers, and then any extra check that relies on any of these is rendered useless.

What if the MD5 of the User-Agent header is used as a browser fingerprint that is propagated with every request, just like the session identifier? In order to bypass this extra safeguard, an attacker would not only have to reproduce the correct session identifier and User-Agent header, but also the correct browser fingerprint. This requires an extra step, so it is more secure.

The weakness with this approach is that guessing the value of the browser fingerprint is not difficult. An MD5 is easily recognizable, and an attacker can use the application itself to get a sample one. With this, figuring out that it's the MD5 of the User-Agent header isn't too terribly difficult. However, consider a browser fingerprint that is generated with the following code:

$string = $_SERVER['HTTP_USER_AGENT'];
$string .= 'SHIFLETT';
$fingerprint = md5($string);

With the addition of some secret padding (SHIFLETT in this example), generating a valid browser fingerprint for someone else is more difficult. In fact, prediction becomes so difficult at this point that capturing a valid browser fingerprint is more likely to be the easiest route for an attacker to take.

To complicate the process of capturing the browser fingerprint, a different method of propagation should be used for the session identifier and browser fingerprint. If both are propagated as cookies, it is reasonable to assume that the same attack can capture both. The same is true if both are propagated as GET data. I recommend propagating the session identifier as a cookie and the browser fingerprint as GET data. If you rely on session.use_trans_sid, then you can simply focus on including the browser fingerprint in each URL. Users who disable cookies will have both the session identifier and browser fingerprint propagated as GET data, but this cannot be avoided. Those who enable cookies will automatically have a bit more protection against impersonation.

Some experts warn against relying on the consistency of the User-Agent header. The argument is that an HTTP proxy in a cluster can modify the User-Agent header inconsistently with other proxies in the same cluster. While I have never observed this myself, it is definitely worth noting.

I have observed that the Accept header can change for Internet Explorer users depending upon whether they refresh the browser to request a page, so this should not be relied upon for consistency.

If you are skeptical about relying on any consistency in the HTTP headers, you can opt to use a unique token rather than a browser fingerprint. More often than note, this is the approach I choose. To generate this token, use code similar to the following:

$token = md5(uniqid(rand(),TRUE));
$_SESSION['token'] = $token;

This token should then be propagated with each request, using a different method than used to propagate the session identifier (just like the browser fingerprint). This token can also be frequently regenerated to tighten the window of opportunity for an attacker.

Until Next Time...

The purpose of this article, like many others here at Security Corner, is to give you enough information to develop solutions that fit you best. Hopefully you now have a clearer understanding of the types of session-based attacks that you must defend against and have a few ideas to get you started protecting your applications. Until next month, be safe.

About this article

Session Hijacking was last updated on 26 Aug 2004. Follow me on Twitter.


1.iges wrote:


/-- article

I recommend propagating the session identifier as a cookie and the browser fingerprint as GET data.


Perhaps it's my limited understanding of english, but I really don't see why you would want to propagate the browser fingerprint at all to the client?!

The point of the fingerpoint IMHO should be that it's a server side only thus the client will not even know it's being used to validate the request.

Thu, 06 Oct 2005 at 10:08:28 GMT Link

2.Zack wrote:

Can somebody please give an example on how to properly implement the token technique? Thanks.

Sat, 15 Oct 2005 at 19:44:08 GMT Link

3.Joe Hanink wrote:

It sees that using Page Tokens will impose a some of work on the page developers. I've written a description of a similar idea that I call Request Tokens that passes a token by cookie rather than by link. The benefit of using a cookie is that a page author needn't concern himself with it. There is some work needed by the application developer but that's more at the framework level. This system also supports concurrency -- simultaneous requests with the same token.

I've added my discussion to wikipedia under Session Hijacking


I'd be interested in your review.

Mon, 14 Nov 2005 at 14:18:54 GMT Link

4.Joe Hanink wrote:

in previous post, the first two words should be "It seems"...

Mon, 14 Nov 2005 at 20:36:01 GMT Link

5.lezzard wrote:

@iges: the use of browser fingerprints is to enforce security in a worst case scenario where both Session ID and User-Agent of the victim (the original client) have been collected by the impersonating attacker. It would be very easy for the attacker to send his request headers with this collected information, so we create a browser fingerprint out of the User-Agent and some secret phrase or whatever. The fingerprint must be propagated to the client, as this will be his ticket to ride.


Fri, 23 Dec 2005 at 02:37:41 GMT Link

6.Joe wrote:

I might be missing something obvious, but here is a measure that might be useable - Since we can use the session_name() function or session.name directive freely(PHP_INI_ALL- can be set anywhere), if I always use an obscure MD5(salt et al) string instead of PHPSESSID, does it get me any security against attacks of the type http://example.com/example.php?PHPSESSID=1234 ?

Sat, 21 Jan 2006 at 19:29:04 GMT Link

7.Chris Shiflett wrote:

Joe, not at all. It's trivial for an attacker to visit your site to obtain a session identifier and then use that in the attack, regardless of its name or value. It raises the bar, but very little.

Others have also made the mistake of thinking that this eliminates session fixation:


Unfortunately, it doesn't.

Sat, 21 Jan 2006 at 19:54:38 GMT Link

8.KTH wrote:

(1) What is the difference between session.use_trans_sid and session.use_only_cookies; it seems to me that they both require sessions to be handled in cookies.

(2) If the bad guy has obtained the sessionID and presumably the user-agent information, how does he not also have the fingerprint from the URL?

Wed, 15 Feb 2006 at 01:41:54 GMT Link

9.Jared Evans wrote:

I just don't see how the fingerprinting will help the security at all.

If the attacker has the sessionID and is able to grab the User-Agent from a visitor, he would be able to find the fingerprint information from the URL and use it in the attack.

Please explain more how this can be prevented, if at all.

Tue, 11 Apr 2006 at 23:53:22 GMT Link

10.Chris Shiflett wrote:

Hi Jared,

You're making things sound trivial that aren't at all. How can an attacker "find the fingerprint information from the URL" exactly?

Yes, it is possible that a victim has been lured to an attacker's web site, so the User-Agent header might be compromised, but that's not all that's necessary for impersonation.

Also, in case it's not clear from the article, these are Defense in Depth measures and should not be considered primary safeguards. Keeping the session identifier a secret is the primary objective.

Hope that helps.

Wed, 12 Apr 2006 at 00:00:05 GMT Link

11.Jared Evans wrote:

The attacker could try starting many different sessions with different User-Agents then storing the different fingerprints off the GET data.

When the attacker captures a visitor with a valid sessionID and takes a look at the user's User-Agent, the attacker can preload the corresponding fingerprint along with the request.

There are not that many different User-Agents to try out, even just the top 50 popular ones could be pre-run against the website which would match up with a high percentage of web users.

Wed, 12 Apr 2006 at 01:46:03 GMT Link

12.Chris Shiflett wrote:

Hi Jared,

Yes, an attacker can profile your application to create a rainbow table. This is similar in idea to sites like the following:


The difference is that, because of the seed, a unique rainbow table must be created for your application, and it must be updated whenever you change the seed.

You can make it more complicated to create such a table by only using sessions when you need to, such as when someone logs in. An account showing an abnormally high User-Agent inconsistency rate can be temporarily suspended (because it is being used for profiling). There are numerous steps that, when combined, can strengthen a session mechanism.

And again, I want to stress that these are all secondary, Defense in Depth measures. Most developers trust the session identifier absolutely, and simple additional measures like these can help. Using SSL, requiring authentication immediately prior to sensitive actions, and other standard techniques can still be applied. Joe's article mentioned above might be of interest to you:


Hope that helps.

Wed, 12 Apr 2006 at 02:17:41 GMT Link

13.Chris Shiflett wrote:

I forgot to point out that you might prefer generating a random token as mentioned in the article. This does not depend on User-Agent, so it is not weakened in the situation where this header has been compromised.

I should update the article to describe combining these two methods, since that is another possibility.

Wed, 12 Apr 2006 at 02:25:53 GMT Link

14.Jared Evans wrote:

I have not attempted this plan of attack yet but it could be technically possible for this attack to defeat a fingerprint on a website where the seed changes often.

After getting the User-Agent of a unsuspecting visitor:

The attacker could start a request to the website with a sessionID to obtain the fingerprint for the User-Agent. This sessionID would be tossed aside then the attacker would open another request with a new sessionID, the visitor's User-Agent, and the fingerprint that was just retrieved.

This way, it wouldn't matter how often the seed was changed because the attacker would be able to obtain a valid fingerprint within a few seconds.

Wed, 12 Apr 2006 at 02:36:08 GMT Link

15.Lance wrote:

You've already made the disclaimer that any measure is better than none when it comes to security however it seems to me if a hacker is sniffing the network and gets access to your Request Header won't they have your sessionId and any GET variables that you're propagating. I'm not too familiar with network sniffing but I know that basic sniffers give you Cookie and Get information. If they are in fact sniffing the network then different means of propagation seem ineffective.

BTW, your article was very helpful to me in understanding exactly how sessions work.


Sun, 04 Jun 2006 at 09:36:57 GMT Link

16.Roman wrote:


Great article. I do have one question regarding what you said earlier about "Defense in Depth":

The "members area" of the website I'm developing is being run entirely via HTTPS connection using a trusted SSL certificate. In addition, instead of relying on User-Agent and other such headers, my authentication mechanism uses the "random token" approach. In addition, I don't propagate anything via GET method.

My question is: if all the session cookies, including session ID and the token are encrypted how can the attacker actually capture them in the first place?

I'm currently re-evaluating the security measures for my website and having some doubts whether the "random token" approach is any more secure than using the headers like User-Agent.



Thu, 07 Dec 2006 at 04:24:50 GMT Link

17.Chris Shiflett wrote:

Hi Roman,

Even with SSL and everything you're doing, a simple XSS vulnerability would be all an attacker needs in order to steal your users' cookies.

The cookies would still be encrypted of course, but you want to ask yourself whether that actually offers any protection in this case.

Thanks for the question. You made me realize that I don't have another article to point to for examples, so maybe this is a good topic to explore in writing. :-)

Thu, 07 Dec 2006 at 05:03:40 GMT Link

18.Joeri wrote:

I like the idea of adding a fingerprint and prepend a string to it. But considering the string having a predefined value, the fingerprint for a certain user agent is always the same. changing the string value added to the fingerprint to a random one would render a unique fingerprint for every user. thus combining the token & fingerprint method... I might be missing something but wouldn't increase security?

Your article was an eye opener btw, thanks!

Thu, 21 Dec 2006 at 13:56:18 GMT Link

19.Chris Shiflett wrote:

Hi Joeri,

Yes, that's a good idea. :-)

Thu, 21 Dec 2006 at 15:16:01 GMT Link

20.Rev wrote:

When using a random token in place of a header fingerprint, how is the token actually used/verified? Database check on each hit?

Tue, 20 Feb 2007 at 21:21:21 GMT Link

21.Roman wrote:

Apologies for posting so late in the discussion. I’m not sure if it's still relevant. But for what it’s worth, here it is:

I did a bit more thinking and implemented the following security approach:

Once the user successfully logs into the member area, a session record is created in the SESSIONS database table and he is given a session ID as well as a request token. As soon as they issue the next HTTP/HTTPS request, the server authenticates the request, and if successful – issues the next HTTP/HTTPS token for the next request. Once the next request is made, a new token is issued – and so on. Therefore, the session ID remains fixed, but the new request token is issued upon each request – AS LONG AS the request has been positively authenticated.

So, what constitutes request authentication? Upon each request to do something in the member area, the server must check for 3 things:

- session ID (cookie compared to a value stored in the SESSIONS table record)

- last-issued request token (cookie compared to a value stored in the SESSIONS table record)

- User-Agent (header value compared to a value stored in the SESSIONS table record)

If there is a record in the SESSIONS table where all 3 conditions are satisfied, the request is deemed authentic and the server goes ahead to process the request appropriately. Once the server is done, it sets the new value for last-issued request token cookie (i.e. the new request token for the client to use upon the next request)

If the session ID and the request token have somehow been captured, they are only good enough until the legitimate user issues the next request. In this case, the server will detect the mismatch between the last-issued request token and the request token presented in the cookies and kill the whole session under the suspicion that it has been taken hostage.

Then, the question is – what happens if the legitimate user has left the session idle and the malicious requests have taken over? To address that, I implemented a mechanism that would issue "idle" requests to the server (using AJAX) every 3 minutes. So, even if the user has left the session idle, the page can still issue idle requests. This way, the attacker only has a maximum 3-minute window until their malicious request is followed by the "idle" request from the legitimate user's browser. The server will then detect the mismatch of tokens – and kill the session.

Plus, I added another mechanism to log the user out and kill their session once the server receives 10 idle requests in a row (i.e. 30 minutes of inactivity).

There may need to be some tweaking to allow for near-simultaneous requests both of which are legitimate. I addressed it by comparing the request token presented in the cookie with not just "last-issued" token but also "second-last issued token", and imposed a limitation that the time-difference between the two must be no more than 3 seconds – otherwise the 2 requests are not deemed near-simultaneous and the server kills the session under the suspicion that legitimate requests are accompanied by malicious requests.

All of this adds extra processing around authenticating each individual request. In my case, the increase in processing was negligible.

I suppose it depends on your needs. Perhaps what I've just described above is a bit of an over-kill.

Any ideas? Comments? Issues? I’m happy to hear them all.

Fri, 18 May 2007 at 01:27:23 GMT Link

22.Lucian Sabo wrote:

- session ID (cookie compared to a value stored in the SESSIONS table record)

This refers to the session fixation problem, not session hijacking.

- last-issued request token (cookie compared to a value stored in the SESSIONS table record)

To find out the session id an attacher would use either XSS or network sniffing. Either way, the cookies are in his hands if we are using a non-SSL connection.

Chris said that propagating with a different method (like GET) is a good idea.

An XSS attacker could transmit the GET request token and the cookies also using document.cookie+document.location.search. Try it !

With a network sniffer... no problem if it's plain text.

So a reasonable way to protect agains the session hijacking

is changing the request token GUID on each request (like Roman suggested).

This way a hijacked session will be closed in the next request by the legitimate user or the hijacker by generating a different GUID.

PHP sample code:



//session Hijacking protection


if ($_SESSION['request_token'] != @$_COOKIE["request_token_guid"])




header("Location: LoginForm.php");



else $_SESSION['request_token']=md5(uniqid(rand(),true)); //first time guid generation

//generate a new request token GUID for each HTTP request for improved protection




- User-Agent (header value compared to a value stored in the SESSIONS table record)

The attacher can use the same browser.

:) He could try with IE, Firefox and Opera, ... it's not so hard to find the browser used by the valid member.

For example he could send it by XSS.

No. Relying on browser fingerprint it's not a security measure.

Mon, 21 May 2007 at 09:50:59 GMT Link

23.Eeve wrote:

Could you not create a type of footprint using some harder to guess/spoof data, and store it in a session variable that does not give a clue about it's contents? Example:

$_SESSION['user_key'] = md5("my secret words") . md5( $_SERVER['HTTP_USER_AGENT'] ) . md5 ( $username );

So, my footprint doesn't automatically look like an md5, and the hijacker would be unable to guess what it is that I'm hashing. I could even use md5 AND sha1.

Short of actually getting a look at your PHP script, I don't see how someone trying to hijack the session could spoof this. If you don't care about AOL users, you could even add the md5 of the IP address too.

Does anyone see a flaw here?

Thu, 21 Jun 2007 at 17:59:21 GMT Link

24.Eeve wrote:

... actually, I would combine my inputs and THEN md5 them, and add something else to the end. This way the beginning of the footprint is not always the same.

Thu, 21 Jun 2007 at 18:02:51 GMT Link

25.beaule wrote:

Hi everyone.

You speak about a unique token per request wich is validated at a server level.

Ok, looks good, but what about user double click on HREF?

Mon, 09 Jul 2007 at 14:44:58 GMT Link

26.Roman wrote:


Double-clicking on HREF means generating two "near-simultaneous" requests. So, while the server is still processing the first request and hasn't yet issued a fresh new request token, the second request is already on its way.

To avoid session termination, the idea is to store not just the last token but also the second-last token. And also, store the timestamp of both last token and second-last one.

So, in the event of 2 near-simultaneous requests, your server-side script must compare the request token supplied in the cookie with not just "last-issued" token but also "second-last issued token".

BUT this opens up a security hole: the attacker can time his requests so that they alternate with those of the legit user (so, malicious request -> legit request -> malicious request -> legit request, and so on). Thus a malicious request's token will always match the second-last token and so the attacker will be able to do bad things while the user is doing legit things - all within the same session.

To avoid this, your server script MUST impose a limitation that the time difference between the last and second-last requests must be no more than 3 seconds – otherwise the 2 requests are not deemed near-simultaneous and the server kills the session under the suspicion that legitimate requests are being accompanied by malicious requests.

This will only give the attacker a 3-second window to do something bad, until the server kills the session deeming it hijacked. Then, the attacker would have to start all over again (i.e. get hold of the legit user's cookies, etc)

Coming back to the "double-click" situation - because double-clicking will always happen within the 3 second interval, the server will be presented with 2 ligitimate near-simultaneous requests.

I've tested this scenario in my web apps and it seems to be working well.

Hope this answers your question.

Fri, 20 Jul 2007 at 06:41:16 GMT Link

27.Mambo wrote:

The $token = md5(uniqid(rand(),TRUE)); should be $token = uniqid(md5(mt_rand(),TRUE)); instead. md5 has security flaws as you know and mt_rand() generates a better random value than rand().

Tue, 31 Jul 2007 at 08:41:40 GMT Link

28.Romil Jain wrote:

Chris, Roman, Beul - gr8 discussion.

Couple of questions/comments:

1) I think if a hacker is hell-bent, then he can easily create a program to do the following:

- Sniff server responses and identify ones that contain a sessionid, last issued token etc.

- generate a server request with the sniffed sessionid, token

- it doesn't matter even if these are encrypted. Its the server's job to decrypt them. The hacker just has to send back the encrypted values.

This can be easily done within milliseconds with a powerful dual core proc. So it easily beats the 3 sec. window

2) I analyzed Orkut's authentication/authorization procedure:

- Use HTTPS to transmit username/password

- Send back some cookies (over SSL), once authenticated

- Redirect to some HTTP page

After this stage, all authentication is done through few cookies.

These cookies are authorized for the following URL's

- www.google.com/accounts (cookies rememberme, SID)

- google.com/ (cookie LSID)

- orkut.com/ cookies (_utma, _utmb, _utmz)

If I delete even 1 of them, the authentication fails.

However, I am just clicking on http://www.orkut.com/... URLs. So only the last cookie should be useful and deleting the rest should not have any effect. Also, there is no redirection happening b/w orkut & google. So I fail to see why deleting the Google cookies are having any effect for subsequent requests.

Anyway, the point of illustrating Orkut's example is the following:

- Orkut does not use any javascript for authentication. Everything works just fine even if you've disable javascript.

So no 3 second windows etc. can be implemented.

- Post initial authentication (through username/password over HTTPS), all authentication is taking place using cookies over HTTP.

Now, the only thing that could distinguish b/w two requests with similar cookies are the following:

1) HTTP Headers (USER-AGENT, ACCEPT etc.)

2) IP Address.

- The first one is really easy to duplicated.

- IP spoofing is not impossible, but extremely hard. But it becomes a child's play when the victim & hacker are both behind a firewall (since Orkut/Google cannot distinguish b/w their IP's).

So how do they distinguish b/w the hacker and the victim? Orkut is backed by Google, which has hundreds of PhD's. So in all likeliness, they use some mechanism which is extremely hard to crack. How do they do it???

Any thoughts/suggestions?



Tue, 25 Sep 2007 at 15:51:16 GMT Link

29.Sherri wrote:

I'm starting to believe that adding IP address to the token is a must for bare minimum (sorry AOL users), but that there is no perfect solution since any info coming to me from the user can be spoofed- there's just no way to tell if the user is legit.

This explains why so many sites ask for your password again on the page where you make any changes to your account - like change your address.

But then what stops someone from spoofing an Amazon session and billing a book order to someone's saved CC and have it shipped to their location of choice? Amazon doesn't ask for your password before it bills the credit card that is on file. That's why I email Amazon and make them remove it from their system. But, if spoofing is so easy, what is protecting Amazon's system for example?

Tue, 16 Oct 2007 at 13:33:11 GMT Link

30.Ryan The Great wrote:

I realize I am posting rather late to this topic, but I am sure some people still reference this page, or stumble across it as I just have.

While a user-agent is an identifiable piece of information for a user, it is hardly strong enough for something containing sensitive session data.

On the notion of fingerprinting, a more unique fingerprint can be created by issuing a hash of information including the user-agent, but more importantly, the user's IP address. While, granted this does not protect against users behind the same router hijacking each others sessions, it limits the number of people who can possibly attempt such an attack to an unbelievably small number.

As for the uniqid(rand()) method, I'm not sure how that identifies a user at all. In what sense does an id based off the time a user loads the page prefixed with a random number aid in prevention of hijacking at all? Without storing the information in some form it would not be possible to validate an id on a successive load, which defeats the purpose.

Perhaps I missed the point of that bit of identification code, but here is an example of a script to validate a user (although offering little to none protection against users session hijacking within their own network)

This is the token that should be generated when originally authenticating the user, and stored in the session 
$sessionToken = sha1('saltdefinedhere' . $_SERVER['HTTP_USER_AGENT'] . $_SERVER['REMOTE_ADDR']);
$_SESSION['token'] = $sessionToken;
This section validates the user on the return to the site, to a certain extent
if($_SESSION['token'] !== sha1('saltdefinedhere' . $_SERVER['HTTP_USER_AGENT'] . $_SERVER['REMOTE_ADDR']))
  $_SESSION = array();
  header('location: login.php'); //send them to wherever they must login, gracefully

For your average site, a method like this will prove relatively sufficient.

Sat, 12 Jan 2008 at 03:31:39 GMT Link

31.Jeff wrote:

I've noticed some real issues in using the User Agent string for preventing session hijacking. For the most part it works great, but lately a number of users have been having trouble with features of my site not working.

Digging into IIS logs, I discovered that IE 7 sometimes sends different User Agent strings in requests. So, after the user logs in, some of the pages work fine and then all of a sudden there's an extra space or some other text(perhaps from plugins) in the user agent string that wasn't there when the user logged in. This of course causes validation to fail for that request.

I've not seen this behavior on any other browser, and oddly it isn't consistent on IE 7 (IE 7 works fine from every computer I've tested it on). I've theorized that there may be something different with IE7 Ajax requests, or something having to do with Vista, but haven't been able to test either of these ideas since I can't reproduce the behavior. For now I've just decided to stop using the User Agent string for session security. Has anyone else come across this odd behavior?

Tue, 06 May 2008 at 01:27:46 GMT Link

32.Richard Edwards wrote:


User Agent is not reliable for people such as AOL users either. It's almost as bad as replying on an IP address.

Remember too that User Agent information can be spoofed.

Tue, 06 May 2008 at 08:16:06 GMT Link

33.Richard Edwards wrote:


Thu, 08 May 2008 at 03:54:41 GMT Link

34.Jon Daley wrote:

It seems like almost all of the writers (author included) are assuming a non-open-source application. It took me a long time to figure out why the "secret key" (or any of the variants) made any difference at all, but it is because you are counting on the PHP script not being available.

I have been trying to think up a method to get a unique (or at least relatively unique) "secret" that could be used for an open source app, where the methods are know.

In the given examples "secretkey".md5(UserAgent), the attacker doesn't care what your secret key is, he just sends the UserAgent.

I am also unclear why people seem to be saying that SSL prevents XSS. I understand that it would prevent sniffing, but that's it. If a user clicked on a javascript link, all methods are out the door.

I wonder if doing ip address inspection only on "change" pages and display a password prompt only in that case would 1, not affect lots of people, and 2, only affect the proxy folks when making changes. I think you still need the new token generation method as well to prevent all attacks.

Maybe we should just use lynx as the browser and avoid all of the javascript problems...

Fri, 30 May 2008 at 15:13:31 GMT Link

35.Amir wrote:

Hi chris!

Please check this and guide me:


Thu, 24 Jul 2008 at 18:50:38 GMT Link

36.alikim wrote:


Thanks for the article! Tell me please if it's enough to use just


at the top of all php scripts to prevent hijacking?

I know it's not always necessary but it's very simple and I don't need to remember taking care of it each time I change user's access level so what do you think?

Thank you,

Wed, 08 Oct 2008 at 09:32:14 GMT Link

Hello! What’s your name?

Want to comment? Please connect with Twitter to join the discussion.