简体   繁体   中英

PDO on Windows ignores host name and username when password is empty

I'm not sure if there's something wrong with my setups or this is a bug in PDO on Windows:

<?php 

$dsn = 'mysql:host=127.0.0.1;dbname=mydb;charset=UTF8';
$username = 'myuser';
$password = '';
$pdo = new PDO($dsn, $username, $password);

Errors out for me with:

Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[42000] [1044] Access denied for user ''@'localhost' to database 'mydb'' in C:\\Ampps\\www\\test.php:6 Stack trace: #0 C:\\Ampps\\www\\test.php(6): PDO->__construct('mysql:host=127....', 'myuser', '') #1 {main} thrown in C:\\Ampps\\www\\test.php on line 6

I've been able to reproduce this on all 3 of my Windows dev machines, but on none of the linux servers.

Can anyone confirm, or point out what could be a problem?

Thank you!

EDIT: The privileges are set correctly on the user with empty password.

EDIT2: There was a report that the issue is reproducible on Mac running MAMP 3.0.3

EDIT3: There were couple of reports before, but it looks like it hasn't been fixed yet:

https://bugs.php.net/bug.php?id=43493

https://bugs.php.net/bug.php?id=46457

My report: https://bugs.php.net/bug.php?id=67026

EDIT4: It works when the permissions are given to 'myuser'@'localhost', but the problem appears when permissions are given to 'myuser'@'%' without password - on linux as well

I'd like to confirm this.

Please make sure the conditions are met before testing this:

  1. Make sure nonexistent_user is not a user in the database.
  2. Make sure root has a password set.
  3. Make sure to run these tests separately.
  4. Make sure to run these tests on Windows (or whatever machine affected).

I have bolded the usernames in question.

Test #1

User that does not exist + empty password = empty username for error message

$mysqli = new Mysqli('localhost', 'nonexistent_user', '', 'database');
$pdo    = new PDO('mysql:host=localhost;dbname=database;charset=UTF8', 'nonexistent_user', '');

Warning: mysqli::mysqli(): (HY000/1044): Access denied for user ''@'localhost' to database 'database' in test.php

Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY000] [1044] Access denied for user ''@'localhost' to database 'database'' in test.php Stack trace: #0 test.php(): PDO->__construct('mysql:host=loca...', 'nonexistent_use...', '') #1 {main} thrown in test.php

Test #2

User that exists + empty password = username set for error message

$mysqli = new Mysqli('localhost', 'root', '', 'database');
$pdo    = new PDO('mysql:host=localhost;dbname=database;charset=UTF8', 'root', '');

Warning: mysqli::mysqli(): (HY000/1045): Access denied for user 'root'@'localhost' (using password: NO) in test.php

Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY000] [1045] Access denied for user 'root'@'localhost' (using password: NO)' in test.php Stack trace: #0 test.php(): PDO->__construct('mysql:host=loca...', 'root', '') #1 {main} thrown in test.php

Test #3

User that does not exist + set password = username set for error message

$mysqli = new Mysqli('localhost', 'nonexistent_user', 'password', 'database');
$pdo    = new PDO('mysql:host=localhost;dbname=database;charset=UTF8', 'nonexistent_user', 'password');

Warning: mysqli::mysqli(): (HY000/1045): Access denied for user 'nonexistent_user'@'localhost' (using password: YES) in test.php

Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY000] [1045] Access denied for user 'nonexistent_user'@'localhost' (using password: YES)' in test.php Stack trace: #0 test.php(): PDO->__construct('mysql:host=loca...', 'nonexistent_use...', 'password') #1 {main} thrown in test.php

When the user does not exists and an empty password is supplied, the error message will show a blank username.

I feel this would be a security risk because an attacker could potentially test which users are valid by sending a test username with an empty password and see if the error response is empty for the username or not.

The issue is not with PHP or PDO, I was able to reproduce the issue directly with MySQL.

If there's ''@'localhost' user, can login with any username without password, and any users @'%' will be ignored on login.

Steps for reproduction: https://gist.github.com/sellvana/9989227

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM