summaryrefslogtreecommitdiff
path: root/sql-common
diff options
context:
space:
mode:
authorunknown <msvensson@neptunus.(none)>2006-04-12 12:52:34 +0200
committerunknown <msvensson@neptunus.(none)>2006-04-12 12:52:34 +0200
commit6af90061f42a0cbdc4f59e5390471b008e24d252 (patch)
treeb54fecadb68c73afdbd6200942aba915902f2d84 /sql-common
parent10633fd8397f8450b5076bb98f336f6d20967b5d (diff)
parentb2d5243e97b7395d38bd6afc4767199703cf7f7c (diff)
downloadmariadb-git-6af90061f42a0cbdc4f59e5390471b008e24d252.tar.gz
Merge neptunus.(none):/home/msvensson/mysql/mysql-5.0
into neptunus.(none):/home/msvensson/mysql/bug17208/my50-bug17208 sql/mysql_priv.h: Auto merged sql/mysqld.cc: Auto merged sql-common/client.c: Auto merged sql/sql_acl.cc: Auto merged
Diffstat (limited to 'sql-common')
-rw-r--r--sql-common/client.c106
1 files changed, 89 insertions, 17 deletions
diff --git a/sql-common/client.c b/sql-common/client.c
index 84df31b7440..da38d022c4d 100644
--- a/sql-common/client.c
+++ b/sql-common/client.c
@@ -1514,8 +1514,7 @@ mysql_ssl_set(MYSQL *mysql __attribute__((unused)) ,
static void
mysql_ssl_free(MYSQL *mysql __attribute__((unused)))
{
- struct st_VioSSLConnectorFd *st=
- (struct st_VioSSLConnectorFd*) mysql->connector_fd;
+ struct st_VioSSLFd *ssl_fd= (struct st_VioSSLFd*) mysql->connector_fd;
DBUG_ENTER("mysql_ssl_free");
my_free(mysql->options.ssl_key, MYF(MY_ALLOW_ZERO_PTR));
@@ -1523,8 +1522,8 @@ mysql_ssl_free(MYSQL *mysql __attribute__((unused)))
my_free(mysql->options.ssl_ca, MYF(MY_ALLOW_ZERO_PTR));
my_free(mysql->options.ssl_capath, MYF(MY_ALLOW_ZERO_PTR));
my_free(mysql->options.ssl_cipher, MYF(MY_ALLOW_ZERO_PTR));
- if (st)
- SSL_CTX_free(st->ssl_context);
+ if (ssl_fd)
+ SSL_CTX_free(ssl_fd->ssl_context);
my_free(mysql->connector_fd,MYF(MY_ALLOW_ZERO_PTR));
mysql->options.ssl_key = 0;
mysql->options.ssl_cert = 0;
@@ -1568,6 +1567,63 @@ static MYSQL_METHODS client_methods=
#endif
};
+int ssl_verify_server_cert(Vio *vio, const char* server_host)
+{
+ SSL *ssl;
+ X509 *server_cert;
+ char *cp1, *cp2;
+ char buf[256];
+ DBUG_ENTER("ssl_verify_server_cert");
+ DBUG_PRINT("enter", ("server_host: %s", server_host));
+
+ if (!(ssl= (SSL*)vio->ssl_arg))
+ {
+ DBUG_PRINT("error", ("No SSL pointer found"));
+ return 1;
+ }
+
+ if (!server_host)
+ {
+ DBUG_PRINT("error", ("No server hostname supplied"));
+ return 1;
+ }
+
+ if (!(server_cert= SSL_get_peer_certificate(ssl)))
+ {
+ DBUG_PRINT("error", ("Could not get server certificate"));
+ return 1;
+ }
+
+ /*
+ We already know that the certificate exchanged was valid; the SSL library
+ handled that. Now we need to verify that the contents of the certificate
+ are what we expect.
+ */
+
+ X509_NAME_oneline(X509_get_subject_name(server_cert), buf, sizeof(buf));
+ X509_free (server_cert);
+
+// X509_NAME_get_text_by_NID(x509_get_subject_name(server_cert), NID_commonName, buf, sizeof(buf));... does the same thing
+
+ DBUG_PRINT("info", ("hostname in cert: %s", buf));
+ cp1 = strstr(buf, "/CN=");
+ if (cp1)
+ {
+ cp1 += 4; // Skip the "/CN=" that we found
+ cp2 = strchr(cp1, '/');
+ if (cp2)
+ *cp2 = '\0';
+ DBUG_PRINT("info", ("Server hostname in cert: ", cp1));
+ if (!strcmp(cp1, server_host))
+ {
+ /* Success */
+ DBUG_RETURN(0);
+ }
+ }
+ DBUG_PRINT("error", ("SSL certificate validation failure"));
+ DBUG_RETURN(1);
+}
+
MYSQL *
CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
@@ -2013,37 +2069,53 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
mysql->client_flag=client_flag;
#ifdef HAVE_OPENSSL
- /*
- Oops.. are we careful enough to not send ANY information without
- encryption?
- */
if (client_flag & CLIENT_SSL)
{
+ /* Do the SSL layering. */
struct st_mysql_options *options= &mysql->options;
+ struct st_VioSSLFd *ssl_fd;
+
+ /*
+ Send client_flag, max_packet_size - unencrypted otherwise
+ the server does not know we want to do SSL
+ */
if (my_net_write(net,buff,(uint) (end-buff)) || net_flush(net))
{
set_mysql_error(mysql, CR_SERVER_LOST, unknown_sqlstate);
goto error;
}
- /* Do the SSL layering. */
- if (!(mysql->connector_fd=
- (gptr) new_VioSSLConnectorFd(options->ssl_key,
- options->ssl_cert,
- options->ssl_ca,
- options->ssl_capath,
- options->ssl_cipher)))
+
+ /* Create the VioSSLConnectorFd - init SSL and load certs */
+ if (!(ssl_fd= new_VioSSLConnectorFd(options->ssl_key,
+ options->ssl_cert,
+ options->ssl_ca,
+ options->ssl_capath,
+ options->ssl_cipher)))
{
set_mysql_error(mysql, CR_SSL_CONNECTION_ERROR, unknown_sqlstate);
goto error;
}
+ mysql->connector_fd= (void*)ssl_fd;
+
+ /* Connect to the server */
DBUG_PRINT("info", ("IO layer change in progress..."));
- if (sslconnect((struct st_VioSSLConnectorFd*)(mysql->connector_fd),
- mysql->net.vio, (long) (mysql->options.connect_timeout)))
+ if (sslconnect(ssl_fd, mysql->net.vio,
+ (long) (mysql->options.connect_timeout)))
{
set_mysql_error(mysql, CR_SSL_CONNECTION_ERROR, unknown_sqlstate);
goto error;
}
DBUG_PRINT("info", ("IO layer change done!"));
+
+#if 0
+ /* Verify server cert */
+ if (mysql->options.ssl_verify_cert &&
+ ssl_verify_server_cert(mysql->net.vio, mysql->host))
+ {
+ set_mysql_error(mysql, CR_SSL_CONNECTION_ERROR, unknown_sqlstate);
+ goto error;
+ }
+#endif
}
#endif /* HAVE_OPENSSL */