diff options
author | unknown <tonu@x153.internalnet> | 2001-07-24 14:07:46 +0800 |
---|---|---|
committer | unknown <tonu@x153.internalnet> | 2001-07-24 14:07:46 +0800 |
commit | 2ec8dce13dc2357179244e73e97648034b7cc5a6 (patch) | |
tree | ed5f3121d49f4cd731f353d0ff4b0684837cc5b5 /vio | |
parent | ce77251db69e1becb2716632e8dbbc3b99391406 (diff) | |
download | mariadb-git-2ec8dce13dc2357179244e73e97648034b7cc5a6.tar.gz |
OpenSSL fixes. Should not affect anything else.
Makefile.am:
Moved bio dir into server_dirs in acinclude.in
client/Makefile.am:
We need OpenSSL includes here
include/global.h:
Workaround for OPENSSL librar bug with defining crypt()
include/violite.h:
small fixes
libmysql/Makefile.am:
We need OpenSSL includes here
libmysql/Makefile.shared:
Yes, we need to compile more programs whtn --with-openssl is used
libmysql/libmysql.c:
Make it work! (openssl)
libmysql_r/Makefile.am:
We need OpenSSL includes here
sql/mysqld.cc:
Memory was not freed before
sql/sql_parse.cc:
fix
vio/Makefile.am:
Added testprogram compilation and openssl libraries linking
vio/viossl.c:
Cleanups, fixes, etc...
vio/viosslfactories.c:
Copyright was missing. Fixed renamed macros for newer OpenSSL
vio/viotest-ssl.c:
Made testprogram work again
BitKeeper/etc/logging_ok:
Logging to logging@openlogging.org accepted
Diffstat (limited to 'vio')
-rw-r--r-- | vio/Makefile.am | 7 | ||||
-rw-r--r-- | vio/viossl.c | 98 | ||||
-rw-r--r-- | vio/viosslfactories.c | 35 | ||||
-rw-r--r-- | vio/viotest-ssl.c | 140 | ||||
-rw-r--r-- | vio/viotest-ssl.cc | 104 |
5 files changed, 250 insertions, 134 deletions
diff --git a/vio/Makefile.am b/vio/Makefile.am index c1a69b26058..e8b226adb37 100644 --- a/vio/Makefile.am +++ b/vio/Makefile.am @@ -15,10 +15,13 @@ # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA INCLUDES = -I$(srcdir)/../include -I../include $(openssl_includes) -LDADD = libvio.a $(openssl_libs) +LDADD = libvio.a $(openssl_libs) pkglib_LIBRARIES = libvio.a -noinst_PROGRAMS = +noinst_PROGRAMS = viotest-ssl noinst_HEADERS = +viotest_ssl_SOURCES = viotest-ssl.c +viotest_ssl_LDADD = ../dbug/libdbug.a libvio.a ../mysys/libmysys.a ../strings/libmystrings.a \ + libvio.a $(openssl_libs) libvio_a_SOURCES = vio.c viosocket.c viossl.c viosslfactories.c OMIT_DEPENDENCIES = pthread.h stdio.h __stdio.h stdlib.h __stdlib.h math.h\ diff --git a/vio/viossl.c b/vio/viossl.c index e4fe9d87228..b9883ba3fa6 100644 --- a/vio/viossl.c +++ b/vio/viossl.c @@ -23,6 +23,9 @@ */ #include <global.h> + +#ifdef HAVE_OPENSSL + #include <mysql_com.h> #include <errno.h> @@ -61,9 +64,6 @@ #define HANDLE void * #endif - -#ifdef HAVE_OPENSSL - static void report_errors() { @@ -105,8 +105,11 @@ int vio_ssl_read(Vio * vio, gptr buf, int size) { int r; DBUG_ENTER("vio_ssl_read"); - DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); + DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d, ssl_=%p", vio->sd, buf, size, vio->ssl_)); assert(vio->ssl_!= 0); + + DBUG_PRINT("info",("SSL_get_cipher_name() = '%s'",SSL_get_cipher_name(vio->ssl_))); + r = SSL_read(vio->ssl_, buf, size); #ifndef DBUG_OFF if ( r< 0) @@ -123,6 +126,7 @@ int vio_ssl_write(Vio * vio, const gptr buf, int size) DBUG_ENTER("vio_ssl_write"); DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); assert(vio->ssl_!=0); + DBUG_PRINT("info",("SSL_get_cipher_name() = '%s'",SSL_get_cipher_name(vio->ssl_))); r = SSL_write(vio->ssl_, buf, size); #ifndef DBUG_OFF if (r<0) @@ -204,6 +208,7 @@ int vio_ssl_close(Vio * vio) if (r) { DBUG_PRINT("error", ("close() failed, error: %d",errno)); + report_errors(); /* FIXME: error handling (not critical for MySQL) */ } vio->type= VIO_CLOSED; @@ -289,12 +294,14 @@ my_bool vio_ssl_poll_read(Vio *vio,uint timeout) /* FIXME: There are some duplicate code in * sslaccept()/sslconnect() which maybe can be eliminated */ -Vio *sslaccept(struct st_VioSSLAcceptorFd* ptr, Vio* sd) +void sslaccept(struct st_VioSSLAcceptorFd* ptr, Vio* sd) { + X509* client_cert; + char *str; DBUG_ENTER("sslaccept"); - DBUG_PRINT("enter", ("sd=%s ptr=%p", sd->desc,ptr)); + DBUG_PRINT("enter", ("sd=%s ptr=%p", sd->sd,ptr)); vio_reset(sd,VIO_TYPE_SSL,sd->sd,0,FALSE); - ptr->bio_=0; +// ptr->bio_=0; sd->ssl_=0; sd->open_=FALSE; assert(sd != 0); @@ -304,9 +311,12 @@ Vio *sslaccept(struct st_VioSSLAcceptorFd* ptr, Vio* sd) { DBUG_PRINT("error", ("SSL_new failure")); report_errors(); - DBUG_RETURN(sd); + DBUG_VOID_RETURN; } - if (!(ptr->bio_ = BIO_new_socket(sd->sd, BIO_NOCLOSE))) + DBUG_PRINT("info", ("ssl_=%p",sd->ssl_)); + SSL_set_fd(sd->ssl_,sd->sd); +// SSL_accept(sd->ssl_); +/* if (!(ptr->bio_ = BIO_new_socket(sd->sd, BIO_NOCLOSE))) { DBUG_PRINT("error", ("BIO_new_socket failure")); report_errors(); @@ -314,18 +324,42 @@ Vio *sslaccept(struct st_VioSSLAcceptorFd* ptr, Vio* sd) sd->ssl_=0; DBUG_RETURN(sd); } - SSL_set_bio(sd->ssl_, ptr->bio_, ptr->bio_); + SSL_set_bio(sd->ssl_, ptr->bio_, ptr->bio_);*/ SSL_set_accept_state(sd->ssl_); - sprintf(ptr->desc_, "VioSSL(%d)", sd->sd); -/* sd->ssl_cip_ = SSL_get_cipher(sd->ssl_); */ +// sprintf(ptr->desc_, "VioSSL(%d)", sd->sd); +// sd->ssl_cip_ = SSL_get_cipher(sd->ssl_); sd->open_ = TRUE; - DBUG_RETURN(sd); + + + client_cert = SSL_get_peer_certificate (sd->ssl_); + if (client_cert != NULL) { + DBUG_PRINT("info",("Client certificate:")); + str = X509_NAME_oneline (X509_get_subject_name (client_cert), 0, 0); + //CHK_NULL(str); + DBUG_PRINT("info",("\t subject: %s", str)); + free (str); + + str = X509_NAME_oneline (X509_get_issuer_name (client_cert), 0, 0); + //CHK_NULL(str); + DBUG_PRINT("info",("\t issuer: %s", str)); + free (str); + + /* We could do all sorts of certificate verification stuff here before + * deallocating the certificate. */ + + X509_free (client_cert); + } else + DBUG_PRINT("info",("Client does not have certificate.")); + + DBUG_VOID_RETURN; } -Vio *sslconnect(struct st_VioSSLConnectorFd* ptr, Vio* sd) +void sslconnect(struct st_VioSSLConnectorFd* ptr, Vio* sd) { + char *str; + X509* server_cert; DBUG_ENTER("sslconnect"); - DBUG_PRINT("enter", ("sd=%s ptr=%p ctx: %p", sd->desc,ptr,ptr->ssl_context_)); + DBUG_PRINT("enter", ("sd=%s ptr=%p ctx: %p", sd->sd,ptr,ptr->ssl_context_)); vio_reset(sd,VIO_TYPE_SSL,sd->sd,0,FALSE); sd->bio_=0; @@ -339,9 +373,11 @@ Vio *sslconnect(struct st_VioSSLConnectorFd* ptr, Vio* sd) { DBUG_PRINT("error", ("SSL_new failure")); report_errors(); - DBUG_RETURN(sd); + DBUG_VOID_RETURN; } - if (!(sd->bio_ = BIO_new_socket(sd->sd, BIO_NOCLOSE))) + DBUG_PRINT("info", ("ssl_=%p",sd->ssl_)); + printf("ssl_=%p\n",sd->ssl_); +/* if (!(sd->bio_ = BIO_new_socket(sd->sd, BIO_NOCLOSE))) { DBUG_PRINT("error", ("BIO_new_socket failure")); report_errors(); @@ -349,12 +385,32 @@ Vio *sslconnect(struct st_VioSSLConnectorFd* ptr, Vio* sd) sd->ssl_=0; DBUG_RETURN(sd); } - SSL_set_bio(sd->ssl_, sd->bio_, sd->bio_); + SSL_set_bio(sd->ssl_, sd->bio_, sd->bio_);*/ + + SSL_set_fd (sd->ssl_, sd->sd); SSL_set_connect_state(sd->ssl_); -/* sprintf(ptr->desc_, "VioSSL(%d)", sd->sd); - sd->ssl_cip_ = SSL_get_cipher(sd->ssl_);*/ + + server_cert = SSL_get_peer_certificate (sd->ssl_); + if (server_cert != NULL) { + DBUG_PRINT("info",("Server certificate:")); + str = X509_NAME_oneline (X509_get_subject_name (server_cert), 0, 0); + DBUG_PRINT("info",("\t subject: %s", str)); + free (str); + + str = X509_NAME_oneline (X509_get_issuer_name (server_cert), 0, 0); + DBUG_PRINT("info",("\t issuer: %s\n", str)); + free (str); + + /* We could do all sorts of certificate verification stuff here before + * deallocating the certificate. */ + + X509_free(server_cert); + } else + DBUG_PRINT("info",("Server does not have certificate.")); + +// sd->ssl_cip_ = SSL_get_cipher(sd->ssl_); sd->open_ = TRUE; - DBUG_RETURN(sd); + DBUG_VOID_RETURN; } diff --git a/vio/viosslfactories.c b/vio/viosslfactories.c index 4be956ed9ba..5285dd0f7b1 100644 --- a/vio/viosslfactories.c +++ b/vio/viosslfactories.c @@ -1,11 +1,29 @@ +/* Copyright (C) 2000 MySQL AB & MySQL Finland AB & TCX DataKonsult AB + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with this library; if not, write to the Free + Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, + MA 02111-1307, USA */ #include <global.h> + +#ifdef HAVE_OPENSSL + #include <my_sys.h> #include <mysql_com.h> #include <violite.h> -#ifdef HAVE_OPENSSL static bool ssl_algorithms_added = FALSE; static bool ssl_error_strings_loaded= FALSE; @@ -142,9 +160,9 @@ struct st_VioSSLConnectorFd* new_VioSSLConnectorFd(const char* key_file, if (!ssl_algorithms_added) { - DBUG_PRINT("info", ("todo: SSLeay_add_ssl_algorithms()")); + DBUG_PRINT("info", ("todo: OpenSSL_add_all_algorithms()")); ssl_algorithms_added = TRUE; - SSLeay_add_ssl_algorithms(); + OpenSSL_add_all_algorithms(); } if (!ssl_error_strings_loaded) { @@ -152,7 +170,7 @@ struct st_VioSSLConnectorFd* new_VioSSLConnectorFd(const char* key_file, ssl_error_strings_loaded = TRUE; SSL_load_error_strings(); } - ptr->ssl_method_ = SSLv3_client_method(); + ptr->ssl_method_ = SSLv23_client_method(); ptr->ssl_context_ = SSL_CTX_new(ptr->ssl_method_); DBUG_PRINT("info", ("ssl_context_: %p",ptr->ssl_context_)); if (ptr->ssl_context_ == 0) @@ -186,6 +204,7 @@ struct st_VioSSLConnectorFd* new_VioSSLConnectorFd(const char* key_file, DBUG_RETURN(ptr); ctor_failure: DBUG_PRINT("exit", ("there was an error")); + my_free((gptr)ptr,MYF(0)); DBUG_RETURN(0); } @@ -216,9 +235,10 @@ new_VioSSLAcceptorFd(const char* key_file, if (!ssl_algorithms_added) { - DBUG_PRINT("info", ("todo: SSLeay_add_ssl_algorithms()")); + DBUG_PRINT("info", ("todo: OpenSSL_add_all_algorithms()")); ssl_algorithms_added = TRUE; - SSLeay_add_ssl_algorithms(); + OpenSSL_add_all_algorithms(); + } if (!ssl_error_strings_loaded) { @@ -226,7 +246,7 @@ new_VioSSLAcceptorFd(const char* key_file, ssl_error_strings_loaded = TRUE; SSL_load_error_strings(); } - ptr->ssl_method_ = SSLv3_server_method(); + ptr->ssl_method_ = SSLv23_server_method(); ptr->ssl_context_ = SSL_CTX_new(ptr->ssl_method_); if (ptr->ssl_context_==0) { @@ -267,6 +287,7 @@ new_VioSSLAcceptorFd(const char* key_file, DBUG_RETURN(ptr); ctor_failure: DBUG_PRINT("exit", ("there was an error")); + my_free((gptr)ptr,MYF(0)); DBUG_RETURN(0); } diff --git a/vio/viotest-ssl.c b/vio/viotest-ssl.c new file mode 100644 index 00000000000..02d47a11294 --- /dev/null +++ b/vio/viotest-ssl.c @@ -0,0 +1,140 @@ +#include <global.h> +#ifdef HAVE_OPENSSL +#include <my_sys.h> +#include <m_string.h> +#include <m_ctype.h> +#include "mysql.h" +#include "errmsg.h" +#include <my_dir.h> +#ifndef __GNU_LIBRARY__ +#define __GNU_LIBRARY__ // Skip warnings in getopt.h +#endif +#include <getopt.h> +//#include "my_readline.h" +#include <signal.h> +#include <violite.h> + +const char *VER="0.1"; + + +#ifndef DBUG_OFF +const char *default_dbug_option="d:t:O,/tmp/viotest-ssl.trace"; +#endif + +void +fatal_error( const char* r) +{ + perror(r); + exit(0); +} + +void +print_usage() +{ + printf("viossl-test: testing SSL virtual IO. Usage:\n"); + printf("viossl-test server-key server-cert client-key client-cert [CAfile] [CApath]\n"); +} + +int +main( int argc, + char** argv) +{ + char* server_key = 0; + char* server_cert = 0; + char* client_key = 0; + char* client_cert = 0; + char* ca_file = 0; + char* ca_path = 0; + int child_pid,sv[2]; + struct st_VioSSLAcceptorFd* ssl_acceptor=0; + struct st_VioSSLConnectorFd* ssl_connector=0; + Vio* client_vio=0; + Vio* server_vio=0; + MY_INIT(argv[0]); +// DBUG_ENTER("main"); + DBUG_PROCESS(argv[0]); + DBUG_PUSH(default_dbug_option); + + + + if (argc<5) + { + print_usage(); + return 1; + } + + server_key = argv[1]; + server_cert = argv[2]; + client_key = argv[3]; + client_cert = argv[4]; + if (argc>5) + ca_file = argv[5]; + if (argc>6) + ca_path = argv[6]; + printf("Server key/cert : %s/%s\n", server_key, server_cert); + printf("Client key/cert : %s/%s\n", client_key, client_cert); + if (ca_file!=0) + printf("CAfile : %s\n", ca_file); + if (ca_path!=0) + printf("CApath : %s\n", ca_path); + + + if (socketpair(PF_UNIX, SOCK_STREAM, IPPROTO_IP, sv)==-1) + fatal_error("socketpair"); + + ssl_acceptor = new_VioSSLAcceptorFd(server_key, server_cert, ca_file, ca_path); + ssl_connector = new_VioSSLConnectorFd(client_key, client_cert, ca_file, ca_path); + + client_vio = (Vio*)my_malloc(sizeof(struct st_vio),MYF(0)); + client_vio->sd = sv[0]; + sslconnect(ssl_connector,client_vio); + server_vio = (Vio*)my_malloc(sizeof(struct st_vio),MYF(0)); + server_vio->sd = sv[1]; + sslaccept(ssl_acceptor,server_vio); + + printf("Socketpair: %d , %d\n", client_vio->sd, server_vio->sd); + + child_pid = fork(); + if (child_pid==-1) { + my_free((gptr)ssl_acceptor,MYF(0)); + my_free((gptr)ssl_connector,MYF(0)); + fatal_error("fork"); + } + if (child_pid==0) { + //child, therefore, client + char xbuf[100]; + int r = vio_ssl_read(client_vio,xbuf, sizeof(xbuf)); + if (r<=0) { + my_free((gptr)ssl_acceptor,MYF(0)); + my_free((gptr)ssl_connector,MYF(0)); + fatal_error("client:SSL_read"); + } +// printf("*** client cipher %s\n",client_vio->cipher_description()); + xbuf[r] = 0; + printf("client:got %s\n", xbuf); + my_free((gptr)client_vio,MYF(0)); + my_free((gptr)ssl_acceptor,MYF(0)); + my_free((gptr)ssl_connector,MYF(0)); + sleep(1); + } else { + const char* s = "Huhuhuh"; + int r = vio_ssl_write(server_vio,(gptr)s, strlen(s)); + if (r<=0) { + my_free((gptr)ssl_acceptor,MYF(0)); + my_free((gptr)ssl_connector,MYF(0)); + fatal_error("server:SSL_write"); + } +// printf("*** server cipher %s\n",server_vio->cipher_description()); + my_free((gptr)server_vio,MYF(0)); + my_free((gptr)ssl_acceptor,MYF(0)); + my_free((gptr)ssl_connector,MYF(0)); + sleep(1); + } + return 0; +} +#else /* HAVE_OPENSSL */ + +int main() { +return 0; +} +#endif /* HAVE_OPENSSL */ diff --git a/vio/viotest-ssl.cc b/vio/viotest-ssl.cc deleted file mode 100644 index a3ad92a7c9c..00000000000 --- a/vio/viotest-ssl.cc +++ /dev/null @@ -1,104 +0,0 @@ -#include "all.h" - -#include <sys/types.h> -#include <sys/socket.h> -#include <stdio.h> -#include <unistd.h> - - -void -fatal_error( const char* r) -{ - perror(r); - exit(0); -} - -void -print_usage() -{ - printf("viossltest: testing SSL virtual IO. Usage:\n"); - printf("viossltest server-key server-cert client-key client-cert [CAfile] [CApath]\n"); -} - -int -main( int argc, - char** argv) -{ - char* server_key = 0; - char* server_cert = 0; - char* client_key = 0; - char* client_cert = 0; - char* ca_file = 0; - char* ca_path = 0; - int sv[2]; - - if (argc<5) - { - print_usage(); - return 1; - } - - if (socketpair(PF_UNIX, SOCK_STREAM, IPPROTO_IP, sv)==-1) - fatal_error("socketpair"); - - server_key = argv[1]; - server_cert = argv[2]; - client_key = argv[3]; - client_cert = argv[4]; - if (argc>5) - ca_file = argv[5]; - if (argc>6) - ca_path = argv[6]; - printf("Server key/cert : %s/%s\n", server_key, server_cert); - printf("Client key/cert : %s/%s\n", client_key, client_cert); - if (ca_file!=0) - printf("CAfile : %s\n", ca_file); - if (ca_path!=0) - printf("CApath : %s\n", ca_path); - - VIO_NS::VioSSLAcceptorFd* ssl_acceptor = new VIO_NS::VioSSLAcceptorFd(server_key, server_cert, ca_file, ca_path); - VIO_NS::VioSSLConnectorFd* ssl_connector = new VIO_NS::VioSSLConnectorFd(client_key, client_cert, ca_file, ca_path); - - printf("Socketpair: %d , %d\n", sv[0], sv[1]); - - VIO_NS::VioSSL* client_vio = ssl_connector->connect(sv[0]); - VIO_NS::VioSSL* server_vio = ssl_acceptor->accept(sv[1]); - - - int child_pid = fork(); - if (child_pid==-1) { - delete ssl_acceptor; - delete ssl_connector; - fatal_error("fork"); - } - if (child_pid==0) { - //child, therefore, client - char xbuf[100]; - int r = client_vio->read(xbuf, sizeof(xbuf)); - if (r<=0) { - delete ssl_acceptor; - delete ssl_connector; - fatal_error("client:SSL_read"); - } - printf("*** client cipher %s\n",client_vio->cipher_description()); - xbuf[r] = 0; - printf("client:got %s\n", xbuf); - delete client_vio; - delete ssl_acceptor; - delete ssl_connector; - sleep(1); - } else { - const char* s = "Huhuhuh"; - int r = server_vio->write((void *)s, strlen(s)); - if (r<=0) { - delete ssl_acceptor; - delete ssl_connector; - fatal_error("server:SSL_write"); - } - printf("*** server cipher %s\n",server_vio->cipher_description()); - delete server_vio; - delete ssl_acceptor; - delete ssl_connector; - sleep(1); - } -} |