php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #78680 mysqlnd's mysql_clear_password does not transmit null-terminated password
Submitted: 2019-10-17 18:47 UTC Modified: 2021-01-13 16:36 UTC
Votes:1
Avg. Score:5.0 ± 0.0
Reproduced:1 of 1 (100.0%)
Same Version:0 (0.0%)
Same OS:0 (0.0%)
From: geoff dot montee at gmail dot com Assigned:
Status: Closed Package: MySQLi related
PHP Version: 7.3.10 OS: Alpine Linux v3.10
Private report: No CVE-ID: None
Welcome back! If you're the original bug submitter, here's where you can edit the bug or add additional notes.
If you forgot your password, you can retrieve your password here.
Password:
Status:
Package:
Bug Type:
Summary:
From: geoff dot montee at gmail dot com
New email:
PHP Version: OS:

 

 [2019-10-17 18:47 UTC] geoff dot montee at gmail dot com
Description:
------------
The mysql_clear_password client authentication plugin is supposed to transmit a null-terminated password to the server. This is described in the following code comment:


"  @startuml
  Server->Client: 20 bytes of scramble to be ignored
  Client->Server: The clear text password. null terminated.
  @enduml"

https://github.com/mysql/mysql-server/blob/mysql-8.0.18/sql-common/client.cc#L8469


PHP's implementation of mysql_clear_password in the mysqlnd driver does not seem to transmit the terminating NULL character with the password. See here:

https://github.com/php/php-src/blob/php-7.3.10/ext/mysqlnd/mysqlnd_auth.c#L610

https://github.com/php/php-src/blob/php-7.3.10/ext/mysqlnd/mysqlnd_auth.c#L115

This can easily be reproduced.

---

Let's say that I have a server running MariaDB 10.4.8. We can configure PAM authentication by performing the following steps:

1.) Create a Unix user account and set a password for the user:


sudo useradd alice
sudo passwd alice


The examples below assume that the password is "uGBXHxID3dJRALw2".

2.) Create the PAM service configuration:


sudo tee /etc/pam.d/mariadb <<EOF
auth required pam_unix.so audit
account required pam_unix.so audit
EOF


3.) Install the pam plugin:


sudo mysql --execute="INSTALL SONAME 'auth_pam'"


4.) Create the relevant user:


sudo mysql --execute="CREATE USER 'alice'@'localhost' IDENTIFIED VIA pam USING 'mariadb'"


5.) Enable the pam_use_cleartext_plugin system variable:


$ sudo mysql -u root --execute="SHOW GLOBAL VARIABLES LIKE 'pam%'"
+--------------------------+-------+
| Variable_name            | Value |
+--------------------------+-------+
| pam_use_cleartext_plugin | ON    |
| pam_winbind_workaround   | OFF   |
+--------------------------+-------+


At this point, PAM is configured.

---

Let's say that I set up PHP 7.3.10 on the same server as the database.

The connectivity can easily be tested by creating the following test script:


tee pamtest.php << EOF
<?php
\$link = mysqli_connect("127.0.0.1", "alice", "uGBXHxID3dJRALw2", "test");
 
if (!\$link) {
    echo "Error: Unable to connect to MySQL." . PHP_EOL;
    echo "Debugging errno: " . mysqli_connect_errno() . PHP_EOL;
    echo "Debugging error: " . mysqli_connect_error() . PHP_EOL;
    exit;
}
 
echo "Success: A proper connection to MySQL was made! The my_db database is great." . PHP_EOL;
echo "Host information: " . mysqli_get_host_info(\$link) . PHP_EOL;
 
mysqli_close(\$link);
?>
EOF
php -f pamtest.php

---

So let's run the test script, and do some debugging.

1.) First, let's attach strace to the mysqld process:


sudo mkdir strace/
cd strace/
sudo strace -o strace.out -f -ff -p $(pidof mysqld)


2.) And then let's also run the PHP script while attaching strace to that process:


strace -o strace.out -f -ff php -f pamtest.php


Authentication will fail on MariaDB 10.4.8, since that MariaDB version currently treats the NULL terminating character as mandatory:


Warning: mysqli_connect(): (HY000/1045): Access denied for user 'alice'@'localhost' (using password: NO) in /var/www/html/pamtest.php on line 2
Error: Unable to connect to MySQL.
Debugging errno: 1045
Debugging error: Access denied for user 'alice'@'localhost' (using password: NO)


The strace output of the PHP script shows that the NULL terminating character is not set:


./strace.out.3393-recvfrom(3, "\26\0\0\2\376mysql_clear_password\0", 32768, MSG_DONTWAIT, NULL, NULL) = 26
./strace.out.3393:sendto(3, "\20\0\0\3uGBXHxID3dJRALw2", 20, MSG_DONTWAIT, NULL, 0) = 20


And the strace output of mysqld shows the same thing:


sendto(154, "\26\0\0\2\376mysql_clear_password\0", 26, MSG_DONTWAIT, NULL, 0) = 26
recvfrom(154, "\20\0\0\3", 4, MSG_DONTWAIT, NULL, NULL) = 4
recvfrom(154, "uGBXHxID3dJRALw2", 16, MSG_DONTWAIT, NULL, NULL) = 16


In contrast, here's the strace output of mysqld with a "working" client:


sendto(154, "\26\0\0\2\376mysql_clear_password\0", 26, MSG_DONTWAIT, NULL, 0) = 26
recvfrom(154, "\21\0\0\3", 4, MSG_DONTWAIT, NULL, NULL) = 4
recvfrom(154, "uGBXHxID3dJRALw2\0", 17, MSG_DONTWAIT, NULL, NULL) = 17


Patches

Pull Requests

Pull requests:

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2019-10-17 19:34 UTC] geoff dot montee at gmail dot com
This problem was discovered due to the following two MariaDB bug reports:

https://jira.mariadb.org/browse/MDEV-19882

https://jira.mariadb.org/browse/MDEV-20571
 [2021-01-13 16:36 UTC] cmb@php.net
Well, that looks indeed wrong in mysqldn.  Would you mind to
provide a pull request[1]?

[1] <https://github.com/php/php-src/pulls>
 [2021-02-05 21:38 UTC] geoff dot montee at gmail dot com
The following pull request has been associated:

Patch Name: Fix #78680: mysqlnd pam plugin missing terminating null
On GitHub:  https://github.com/php/php-src/pull/6667
Patch:      https://github.com/php/php-src/pull/6667.patch
 [2021-02-15 10:33 UTC] nikic@php.net
Automatic comment on behalf of daniel@mariadb.org
Revision: http://git.php.net/?p=php-src.git;a=commit;h=3646604203d80bc0f6a124aa2ac5c448229327ea
Log: Fix #78680: mysqlnd pam plugin missing terminating null
 [2021-02-15 10:33 UTC] nikic@php.net
-Status: Open +Status: Closed
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Sun Dec 22 01:01:30 2024 UTC