summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVladislav Vaintroub <wlad@mariadb.com>2020-08-11 12:11:07 +0000
committerVladislav Vaintroub <wlad@mariadb.com>2020-08-11 12:11:07 +0000
commit2f6492c21fb1816a6a40fb9004fb89b7f17adb3f (patch)
tree3e8c4ef831d68d9144be54348559c3ff7728c374
parent09be96ff08bba1f2dd7ca72f2b28925623be6e79 (diff)
downloadmariadb-git-bb-10.6-MDEV-23238.tar.gz
MDEV-23238 - remove async client from server code.bb-10.6-MDEV-23238
It is already in libmariadb, and server (also that client in server) does not need it. It does not work in embedded either since it relies on non-blocking sockets
-rw-r--r--client/mysqltest.cc5
-rw-r--r--include/my_context.h232
-rw-r--r--include/mysql_async.h38
-rw-r--r--include/sql_common.h7
-rw-r--r--include/violite.h1
-rw-r--r--libmysqld/CMakeLists.txt79
-rw-r--r--mysys/CMakeLists.txt2
-rw-r--r--mysys/my_context.c761
-rw-r--r--sql-common/client.c119
-rw-r--r--sql-common/mysql_async.c1995
-rw-r--r--sql/CMakeLists.txt1
-rw-r--r--tests/mysql_client_fw.c3
-rw-r--r--vio/viosocket.c105
-rw-r--r--vio/viossl.c47
14 files changed, 46 insertions, 3349 deletions
diff --git a/client/mysqltest.cc b/client/mysqltest.cc
index 79ca4ed60e7..6b829ccb8be 100644
--- a/client/mysqltest.cc
+++ b/client/mysqltest.cc
@@ -65,9 +65,8 @@
#define SIGNAL_FMT "signal %d"
#endif
-#include <my_context.h>
static my_bool non_blocking_api_enabled= 0;
-#if !defined(EMBEDDED_LIBRARY) && !defined(MY_CONTEXT_DISABLE)
+#if !defined(EMBEDDED_LIBRARY)
#define WRAP_NONBLOCK_ENABLED non_blocking_api_enabled
#include "../tests/nonblock-wrappers.h"
#endif
@@ -6002,10 +6001,8 @@ void do_connect(struct st_command *command)
if (opt_connect_timeout)
mysql_options(con_slot->mysql, MYSQL_OPT_CONNECT_TIMEOUT,
(void *) &opt_connect_timeout);
-#ifndef MY_CONTEXT_DISABLE
if (mysql_options(con_slot->mysql, MYSQL_OPT_NONBLOCK, 0))
die("Failed to initialise non-blocking API");
-#endif
if (opt_compress || con_compress)
mysql_options(con_slot->mysql, MYSQL_OPT_COMPRESS, NullS);
mysql_options(con_slot->mysql, MYSQL_SET_CHARSET_NAME,
diff --git a/include/my_context.h b/include/my_context.h
deleted file mode 100644
index ea0e3496887..00000000000
--- a/include/my_context.h
+++ /dev/null
@@ -1,232 +0,0 @@
-/*
- Copyright 2011 Kristian Nielsen and Monty Program Ab
-
- This file is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
- Simple API for spawning a co-routine, to be used for async libmysqlclient.
-
- Idea is that by implementing this interface using whatever facilities are
- available for given platform, we can use the same code for the generic
- libmysqlclient-async code.
-
- (This particular implementation uses Posix ucontext swapcontext().)
-*/
-
-#ifdef __WIN__
-#define MY_CONTEXT_USE_WIN32_FIBERS 1
-#elif defined(__GNUC__) && __GNUC__ >= 3 && defined(__x86_64__) && !defined(__ILP32__)
-#define MY_CONTEXT_USE_X86_64_GCC_ASM
-#elif defined(__GNUC__) && __GNUC__ >= 3 && defined(__i386__)
-#define MY_CONTEXT_USE_I386_GCC_ASM
-#elif defined(HAVE_UCONTEXT_H)
-#define MY_CONTEXT_USE_UCONTEXT
-#else
-#define MY_CONTEXT_DISABLE
-#endif
-
-#ifdef MY_CONTEXT_USE_WIN32_FIBERS
-struct my_context {
- void (*user_func)(void *);
- void *user_arg;
- void *app_fiber;
- void *lib_fiber;
- int return_value;
-#ifndef DBUG_OFF
- void *dbug_state;
-#endif
-};
-#endif
-
-
-#ifdef MY_CONTEXT_USE_UCONTEXT
-#include <ucontext.h>
-
-struct my_context {
- void (*user_func)(void *);
- void *user_data;
- void *stack;
- size_t stack_size;
- ucontext_t base_context;
- ucontext_t spawned_context;
- int active;
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- unsigned int valgrind_stack_id;
-#endif
-#ifndef DBUG_OFF
- void *dbug_state;
-#endif
-};
-#endif
-
-
-#ifdef MY_CONTEXT_USE_X86_64_GCC_ASM
-#include <stdint.h>
-
-struct my_context {
- uint64_t save[9];
- void *stack_top;
- void *stack_bot;
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- unsigned int valgrind_stack_id;
-#endif
-#ifndef DBUG_OFF
- void *dbug_state;
-#endif
-};
-#endif
-
-
-#ifdef MY_CONTEXT_USE_I386_GCC_ASM
-#include <stdint.h>
-
-struct my_context {
- uint64_t save[7];
- void *stack_top;
- void *stack_bot;
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- unsigned int valgrind_stack_id;
-#endif
-#ifndef DBUG_OFF
- void *dbug_state;
-#endif
-};
-#endif
-
-
-#ifdef MY_CONTEXT_DISABLE
-struct my_context {
- int dummy;
-};
-#endif
-
-
-/*
- Initialize an asynchroneous context object.
- Returns 0 on success, non-zero on failure.
-*/
-extern int my_context_init(struct my_context *c, size_t stack_size);
-
-/* Free an asynchroneous context object, deallocating any resources used. */
-extern void my_context_destroy(struct my_context *c);
-
-/*
- Spawn an asynchroneous context. The context will run the supplied user
- function, passing the supplied user data pointer.
-
- The context must have been initialised with my_context_init() prior to
- this call.
-
- The user function may call my_context_yield(), which will cause this
- function to return 1. Then later my_context_continue() may be called, which
- will resume the asynchroneous context by returning from the previous
- my_context_yield() call.
-
- When the user function returns, this function returns 0.
-
- In case of error, -1 is returned.
-*/
-extern int my_context_spawn(struct my_context *c, void (*f)(void *), void *d);
-
-/*
- Suspend an asynchroneous context started with my_context_spawn.
-
- When my_context_yield() is called, execution immediately returns from the
- last my_context_spawn() or my_context_continue() call. Then when later
- my_context_continue() is called, execution resumes by returning from this
- my_context_yield() call.
-
- Returns 0 if ok, -1 in case of error.
-*/
-extern int my_context_yield(struct my_context *c);
-
-/*
- Resume an asynchroneous context. The context was spawned by
- my_context_spawn(), and later suspended inside my_context_yield().
-
- The asynchroneous context may be repeatedly suspended with
- my_context_yield() and resumed with my_context_continue().
-
- Each time it is suspended, this function returns 1. When the originally
- spawned user function returns, this function returns 0.
-
- In case of error, -1 is returned.
-*/
-extern int my_context_continue(struct my_context *c);
-
-
-struct mysql_async_context {
- /*
- This is set to the value that should be returned from foo_start() or
- foo_cont() when a call is suspended.
- */
- unsigned int events_to_wait_for;
- /*
- It is also set to the event(s) that triggered when a suspended call is
- resumed, eg. whether we woke up due to connection completed or timeout
- in mysql_real_connect_cont().
- */
- unsigned int events_occurred;
- /*
- This is set to the result of the whole asynchronous operation when it
- completes. It uses a union, as different calls have different return
- types.
- */
- union {
- void *r_ptr;
- const void *r_const_ptr;
- int r_int;
- my_bool r_my_bool;
- } ret_result;
- /*
- The timeout value (in millisecods), for suspended calls that need to wake
- up on a timeout (eg. mysql_real_connect_start().
- */
- unsigned int timeout_value;
- /*
- This flag is set when we are executing inside some asynchronous call
- foo_start() or foo_cont(). It is used to decide whether to use the
- synchronous or asynchronous version of calls that may block such as
- recv().
-
- Note that this flag is not set when a call is suspended, eg. after
- returning from foo_start() and before re-entering foo_cont().
- */
- my_bool active;
- /*
- This flag is set when an asynchronous operation is in progress, but
- suspended. Ie. it is set when foo_start() or foo_cont() returns because
- the operation needs to block, suspending the operation.
-
- It is used to give an error (rather than crash) if the application
- attempts to call some foo_cont() method when no suspended operation foo is
- in progress.
- */
- my_bool suspended;
- /*
- If non-NULL, this is a pointer to a callback hook that will be invoked with
- the user data argument just before the context is suspended, and just after
- it is resumed.
- */
- void (*suspend_resume_hook)(my_bool suspend, void *user_data);
- void *suspend_resume_hook_user_data;
- /*
- This is used to save the execution contexts so that we can suspend an
- operation and switch back to the application context, to resume the
- suspended context later when the application re-invokes us with
- foo_cont().
- */
- struct my_context async_context;
-};
diff --git a/include/mysql_async.h b/include/mysql_async.h
deleted file mode 100644
index 3e4cb351bb5..00000000000
--- a/include/mysql_async.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/* Copyright (C) 2012 MariaDB Services and Kristian Nielsen
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; version 2 of the License.
-
- This program 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 General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, write to the Free Software
- Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA */
-
-/* Common definitions for MariaDB non-blocking client library. */
-
-#ifndef MYSQL_ASYNC_H
-#define MYSQL_ASYNC_H
-
-extern int my_connect_async(struct mysql_async_context *b, my_socket fd,
- const struct sockaddr *name, uint namelen,
- int vio_timeout);
-extern ssize_t my_recv_async(struct mysql_async_context *b, my_socket fd,
- unsigned char *buf, size_t size, int timeout);
-extern ssize_t my_send_async(struct mysql_async_context *b, my_socket fd,
- const unsigned char *buf, size_t size,
- int timeout);
-extern my_bool my_io_wait_async(struct mysql_async_context *b,
- enum enum_vio_io_event event, int timeout);
-#ifdef HAVE_OPENSSL
-extern int my_ssl_read_async(struct mysql_async_context *b, SSL *ssl,
- void *buf, int size);
-extern int my_ssl_write_async(struct mysql_async_context *b, SSL *ssl,
- const void *buf, int size);
-#endif
-
-#endif /* MYSQL_ASYNC_H */
diff --git a/include/sql_common.h b/include/sql_common.h
index 9836d0c1cdc..9fc983616a0 100644
--- a/include/sql_common.h
+++ b/include/sql_common.h
@@ -28,8 +28,6 @@ extern const char *cant_connect_sqlstate;
extern const char *not_error_sqlstate;
-struct mysql_async_context;
-
struct st_mysql_options_extention {
char *plugin_dir;
char *default_auth;
@@ -41,7 +39,6 @@ struct st_mysql_options_extention {
double progress,
const char *proc_info,
uint proc_info_length);
- struct mysql_async_context *async_context;
HASH connection_attributes;
size_t connection_attributes_length;
};
@@ -125,10 +122,6 @@ struct st_mysql_client_plugin;
extern struct st_mysql_client_plugin *mysql_client_builtins[];
uchar * send_client_connect_attrs(MYSQL *mysql, uchar *buf);
-/* Non-blocking client API. */
-void my_context_install_suspend_resume_hook(struct mysql_async_context *b,
- void (*)(my_bool, void *), void *);
-
#ifdef __cplusplus
}
#endif
diff --git a/include/violite.h b/include/violite.h
index 6d09621bea6..2599cbf27e8 100644
--- a/include/violite.h
+++ b/include/violite.h
@@ -249,7 +249,6 @@ struct st_vio
char *read_pos; /* start of unfetched data in the
read buffer */
char *read_end; /* end of unfetched data */
- struct mysql_async_context *async_context; /* For non-blocking API */
int read_timeout; /* Timeout value (ms) for read ops. */
int write_timeout; /* Timeout value (ms) for write ops. */
/* function pointers. They are similar for socket/SSL/whatever */
diff --git a/libmysqld/CMakeLists.txt b/libmysqld/CMakeLists.txt
index 57b468c7245..91cf46c4683 100644
--- a/libmysqld/CMakeLists.txt
+++ b/libmysqld/CMakeLists.txt
@@ -43,7 +43,7 @@ SET(SQL_EMBEDDED_SOURCES emb_qcache.cc libmysqld.c lib_sql.cc
libmysql.c ../sql-common/errmsg.c
../sql-common/client.c
../sql-common/my_user.c ../sql-common/pack.c
- ../sql-common/client_plugin.c ../sql-common/mysql_async.c
+ ../sql-common/client_plugin.c
../sql/password.c ../sql/discover.cc ../sql/derror.cc
../sql/field.cc ../sql/field_conv.cc ../sql/field_comp.cc
../sql/filesort_utils.cc ../sql/sql_digest.cc
@@ -308,82 +308,7 @@ mysql_client_register_plugin
mysql_load_plugin
mysql_load_plugin_v
mysql_plugin_options
-# Async API
-mysql_get_timeout_value
-mysql_get_timeout_value_ms
-mysql_get_socket
-mysql_autocommit_cont
-mysql_autocommit_start
-mysql_change_user_cont
-mysql_change_user_start
-mysql_close_cont
-mysql_close_start
-mysql_commit_cont
-mysql_commit_start
-mysql_dump_debug_info_cont
-mysql_dump_debug_info_start
-mysql_fetch_row_cont
-mysql_fetch_row_start
-mysql_free_result_cont
-mysql_free_result_start
-mysql_kill_cont
-mysql_kill_start
-mysql_list_dbs_cont
-mysql_list_dbs_start
-mysql_list_fields_cont
-mysql_list_fields_start
-mysql_list_processes_cont
-mysql_list_processes_start
-mysql_list_tables_cont
-mysql_list_tables_start
-mysql_next_result_cont
-mysql_next_result_start
-mysql_ping_cont
-mysql_ping_start
-mysql_query_cont
-mysql_query_start
-mysql_read_query_result_cont
-mysql_read_query_result_start
-mysql_real_connect_cont
-mysql_real_connect_start
-mysql_real_query_cont
-mysql_real_query_start
-mysql_refresh_cont
-mysql_refresh_start
-mysql_rollback_cont
-mysql_rollback_start
-mysql_select_db_cont
-mysql_select_db_start
-mysql_send_query_cont
-mysql_send_query_start
-mysql_set_character_set_cont
-mysql_set_character_set_start
-mysql_set_server_option_cont
-mysql_set_server_option_start
-mysql_shutdown_cont
-mysql_shutdown_start
-mysql_stat_cont
-mysql_stat_start
-mysql_stmt_close_cont
-mysql_stmt_close_start
-mysql_stmt_execute_cont
-mysql_stmt_execute_start
-mysql_stmt_fetch_cont
-mysql_stmt_fetch_start
-mysql_stmt_free_result_cont
-mysql_stmt_free_result_start
-mysql_stmt_next_result_cont
-mysql_stmt_next_result_start
-mysql_stmt_prepare_cont
-mysql_stmt_prepare_start
-mysql_stmt_reset_cont
-mysql_stmt_reset_start
-mysql_stmt_send_long_data_cont
-mysql_stmt_send_long_data_start
-mysql_stmt_store_result_cont
-mysql_stmt_store_result_start
-mysql_store_result_cont
-mysql_store_result_start
+
#dynamic columns api
dynamic_column_create
dynamic_column_create_many
diff --git a/mysys/CMakeLists.txt b/mysys/CMakeLists.txt
index 14a4ea9e9bb..3be4bc1b103 100644
--- a/mysys/CMakeLists.txt
+++ b/mysys/CMakeLists.txt
@@ -43,7 +43,7 @@ SET(MYSYS_SOURCES array.c charset-def.c charset.c checksum.c my_default.c
safemalloc.c my_new.cc
my_getncpus.c my_safehash.c my_chmod.c my_rnd.c
my_uuid.c wqueue.c waiting_threads.c ma_dyncol.c ../sql-common/my_time.c
- my_rdtsc.c my_context.c psi_noop.c
+ my_rdtsc.c psi_noop.c
my_atomic_writes.c my_cpu.c my_likely.c my_largepage.c
file_logger.c my_dlerror.c)
diff --git a/mysys/my_context.c b/mysys/my_context.c
deleted file mode 100644
index 5423f59d19b..00000000000
--- a/mysys/my_context.c
+++ /dev/null
@@ -1,761 +0,0 @@
-/*
- Copyright 2011, 2012 Kristian Nielsen and Monty Program Ab
-
- This file is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
- Implementation of async context spawning using Posix ucontext and
- swapcontext().
-*/
-
-#include "mysys_priv.h"
-#include "m_string.h"
-#include "my_context.h"
-
-#ifdef HAVE_VALGRIND_MEMCHECK_H
-#include <valgrind/valgrind.h>
-#endif
-
-#ifdef MY_CONTEXT_USE_UCONTEXT
-/*
- The makecontext() only allows to pass integers into the created context :-(
- We want to pass pointers, so we do it this kinda hackish way.
- Anyway, it should work everywhere, and at least it does not break strict
- aliasing.
-*/
-union pass_void_ptr_as_2_int {
- int a[2];
- void *p;
-};
-
-
-/*
- We use old-style function definition here, as this is passed to
- makecontext(). And the type of the makecontext() argument does not match
- the actual type (as the actual type can differ from call to call).
-*/
-static void
-my_context_spawn_internal(i0, i1)
-int i0, i1;
-{
- int err;
- struct my_context *c;
- union pass_void_ptr_as_2_int u;
-
- u.a[0]= i0;
- u.a[1]= i1;
- c= (struct my_context *)u.p;
-
- (*c->user_func)(c->user_data);
- c->active= 0;
- err= setcontext(&c->base_context);
- fprintf(stderr, "Aieie, setcontext() failed: %d (errno=%d)\n", err, errno);
-}
-
-
-int
-my_context_continue(struct my_context *c)
-{
- int err;
-
- if (!c->active)
- return 0;
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
- err= swapcontext(&c->base_context, &c->spawned_context);
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
- if (err)
- {
- fprintf(stderr, "Aieie, swapcontext() failed: %d (errno=%d)\n",
- err, errno);
- return -1;
- }
-
- return c->active;
-}
-
-
-int
-my_context_spawn(struct my_context *c, void (*f)(void *), void *d)
-{
- int err;
- union pass_void_ptr_as_2_int u;
-
- err= getcontext(&c->spawned_context);
- if (err)
- return -1;
- c->spawned_context.uc_stack.ss_sp= c->stack;
- c->spawned_context.uc_stack.ss_size= c->stack_size;
- c->spawned_context.uc_link= NULL;
- c->user_func= f;
- c->user_data= d;
- c->active= 1;
- u.p= c;
- makecontext(&c->spawned_context, my_context_spawn_internal, 2,
- u.a[0], u.a[1]);
-
- return my_context_continue(c);
-}
-
-
-int
-my_context_yield(struct my_context *c)
-{
- int err;
-
- if (!c->active)
- return -1;
-
- err= swapcontext(&c->spawned_context, &c->base_context);
- if (err)
- return -1;
- return 0;
-}
-
-int
-my_context_init(struct my_context *c, size_t stack_size)
-{
-#if SIZEOF_CHARP > SIZEOF_INT*2
-#error Error: Unable to store pointer in 2 ints on this architecture
-#endif
- bzero(c, sizeof(*c));
- if (!(c->stack= malloc(stack_size)))
- return -1; /* Out of memory */
- c->stack_size= stack_size;
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- c->valgrind_stack_id=
- VALGRIND_STACK_REGISTER(c->stack, ((unsigned char *)(c->stack))+stack_size);
-#endif
- return 0;
-}
-
-void
-my_context_destroy(struct my_context *c)
-{
- if (c->stack)
- {
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- VALGRIND_STACK_DEREGISTER(c->valgrind_stack_id);
-#endif
- free(c->stack);
- }
- DBUG_FREE_CODE_STATE(&c->dbug_state);
-}
-
-#endif /* MY_CONTEXT_USE_UCONTEXT */
-
-
-#ifdef MY_CONTEXT_USE_X86_64_GCC_ASM
-/*
- GCC-amd64 implementation of my_context.
-
- This is slightly optimized in the common case where we never yield
- (eg. fetch next row and it is already fully received in buffer). In this
- case we do not need to restore registers at return (though we still need to
- save them as we cannot know if we will yield or not in advance).
-*/
-
-#include <stdint.h>
-#include <stdlib.h>
-
-/*
- Layout of saved registers etc.
- Since this is accessed through gcc inline assembler, it is simpler to just
- use numbers than to try to define nice constants or structs.
-
- 0 0 %rsp
- 1 8 %rbp
- 2 16 %rbx
- 3 24 %r12
- 4 32 %r13
- 5 40 %r14
- 6 48 %r15
- 7 56 %rip for done
- 8 64 %rip for yield/continue
-*/
-
-int
-my_context_spawn(struct my_context *c, void (*f)(void *), void *d)
-{
- int ret;
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- /*
- There are 6 callee-save registers we need to save and restore when
- suspending and continuing, plus stack pointer %rsp and instruction pointer
- %rip.
-
- However, if we never suspend, the user-supplied function will in any case
- restore the 6 callee-save registers, so we can avoid restoring them in
- this case.
- */
- __asm__ __volatile__
- (
- "movq %%rsp, (%[save])\n\t"
- "movq %[stack], %%rsp\n\t"
-#if (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 4) || __clang__) && \
- !defined(__INTEL_COMPILER)
- /*
- This emits a DWARF DW_CFA_undefined directive to make the return address
- undefined. This indicates that this is the top of the stack frame, and
- helps tools that use DWARF stack unwinding to obtain stack traces.
- (I use numeric constant to avoid a dependency on libdwarf includes).
- */
- ".cfi_escape 0x07, 16\n\t"
-#endif
- "movq %%rbp, 8(%[save])\n\t"
- "movq %%rbx, 16(%[save])\n\t"
- "movq %%r12, 24(%[save])\n\t"
- "movq %%r13, 32(%[save])\n\t"
- "movq %%r14, 40(%[save])\n\t"
- "movq %%r15, 48(%[save])\n\t"
- "leaq 1f(%%rip), %%rax\n\t"
- "leaq 2f(%%rip), %%rcx\n\t"
- "movq %%rax, 56(%[save])\n\t"
- "movq %%rcx, 64(%[save])\n\t"
- /*
- Constraint below puts the argument to the user function into %rdi, as
- needed for the calling convention.
- */
- "callq *%[f]\n\t"
- "jmpq *56(%[save])\n"
- /*
- Come here when operation is done.
- We do not need to restore callee-save registers, as the called function
- will do this for us if needed.
- */
- "1:\n\t"
- "movq (%[save]), %%rsp\n\t"
- "xorl %[ret], %[ret]\n\t"
- "jmp 3f\n"
- /* Come here when operation was suspended. */
- "2:\n\t"
- "movl $1, %[ret]\n"
- "3:\n"
- : [ret] "=a" (ret),
- [f] "+S" (f),
- /* Need this in %rdi to follow calling convention. */
- [d] "+D" (d)
- : [stack] "a" (c->stack_top),
- /* Need this in callee-save register to preserve in function call. */
- [save] "b" (&c->save[0])
- : "rcx", "rdx", "r8", "r9", "r10", "r11", "memory", "cc"
- );
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- return ret;
-}
-
-int
-my_context_continue(struct my_context *c)
-{
- int ret;
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- __asm__ __volatile__
- (
- "movq (%[save]), %%rax\n\t"
- "movq %%rsp, (%[save])\n\t"
- "movq %%rax, %%rsp\n\t"
- "movq 8(%[save]), %%rax\n\t"
- "movq %%rbp, 8(%[save])\n\t"
- "movq %%rax, %%rbp\n\t"
- "movq 24(%[save]), %%rax\n\t"
- "movq %%r12, 24(%[save])\n\t"
- "movq %%rax, %%r12\n\t"
- "movq 32(%[save]), %%rax\n\t"
- "movq %%r13, 32(%[save])\n\t"
- "movq %%rax, %%r13\n\t"
- "movq 40(%[save]), %%rax\n\t"
- "movq %%r14, 40(%[save])\n\t"
- "movq %%rax, %%r14\n\t"
- "movq 48(%[save]), %%rax\n\t"
- "movq %%r15, 48(%[save])\n\t"
- "movq %%rax, %%r15\n\t"
-
- "leaq 1f(%%rip), %%rax\n\t"
- "leaq 2f(%%rip), %%rcx\n\t"
- "movq %%rax, 56(%[save])\n\t"
- "movq 64(%[save]), %%rax\n\t"
- "movq %%rcx, 64(%[save])\n\t"
-
- "movq 16(%[save]), %%rcx\n\t"
- "movq %%rbx, 16(%[save])\n\t"
- "movq %%rcx, %%rbx\n\t"
-
- "jmpq *%%rax\n"
- /*
- Come here when operation is done.
- Be sure to use the same callee-save register for %[save] here and in
- my_context_spawn(), so we preserve the value correctly at this point.
- */
- "1:\n\t"
- "movq (%[save]), %%rsp\n\t"
- "movq 8(%[save]), %%rbp\n\t"
- /* %rbx is preserved from my_context_spawn() in this case. */
- "movq 24(%[save]), %%r12\n\t"
- "movq 32(%[save]), %%r13\n\t"
- "movq 40(%[save]), %%r14\n\t"
- "movq 48(%[save]), %%r15\n\t"
- "xorl %[ret], %[ret]\n\t"
- "jmp 3f\n"
- /* Come here when operation is suspended. */
- "2:\n\t"
- "movl $1, %[ret]\n"
- "3:\n"
- : [ret] "=a" (ret)
- : /* Need this in callee-save register to preserve in function call. */
- [save] "b" (&c->save[0])
- : "rcx", "rdx", "rsi", "rdi", "r8", "r9", "r10", "r11", "memory", "cc"
- );
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- return ret;
-}
-
-int
-my_context_yield(struct my_context *c)
-{
- uint64_t *save= &c->save[0];
- __asm__ __volatile__
- (
- "movq (%[save]), %%rax\n\t"
- "movq %%rsp, (%[save])\n\t"
- "movq %%rax, %%rsp\n\t"
- "movq 8(%[save]), %%rax\n\t"
- "movq %%rbp, 8(%[save])\n\t"
- "movq %%rax, %%rbp\n\t"
- "movq 16(%[save]), %%rax\n\t"
- "movq %%rbx, 16(%[save])\n\t"
- "movq %%rax, %%rbx\n\t"
- "movq 24(%[save]), %%rax\n\t"
- "movq %%r12, 24(%[save])\n\t"
- "movq %%rax, %%r12\n\t"
- "movq 32(%[save]), %%rax\n\t"
- "movq %%r13, 32(%[save])\n\t"
- "movq %%rax, %%r13\n\t"
- "movq 40(%[save]), %%rax\n\t"
- "movq %%r14, 40(%[save])\n\t"
- "movq %%rax, %%r14\n\t"
- "movq 48(%[save]), %%rax\n\t"
- "movq %%r15, 48(%[save])\n\t"
- "movq %%rax, %%r15\n\t"
- "movq 64(%[save]), %%rax\n\t"
- "leaq 1f(%%rip), %%rcx\n\t"
- "movq %%rcx, 64(%[save])\n\t"
-
- "jmpq *%%rax\n"
-
- "1:\n"
- : [save] "+D" (save)
- :
- : "rax", "rcx", "rdx", "rsi", "r8", "r9", "r10", "r11", "memory", "cc"
- );
- return 0;
-}
-
-int
-my_context_init(struct my_context *c, size_t stack_size)
-{
- bzero(c, sizeof(*c));
-
- if (!(c->stack_bot= malloc(stack_size)))
- return -1; /* Out of memory */
- /*
- The x86_64 ABI specifies 16-byte stack alignment.
- Also put two zero words at the top of the stack.
- */
- c->stack_top= (void *)
- (( ((intptr)c->stack_bot + stack_size) & ~(intptr)0xf) - 16);
- bzero(c->stack_top, 16);
-
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- c->valgrind_stack_id=
- VALGRIND_STACK_REGISTER(c->stack_bot, c->stack_top);
-#endif
- return 0;
-}
-
-void
-my_context_destroy(struct my_context *c)
-{
- if (c->stack_bot)
- {
- free(c->stack_bot);
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- VALGRIND_STACK_DEREGISTER(c->valgrind_stack_id);
-#endif
- }
- DBUG_FREE_CODE_STATE(&c->dbug_state);
-}
-
-#endif /* MY_CONTEXT_USE_X86_64_GCC_ASM */
-
-
-#ifdef MY_CONTEXT_USE_I386_GCC_ASM
-/*
- GCC-i386 implementation of my_context.
-
- This is slightly optimized in the common case where we never yield
- (eg. fetch next row and it is already fully received in buffer). In this
- case we do not need to restore registers at return (though we still need to
- save them as we cannot know if we will yield or not in advance).
-*/
-
-#include <stdint.h>
-#include <stdlib.h>
-
-/*
- Layout of saved registers etc.
- Since this is accessed through gcc inline assembler, it is simpler to just
- use numbers than to try to define nice constants or structs.
-
- 0 0 %esp
- 1 4 %ebp
- 2 8 %ebx
- 3 12 %esi
- 4 16 %edi
- 5 20 %eip for done
- 6 24 %eip for yield/continue
-*/
-
-int
-my_context_spawn(struct my_context *c, void (*f)(void *), void *d)
-{
- int ret;
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- /*
- There are 4 callee-save registers we need to save and restore when
- suspending and continuing, plus stack pointer %esp and instruction pointer
- %eip.
-
- However, if we never suspend, the user-supplied function will in any case
- restore the 4 callee-save registers, so we can avoid restoring them in
- this case.
- */
- __asm__ __volatile__
- (
- "movl %%esp, (%[save])\n\t"
- "movl %[stack], %%esp\n\t"
-#if (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 4)) && !defined(__INTEL_COMPILER)
- /*
- This emits a DWARF DW_CFA_undefined directive to make the return address
- undefined. This indicates that this is the top of the stack frame, and
- helps tools that use DWARF stack unwinding to obtain stack traces.
- (I use numeric constant to avoid a dependency on libdwarf includes).
- */
- ".cfi_escape 0x07, 8\n\t"
-#endif
- /* Push the parameter on the stack. */
- "pushl %[d]\n\t"
- "movl %%ebp, 4(%[save])\n\t"
- "movl %%ebx, 8(%[save])\n\t"
- "movl %%esi, 12(%[save])\n\t"
- "movl %%edi, 16(%[save])\n\t"
- /* Get label addresses in -fPIC-compatible way (no pc-relative on 32bit) */
- "call 1f\n"
- "1:\n\t"
- "popl %%eax\n\t"
- "addl $(2f-1b), %%eax\n\t"
- "movl %%eax, 20(%[save])\n\t"
- "addl $(3f-2f), %%eax\n\t"
- "movl %%eax, 24(%[save])\n\t"
- "call *%[f]\n\t"
- "jmp *20(%[save])\n"
- /*
- Come here when operation is done.
- We do not need to restore callee-save registers, as the called function
- will do this for us if needed.
- */
- "2:\n\t"
- "movl (%[save]), %%esp\n\t"
- "xorl %[ret], %[ret]\n\t"
- "jmp 4f\n"
- /* Come here when operation was suspended. */
- "3:\n\t"
- "movl $1, %[ret]\n"
- "4:\n"
- : [ret] "=a" (ret),
- [f] "+c" (f),
- [d] "+d" (d)
- : [stack] "a" (c->stack_top),
- /* Need this in callee-save register to preserve across function call. */
- [save] "D" (&c->save[0])
- : "memory", "cc"
- );
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- return ret;
-}
-
-int
-my_context_continue(struct my_context *c)
-{
- int ret;
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- __asm__ __volatile__
- (
- "movl (%[save]), %%eax\n\t"
- "movl %%esp, (%[save])\n\t"
- "movl %%eax, %%esp\n\t"
- "movl 4(%[save]), %%eax\n\t"
- "movl %%ebp, 4(%[save])\n\t"
- "movl %%eax, %%ebp\n\t"
- "movl 8(%[save]), %%eax\n\t"
- "movl %%ebx, 8(%[save])\n\t"
- "movl %%eax, %%ebx\n\t"
- "movl 12(%[save]), %%eax\n\t"
- "movl %%esi, 12(%[save])\n\t"
- "movl %%eax, %%esi\n\t"
-
- "movl 24(%[save]), %%eax\n\t"
- "call 1f\n"
- "1:\n\t"
- "popl %%ecx\n\t"
- "addl $(2f-1b), %%ecx\n\t"
- "movl %%ecx, 20(%[save])\n\t"
- "addl $(3f-2f), %%ecx\n\t"
- "movl %%ecx, 24(%[save])\n\t"
-
- /* Must restore %edi last as it is also our %[save] register. */
- "movl 16(%[save]), %%ecx\n\t"
- "movl %%edi, 16(%[save])\n\t"
- "movl %%ecx, %%edi\n\t"
-
- "jmp *%%eax\n"
- /*
- Come here when operation is done.
- Be sure to use the same callee-save register for %[save] here and in
- my_context_spawn(), so we preserve the value correctly at this point.
- */
- "2:\n\t"
- "movl (%[save]), %%esp\n\t"
- "movl 4(%[save]), %%ebp\n\t"
- "movl 8(%[save]), %%ebx\n\t"
- "movl 12(%[save]), %%esi\n\t"
- "movl 16(%[save]), %%edi\n\t"
- "xorl %[ret], %[ret]\n\t"
- "jmp 4f\n"
- /* Come here when operation is suspended. */
- "3:\n\t"
- "movl $1, %[ret]\n"
- "4:\n"
- : [ret] "=a" (ret)
- : /* Need this in callee-save register to preserve in function call. */
- [save] "D" (&c->save[0])
- : "ecx", "edx", "memory", "cc"
- );
-
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- return ret;
-}
-
-int
-my_context_yield(struct my_context *c)
-{
- uint64_t *save= &c->save[0];
- __asm__ __volatile__
- (
- "movl (%[save]), %%eax\n\t"
- "movl %%esp, (%[save])\n\t"
- "movl %%eax, %%esp\n\t"
- "movl 4(%[save]), %%eax\n\t"
- "movl %%ebp, 4(%[save])\n\t"
- "movl %%eax, %%ebp\n\t"
- "movl 8(%[save]), %%eax\n\t"
- "movl %%ebx, 8(%[save])\n\t"
- "movl %%eax, %%ebx\n\t"
- "movl 12(%[save]), %%eax\n\t"
- "movl %%esi, 12(%[save])\n\t"
- "movl %%eax, %%esi\n\t"
- "movl 16(%[save]), %%eax\n\t"
- "movl %%edi, 16(%[save])\n\t"
- "movl %%eax, %%edi\n\t"
-
- "movl 24(%[save]), %%eax\n\t"
- "call 1f\n"
- "1:\n\t"
- "popl %%ecx\n\t"
- "addl $(2f-1b), %%ecx\n\t"
- "movl %%ecx, 24(%[save])\n\t"
-
- "jmp *%%eax\n"
-
- "2:\n"
- : [save] "+d" (save)
- :
- : "eax", "ecx", "memory", "cc"
- );
- return 0;
-}
-
-int
-my_context_init(struct my_context *c, size_t stack_size)
-{
- bzero(c, sizeof(*c));
- if (!(c->stack_bot= malloc(stack_size)))
- return -1; /* Out of memory */
- c->stack_top= (void *)
- (( ((intptr)c->stack_bot + stack_size) & ~(intptr)0xf) - 16);
- bzero(c->stack_top, 16);
-
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- c->valgrind_stack_id=
- VALGRIND_STACK_REGISTER(c->stack_bot, c->stack_top);
-#endif
- return 0;
-}
-
-void
-my_context_destroy(struct my_context *c)
-{
- if (c->stack_bot)
- {
- free(c->stack_bot);
-#ifdef HAVE_VALGRIND_MEMCHECK_H
- VALGRIND_STACK_DEREGISTER(c->valgrind_stack_id);
-#endif
- }
- DBUG_FREE_CODE_STATE(&c->dbug_state);
-}
-
-#endif /* MY_CONTEXT_USE_I386_GCC_ASM */
-
-
-#ifdef MY_CONTEXT_USE_WIN32_FIBERS
-int
-my_context_yield(struct my_context *c)
-{
- c->return_value= 1;
- SwitchToFiber(c->app_fiber);
- return 0;
-}
-
-
-static void WINAPI
-my_context_trampoline(void *p)
-{
- struct my_context *c= (struct my_context *)p;
- /*
- Reuse the Fiber by looping infinitely, each time we are scheduled we
- spawn the appropriate function and switch back when it is done.
-
- This way we avoid the overhead of CreateFiber() for every asynchroneous
- operation.
- */
- for(;;)
- {
- (*(c->user_func))(c->user_arg);
- c->return_value= 0;
- SwitchToFiber(c->app_fiber);
- }
-}
-
-int
-my_context_init(struct my_context *c, size_t stack_size)
-{
- bzero(c, sizeof(*c));
- c->lib_fiber= CreateFiber(stack_size, my_context_trampoline, c);
- if (c->lib_fiber)
- return 0;
- return -1;
-}
-
-void
-my_context_destroy(struct my_context *c)
-{
- DBUG_FREE_CODE_STATE(&c->dbug_state);
- if (c->lib_fiber)
- {
- DeleteFiber(c->lib_fiber);
- c->lib_fiber= NULL;
- }
-}
-
-int
-my_context_spawn(struct my_context *c, void (*f)(void *), void *d)
-{
- c->user_func= f;
- c->user_arg= d;
- return my_context_continue(c);
-}
-
-int
-my_context_continue(struct my_context *c)
-{
- /*
- This seems to be a common trick to run ConvertThreadToFiber() only on the
- first occurrence in a thread, in a way that works on multiple Windows
- versions.
- */
- void *current_fiber= GetCurrentFiber();
- if (current_fiber == NULL || current_fiber == (void *)0x1e00)
- current_fiber= ConvertThreadToFiber(c);
- c->app_fiber= current_fiber;
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
- SwitchToFiber(c->lib_fiber);
- DBUG_SWAP_CODE_STATE(&c->dbug_state);
-
- return c->return_value;
-}
-
-#endif /* MY_CONTEXT_USE_WIN32_FIBERS */
-
-#ifdef MY_CONTEXT_DISABLE
-int
-my_context_continue(struct my_context *c __attribute__((unused)))
-{
- return -1;
-}
-
-
-int
-my_context_spawn(struct my_context *c __attribute__((unused)),
- void (*f)(void *) __attribute__((unused)),
- void *d __attribute__((unused)))
-{
- return -1;
-}
-
-
-int
-my_context_yield(struct my_context *c __attribute__((unused)))
-{
- return -1;
-}
-
-int
-my_context_init(struct my_context *c __attribute__((unused)),
- size_t stack_size __attribute__((unused)))
-{
- return -1; /* Out of memory */
-}
-
-void
-my_context_destroy(struct my_context *c __attribute__((unused)))
-{
-}
-
-#endif
diff --git a/sql-common/client.c b/sql-common/client.c
index c12b3ef5c0a..5e072a8b538 100644
--- a/sql-common/client.c
+++ b/sql-common/client.c
@@ -100,8 +100,6 @@ my_bool net_flush(NET *net);
#include <ssl_compat.h>
#include <sql_common.h>
#include <mysql/client_plugin.h>
-#include <my_context.h>
-#include <mysql_async.h>
typedef enum {
ALWAYS_ACCEPT, /* heuristics is disabled, use CLIENT_LOCAL_FILES */
@@ -2607,20 +2605,11 @@ int run_plugin_auth(MYSQL *mysql, char *data, uint data_len,
static int
-connect_sync_or_async(MYSQL *mysql, NET *net, my_socket fd,
+connect_sync(MYSQL *mysql, NET *net, my_socket fd,
struct sockaddr *name, uint namelen)
{
int vio_timeout = get_vio_connect_timeout(mysql);
- if (mysql->options.extension && mysql->options.extension->async_context &&
- mysql->options.extension->async_context->active)
- {
- my_bool old_mode;
- vio_blocking(net->vio, FALSE, &old_mode);
- return my_connect_async(mysql->options.extension->async_context, fd,
- name, namelen, vio_timeout);
- }
-
return vio_socket_connect(net->vio, name, namelen, vio_timeout);
}
@@ -2787,7 +2776,7 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
bzero((char*) &UNIXaddr, sizeof(UNIXaddr));
UNIXaddr.sun_family= AF_UNIX;
strmake_buf(UNIXaddr.sun_path, unix_socket);
- if (connect_sync_or_async(mysql, net, sock,
+ if (connect_sync(mysql, net, sock,
(struct sockaddr *) &UNIXaddr, sizeof(UNIXaddr)))
{
DBUG_PRINT("error",("Got error %d on connect to local server",
@@ -2902,7 +2891,7 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
}
DBUG_PRINT("info", ("Connect socket"));
- status= connect_sync_or_async(mysql, net, sock,
+ status= connect_sync(mysql, net, sock,
t_res->ai_addr, (uint)t_res->ai_addrlen);
/*
Here we rely on my_connect() to return success only if the
@@ -2952,9 +2941,6 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
goto error;
}
- if (mysql->options.extension && mysql->options.extension->async_context)
- net->vio->async_context= mysql->options.extension->async_context;
-
if (my_net_init(net, net->vio, _current_thd(), MYF(0)))
{
vio_delete(net->vio);
@@ -3195,42 +3181,16 @@ error:
/* Free alloced memory */
end_server(mysql);
mysql_close_free(mysql);
- if (!(client_flag & CLIENT_REMEMBER_OPTIONS) &&
- !(mysql->options.extension && mysql->options.extension->async_context))
+ if (!(client_flag & CLIENT_REMEMBER_OPTIONS))
mysql_close_free_options(mysql);
}
DBUG_RETURN(0);
}
-struct my_hook_data {
- MYSQL *orig_mysql;
- MYSQL *new_mysql;
- /* This is always NULL currently, but restoring does not hurt just in case. */
- Vio *orig_vio;
-};
-/*
- Callback hook to make the new VIO accessible via the old MYSQL to calling
- application when suspending a non-blocking call during automatic reconnect.
-*/
-static void
-my_suspend_hook(my_bool suspend, void *data)
-{
- struct my_hook_data *hook_data= (struct my_hook_data *)data;
- if (suspend)
- {
- hook_data->orig_vio= hook_data->orig_mysql->net.vio;
- hook_data->orig_mysql->net.vio= hook_data->new_mysql->net.vio;
- }
- else
- hook_data->orig_mysql->net.vio= hook_data->orig_vio;
-}
-
my_bool mysql_reconnect(MYSQL *mysql)
{
MYSQL tmp_mysql;
- struct my_hook_data hook_data;
- struct mysql_async_context *ctxt= NULL;
DBUG_ENTER("mysql_reconnect");
DBUG_ASSERT(mysql);
DBUG_PRINT("enter", ("mysql->reconnect: %d", mysql->reconnect));
@@ -3247,31 +3207,11 @@ my_bool mysql_reconnect(MYSQL *mysql)
tmp_mysql.options= mysql->options;
tmp_mysql.options.my_cnf_file= tmp_mysql.options.my_cnf_group= 0;
- /*
- If we are automatically re-connecting inside a non-blocking API call, we
- may need to suspend and yield to the user application during the reconnect.
- If so, the user application will need access to the new VIO already then
- so that it can correctly wait for I/O to become ready.
- To achieve this, we temporarily install a hook that will temporarily put in
- the VIO while we are suspended.
- (The vio will be put in the original MYSQL permanently once we successfully
- reconnect, or be discarded if we fail to reconnect.)
- */
- if (mysql->options.extension &&
- (ctxt= mysql->options.extension->async_context) &&
- mysql->options.extension->async_context->active)
- {
- hook_data.orig_mysql= mysql;
- hook_data.new_mysql= &tmp_mysql;
- hook_data.orig_vio= mysql->net.vio;
- my_context_install_suspend_resume_hook(ctxt, my_suspend_hook, &hook_data);
- }
+
if (!mysql_real_connect(&tmp_mysql,mysql->host,mysql->user,mysql->passwd,
mysql->db, mysql->port, mysql->unix_socket,
mysql->client_flag | CLIENT_REMEMBER_OPTIONS))
{
- if (ctxt)
- my_context_install_suspend_resume_hook(ctxt, NULL, NULL);
mysql->net.last_errno= tmp_mysql.net.last_errno;
strmov(mysql->net.last_error, tmp_mysql.net.last_error);
strmov(mysql->net.sqlstate, tmp_mysql.net.sqlstate);
@@ -3282,15 +3222,11 @@ my_bool mysql_reconnect(MYSQL *mysql)
DBUG_PRINT("error", ("mysql_set_character_set() failed"));
bzero((char*) &tmp_mysql.options,sizeof(tmp_mysql.options));
mysql_close(&tmp_mysql);
- if (ctxt)
- my_context_install_suspend_resume_hook(ctxt, NULL, NULL);
mysql->net.last_errno= tmp_mysql.net.last_errno;
strmov(mysql->net.last_error, tmp_mysql.net.last_error);
strmov(mysql->net.sqlstate, tmp_mysql.net.sqlstate);
DBUG_RETURN(1);
}
- if (ctxt)
- my_context_install_suspend_resume_hook(ctxt, NULL, NULL);
DBUG_PRINT("info", ("reconnect succeeded"));
tmp_mysql.reconnect= 1;
@@ -3365,15 +3301,9 @@ static void mysql_close_free_options(MYSQL *mysql)
#endif /* HAVE_OPENSSL && !EMBEDDED_LIBRARY */
if (mysql->options.extension)
{
- struct mysql_async_context *ctxt= mysql->options.extension->async_context;
my_free(mysql->options.extension->plugin_dir);
my_free(mysql->options.extension->default_auth);
my_hash_free(&mysql->options.extension->connection_attributes);
- if (ctxt)
- {
- my_context_destroy(&ctxt->async_context);
- my_free(ctxt);
- }
my_free(mysql->options.extension);
}
bzero((char*) &mysql->options,sizeof(mysql->options));
@@ -3806,15 +3736,9 @@ mysql_fetch_lengths(MYSQL_RES *res)
return res->lengths;
}
-
-#define ASYNC_CONTEXT_DEFAULT_STACK_SIZE (4096*15)
-
int STDCALL
mysql_options(MYSQL *mysql,enum mysql_option option, const void *arg)
{
- struct mysql_async_context *ctxt;
- size_t stacksize;
-
DBUG_ENTER("mysql_options");
DBUG_PRINT("enter",("option: %d",(int) option));
switch (option) {
@@ -3910,39 +3834,6 @@ mysql_options(MYSQL *mysql,enum mysql_option option, const void *arg)
(void (*)(const MYSQL *, uint, uint, double, const char *, uint)) arg;
break;
case MYSQL_OPT_NONBLOCK:
- if (mysql->options.extension &&
- (ctxt = mysql->options.extension->async_context) != 0)
- {
- /*
- We must not allow changing the stack size while a non-blocking call is
- suspended (as the stack is then in use).
- */
- if (ctxt->suspended)
- DBUG_RETURN(1);
- my_context_destroy(&ctxt->async_context);
- my_free(ctxt);
- }
- if (!(ctxt= (struct mysql_async_context *)
- my_malloc(PSI_INSTRUMENT_ME, sizeof(*ctxt), MYF(MY_ZEROFILL))))
- {
- set_mysql_error(mysql, CR_OUT_OF_MEMORY, unknown_sqlstate);
- DBUG_RETURN(1);
- }
- stacksize= 0;
- if (arg)
- stacksize= *(const size_t *)arg;
- if (!stacksize)
- stacksize= ASYNC_CONTEXT_DEFAULT_STACK_SIZE;
- if (my_context_init(&ctxt->async_context, stacksize))
- {
- set_mysql_error(mysql, CR_OUT_OF_MEMORY, unknown_sqlstate);
- my_free(ctxt);
- DBUG_RETURN(1);
- }
- ENSURE_EXTENSIONS_PRESENT(&(mysql->options));
- mysql->options.extension->async_context= ctxt;
- if (mysql->net.vio)
- mysql->net.vio->async_context= ctxt;
break;
case MYSQL_OPT_SSL_KEY:
SET_SSL_PATH_OPTION(&mysql->options,ssl_key, arg);
diff --git a/sql-common/mysql_async.c b/sql-common/mysql_async.c
deleted file mode 100644
index a19955c49de..00000000000
--- a/sql-common/mysql_async.c
+++ /dev/null
@@ -1,1995 +0,0 @@
-/*
- Copyright 2011 Kristian Nielsen and Monty Program Ab
-
- This file is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-/*
- MySQL non-blocking client library functions.
-*/
-
-#include "my_global.h"
-#include "my_sys.h"
-#include "mysql.h"
-#include "errmsg.h"
-#include "sql_common.h"
-#include "my_context.h"
-#include "violite.h"
-#include "mysql_async.h"
-
-
-#ifdef __WIN__
-/*
- Windows does not support MSG_DONTWAIT for send()/recv(). So we need to ensure
- that the socket is non-blocking at the start of every operation.
-*/
-#define WIN_SET_NONBLOCKING(mysql) { \
- my_bool old_mode; \
- if ((mysql)->net.vio) vio_blocking((mysql)->net.vio, FALSE, &old_mode); \
- }
-#else
-#define WIN_SET_NONBLOCKING(mysql)
-#endif
-
-
-void
-my_context_install_suspend_resume_hook(struct mysql_async_context *b,
- void (*hook)(my_bool, void *),
- void *user_data)
-{
- b->suspend_resume_hook= hook;
- b->suspend_resume_hook_user_data= user_data;
-}
-
-
-/* Asynchronous connect(); socket must already be set non-blocking. */
-int
-my_connect_async(struct mysql_async_context *b, my_socket fd,
- const struct sockaddr *name, uint namelen, int vio_timeout)
-{
- int res;
- size_socket s_err_size;
-
- /* Make the socket non-blocking. */
-#ifdef __WIN__
- ulong arg= 1;
- ioctlsocket(fd, FIONBIO, (void *)&arg);
-#else
- fcntl(fd, F_SETFL, O_NONBLOCK);
-#endif
-
- b->events_to_wait_for= 0;
- /*
- Start to connect asynchronously.
- If this will block, we suspend the call and return control to the
- application context. The application will then resume us when the socket
- polls ready for write, indicating that the connection attempt completed.
- */
- res= connect(fd, name, namelen);
- if (res != 0)
- {
-#ifdef __WIN__
- int wsa_err= WSAGetLastError();
- if (wsa_err != WSAEWOULDBLOCK)
- return res;
- b->events_to_wait_for|= MYSQL_WAIT_EXCEPT;
-#else
- int err= errno;
- if (err != EINPROGRESS && err != EALREADY && err != EAGAIN)
- return res;
-#endif
- b->events_to_wait_for|= MYSQL_WAIT_WRITE;
- if (vio_timeout >= 0)
- {
- b->timeout_value= vio_timeout;
- b->events_to_wait_for|= MYSQL_WAIT_TIMEOUT;
- }
- else
- b->timeout_value= 0;
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(TRUE, b->suspend_resume_hook_user_data);
- my_context_yield(&b->async_context);
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(FALSE, b->suspend_resume_hook_user_data);
- if (b->events_occurred & MYSQL_WAIT_TIMEOUT)
- return -1;
-
- s_err_size= sizeof(res);
- if (getsockopt(fd, SOL_SOCKET, SO_ERROR, (char*) &res, &s_err_size) != 0)
- return -1;
- if (res)
- {
- errno= res;
- return -1;
- }
- }
- return res;
-}
-
-#define IS_BLOCKING_ERROR() \
- IF_WIN(WSAGetLastError() != WSAEWOULDBLOCK, \
- (errno != EAGAIN && errno != EINTR))
-
-#ifdef _AIX
-#ifndef MSG_DONTWAIT
-#define MSG_DONTWAIT 0
-#endif
-#endif
-
-ssize_t
-my_recv_async(struct mysql_async_context *b, my_socket fd,
- unsigned char *buf, size_t size, int timeout)
-{
- ssize_t res;
-
- for (;;)
- {
- res= recv(fd, buf, (int)size, IF_WIN(0, MSG_DONTWAIT));
- if (res >= 0 || IS_BLOCKING_ERROR())
- return res;
- b->events_to_wait_for= MYSQL_WAIT_READ;
- if (timeout >= 0)
- {
- b->events_to_wait_for|= MYSQL_WAIT_TIMEOUT;
- b->timeout_value= timeout;
- }
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(TRUE, b->suspend_resume_hook_user_data);
- my_context_yield(&b->async_context);
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(FALSE, b->suspend_resume_hook_user_data);
- if (b->events_occurred & MYSQL_WAIT_TIMEOUT)
- return -1;
- }
-}
-
-
-ssize_t
-my_send_async(struct mysql_async_context *b, my_socket fd,
- const unsigned char *buf, size_t size, int timeout)
-{
- ssize_t res;
-
- for (;;)
- {
- res= send(fd, buf, (int)size, IF_WIN(0, MSG_DONTWAIT));
- if (res >= 0 || IS_BLOCKING_ERROR())
- return res;
- b->events_to_wait_for= MYSQL_WAIT_WRITE;
- if (timeout >= 0)
- {
- b->events_to_wait_for|= MYSQL_WAIT_TIMEOUT;
- b->timeout_value= timeout;
- }
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(TRUE, b->suspend_resume_hook_user_data);
- my_context_yield(&b->async_context);
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(FALSE, b->suspend_resume_hook_user_data);
- if (b->events_occurred & MYSQL_WAIT_TIMEOUT)
- return -1;
- }
-}
-
-
-my_bool
-my_io_wait_async(struct mysql_async_context *b, enum enum_vio_io_event event,
- int timeout)
-{
- switch (event)
- {
- case VIO_IO_EVENT_READ:
- b->events_to_wait_for = MYSQL_WAIT_READ;
- break;
- case VIO_IO_EVENT_WRITE:
- b->events_to_wait_for = MYSQL_WAIT_WRITE;
- break;
- case VIO_IO_EVENT_CONNECT:
- b->events_to_wait_for = MYSQL_WAIT_WRITE | IF_WIN(0, MYSQL_WAIT_EXCEPT);
- break;
- }
-
- if (timeout >= 0)
- {
- b->events_to_wait_for |= MYSQL_WAIT_TIMEOUT;
- b->timeout_value= timeout;
- }
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(TRUE, b->suspend_resume_hook_user_data);
- my_context_yield(&b->async_context);
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(FALSE, b->suspend_resume_hook_user_data);
- return (b->events_occurred & MYSQL_WAIT_TIMEOUT) ? 0 : 1;
-}
-
-
-#ifdef HAVE_OPENSSL
-static my_bool
-my_ssl_async_check_result(int res, struct mysql_async_context *b, SSL *ssl)
-{
- int ssl_err;
- b->events_to_wait_for= 0;
- if (res >= 0)
- return 1;
- ssl_err= SSL_get_error(ssl, res);
- if (ssl_err == SSL_ERROR_WANT_READ)
- b->events_to_wait_for|= MYSQL_WAIT_READ;
- else if (ssl_err == SSL_ERROR_WANT_WRITE)
- b->events_to_wait_for|= MYSQL_WAIT_WRITE;
- else
- return 1;
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(TRUE, b->suspend_resume_hook_user_data);
- my_context_yield(&b->async_context);
- if (b->suspend_resume_hook)
- (*b->suspend_resume_hook)(FALSE, b->suspend_resume_hook_user_data);
- return 0;
-}
-
-int
-my_ssl_read_async(struct mysql_async_context *b, SSL *ssl,
- void *buf, int size)
-{
- int res;
-
- for (;;)
- {
- res= SSL_read(ssl, buf, size);
- if (my_ssl_async_check_result(res, b, ssl))
- return res;
- }
-}
-
-int
-my_ssl_write_async(struct mysql_async_context *b, SSL *ssl,
- const void *buf, int size)
-{
- int res;
-
- for (;;)
- {
- res= SSL_write(ssl, buf, size);
- if (my_ssl_async_check_result(res, b, ssl))
- return res;
- }
-}
-#endif /* HAVE_OPENSSL */
-
-/*
- Legacy support of the MariaDB 5.5 version, where timeouts where only in
- seconds resolution. Applications that use this will be asked to set a timeout
- at the nearest higher whole-seconds value.
-*/
-unsigned int STDCALL
-mysql_get_timeout_value(const MYSQL *mysql)
-{
- unsigned int timeout= mysql->options.extension->async_context->timeout_value;
- /* Avoid overflow. */
- if (timeout > UINT_MAX - 999)
- return (timeout - 1)/1000 + 1;
- else
- return (timeout+999)/1000;
-}
-
-
-unsigned int STDCALL
-mysql_get_timeout_value_ms(const MYSQL *mysql)
-{
- return mysql->options.extension->async_context->timeout_value;
-}
-
-
-/*
- Now create non-blocking definitions for all the calls that may block.
-
- Each call FOO gives rise to FOO_start() that prepares the MYSQL object for
- doing non-blocking calls that can suspend operation mid-way, and then starts
- the call itself. And a FOO_start_internal trampoline to assist with running
- the real call in a co-routine that can be suspended. And a FOO_cont() that
- can continue a suspended operation.
-*/
-
-#define MK_ASYNC_INTERNAL_BODY(call, invoke_args, mysql_val, ret_type, ok_val)\
- struct call ## _params *parms= (struct call ## _params *)d; \
- ret_type ret; \
- struct mysql_async_context *b= \
- (mysql_val)->options.extension->async_context; \
- \
- ret= call invoke_args; \
- b->ret_result. ok_val = ret; \
- b->events_to_wait_for= 0;
-
-#define MK_ASYNC_START_BODY(call, mysql_val, parms_assign, err_val, ok_val, extra1) \
- int res; \
- struct mysql_async_context *b; \
- struct call ## _params parms; \
- \
- extra1 \
- b= mysql_val->options.extension->async_context; \
- parms_assign \
- \
- b->active= 1; \
- res= my_context_spawn(&b->async_context, call ## _start_internal, &parms); \
- b->active= b->suspended= 0; \
- if (res > 0) \
- { \
- /* Suspended. */ \
- b->suspended= 1; \
- return b->events_to_wait_for; \
- } \
- if (res < 0) \
- { \
- set_mysql_error((mysql_val), CR_OUT_OF_MEMORY, unknown_sqlstate); \
- *ret= err_val; \
- } \
- else \
- *ret= b->ret_result. ok_val; \
- return 0;
-
-#define MK_ASYNC_CONT_BODY(mysql_val, err_val, ok_val) \
- int res; \
- struct mysql_async_context *b= \
- (mysql_val)->options.extension->async_context; \
- if (!b->suspended) \
- { \
- set_mysql_error((mysql_val), CR_COMMANDS_OUT_OF_SYNC, unknown_sqlstate); \
- *ret= err_val; \
- return 0; \
- } \
- \
- b->active= 1; \
- b->events_occurred= ready_status; \
- res= my_context_continue(&b->async_context); \
- b->active= 0; \
- if (res > 0) \
- return b->events_to_wait_for; /* (Still) suspended */ \
- b->suspended= 0; \
- if (res < 0) \
- { \
- set_mysql_error((mysql_val), CR_OUT_OF_MEMORY, unknown_sqlstate); \
- *ret= err_val; \
- } \
- else \
- *ret= b->ret_result. ok_val; /* Finished. */ \
- return 0;
-
-#define MK_ASYNC_INTERNAL_BODY_VOID_RETURN(call, invoke_args, mysql_val) \
- struct call ## _params *parms= (struct call ## _params *)d; \
- struct mysql_async_context *b= \
- (mysql_val)->options.extension->async_context; \
- \
- call invoke_args; \
- b->events_to_wait_for= 0;
-
-#define MK_ASYNC_START_BODY_VOID_RETURN(call, mysql_val, parms_assign, extra1)\
- int res; \
- struct mysql_async_context *b; \
- struct call ## _params parms; \
- \
- extra1 \
- b= mysql_val->options.extension->async_context; \
- parms_assign \
- \
- b->active= 1; \
- res= my_context_spawn(&b->async_context, call ## _start_internal, &parms); \
- b->active= b->suspended= 0; \
- if (res > 0) \
- { \
- /* Suspended. */ \
- b->suspended= 1; \
- return b->events_to_wait_for; \
- } \
- if (res < 0) \
- set_mysql_error((mysql_val), CR_OUT_OF_MEMORY, unknown_sqlstate); \
- return 0;
-
-#define MK_ASYNC_CONT_BODY_VOID_RETURN(mysql_val) \
- int res; \
- struct mysql_async_context *b= \
- (mysql_val)->options.extension->async_context; \
- if (!b->suspended) \
- { \
- set_mysql_error((mysql_val), CR_COMMANDS_OUT_OF_SYNC, unknown_sqlstate); \
- return 0; \
- } \
- \
- b->active= 1; \
- b->events_occurred= ready_status; \
- res= my_context_continue(&b->async_context); \
- b->active= 0; \
- if (res > 0) \
- return b->events_to_wait_for; /* (Still) suspended */ \
- b->suspended= 0; \
- if (res < 0) \
- set_mysql_error((mysql_val), CR_OUT_OF_MEMORY, unknown_sqlstate); \
- return 0;
-
-
-/* Structure used to pass parameters from mysql_real_connect_start(). */
-struct mysql_real_connect_params {
- MYSQL *mysql;
- const char *host;
- const char *user;
- const char *passwd;
- const char *db;
- unsigned int port;
- const char *unix_socket;
- unsigned long client_flags;
-};
-static void
-mysql_real_connect_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_real_connect,
- (parms->mysql, parms->host, parms->user, parms->passwd, parms->db,
- parms->port, parms->unix_socket, parms->client_flags),
- parms->mysql,
- MYSQL *,
- r_ptr)
-}
-int STDCALL
-mysql_real_connect_start(MYSQL **ret, MYSQL *mysql, const char *host,
- const char *user, const char *passwd, const char *db,
- unsigned int port, const char *unix_socket,
- unsigned long client_flags)
-{
-MK_ASYNC_START_BODY(
- mysql_real_connect,
- mysql,
- {
- parms.mysql= mysql;
- parms.host= host;
- parms.user= user;
- parms.passwd= passwd;
- parms.db= db;
- parms.port= port;
- parms.unix_socket= unix_socket;
- /*
- async wrapper enforce the CLIENT_REMEMBER_OPTIONS flag to be
- functional (otherwise it can't operate)
- */
- parms.client_flags= client_flags | CLIENT_REMEMBER_OPTIONS;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_real_connect_cont(MYSQL **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_real_query_start(). */
-struct mysql_real_query_params {
- MYSQL *mysql;
- const char *stmt_str;
- unsigned long length;
-};
-static void
-mysql_real_query_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_real_query,
- (parms->mysql, parms->stmt_str, parms->length),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_real_query_start(int *ret, MYSQL *mysql, const char *stmt_str, unsigned long length)
-{
-MK_ASYNC_START_BODY(
- mysql_real_query,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.stmt_str= stmt_str;
- parms.length= length;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_real_query_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_fetch_row_start(). */
-struct mysql_fetch_row_params {
- MYSQL_RES *result;
-};
-static void
-mysql_fetch_row_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_fetch_row,
- (parms->result),
- parms->result->handle,
- MYSQL_ROW,
- r_ptr)
-}
-int STDCALL
-mysql_fetch_row_start(MYSQL_ROW *ret, MYSQL_RES *result)
-{
-MK_ASYNC_START_BODY(
- mysql_fetch_row,
- result->handle,
- {
- WIN_SET_NONBLOCKING(result->handle)
- parms.result= result;
- },
- NULL,
- r_ptr,
- /*
- If we already fetched all rows from server (eg. mysql_store_result()),
- then result->handle will be NULL and we cannot suspend. But that is fine,
- since in this case mysql_fetch_row cannot block anyway. Just return
- directly.
- */
- if (!result->handle)
- {
- *ret= mysql_fetch_row(result);
- return 0;
- })
-}
-int STDCALL
-mysql_fetch_row_cont(MYSQL_ROW *ret, MYSQL_RES *result, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- result->handle,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_set_character_set_start(). */
-struct mysql_set_character_set_params {
- MYSQL *mysql;
- const char *csname;
-};
-static void
-mysql_set_character_set_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_set_character_set,
- (parms->mysql, parms->csname),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_set_character_set_start(int *ret, MYSQL *mysql, const char *csname)
-{
-MK_ASYNC_START_BODY(
- mysql_set_character_set,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.csname= csname;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_set_character_set_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_sekect_db_start(). */
-struct mysql_select_db_params {
- MYSQL *mysql;
- const char *db;
-};
-static void
-mysql_select_db_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_select_db,
- (parms->mysql, parms->db),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_select_db_start(int *ret, MYSQL *mysql, const char *db)
-{
-MK_ASYNC_START_BODY(
- mysql_select_db,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.db= db;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_select_db_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_send_query_start(). */
-struct mysql_send_query_params {
- MYSQL *mysql;
- const char *q;
- unsigned long length;
-};
-static void
-mysql_send_query_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_send_query,
- (parms->mysql, parms->q, parms->length),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_send_query_start(int *ret, MYSQL *mysql, const char *q, unsigned long length)
-{
-MK_ASYNC_START_BODY(
- mysql_send_query,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.q= q;
- parms.length= length;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_send_query_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_store_result_start(). */
-struct mysql_store_result_params {
- MYSQL *mysql;
-};
-static void
-mysql_store_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_store_result,
- (parms->mysql),
- parms->mysql,
- MYSQL_RES *,
- r_ptr)
-}
-int STDCALL
-mysql_store_result_start(MYSQL_RES **ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_store_result,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_store_result_cont(MYSQL_RES **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_free_result_start(). */
-struct mysql_free_result_params {
- MYSQL_RES *result;
-};
-static void
-mysql_free_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY_VOID_RETURN(
- mysql_free_result,
- (parms->result),
- parms->result->handle)
-}
-int STDCALL
-mysql_free_result_start(MYSQL_RES *result)
-{
-MK_ASYNC_START_BODY_VOID_RETURN(
- mysql_free_result,
- result->handle,
- {
- WIN_SET_NONBLOCKING(result->handle)
- parms.result= result;
- },
- /*
- mysql_free_result() can have NULL in result->handle (this happens when all
- rows have been fetched and mysql_fetch_row() returned NULL.)
- So we cannot suspend, but it does not matter, as in this case
- mysql_free_result() cannot block.
- It is also legitimate to have NULL result, which will do nothing.
- */
- if (!result || !result->handle)
- {
- mysql_free_result(result);
- return 0;
- })
-}
-int STDCALL
-mysql_free_result_cont(MYSQL_RES *result, int ready_status)
-{
-MK_ASYNC_CONT_BODY_VOID_RETURN(result->handle)
-}
-
-/* Structure used to pass parameters from mysql_close_slow_part_start(). */
-struct mysql_close_slow_part_params {
- MYSQL *sock;
-};
-/*
- We need special handling for mysql_close(), as the first part may block,
- while the last part needs to free our extra library context stack.
-
- So we do the first part (mysql_close_slow_part()) non-blocking, but the last
- part blocking.
-*/
-static void
-mysql_close_slow_part_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY_VOID_RETURN(
- mysql_close_slow_part,
- (parms->sock),
- parms->sock)
-}
-int STDCALL
-mysql_close_slow_part_start(MYSQL *sock)
-{
-MK_ASYNC_START_BODY_VOID_RETURN(
- mysql_close_slow_part,
- sock,
- {
- WIN_SET_NONBLOCKING(sock)
- parms.sock= sock;
- },
- /* Nothing */)
-}
-int STDCALL
-mysql_close_slow_part_cont(MYSQL *sock, int ready_status)
-{
-MK_ASYNC_CONT_BODY_VOID_RETURN(sock)
-}
-int STDCALL
-mysql_close_start(MYSQL *sock)
-{
- int res;
-
- /* It is legitimate to have NULL sock argument, which will do nothing. */
- if (sock)
- {
- res= mysql_close_slow_part_start(sock);
- /* If we need to block, return now and do the rest in mysql_close_cont(). */
- if (res)
- return res;
- }
- mysql_close(sock);
- return 0;
-}
-int STDCALL
-mysql_close_cont(MYSQL *sock, int ready_status)
-{
- int res;
-
- res= mysql_close_slow_part_cont(sock, ready_status);
- if (res)
- return res;
- mysql_close(sock);
- return 0;
-}
-
-/*
- These following are not available inside the server (neither blocking or
- non-blocking).
-*/
-#ifndef MYSQL_SERVER
-/* Structure used to pass parameters from mysql_change_user_start(). */
-struct mysql_change_user_params {
- MYSQL *mysql;
- const char *user;
- const char *passwd;
- const char *db;
-};
-static void
-mysql_change_user_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_change_user,
- (parms->mysql, parms->user, parms->passwd, parms->db),
- parms->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_change_user_start(my_bool *ret, MYSQL *mysql, const char *user, const char *passwd, const char *db)
-{
-MK_ASYNC_START_BODY(
- mysql_change_user,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.user= user;
- parms.passwd= passwd;
- parms.db= db;
- },
- TRUE,
- r_my_bool,
- /* Nothing */)
-}
-int STDCALL
-mysql_change_user_cont(my_bool *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_query_start(). */
-struct mysql_query_params {
- MYSQL *mysql;
- const char *q;
-};
-static void
-mysql_query_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_query,
- (parms->mysql, parms->q),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_query_start(int *ret, MYSQL *mysql, const char *q)
-{
-MK_ASYNC_START_BODY(
- mysql_query,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.q= q;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_query_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_shutdown_start(). */
-struct mysql_shutdown_params {
- MYSQL *mysql;
- enum mysql_enum_shutdown_level shutdown_level;
-};
-static void
-mysql_shutdown_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_shutdown,
- (parms->mysql, parms->shutdown_level),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_shutdown_start(int *ret, MYSQL *mysql, enum mysql_enum_shutdown_level shutdown_level)
-{
-MK_ASYNC_START_BODY(
- mysql_shutdown,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.shutdown_level= shutdown_level;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_shutdown_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_dump_debug_info_start(). */
-struct mysql_dump_debug_info_params {
- MYSQL *mysql;
-};
-static void
-mysql_dump_debug_info_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_dump_debug_info,
- (parms->mysql),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_dump_debug_info_start(int *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_dump_debug_info,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_dump_debug_info_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_refresh_start(). */
-struct mysql_refresh_params {
- MYSQL *mysql;
- unsigned int refresh_options;
-};
-static void
-mysql_refresh_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_refresh,
- (parms->mysql, parms->refresh_options),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_refresh_start(int *ret, MYSQL *mysql, unsigned int refresh_options)
-{
-MK_ASYNC_START_BODY(
- mysql_refresh,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.refresh_options= refresh_options;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_refresh_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_kill_start(). */
-struct mysql_kill_params {
- MYSQL *mysql;
- unsigned long pid;
-};
-static void
-mysql_kill_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_kill,
- (parms->mysql, parms->pid),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_kill_start(int *ret, MYSQL *mysql, unsigned long pid)
-{
-MK_ASYNC_START_BODY(
- mysql_kill,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.pid= pid;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_kill_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_set_server_option_start(). */
-struct mysql_set_server_option_params {
- MYSQL *mysql;
- enum enum_mysql_set_option option;
-};
-static void
-mysql_set_server_option_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_set_server_option,
- (parms->mysql, parms->option),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_set_server_option_start(int *ret, MYSQL *mysql,
- enum enum_mysql_set_option option)
-{
-MK_ASYNC_START_BODY(
- mysql_set_server_option,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.option= option;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_set_server_option_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_ping_start(). */
-struct mysql_ping_params {
- MYSQL *mysql;
-};
-static void
-mysql_ping_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_ping,
- (parms->mysql),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_ping_start(int *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_ping,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_ping_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stat_start(). */
-struct mysql_stat_params {
- MYSQL *mysql;
-};
-static void
-mysql_stat_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stat,
- (parms->mysql),
- parms->mysql,
- const char *,
- r_const_ptr)
-}
-int STDCALL
-mysql_stat_start(const char **ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_stat,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- NULL,
- r_const_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_stat_cont(const char **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_const_ptr)
-}
-
-/* Structure used to pass parameters from mysql_list_dbs_start(). */
-struct mysql_list_dbs_params {
- MYSQL *mysql;
- const char *wild;
-};
-static void
-mysql_list_dbs_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_list_dbs,
- (parms->mysql, parms->wild),
- parms->mysql,
- MYSQL_RES *,
- r_ptr)
-}
-int STDCALL
-mysql_list_dbs_start(MYSQL_RES **ret, MYSQL *mysql, const char *wild)
-{
-MK_ASYNC_START_BODY(
- mysql_list_dbs,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.wild= wild;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_list_dbs_cont(MYSQL_RES **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_list_tables_start(). */
-struct mysql_list_tables_params {
- MYSQL *mysql;
- const char *wild;
-};
-static void
-mysql_list_tables_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_list_tables,
- (parms->mysql, parms->wild),
- parms->mysql,
- MYSQL_RES *,
- r_ptr)
-}
-int STDCALL
-mysql_list_tables_start(MYSQL_RES **ret, MYSQL *mysql, const char *wild)
-{
-MK_ASYNC_START_BODY(
- mysql_list_tables,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.wild= wild;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_list_tables_cont(MYSQL_RES **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_list_processes_start(). */
-struct mysql_list_processes_params {
- MYSQL *mysql;
-};
-static void
-mysql_list_processes_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_list_processes,
- (parms->mysql),
- parms->mysql,
- MYSQL_RES *,
- r_ptr)
-}
-int STDCALL
-mysql_list_processes_start(MYSQL_RES **ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_list_processes,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_list_processes_cont(MYSQL_RES **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_list_fields_start(). */
-struct mysql_list_fields_params {
- MYSQL *mysql;
- const char *table;
- const char *wild;
-};
-static void
-mysql_list_fields_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_list_fields,
- (parms->mysql, parms->table, parms->wild),
- parms->mysql,
- MYSQL_RES *,
- r_ptr)
-}
-int STDCALL
-mysql_list_fields_start(MYSQL_RES **ret, MYSQL *mysql, const char *table,
- const char *wild)
-{
-MK_ASYNC_START_BODY(
- mysql_list_fields,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.table= table;
- parms.wild= wild;
- },
- NULL,
- r_ptr,
- /* Nothing */)
-}
-int STDCALL
-mysql_list_fields_cont(MYSQL_RES **ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- NULL,
- r_ptr)
-}
-
-/* Structure used to pass parameters from mysql_read_query_result_start(). */
-struct mysql_read_query_result_params {
- MYSQL *mysql;
-};
-static void
-mysql_read_query_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_read_query_result,
- (parms->mysql),
- parms->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_read_query_result_start(my_bool *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_read_query_result,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- TRUE,
- r_my_bool,
- /* Nothing */)
-}
-int STDCALL
-mysql_read_query_result_cont(my_bool *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_stmt_prepare_start(). */
-struct mysql_stmt_prepare_params {
- MYSQL_STMT *stmt;
- const char *query;
- unsigned long length;
-};
-static void
-mysql_stmt_prepare_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_prepare,
- (parms->stmt, parms->query, parms->length),
- parms->stmt->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_stmt_prepare_start(int *ret, MYSQL_STMT *stmt, const char *query,
- unsigned long length)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_prepare,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- parms.query= query;
- parms.length= length;
- },
- 1,
- r_int,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_prepare(stmt, query, length);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_prepare_cont(int *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stmt_execute_start(). */
-struct mysql_stmt_execute_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_execute_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_execute,
- (parms->stmt),
- parms->stmt->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_stmt_execute_start(int *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_execute,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- 1,
- r_int,
- /*
- If eg. mysql_change_user(), stmt->mysql will be NULL.
- In this case, we cannot block.
- */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_execute(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_execute_cont(int *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stmt_fetch_start(). */
-struct mysql_stmt_fetch_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_fetch_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_fetch,
- (parms->stmt),
- parms->stmt->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_stmt_fetch_start(int *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_fetch,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- 1,
- r_int,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_fetch(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_fetch_cont(int *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stmt_store_result_start(). */
-struct mysql_stmt_store_result_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_store_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_store_result,
- (parms->stmt),
- parms->stmt->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_stmt_store_result_start(int *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_store_result,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- 1,
- r_int,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_store_result(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_store_result_cont(int *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stmt_close_start(). */
-struct mysql_stmt_close_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_close_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_close,
- (parms->stmt),
- parms->stmt->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_stmt_close_start(my_bool *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_close,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- TRUE,
- r_my_bool,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_close(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_close_cont(my_bool *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_stmt_reset_start(). */
-struct mysql_stmt_reset_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_reset_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_reset,
- (parms->stmt),
- parms->stmt->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_stmt_reset_start(my_bool *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_reset,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- TRUE,
- r_my_bool,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_reset(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_reset_cont(my_bool *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_stmt_free_result_start(). */
-struct mysql_stmt_free_result_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_free_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_free_result,
- (parms->stmt),
- parms->stmt->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_stmt_free_result_start(my_bool *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_free_result,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- TRUE,
- r_my_bool,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_free_result(stmt);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_free_result_cont(my_bool *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_stmt_send_long_data_start(). */
-struct mysql_stmt_send_long_data_params {
- MYSQL_STMT *stmt;
- unsigned int param_number;
- const char *data;
- unsigned long length;
-};
-static void
-mysql_stmt_send_long_data_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_send_long_data,
- (parms->stmt, parms->param_number, parms->data, parms->length),
- parms->stmt->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_stmt_send_long_data_start(my_bool *ret, MYSQL_STMT *stmt,
- unsigned int param_number,
- const char *data, unsigned long length)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_send_long_data,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- parms.param_number= param_number;
- parms.data= data;
- parms.length= length;
- },
- TRUE,
- r_my_bool,
- /* If stmt->mysql==NULL then we will not block so can call directly. */
- if (!stmt->mysql)
- {
- *ret= mysql_stmt_send_long_data(stmt, param_number, data, length);
- return 0;
- })
-}
-int STDCALL
-mysql_stmt_send_long_data_cont(my_bool *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_commit_start(). */
-struct mysql_commit_params {
- MYSQL *mysql;
-};
-static void
-mysql_commit_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_commit,
- (parms->mysql),
- parms->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_commit_start(my_bool *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_commit,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- TRUE,
- r_my_bool,
- /* Nothing */)
-}
-int STDCALL
-mysql_commit_cont(my_bool *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_rollback_start(). */
-struct mysql_rollback_params {
- MYSQL *mysql;
-};
-static void
-mysql_rollback_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_rollback,
- (parms->mysql),
- parms->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_rollback_start(my_bool *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_rollback,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- TRUE,
- r_my_bool,
- /* Nothing */)
-}
-int STDCALL
-mysql_rollback_cont(my_bool *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_autocommit_start(). */
-struct mysql_autocommit_params {
- MYSQL *mysql;
- my_bool auto_mode;
-};
-static void
-mysql_autocommit_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_autocommit,
- (parms->mysql, parms->auto_mode),
- parms->mysql,
- my_bool,
- r_my_bool)
-}
-int STDCALL
-mysql_autocommit_start(my_bool *ret, MYSQL *mysql, my_bool auto_mode)
-{
-MK_ASYNC_START_BODY(
- mysql_autocommit,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- parms.auto_mode= auto_mode;
- },
- TRUE,
- r_my_bool,
- /* Nothing */)
-}
-int STDCALL
-mysql_autocommit_cont(my_bool *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- TRUE,
- r_my_bool)
-}
-
-/* Structure used to pass parameters from mysql_next_result_start(). */
-struct mysql_next_result_params {
- MYSQL *mysql;
-};
-static void
-mysql_next_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_next_result,
- (parms->mysql),
- parms->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_next_result_start(int *ret, MYSQL *mysql)
-{
-MK_ASYNC_START_BODY(
- mysql_next_result,
- mysql,
- {
- WIN_SET_NONBLOCKING(mysql)
- parms.mysql= mysql;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_next_result_cont(int *ret, MYSQL *mysql, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- mysql,
- 1,
- r_int)
-}
-
-/* Structure used to pass parameters from mysql_stmt_next_result_start(). */
-struct mysql_stmt_next_result_params {
- MYSQL_STMT *stmt;
-};
-static void
-mysql_stmt_next_result_start_internal(void *d)
-{
-MK_ASYNC_INTERNAL_BODY(
- mysql_stmt_next_result,
- (parms->stmt),
- parms->stmt->mysql,
- int,
- r_int)
-}
-int STDCALL
-mysql_stmt_next_result_start(int *ret, MYSQL_STMT *stmt)
-{
-MK_ASYNC_START_BODY(
- mysql_stmt_next_result,
- stmt->mysql,
- {
- WIN_SET_NONBLOCKING(stmt->mysql)
- parms.stmt= stmt;
- },
- 1,
- r_int,
- /* Nothing */)
-}
-int STDCALL
-mysql_stmt_next_result_cont(int *ret, MYSQL_STMT *stmt, int ready_status)
-{
-MK_ASYNC_CONT_BODY(
- stmt->mysql,
- 1,
- r_int)
-}
-#endif
-
-
-/*
- The following functions are deprecated, and so have no non-blocking version:
-
- mysql_connect
- mysql_create_db
- mysql_drop_db
-*/
-
-/*
- The following functions can newer block, and so do not have special
- non-blocking versions:
-
- mysql_num_rows()
- mysql_num_fields()
- mysql_eof()
- mysql_fetch_field_direct()
- mysql_fetch_fields()
- mysql_row_tell()
- mysql_field_tell()
- mysql_field_count()
- mysql_affected_rows()
- mysql_insert_id()
- mysql_errno()
- mysql_error()
- mysql_sqlstate()
- mysql_warning_count()
- mysql_info()
- mysql_thread_id()
- mysql_character_set_name()
- mysql_init()
- mysql_ssl_set()
- mysql_get_ssl_cipher()
- mysql_use_result()
- mysql_get_character_set_info()
- mysql_set_local_infile_handler()
- mysql_set_local_infile_default()
- mysql_get_server_info()
- mysql_get_server_name()
- mysql_get_client_info()
- mysql_get_client_version()
- mysql_get_host_info()
- mysql_get_server_version()
- mysql_get_proto_info()
- mysql_options()
- mysql_data_seek()
- mysql_row_seek()
- mysql_field_seek()
- mysql_fetch_lengths()
- mysql_fetch_field()
- mysql_escape_string()
- mysql_hex_string()
- mysql_real_escape_string()
- mysql_debug()
- myodbc_remove_escape()
- mysql_thread_safe()
- mysql_embedded()
- mariadb_connection()
- mysql_stmt_init()
- mysql_stmt_fetch_column()
- mysql_stmt_param_count()
- mysql_stmt_attr_set()
- mysql_stmt_attr_get()
- mysql_stmt_bind_param()
- mysql_stmt_bind_result()
- mysql_stmt_result_metadata()
- mysql_stmt_param_metadata()
- mysql_stmt_errno()
- mysql_stmt_error()
- mysql_stmt_sqlstate()
- mysql_stmt_row_seek()
- mysql_stmt_row_tell()
- mysql_stmt_data_seek()
- mysql_stmt_num_rows()
- mysql_stmt_affected_rows()
- mysql_stmt_insert_id()
- mysql_stmt_field_count()
- mysql_more_results()
- mysql_get_socket()
- mysql_get_timeout_value()
-*/
diff --git a/sql/CMakeLists.txt b/sql/CMakeLists.txt
index 1a53db4aa61..b11f74aef45 100644
--- a/sql/CMakeLists.txt
+++ b/sql/CMakeLists.txt
@@ -139,7 +139,6 @@ SET (SQL_SOURCE
opt_index_cond_pushdown.cc opt_subselect.cc
opt_table_elimination.cc sql_expression_cache.cc
gcalc_slicescan.cc gcalc_tools.cc
- ../sql-common/mysql_async.c
my_apc.cc mf_iocache_encr.cc item_jsonfunc.cc
my_json_writer.cc
rpl_gtid.cc rpl_parallel.cc
diff --git a/tests/mysql_client_fw.c b/tests/mysql_client_fw.c
index aea0562672c..bcf62eb0e18 100644
--- a/tests/mysql_client_fw.c
+++ b/tests/mysql_client_fw.c
@@ -31,9 +31,8 @@
and use poll()/select() to wait for them to complete. This way we can get
a good coverage testing of the non-blocking API as well.
*/
-#include <my_context.h>
static my_bool non_blocking_api_enabled= 0;
-#if !defined(EMBEDDED_LIBRARY) && !defined(MY_CONTEXT_DISABLE)
+#if !defined(EMBEDDED_LIBRARY)
#define WRAP_NONBLOCK_ENABLED non_blocking_api_enabled
#include "nonblock-wrappers.h"
#endif
diff --git a/vio/viosocket.c b/vio/viosocket.c
index 9cad035161c..f84d0e0738b 100644
--- a/vio/viosocket.c
+++ b/vio/viosocket.c
@@ -31,8 +31,6 @@
#include <mstcpip.h>
#pragma comment(lib, "ws2_32.lib")
#endif
-#include "my_context.h"
-#include <mysql_async.h>
#ifdef FIONREAD_IN_SYS_FILIO
# include <sys/filio.h>
@@ -171,34 +169,18 @@ size_t vio_read(Vio *vio, uchar *buf, size_t size)
if (vio->read_timeout >= 0)
flags= VIO_DONTWAIT;
- if (vio->async_context && vio->async_context->active)
- ret= my_recv_async(vio->async_context,
- mysql_socket_getfd(vio->mysql_socket),
- buf, size, vio->read_timeout);
- else
+ while ((ret= mysql_socket_recv(vio->mysql_socket, (SOCKBUF_T *)buf, size,
+ flags)) == -1)
{
- if (vio->async_context)
- {
- /*
- If switching from non-blocking to blocking API usage, set the socket
- back to blocking mode.
- */
- my_bool old_mode;
- vio_blocking(vio, TRUE, &old_mode);
- }
- while ((ret= mysql_socket_recv(vio->mysql_socket, (SOCKBUF_T *)buf, size,
- flags)) == -1)
- {
- int error= socket_errno;
+ int error= socket_errno;
- /* The operation would block? */
- if (error != SOCKET_EAGAIN && error != SOCKET_EWOULDBLOCK)
- break;
+ /* The operation would block? */
+ if (error != SOCKET_EAGAIN && error != SOCKET_EWOULDBLOCK)
+ break;
- /* Wait for input data to become available. */
- if ((ret= vio_socket_io_wait(vio, VIO_IO_EVENT_READ)))
- break;
- }
+ /* Wait for input data to become available. */
+ if ((ret= vio_socket_io_wait(vio, VIO_IO_EVENT_READ)))
+ break;
}
#ifndef DBUG_OFF
if (ret == -1)
@@ -282,33 +264,17 @@ size_t vio_write(Vio *vio, const uchar* buf, size_t size)
if (vio->write_timeout >= 0)
flags= VIO_DONTWAIT;
- if (vio->async_context && vio->async_context->active)
- ret= my_send_async(vio->async_context,
- mysql_socket_getfd(vio->mysql_socket), buf, size,
- vio->write_timeout);
- else
+ while ((ret= mysql_socket_send(vio->mysql_socket, (SOCKBUF_T *)buf, size,
+ flags)) == -1)
{
- if (vio->async_context)
- {
- /*
- If switching from non-blocking to blocking API usage, set the socket
- back to blocking mode.
- */
- my_bool old_mode;
- vio_blocking(vio, TRUE, &old_mode);
- }
- while ((ret= mysql_socket_send(vio->mysql_socket, (SOCKBUF_T *)buf, size,
- flags)) == -1)
- {
- int error= socket_errno;
- /* The operation would block? */
- if (error != SOCKET_EAGAIN && error != SOCKET_EWOULDBLOCK)
- break;
-
- /* Wait for the output buffer to become writable.*/
- if ((ret= vio_socket_io_wait(vio, VIO_IO_EVENT_WRITE)))
- break;
- }
+ int error= socket_errno;
+ /* The operation would block? */
+ if (error != SOCKET_EAGAIN && error != SOCKET_EWOULDBLOCK)
+ break;
+
+ /* Wait for the output buffer to become writable.*/
+ if ((ret= vio_socket_io_wait(vio, VIO_IO_EVENT_WRITE)))
+ break;
}
#ifndef DBUG_OFF
if (ret == -1)
@@ -953,24 +919,6 @@ int vio_io_wait(Vio *vio, enum enum_vio_io_event event, int timeout)
DBUG_ENTER("vio_io_wait");
DBUG_PRINT("enter", ("timeout: %d", timeout));
- /*
- Note that if zero timeout, then we will not block, so we do not need to
- yield to calling application in the async case.
- */
- if (timeout != 0 && vio->async_context && vio->async_context->active)
- {
- START_SOCKET_WAIT(locker, &state, vio->mysql_socket,
- PSI_SOCKET_SELECT, timeout);
- ret= my_io_wait_async(vio->async_context, event, timeout);
- if (ret == 0)
- {
- DBUG_PRINT("info", ("timeout"));
- errno= SOCKET_ETIMEDOUT;
- }
- END_SOCKET_WAIT(locker,timeout);
- DBUG_RETURN(ret);
- }
-
memset(&pfd, 0, sizeof(pfd));
pfd.fd= sd;
@@ -1032,21 +980,6 @@ int vio_io_wait(Vio *vio, enum enum_vio_io_event event, int timeout)
MYSQL_SOCKET_WAIT_VARIABLES(locker, state) /* no ';' */
DBUG_ENTER("vio_io_wait");
- /*
- Note that if zero timeout, then we will not block, so we do not need to
- yield to calling application in the async case.
- */
- if (timeout != 0 && vio->async_context && vio->async_context->active)
- {
- START_SOCKET_WAIT(locker, &state, vio->mysql_socket,
- PSI_SOCKET_SELECT, timeout);
- ret= my_io_wait_async(vio->async_context, event, timeout);
- if (ret == 0)
- WSASetLastError(SOCKET_ETIMEDOUT);
- END_SOCKET_WAIT(locker, timeout);
- DBUG_RETURN(ret);
- }
-
/* Convert the timeout, in milliseconds, to seconds and microseconds. */
if (timeout >= 0)
{
diff --git a/vio/viossl.c b/vio/viossl.c
index a5b3396953e..04bc0e41ae9 100644
--- a/vio/viossl.c
+++ b/vio/viossl.c
@@ -21,8 +21,6 @@
*/
#include "vio_priv.h"
-#include "my_context.h"
-#include <mysql_async.h>
#ifdef HAVE_OPENSSL
@@ -129,21 +127,17 @@ size_t vio_ssl_read(Vio *vio, uchar *buf, size_t size)
(int)mysql_socket_getfd(vio->mysql_socket), buf, size,
vio->ssl_arg));
- if (vio->async_context && vio->async_context->active)
- ret= my_ssl_read_async(vio->async_context, (SSL *)vio->ssl_arg, buf, (int)size);
- else
+
+ while ((ret= SSL_read(ssl, buf, (int)size)) < 0)
{
- while ((ret= SSL_read(ssl, buf, (int)size)) < 0)
- {
- enum enum_vio_io_event event;
+ enum enum_vio_io_event event;
- /* Process the SSL I/O error. */
- if (!ssl_should_retry(vio, ret, &event))
- break;
- /* Attempt to wait for an I/O event. */
- if (vio_socket_io_wait(vio, event))
- break;
- }
+ /* Process the SSL I/O error. */
+ if (!ssl_should_retry(vio, ret, &event))
+ break;
+ /* Attempt to wait for an I/O event. */
+ if (vio_socket_io_wait(vio, event))
+ break;
}
DBUG_PRINT("exit", ("%d", (int) ret));
@@ -160,24 +154,17 @@ size_t vio_ssl_write(Vio *vio, const uchar *buf, size_t size)
DBUG_PRINT("enter", ("sd: %d buf: %p size: %zu",
(int)mysql_socket_getfd(vio->mysql_socket),
buf, size));
-
- if (vio->async_context && vio->async_context->active)
- ret= my_ssl_write_async(vio->async_context, (SSL *)vio->ssl_arg, buf,
- (int)size);
- else
+ while ((ret= SSL_write(ssl, buf, (int)size)) < 0)
{
- while ((ret= SSL_write(ssl, buf, (int)size)) < 0)
- {
- enum enum_vio_io_event event;
+ enum enum_vio_io_event event;
- /* Process the SSL I/O error. */
- if (!ssl_should_retry(vio, ret, &event))
- break;
+ /* Process the SSL I/O error. */
+ if (!ssl_should_retry(vio, ret, &event))
+ break;
- /* Attempt to wait for an I/O event. */
- if (vio_socket_io_wait(vio, event))
- break;
- }
+ /* Attempt to wait for an I/O event. */
+ if (vio_socket_io_wait(vio, event))
+ break;
}
DBUG_RETURN(ret < 0 ? -1 : ret);