php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #44166 Parameter handling flaw in PDO::getAvailableDrivers()
Submitted: 2008-02-19 13:00 UTC Modified: 2008-03-03 21:14 UTC
From: uwendel at mysql dot com Assigned:
Status: Closed Package: PDO related
PHP Version: 5.3CVS-2008-02-19 (CVS) OS: Linux
Private report: No CVE-ID: None
 [2008-02-19 13:00 UTC] uwendel at mysql dot com
Description:
------------
There's a little parameter handling flaw in PDO::getAvailableDrivers(). The function expects no parameter to be passed. If you pass some, it does not bail like most other functions do which do not expect any parameter.

nixnutz@ulflinux:~/php53> sapi/cli/php -r 'var_dump(PDO::getAvailableDrivers("too many", "args")); var_dump(get_include_path("too many", "args"));'
array(4) {
  [0]=>
  string(7) "sqlite2"
  [1]=>
  string(6) "sqlite"
  [2]=>
  string(5) "pgsql"
  [3]=>
  string(5) "mysql"
}

Warning: get_include_path() expects exactly 0 parameters, 2 given in Command line code on line 1
NULL


Reproduce code:
---------------
nixnutz@ulflinux:~/php53> sapi/cli/php -r 'var_dump(PDO::getAvailableDrivers("too many", "args"));'


Expected result:
----------------
Warning: PDO::getAvailableDrivers() expects exactly 0 parameters, 2 given in Command line code on line %d
NULL

Actual result:
--------------
No warning, array returned

Patches

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2008-02-19 13:18 UTC] uwendel at mysql dot com
If you fix this and decide on #44167, you might want to use the following test:

--TEST--
PDO Common: PDOStatement::getAvailableDrivers()
--SKIPIF--
<?php # vim:ft=php
if (!extension_loaded('pdo')) die('skip');
$dir = getenv('REDIR_TEST_DIR');
if (false == $dir) die('skip no driver');
require_once $dir . 'pdo_test.inc';
PDOTest::skip();
?>
--FILE--
<?php
if (getenv('REDIR_TEST_DIR') === false) putenv('REDIR_TEST_DIR='.dirname(__FILE__) . '/../../pdo/tests/');
require_once getenv('REDIR_TEST_DIR') . 'pdo_test.inc';
$db = PDOTest::factory();

try {
	$tmp = PDO::getAvailableDrivers('args', 'args');
	if ((false !== $tmp) && (!is_null($tmp)))
		printf("[001] Typically functions that get invoked with invalid arguments return NULL or false, this one returned %s (%s)\n",
			gettype($tmp), ((is_scalar($tmp)) ? var_export($tmp, true) : gettype($tmp)));

	$tmp = PDO::getAvailableDrivers();
	if (!is_array($tmp)) {
		printf("[002] Expecting array, got %s?\n", gettype($tmp));
	} else {
		if (count($tmp) < 1)
			printf("[003] Expecting array with at least one element\n");

		if (!isset($tmp[0]))
			printf("[004] Array should be a list, indexing should start at zero\n");

		$driver = $db->getAttribute(PDO::ATTR_DRIVER_NAME);
		$found = false;
		foreach ($tmp as $k => $v) {
			if ($v === $driver) {
				$found = true;
				break;
			}
		}

		if (!$found) {
			printf("[005] getAttribute(PDO::ATTR_DRIVER_NAME) and PDO::getAvailableDrivers() seem inconsistent. Dumping data.\n");
			var_dump($driver);
			var_dump($tmp);
		}

		/* undocumented, from pdo.c */
		$tmp2 = pdo_drivers();
		$tmp2 = array_flip($tmp2);
		foreach ($tmp as $k => $driver) {
			if (isset($tmp2[$driver])) {
				unset($tmp2[$driver]);
				unset($tmp[$k]);
			}
		}

		if (!empty($tmp)) {
			printf("[006] Dumping list of drivers returned by PDO::getAvailableDrivers() but not returned by pdo_drivers()\n");
			var_dump($tmp);
		}

	if (!empty($tmp2)) {
			printf("[007] Dumping list of drivers returned by pdo_drivers() but not returned by PDO::getAvailableDrivers()\n");
			var_dump($tmp2);
		}

	}

	/*
	Citing the manual:
		This function returns all currently available PDO drivers which can be used in DSN parameter of PDO->__construct(). This is a static method.
	*/
	// Fatal error
	$tmp = $db->getAvailableDrivers();
	if (is_array($tmp))
		printf("[008] This is not a static method, change the manual or the implementation!\n");

} catch (PDOException $e) {
	printf("[009] %s, [%s] %s\n",
		$e->getMessage(), $db->errorCode(), implode(' ', $db->errorInfo()));
}

print "done!";
?>
--EXPECTF--
Fatal error or exception
 [2008-02-19 13:19 UTC] uwendel at mysql dot com
Oh, well forgot to say that for using the test you also have to decide on #44155.
 [2008-03-03 21:14 UTC] iliaa@php.net
This bug has been fixed in CVS.

Snapshots of the sources are packaged every three hours; this change
will be in the next snapshot. You can grab the snapshot at
http://snaps.php.net/.
 
Thank you for the report, and for helping us make PHP better.


 
PHP Copyright © 2001-2018 The PHP Group
All rights reserved.
Last updated: Thu Nov 15 04:01:25 2018 UTC