New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Set ssl_mode for Oracle MySQL if applicable. #108
Conversation
c9995ea
to
c630ee8
Compare
With some versions of mysql client compilation failed... Looks like these continuous-integration tests are really good for catching problems with code which has lot of #ifdefs... |
Anyway, I do not think that usage of SSL/TLS tunel without verifycation of server certificate (either by CA or certificate chain or directly by fingerprint of server certificate) is a good idea. In some cases it could make sense (e.g. passive scanning), but basically it has similar security as not using SSL/TLS tunel. Without verification of server certificate MITM is possible in same way as MITM for plain text without SSL/TLS. I really would suggest that verification of server certificate should be preferred option. We probably want to have backward compatibility, but at least examples and documentation can be updated to show people default usage of certificate verification. In every case it is better if users of DBD::mysql starts doing certificate verification. And documentation or "example" usage could help... |
c630ee8
to
19ea86f
Compare
It is slightly better than not using TLS as it protects against passive attacks.
Yes indeed.
Yes, VERIFY_CA is reasonably secure. VERIFY_IDENTITY is more secure, but hostname validation is in practice not always possible becuase MySQL and MariaDB don't support SubjectAlternativeName.
Indeed. |
dbdimp.c
Outdated
@@ -2083,11 +2081,33 @@ MYSQL *mysql_dr_connect( | |||
|
|||
mysql_ssl_set(sock, client_key, client_cert, ca_file, | |||
ca_path, cipher); | |||
#if MYSQL_VERSION_ID >= SSL_VERIFY_VERSION && MYSQL_VERSION_ID <= SSL_LAST_VERIFY_VERSION | |||
#ifdef MYSQL_SSL_MODE | |||
if ssl_verify_true: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
syntax error. In C it is if (ssl_verify_true)
and no colon at the end.
dbdimp.h
Outdated
/* This is to avoid the ugly #ifdef mess in dbdimp.c */ | ||
#if MYSQL_VERSION_ID < SQL_STATE_VERSION | ||
#define mysql_sqlstate(svsock) (NULL) | ||
#endif | ||
|
||
#ifdef SSL_MODE_PREFERRED |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like SSL_MODE_PREFERRED
is not macro so this #ifdef is always false and MYSQL_SSL_MODE
is never defined.
de57748
to
eb88c1b
Compare
dbdimp.c
Outdated
#ifdef MYSQL_SSL_MODE | ||
if (ssl_verify_true) | ||
ssl_mode = SSL_MODE_VERIFY_IDENTITY; | ||
else if (strlen(ca_file) > 0) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ca_file and also ca_path could be NULL which means strlen here can crash
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed
dbdimp.c
Outdated
mysql_options(sock, MYSQL_OPT_SSL_ENFORCE, &ssl_verify_true); | ||
#endif | ||
#else | ||
warn("Can't enable strict certificate checks"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would say this is a fatal error.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes I agree. Note that currently there isn't even a warning in this case.
Now we have there Riddle vulnerability at http://riddle.link/ And looks like Oracle probably fixes SSL enforcement in 5.5 and 5.6 versions of MySQL as documentation was already updated. Compare:
But MySQL 5.5.55 was not released yet... |
eb88c1b
to
558959a
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This code starts to be a big #if mess with long conditions after #if... I do not have idea how to improve it right now.
But it would be a big problem after release of 5.5.55 as specified in documentation...
dbdimp.c
Outdated
mysql_options(sock, MYSQL_OPT_SSL_ENFORCE, &ssl_verify_true); | ||
#endif | ||
#else | ||
die("Can't enable strict certificate checks"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use croak(...)
as you are not passing return value from die(...)
somewhere else. Look into perlapi for details.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've fixed that
dbdimp.c
Outdated
ssl_mode = SSL_MODE_VERIFY_CA; | ||
else if (ca_path && (strlen(ca_path) > 0)) | ||
ssl_mode = SSL_MODE_VERIFY_CA; | ||
mysql_options(sock, MYSQL_OPT_SSL_MODE, &ssl_mode); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Seems your patch is whitespace inconsistence with code around... See indentation. If it is possible try to fix it...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've tried to fix it.
dbdimp.c
Outdated
#ifdef MYSQL_SSL_MODE | ||
if (ssl_verify_true) | ||
ssl_mode = SSL_MODE_VERIFY_IDENTITY; | ||
else if (ca_file && (strlen(ca_file) > 0)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we need check for strlen()
? I have not find any information about it and variables are already passed to mysql_ssl_set()
without strlen()
check... So I'm not sure there...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removed strlen.
I'm afraid this will get worse over time because MySQL and MariaDB are (very) slowly diverging. We can try to prevent that as much as possible, but eventually it might make sense to split this into DBD::mysql and DBD::mariadb. |
Probably...
But here we have another problem unrelated to MariaDB... Problem is with different MySQL versions. So splitting into DBD::mysql and DBD::mariadb does not help there. And there are still very large common codebase so I do not think split is good idea. |
558959a
to
3085995
Compare
If |
I did some SSL changes here: #114 I tried to make that ifdef hell more readable and prepare ground for new MySQL 5.5.55 which should finally have fixed Riddle vulnerability. |
@pali should we wait on your ssl branch to be ready to merge? Or should this branch be merged? |
For me this is PR is ready to merge, I already marked it. |
I updated my #114 on top of master (so including this PR). |
@dveeden this PR #108 broke compilation for MySQL C/Connector 6.0: |
Supersedes #82