2

We have a server with mysql on port 3306. We have sertifications and key and we try to connect to this server. But we see such problem:

Peer certificate CN='SomeName' did not match expected CN='someIP'

I've read a lot of articles and can't find answer for PDO PHP. The most interesting is that the SQLYog could connect with all settings.

I've read that I verify_peer_names can be disabled (I hope I understand what is peer_names...), but only if we use openssl_{functions} or mysqli, not PDO. Both options are not appropriate for me. I need PDO.

What I tried to do:

  • switch between versions of php. It helped me, but I need 5.6 or higher. For php 7.0 the same error.
  • find another versions of openssl and pdo; fast I understood that its a bad idea :)
  • find some settings in php.ini, but no settings for my problem, only for creating ssl.

My code for connection:

$dbInfo = array
(
'dsn' => 'mysql:host=123.45.67.890;dbname=someDB;port=3306',
'user' => 'user',
'pass' => 'userpassword'
);

$con = new PDO
    (
    $dbInfo['dsn'], $dbInfo['user'], $dbInfo['pass'], 
    array(
        PDO::MYSQL_ATTR_SSL_CIPHER => 'AES256-SHA',
        PDO::MYSQL_ATTR_SSL_CA     => 'SSLCert/ca-cert.pem',
        PDO::MYSQL_ATTR_SSL_KEY    => 'SSLCert/client-key.pem',
        PDO::MYSQL_ATTR_SSL_CERT   => 'SSLCert/client-cert.pem',
    )
    );

echo 'Connection OK!';
  • 2
    It's a known issue, see: [php bug #71003](https://bugs.php.net/bug.php?id=71003) – eM. Sep 24 '16 at 16:27
  • 2
    Thanks man! But I still don't understand what I have to do with ssl connection. I read that they fix it in some patch, they dig openssl lib, but first I'm not a good to dig inside a lib, second - it's not a good idea to fix lib by myself. Maybe I'm carelles and didn't find the answer... If you worked and solved this problem for yourself - can you hint me somehow what to do? – Nikita_kharkov_ua Oct 06 '16 at 07:06

1 Answers1

3

We got it working for our internal self-signed certs by not using IP addresses but machine(+domain) names as the CN and connection settings.

So, put 'dbServer1.company.local' as the CN for the server certificate and use the same 'dbServer1.company.local' address as the host part of the DSN for the PDO connection. If you like, you can just use 'dbServer1' but make sure you use it in both places.

This will get you going:

$pdo_options = array(
    PDO::MYSQL_ATTR_SSL_KEY => 'path/to/client-key.pem',
    PDO::MYSQL_ATTR_SSL_CERT => 'path/to/client-cert.pem',
    PDO::MYSQL_ATTR_SSL_CA => 'path/to/ca.pem'
);

PDO::__construct('mysql:host=dbServer1.company.local;dbname=someDB','someUser', 'somePass', $pdo_options);

We manage our own DNS so resolving dbServer1.company.local is not an issue but if your webserver cannot resolve it you or you don't/can't manage the DNS entry, then hack in something like the following to your etc/hosts file:

10.5.5.20 dbServer1.company.local

or

10.5.5.20 dbServer1
PadraigD
  • 641
  • 5
  • 13