php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #12575 Session register & destroy flaws/bugs(?)
Submitted: 2001-08-05 07:32 UTC Modified: 2001-08-06 01:00 UTC
From: nick at macaw dot demon dot co dot uk Assigned:
Status: Closed Package: Session related
PHP Version: 4.0.6 OS: Linux
Private report: No CVE-ID: None
 [2001-08-05 07:32 UTC] nick at macaw dot demon dot co dot uk
Whilst the PHP session support is a great feature, handling session state as of 4.0.6 is inconsistent and arguably flawed and has some gotchas, as illustrated in the two scripts after these details. There are workarounds which I'll explain. This assumes track vars enabled, as it always is since 4.0.3 anyway, and register globals is enabled.

In summary
1) Registering a global with session_register() doesn't update $HTTP_SESSION_VARS until the session is restored, so don't use $HTTP_SESSION_VARS for accessing intra-session state changes unless you set $HTTP_SESSION_VARS as well as your global.

2) Destroying a session doesn't reset the state of $HTTP_SESSION_VARS. Ouch! Creating a new session immediately afterwards does work as expected though, and produces a clean session.

3) BUT, destroying a session never unsets the state of registered globals. Ouch again! So be wary of using globals rather than HTTP_SESSION_VARS for getting at session state if you ever conditionally destroy sessions and subsequently access session data, unless of course you explicitly unset your globals too.

Executing x.php then y.php illustrate the problems.
The output is:
Assert failed: OOPS, foo session var is unset
Assert failed: OOPS, foo session var still set on destroyed session
Assert failed: OOPS, global foo is still set

x.php:
<?php // -*- c++ -*-

// track vars and register globals enabled

function myassert($b, $what)
{
  if ($b !== true) {
    echo "<pre>Assert failed: $what</pre>";
  }
}

// Get a clean session
session_start();
session_destroy();
session_start();

// Style 1. We use HTTP_SESSION_VARS to access session state
// This works fine for a restored session, but intra-session
// it doesn't. e.g.
$foo = 'bar';			// Set it
session_register('foo');	// Register global

// Assert fails - foo isn't a useable session variable (yet) after all
myassert(isset($HTTP_SESSION_VARS['foo']), "OOPS, foo session var is unset");

?>

y.php:
<?php // -*- c++ -*-

ob_start();

// track vars and register globals enabled

function myassert($b, $what)
{
  if ($b !== true) {
    echo "<pre>Assert failed: $what</pre>";
  }
}

// Restore session with foo set from x.php
session_start();

// Style 2. As HTTP_SESSION_VARS doesn't get set intra-session, lets
// try using globals as our session mechanism instead.
myassert(isset($foo), "Global foo not restored"); // OK. global restored
myassert(isset($HTTP_SESSION_VARS['foo']), "Session foo not restored"); // OK

// Now lets try destroying the session as, for example, our script was
// passed a logout request somehow

session_destroy();		// This should do it

myassert(!isset($HTTP_SESSION_VARS['foo']), "OOPS, foo session var still set on destroyed session"); // FAILS

session_start();

myassert(!isset($HTTP_SESSION_VARS['foo']), "foo session var still set on destroyed session"); // OK, not it's not

// But remember that we decided to use globals because of the problems with
// HTTP_SESSION_VARS not being updated intra-session, well lets check the
// state of our global $foo

myassert(!isset($foo), "OOPS, global foo is still set"); /// FAILS, oh dear!

ob_end_flush();

?>


Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2001-08-05 14:34 UTC] rasmus@php.net
I think this is consistent behaviour.  session_start() brings data from your session backend into your current script.  session_destroy() destroys the session data in your session backend.  It does not and should not affect variables which are currently active in your script.  The session_start() and session_unset() functions are designed to affect the current active symbol table.
 [2001-08-06 01:00 UTC] sniper@php.net
Not a bug.



 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Fri Apr 19 18:01:28 2024 UTC