From 9b1cbf15a5963e28ead142cceacc30f0e5d14f0a Mon Sep 17 00:00:00 2001 From: Georg Richter Date: Sun, 15 Nov 2015 08:00:43 +0100 Subject: [PATCH] Fix for asynchronous connect: Unless the connection was successfully established mysql_get_socket will return INVALID_SOCKET. In this case we need to check if an asynchronous operation is in progress and return pvio from asynchronous context. --- include/my_context.h | 2 ++ libmariadb/libmariadb.c | 14 +++++++++++--- plugins/auth/my_auth.c | 2 +- plugins/pvio/pvio_socket.c | 3 +++ unittest/libmariadb/async.c | 9 ++++++--- 5 files changed, 23 insertions(+), 7 deletions(-) diff --git a/include/my_context.h b/include/my_context.h index c7b41666..591a064a 100644 --- a/include/my_context.h +++ b/include/my_context.h @@ -166,6 +166,7 @@ extern int my_context_yield(struct my_context *c); */ extern int my_context_continue(struct my_context *c); +struct st_ma_pvio; struct mysql_async_context { /* @@ -220,6 +221,7 @@ struct mysql_async_context { the user data argument just before the context is suspended, and just after it is resumed. */ + struct st_ma_pvio *pvio; void (*suspend_resume_hook)(my_bool suspend, void *user_data); void *suspend_resume_hook_user_data; /* diff --git a/libmariadb/libmariadb.c b/libmariadb/libmariadb.c index 3c7f5192..ae577c36 100644 --- a/libmariadb/libmariadb.c +++ b/libmariadb/libmariadb.c @@ -3251,13 +3251,21 @@ mysql_get_parameters(void) my_socket STDCALL mysql_get_socket(const MYSQL *mysql) { - my_socket sock; + my_socket sock= INVALID_SOCKET; if (mysql->net.pvio) { ma_pvio_get_handle(mysql->net.pvio, &sock); - return sock; } - return INVALID_SOCKET; + /* if an asynchronous connect is in progress, we need to obtain + pvio handle from async_context until the connection was + successfully established. + */ + else if (mysql->options.extension && mysql->options.extension->async_context && + mysql->options.extension->async_context->pvio) + { + ma_pvio_get_handle(mysql->options.extension->async_context->pvio, &sock); + } + return sock; } /* diff --git a/plugins/auth/my_auth.c b/plugins/auth/my_auth.c index a176e863..08505685 100644 --- a/plugins/auth/my_auth.c +++ b/plugins/auth/my_auth.c @@ -77,7 +77,7 @@ static int native_password_auth_client(MYSQL_PLUGIN_VIO *vio, MYSQL *mysql) mysql->scramble_buff[SCRAMBLE_LENGTH] = 0; } - if (mysql->passwd[0]) + if (mysql && mysql->passwd[0]) { char scrambled[SCRAMBLE_LENGTH + 1]; my_scramble_41((uchar *)scrambled, (char*)pkt, mysql->passwd); diff --git a/plugins/pvio/pvio_socket.c b/plugins/pvio/pvio_socket.c index 394951ab..aa5c407c 100644 --- a/plugins/pvio/pvio_socket.c +++ b/plugins/pvio/pvio_socket.c @@ -661,6 +661,9 @@ pvio_socket_connect_sync_or_async(MARIADB_PVIO *pvio, if (mysql->options.extension && mysql->options.extension->async_context && mysql->options.extension->async_context->active) { + /* even if we are not connected yet, application needs to check socket + * via mysql_get_socket api call, so we need to assign pvio */ + mysql->options.extension->async_context->pvio= pvio; pvio_socket_blocking(pvio, 0, 0); return my_connect_async(pvio, name, namelen, pvio->timeout[PVIO_CONNECT_TIMEOUT]); } diff --git a/unittest/libmariadb/async.c b/unittest/libmariadb/async.c index 2594b726..95e1b258 100644 --- a/unittest/libmariadb/async.c +++ b/unittest/libmariadb/async.c @@ -118,7 +118,7 @@ wait_for_mysql(MYSQL *mysql, int status) static int async1(MYSQL *my) { - int err; + int err, rc; MYSQL mysql, *ret; MYSQL_RES *res; MYSQL_ROW row; @@ -130,7 +130,8 @@ static int async1(MYSQL *my) { mysql_init(&mysql); - mysql_options(&mysql, MYSQL_OPT_NONBLOCK, 0); + rc= mysql_options(&mysql, MYSQL_OPT_NONBLOCK, 0); + check_mysql_rc(rc, (MYSQL *)&mysql); /* set timeouts to 300 microseconds */ default_timeout= 300; @@ -193,9 +194,11 @@ static int async1(MYSQL *my) static int test_conc131(MYSQL *my) { + int rc; /* this test needs to run under valgrind */ MYSQL *mysql=mysql_init(NULL); - mysql_options(mysql, MYSQL_OPT_NONBLOCK, 0); + rc= mysql_options(mysql, MYSQL_OPT_NONBLOCK, 0); + check_mysql_rc(rc, mysql); mysql_close(mysql); return OK; }