Bug #62469 | JDBC Authentication Fails with Null Byte in Scramble | ||
---|---|---|---|
Submitted: | 18 Sep 2011 19:52 | Modified: | 19 Oct 2013 2:46 |
Reporter: | Christian Warden | Email Updates: | |
Status: | Closed | Impact on me: | |
Category: | Connector / J | Severity: | S3 (Non-critical) |
Version: | 5.1.17 | OS: | Linux (Debian sid) |
Assigned to: | Alexander Soklakov | CPU Architecture: | Any |
Tags: | jdbc, mysql-proxy, password |
[18 Sep 2011 19:52]
Christian Warden
[19 Sep 2011 23:41]
Christian Warden
I've tracked the problem down to null bytes in the scramble sent by the lua script and the fact that com.mysql.jdbc.MysqlIO.doHandshake only reads up to the first null byte when reading in the first eight bytes of the scramble. The create_random_string function in sql/password.c generates printable characters for the scramble. I'm not sure if only printable characters are supposed to be allowed.
[20 Sep 2011 0:01]
Christian Warden
com.mysql.jdbc.MysqlIO.doHandshake also ignores the scramble buffer length byte and reads a null-terminated string for the second part of the scramble buffer.
[28 Sep 2011 8:10]
Tonci Grgin
Hi Christian and thanks for your report. I do not see a bug here. Please refer to http://forge.mysql.com/wiki/MySQL_Internals_ClientServer_Protocol#Handshake_Initialization... and inspect how this should work. First 8 bytes of scramble should not contain \0 and indeed the extra \0 filler behind is there to make it look like a 0-terminated string. Also, just noting the fact that the usage of the scramble buffer subtly changed between 4.1 and 4.1.1 (see above). So, by having \0 in scramble buffer you messed up the packet sequence leading to error reported.
[28 Sep 2011 16:00]
Christian Warden
Thanks for taking a look at this, Tonci. I think the documentation at forge.mysql.com is ambiguous: - the first part of the scramble fixed length - the first part of the scramble contains a null after the fixed length part - the full length of scramble is included in the packet - the second part of the scramble is null-terminated Since the handshake packet documentation is based on the mysql-server source code, I would refer to the source to clear up the ambiguity. The C client code does not treat the two parts of the scramble as null-terminated strings. It reads the full 8 bytes (SCRAMBLE_LENGTH_323) from the first part of the scramble and uses the length byte to figure out how long the rest of the scramble is: http://bit.ly/rbK6RY My suggestion would be for the jdbc driver to follow the C client code. The change is minimally intrusive, and although the problem in the jdbc driver only happens in uncommon scenarios, it causes a problem that is difficult to track down because the server capabilities and the rest of the fields in the initialization packet get read out of the wrong bytes.
[28 Sep 2011 20:30]
Mark Matthews
This should be fixed to match libmysql. In the future, libmysql should be required to match the documentation :)
[19 Oct 2013 2:46]
Daniel So
Added the following entry in the Connector/J 5.2 changelog: "JDBC authentication failed when there was a null byte in the scramble, because com.mysql.jdbc.MysqlIO.doHandshake only read up to the first null byte when reading in the first eight bytes of the scramble."
[21 Oct 2013 14:37]
Daniel So
CORRECTION: the changelog entry mentioned above is for Connector J/5.1.