Commit 55988e53 authored by unknown's avatar unknown

Merge mysql.com:/home/wax/mysql-4n into mysql.com:/home/wax/mysql-4sm

parents d9e524c2 64f40ef4
...@@ -90,6 +90,7 @@ venu@myvenu.com ...@@ -90,6 +90,7 @@ venu@myvenu.com
venu@work.mysql.com venu@work.mysql.com
vva@genie.(none) vva@genie.(none)
walrus@mysql.com walrus@mysql.com
wax@mysql.com
worm@altair.is.lan worm@altair.is.lan
zak@balfor.local zak@balfor.local
zak@linux.local zak@linux.local
......
...@@ -37,4 +37,5 @@ enum options { OPT_CHARSETS_DIR=256, OPT_DEFAULT_CHARSET, ...@@ -37,4 +37,5 @@ enum options { OPT_CHARSETS_DIR=256, OPT_DEFAULT_CHARSET,
OPT_SELECT_LIMIT, OPT_MAX_JOIN_SIZE, OPT_SSL_SSL, OPT_SELECT_LIMIT, OPT_MAX_JOIN_SIZE, OPT_SSL_SSL,
OPT_SSL_KEY, OPT_SSL_CERT, OPT_SSL_CA, OPT_SSL_CAPATH, OPT_SSL_KEY, OPT_SSL_CERT, OPT_SSL_CA, OPT_SSL_CAPATH,
OPT_SSL_CIPHER, OPT_SHUTDOWN_TIMEOUT, OPT_LOCAL_INFILE, OPT_SSL_CIPHER, OPT_SHUTDOWN_TIMEOUT, OPT_LOCAL_INFILE,
OPT_PROMPT, OPT_IGN_LINES,OPT_TRANSACTION }; OPT_PROMPT, OPT_IGN_LINES,OPT_TRANSACTION,OPT_MYSQL_PROTOCOL,
OPT_SHARED_MEMORY_BASE_NAME };
...@@ -152,6 +152,11 @@ static FILE *PAGER, *OUTFILE; ...@@ -152,6 +152,11 @@ static FILE *PAGER, *OUTFILE;
static MEM_ROOT hash_mem_root; static MEM_ROOT hash_mem_root;
static uint prompt_counter; static uint prompt_counter;
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
#include "sslopt-vars.h" #include "sslopt-vars.h"
#ifndef DBUG_OFF #ifndef DBUG_OFF
...@@ -425,6 +430,9 @@ sig_handler mysql_end(int sig) ...@@ -425,6 +430,9 @@ sig_handler mysql_end(int sig)
my_free(full_username,MYF(MY_ALLOW_ZERO_PTR)); my_free(full_username,MYF(MY_ALLOW_ZERO_PTR));
my_free(part_username,MYF(MY_ALLOW_ZERO_PTR)); my_free(part_username,MYF(MY_ALLOW_ZERO_PTR));
my_free(default_prompt,MYF(MY_ALLOW_ZERO_PTR)); my_free(default_prompt,MYF(MY_ALLOW_ZERO_PTR));
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
my_free(current_prompt,MYF(MY_ALLOW_ZERO_PTR)); my_free(current_prompt,MYF(MY_ALLOW_ZERO_PTR));
mysql_server_end(); mysql_server_end();
free_defaults(defaults_argv); free_defaults(defaults_argv);
...@@ -532,6 +540,8 @@ static struct my_option my_long_options[] = ...@@ -532,6 +540,8 @@ static struct my_option my_long_options[] =
{"prompt", OPT_PROMPT, "Set the mysql prompt to this value.", {"prompt", OPT_PROMPT, "Set the mysql prompt to this value.",
(gptr*) &current_prompt, (gptr*) &current_prompt, 0, GET_STR_ALLOC, (gptr*) &current_prompt, (gptr*) &current_prompt, 0, GET_STR_ALLOC,
REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"protocol", OPT_MYSQL_PROTOCOL, "The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"quick", 'q', {"quick", 'q',
"Don't cache result, print it row by row. This may slow down the server if the output is suspended. Doesn't use history file. ", "Don't cache result, print it row by row. This may slow down the server if the output is suspended. Doesn't use history file. ",
(gptr*) &quick, (gptr*) &quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, (gptr*) &quick, (gptr*) &quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
...@@ -540,6 +550,11 @@ static struct my_option my_long_options[] = ...@@ -540,6 +550,11 @@ static struct my_option my_long_options[] =
0, 0, 0}, 0, 0, 0},
{"silent", 's', "Be more silent.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, {"silent", 's', "Be more silent.", 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0,
0, 0}, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
(gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR_ALLOC, (gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR_ALLOC,
REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
...@@ -644,6 +659,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -644,6 +659,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
case OPT_NOPAGER: case OPT_NOPAGER:
printf("WARNING: option deprecated; use --disable-pager instead.\n"); printf("WARNING: option deprecated; use --disable-pager instead.\n");
opt_nopager= 1; opt_nopager= 1;
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
break; break;
case 'A': case 'A':
rehash= 0; rehash= 0;
...@@ -706,7 +730,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -706,7 +730,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
case 'W': case 'W':
#ifdef __WIN__ #ifdef __WIN__
opt_mysql_unix_port= my_strdup(MYSQL_NAMEDPIPE, MYF(0)); opt_protocol = MYSQL_PROTOCOL_PIPE;
#endif #endif
break; break;
#include <sslopt-case.h> #include <sslopt-case.h>
...@@ -2349,6 +2373,12 @@ sql_real_connect(char *host,char *database,char *user,char *password, ...@@ -2349,6 +2373,12 @@ sql_real_connect(char *host,char *database,char *user,char *password,
if (opt_use_ssl) if (opt_use_ssl)
mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif
if (opt_protocol)
mysql_options(&mysql,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif #endif
if (safe_updates) if (safe_updates)
{ {
......
...@@ -23,6 +23,7 @@ ...@@ -23,6 +23,7 @@
#include <my_pthread.h> /* because of signal() */ #include <my_pthread.h> /* because of signal() */
#endif #endif
#include <sys/stat.h> #include <sys/stat.h>
#include <mysql.h>
#define ADMIN_VERSION "8.38" #define ADMIN_VERSION "8.38"
#define MAX_MYSQL_VAR 128 #define MAX_MYSQL_VAR 128
...@@ -42,6 +43,11 @@ static uint tcp_port = 0, option_wait = 0, option_silent=0, nr_iterations, ...@@ -42,6 +43,11 @@ static uint tcp_port = 0, option_wait = 0, option_silent=0, nr_iterations,
static ulong opt_connect_timeout, opt_shutdown_timeout; static ulong opt_connect_timeout, opt_shutdown_timeout;
static my_string unix_port=0; static my_string unix_port=0;
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
/* /*
When using extended-status relatively, ex_val_max_len is the estimated When using extended-status relatively, ex_val_max_len is the estimated
maximum length for any relative value printed by extended-status. The maximum length for any relative value printed by extended-status. The
...@@ -135,6 +141,8 @@ static struct my_option my_long_options[] = ...@@ -135,6 +141,8 @@ static struct my_option my_long_options[] =
#endif #endif
{"port", 'P', "Port number to use for connection.", (gptr*) &tcp_port, {"port", 'P', "Port number to use for connection.", (gptr*) &tcp_port,
(gptr*) &tcp_port, 0, GET_UINT, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, (gptr*) &tcp_port, 0, GET_UINT, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"protocol", OPT_MYSQL_PROTOCOL, "The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"relative", 'r', {"relative", 'r',
"Show difference between current and previous values when used with -i. Currently works only with extended-status.", "Show difference between current and previous values when used with -i. Currently works only with extended-status.",
(gptr*) &opt_relative, (gptr*) &opt_relative, 0, GET_BOOL, NO_ARG, 0, 0, 0, (gptr*) &opt_relative, (gptr*) &opt_relative, 0, GET_BOOL, NO_ARG, 0, 0, 0,
...@@ -142,6 +150,11 @@ static struct my_option my_long_options[] = ...@@ -142,6 +150,11 @@ static struct my_option my_long_options[] =
{"set-variable", 'O', {"set-variable", 'O',
"Change the value of a variable. Please note that this option is deprecated; you can set variables directly with --variable-name=value.", "Change the value of a variable. Please note that this option is deprecated; you can set variables directly with --variable-name=value.",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"silent", 's', "Silently exit if one can't connect to server", {"silent", 's', "Silently exit if one can't connect to server",
0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
...@@ -205,7 +218,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -205,7 +218,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
case 'W': case 'W':
#ifdef __WIN__ #ifdef __WIN__
unix_port=MYSQL_NAMEDPIPE; opt_protocol = MYSQL_PROTOCOL_PIPE;
#endif #endif
break; break;
case '#': case '#':
...@@ -234,6 +247,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -234,6 +247,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
charsets_dir = argument; charsets_dir = argument;
#endif #endif
break; break;
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
} }
if (error) if (error)
{ {
...@@ -284,6 +306,12 @@ int main(int argc,char *argv[]) ...@@ -284,6 +306,12 @@ int main(int argc,char *argv[])
mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif #endif
if (opt_protocol)
mysql_options(&mysql,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif
if (sql_connect(&mysql, option_wait)) if (sql_connect(&mysql, option_wait))
error = 1; error = 1;
else else
...@@ -326,6 +354,9 @@ int main(int argc,char *argv[]) ...@@ -326,6 +354,9 @@ int main(int argc,char *argv[])
} }
my_free(opt_password,MYF(MY_ALLOW_ZERO_PTR)); my_free(opt_password,MYF(MY_ALLOW_ZERO_PTR));
my_free(user,MYF(MY_ALLOW_ZERO_PTR)); my_free(user,MYF(MY_ALLOW_ZERO_PTR));
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
free_defaults(save_argv); free_defaults(save_argv);
my_end(0); my_end(0);
exit(error ? 1 : 0); exit(error ? 1 : 0);
......
...@@ -41,6 +41,10 @@ static char *opt_password = 0, *current_user = 0, *default_charset = 0, ...@@ -41,6 +41,10 @@ static char *opt_password = 0, *current_user = 0, *default_charset = 0,
*current_host = 0; *current_host = 0;
static int first_error = 0; static int first_error = 0;
DYNAMIC_ARRAY tables4repair; DYNAMIC_ARRAY tables4repair;
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
enum operations {DO_CHECK, DO_REPAIR, DO_ANALYZE, DO_OPTIMIZE}; enum operations {DO_CHECK, DO_REPAIR, DO_ANALYZE, DO_OPTIMIZE};
...@@ -109,6 +113,8 @@ static struct my_option my_long_options[] = ...@@ -109,6 +113,8 @@ static struct my_option my_long_options[] =
{"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port, {"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port,
(gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0, (gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0,
0}, 0},
{"protocol", OPT_MYSQL_PROTOCOL, "The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"quick", 'q', {"quick", 'q',
"If you are using this option with CHECK TABLE, it prevents the check from scanning the rows to check for wrong links. This is the fastest check. If you are using this option with REPAIR TABLE, it will try to repair only the index tree. This is the fastest repair method for a table.", "If you are using this option with CHECK TABLE, it prevents the check from scanning the rows to check for wrong links. This is the fastest check. If you are using this option with REPAIR TABLE, it will try to repair only the index tree. This is the fastest repair method for a table.",
(gptr*) &opt_quick, (gptr*) &opt_quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, (gptr*) &opt_quick, (gptr*) &opt_quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0,
...@@ -116,6 +122,11 @@ static struct my_option my_long_options[] = ...@@ -116,6 +122,11 @@ static struct my_option my_long_options[] =
{"repair", 'r', {"repair", 'r',
"Can fix almost anything except unique keys that aren't unique.", "Can fix almost anything except unique keys that aren't unique.",
0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0}, 0, 0, 0, GET_NO_ARG, NO_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"silent", 's', "Print only error messages.", (gptr*) &opt_silent, {"silent", 's', "Print only error messages.", (gptr*) &opt_silent,
(gptr*) &opt_silent, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, (gptr*) &opt_silent, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
...@@ -233,7 +244,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -233,7 +244,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
case 'W': case 'W':
#ifdef __WIN__ #ifdef __WIN__
opt_mysql_unix_port = MYSQL_NAMEDPIPE; opt_protocol = MYSQL_PROTOCOL_PIPE;
#endif #endif
break; break;
case '#': case '#':
...@@ -247,6 +258,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -247,6 +258,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
verbose++; verbose++;
break; break;
case 'V': print_version(); exit(0); case 'V': print_version(); exit(0);
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
} }
return 0; return 0;
} }
...@@ -533,6 +553,12 @@ static int dbConnect(char *host, char *user, char *passwd) ...@@ -533,6 +553,12 @@ static int dbConnect(char *host, char *user, char *passwd)
if (opt_use_ssl) if (opt_use_ssl)
mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif
if (opt_protocol)
mysql_options(&mysql_connection,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql_connection,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif #endif
if (!(sock = mysql_real_connect(&mysql_connection, host, user, passwd, if (!(sock = mysql_real_connect(&mysql_connection, host, user, passwd,
NULL, opt_mysql_port, opt_mysql_unix_port, 0))) NULL, opt_mysql_port, opt_mysql_unix_port, 0)))
...@@ -621,6 +647,9 @@ int main(int argc, char **argv) ...@@ -621,6 +647,9 @@ int main(int argc, char **argv)
if (opt_auto_repair) if (opt_auto_repair)
delete_dynamic(&tables4repair); delete_dynamic(&tables4repair);
my_free(opt_password, MYF(MY_ALLOW_ZERO_PTR)); my_free(opt_password, MYF(MY_ALLOW_ZERO_PTR));
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
my_end(0); my_end(0);
return(first_error!=0); return(first_error!=0);
} /* main */ } /* main */
...@@ -90,6 +90,10 @@ extern ulong net_buffer_length; ...@@ -90,6 +90,10 @@ extern ulong net_buffer_length;
static DYNAMIC_STRING extended_row; static DYNAMIC_STRING extended_row;
#include <sslopt-vars.h> #include <sslopt-vars.h>
FILE *md_result_file; FILE *md_result_file;
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
static struct my_option my_long_options[] = static struct my_option my_long_options[] =
{ {
...@@ -200,6 +204,8 @@ static struct my_option my_long_options[] = ...@@ -200,6 +204,8 @@ static struct my_option my_long_options[] =
{"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port, {"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port,
(gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0, (gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0,
0}, 0},
{"protocol", OPT_MYSQL_PROTOCOL, "The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"quick", 'q', "Don't buffer query, dump directly to stdout.", {"quick", 'q', "Don't buffer query, dump directly to stdout.",
(gptr*) &quick, (gptr*) &quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, (gptr*) &quick, (gptr*) &quick, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
{"quote-names",'Q', "Quote table and column names with a `", {"quote-names",'Q', "Quote table and column names with a `",
...@@ -208,6 +214,11 @@ static struct my_option my_long_options[] = ...@@ -208,6 +214,11 @@ static struct my_option my_long_options[] =
{"result-file", 'r', {"result-file", 'r',
"Direct output to a given file. This option should be used in MSDOS, because it prevents new line '\\n' from being converted to '\\r\\n' (carriage return + line feed).", "Direct output to a given file. This option should be used in MSDOS, because it prevents new line '\\n' from being converted to '\\r\\n' (carriage return + line feed).",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
(gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR, (gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR,
REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
...@@ -338,7 +349,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -338,7 +349,7 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
case 'W': case 'W':
#ifdef __WIN__ #ifdef __WIN__
opt_mysql_unix_port=MYSQL_NAMEDPIPE; opt_protocol = MYSQL_PROTOCOL_PIPE;
#endif #endif
break; break;
case 'T': case 'T':
...@@ -365,6 +376,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -365,6 +376,15 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
case (int) OPT_TABLES: case (int) OPT_TABLES:
opt_databases=0; opt_databases=0;
break; break;
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
} }
return 0; return 0;
} }
...@@ -473,6 +493,12 @@ static int dbConnect(char *host, char *user,char *passwd) ...@@ -473,6 +493,12 @@ static int dbConnect(char *host, char *user,char *passwd)
if (opt_use_ssl) if (opt_use_ssl)
mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif
if (opt_protocol)
mysql_options(&mysql_connection,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql_connection,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif #endif
if (!(sock= mysql_real_connect(&mysql_connection,host,user,passwd, if (!(sock= mysql_real_connect(&mysql_connection,host,user,passwd,
NULL,opt_mysql_port,opt_mysql_unix_port, NULL,opt_mysql_port,opt_mysql_unix_port,
...@@ -1471,6 +1497,9 @@ int main(int argc, char **argv) ...@@ -1471,6 +1497,9 @@ int main(int argc, char **argv)
MYF(0), mysql_error(sock)); MYF(0), mysql_error(sock));
} }
else if (opt_single_transaction) /* Just to make it beautiful enough */ else if (opt_single_transaction) /* Just to make it beautiful enough */
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
{ {
/* /*
In case we were locking all tables, we did not start transaction In case we were locking all tables, we did not start transaction
......
...@@ -49,6 +49,11 @@ static my_string opt_mysql_unix_port=0; ...@@ -49,6 +49,11 @@ static my_string opt_mysql_unix_port=0;
static my_string opt_ignore_lines=0; static my_string opt_ignore_lines=0;
#include <sslopt-vars.h> #include <sslopt-vars.h>
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
static struct my_option my_long_options[] = static struct my_option my_long_options[] =
{ {
{"character-sets-dir", OPT_CHARSETS_DIR, {"character-sets-dir", OPT_CHARSETS_DIR,
...@@ -112,8 +117,15 @@ static struct my_option my_long_options[] = ...@@ -112,8 +117,15 @@ static struct my_option my_long_options[] =
{"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port, {"port", 'P', "Port number to use for connection.", (gptr*) &opt_mysql_port,
(gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0, (gptr*) &opt_mysql_port, 0, GET_UINT, REQUIRED_ARG, MYSQL_PORT, 0, 0, 0, 0,
0}, 0},
{"protocol", OPT_MYSQL_PROTOCOL,"The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
{"replace", 'r', "If duplicate unique key was found, replace old row.", {"replace", 'r', "If duplicate unique key was found, replace old row.",
(gptr*) &replace, (gptr*) &replace, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, (gptr*) &replace, (gptr*) &replace, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"silent", 's', "Be more silent.", (gptr*) &silent, (gptr*) &silent, 0, {"silent", 's', "Be more silent.", (gptr*) &silent, (gptr*) &silent, 0,
GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0}, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
...@@ -181,10 +193,19 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -181,10 +193,19 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
#ifdef __WIN__ #ifdef __WIN__
case 'W': case 'W':
opt_mysql_unix_port=MYSQL_NAMEDPIPE; opt_protocol = MYSQL_PROTOCOL_PIPE;
opt_local_file=1; opt_local_file=1;
break; break;
#endif #endif
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
case '#': case '#':
DBUG_PUSH(argument ? argument : "d:t:o"); DBUG_PUSH(argument ? argument : "d:t:o");
break; break;
...@@ -351,6 +372,12 @@ static MYSQL *db_connect(char *host, char *database, char *user, char *passwd) ...@@ -351,6 +372,12 @@ static MYSQL *db_connect(char *host, char *database, char *user, char *passwd)
if (opt_use_ssl) if (opt_use_ssl)
mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql_connection, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif
if (opt_protocol)
mysql_options(&mysql_connection,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql_connection,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif #endif
if (!(sock= mysql_real_connect(&mysql_connection,host,user,passwd, if (!(sock= mysql_real_connect(&mysql_connection,host,user,passwd,
database,opt_mysql_port,opt_mysql_unix_port, database,opt_mysql_port,opt_mysql_unix_port,
...@@ -486,6 +513,9 @@ int main(int argc, char **argv) ...@@ -486,6 +513,9 @@ int main(int argc, char **argv)
exitcode = error; exitcode = error;
db_disconnect(current_host, sock); db_disconnect(current_host, sock);
my_free(opt_password,MYF(MY_ALLOW_ZERO_PTR)); my_free(opt_password,MYF(MY_ALLOW_ZERO_PTR));
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
free_defaults(argv_to_free); free_defaults(argv_to_free);
my_end(0); my_end(0);
return(exitcode); return(exitcode);
......
...@@ -31,6 +31,11 @@ static my_string host=0,opt_password=0,user=0; ...@@ -31,6 +31,11 @@ static my_string host=0,opt_password=0,user=0;
static my_bool opt_show_keys=0,opt_compress=0,opt_status=0, tty_password=0; static my_bool opt_show_keys=0,opt_compress=0,opt_status=0, tty_password=0;
static uint opt_verbose=0; static uint opt_verbose=0;
#ifdef HAVE_SMEM
static char *shared_memory_base_name=0;
#endif
static uint opt_protocol=0;
static void get_options(int *argc,char ***argv); static void get_options(int *argc,char ***argv);
static uint opt_mysql_port=0; static uint opt_mysql_port=0;
static int list_dbs(MYSQL *mysql,const char *wild); static int list_dbs(MYSQL *mysql,const char *wild);
...@@ -86,6 +91,12 @@ int main(int argc, char **argv) ...@@ -86,6 +91,12 @@ int main(int argc, char **argv)
if (opt_use_ssl) if (opt_use_ssl)
mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca, mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
opt_ssl_capath, opt_ssl_cipher); opt_ssl_capath, opt_ssl_cipher);
#endif
if (opt_protocol)
mysql_options(&mysql,MYSQL_OPT_PROTOCOL,(char*)&opt_protocol);
#ifdef HAVE_SMEM
if (shared_memory_base_name)
mysql_options(&mysql,MYSQL_SHARED_MEMORY_BASE_NAME,shared_memory_base_name);
#endif #endif
if (!(mysql_real_connect(&mysql,host,user,opt_password, if (!(mysql_real_connect(&mysql,host,user,opt_password,
argv[0],opt_mysql_port,opt_mysql_unix_port, argv[0],opt_mysql_port,opt_mysql_unix_port,
...@@ -114,6 +125,9 @@ int main(int argc, char **argv) ...@@ -114,6 +125,9 @@ int main(int argc, char **argv)
mysql_close(&mysql); /* Close & free connection */ mysql_close(&mysql); /* Close & free connection */
if (opt_password) if (opt_password)
my_free(opt_password,MYF(0)); my_free(opt_password,MYF(0));
#ifdef HAVE_SMEM
my_free(shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif
my_end(0); my_end(0);
exit(error ? 1 : 0); exit(error ? 1 : 0);
return 0; /* No compiler warnings */ return 0; /* No compiler warnings */
...@@ -147,6 +161,13 @@ static struct my_option my_long_options[] = ...@@ -147,6 +161,13 @@ static struct my_option my_long_options[] =
#ifdef __WIN__ #ifdef __WIN__
{"pipe", 'W', "Use named pipes to connect to server.", 0, 0, 0, GET_NO_ARG, {"pipe", 'W', "Use named pipes to connect to server.", 0, 0, 0, GET_NO_ARG,
NO_ARG, 0, 0, 0, 0, 0, 0}, NO_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"protocol", OPT_MYSQL_PROTOCOL,"The protocol of connection (tcp,socket,pipe,memory)",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name", OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR_ALLOC, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif #endif
{"socket", 'S', "Socket file to use for connection.", {"socket", 'S', "Socket file to use for connection.",
(gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR, (gptr*) &opt_mysql_unix_port, (gptr*) &opt_mysql_unix_port, 0, GET_STR,
...@@ -213,9 +234,18 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), ...@@ -213,9 +234,18 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)),
break; break;
case 'W': case 'W':
#ifdef __WIN__ #ifdef __WIN__
opt_mysql_unix_port=MYSQL_NAMEDPIPE; opt_protocol = MYSQL_PROTOCOL_PIPE;
#endif #endif
break; break;
case OPT_MYSQL_PROTOCOL:
{
if ((opt_protocol = find_type(argument, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", argument);
exit(1);
}
break;
}
case '#': case '#':
DBUG_PUSH(argument ? argument : "d:t:o"); DBUG_PUSH(argument ? argument : "d:t:o");
break; break;
......
...@@ -23,6 +23,8 @@ ...@@ -23,6 +23,8 @@
#include <io.h> #include <io.h>
#include <malloc.h> #include <malloc.h>
#define HAVE_SMEM 1
#if defined(__NT__) #if defined(__NT__)
#define SYSTEM_TYPE "NT" #define SYSTEM_TYPE "NT"
#elif defined(__WIN2000__) #elif defined(__WIN2000__)
...@@ -311,3 +313,6 @@ inline double ulonglong2double(ulonglong value) ...@@ -311,3 +313,6 @@ inline double ulonglong2double(ulonglong value)
#define statistic_add(V,C,L) (V)+=(C) #define statistic_add(V,C,L) (V)+=(C)
#endif #endif
#define statistic_increment(V,L) thread_safe_increment((V),(L)) #define statistic_increment(V,L) thread_safe_increment((V),(L))
#define shared_memory_buffer_length 16000
#define default_shared_memory_base_name "MYSQL";
...@@ -72,3 +72,15 @@ extern const char *client_errors[]; /* Error messages */ ...@@ -72,3 +72,15 @@ extern const char *client_errors[]; /* Error messages */
#define CR_INVALID_PARAMETER_NO 2032 #define CR_INVALID_PARAMETER_NO 2032
#define CR_INVALID_BUFFER_USE 2033 #define CR_INVALID_BUFFER_USE 2033
#define CR_UNSUPPORTED_PARAM_TYPE 2034 #define CR_UNSUPPORTED_PARAM_TYPE 2034
#define CR_SHARED_MEMORY_CONNECTION 2035
#define CR_SHARED_MEMORY_CONNECT_REQUEST_ERROR 2036
#define CR_SHARED_MEMORY_CONNECT_ANSWER_ERROR 2037
#define CR_SHARED_MEMORY_CONNECT_FILE_MAP_ERROR 2038
#define CR_SHARED_MEMORY_CONNECT_MAP_ERROR 2039
#define CR_SHARED_MEMORY_FILE_MAP_ERROR 2040
#define CR_SHARED_MEMORY_MAP_ERROR 2041
#define CR_SHARED_MEMORY_EVENT_ERROR 2042
#define CR_SHARED_MEMORY_CONNECT_ABANDODED_ERROR 2043
#define CR_SHARED_MEMORY_CONNECT_SET_ERROR 2046
#define CR_CONN_UNKNOW_PROTOCOL 2048
...@@ -37,6 +37,7 @@ extern int NEAR my_errno; /* Last error in mysys */ ...@@ -37,6 +37,7 @@ extern int NEAR my_errno; /* Last error in mysys */
#endif #endif
#include <stdarg.h> #include <stdarg.h>
#include <typelib.h>
#define MYSYS_PROGRAM_USES_CURSES() { error_handler_hook = my_message_curses; mysys_uses_curses=1; } #define MYSYS_PROGRAM_USES_CURSES() { error_handler_hook = my_message_curses; mysys_uses_curses=1; }
#define MYSYS_PROGRAM_DONT_USE_CURSES() { error_handler_hook = my_message_no_curses; mysys_uses_curses=0;} #define MYSYS_PROGRAM_DONT_USE_CURSES() { error_handler_hook = my_message_no_curses; mysys_uses_curses=0;}
...@@ -247,12 +248,6 @@ typedef struct wild_file_pack /* Struct to hold info when selecting files */ ...@@ -247,12 +248,6 @@ typedef struct wild_file_pack /* Struct to hold info when selecting files */
my_string *wild; /* Pointer to wildcards */ my_string *wild; /* Pointer to wildcards */
} WF_PACK; } WF_PACK;
typedef struct st_typelib { /* Different types saved here */
uint count; /* How many types */
const char *name; /* Name of typelib */
const char **type_names;
} TYPELIB;
enum cache_type enum cache_type
{ {
READ_CACHE,WRITE_CACHE, READ_CACHE,WRITE_CACHE,
...@@ -558,6 +553,7 @@ extern char *_my_strdup_with_length(const byte *from, uint length, ...@@ -558,6 +553,7 @@ extern char *_my_strdup_with_length(const byte *from, uint length,
const char *sFile, uint uLine, const char *sFile, uint uLine,
myf MyFlag); myf MyFlag);
#ifndef TERMINATE #ifndef TERMINATE
extern void TERMINATE(FILE *file); extern void TERMINATE(FILE *file);
#endif #endif
...@@ -706,9 +702,6 @@ extern void freeze_size(DYNAMIC_ARRAY *array); ...@@ -706,9 +702,6 @@ extern void freeze_size(DYNAMIC_ARRAY *array);
#define dynamic_element(array,array_index,type) ((type)((array)->buffer) +(array_index)) #define dynamic_element(array,array_index,type) ((type)((array)->buffer) +(array_index))
#define push_dynamic(A,B) insert_dynamic(A,B) #define push_dynamic(A,B) insert_dynamic(A,B)
extern int find_type(my_string x,TYPELIB *typelib,uint full_name);
extern void make_type(my_string to,uint nr,TYPELIB *typelib);
extern const char *get_type(TYPELIB *typelib,uint nr);
extern my_bool init_dynamic_string(DYNAMIC_STRING *str, const char *init_str, extern my_bool init_dynamic_string(DYNAMIC_STRING *str, const char *init_str,
uint init_alloc,uint alloc_increment); uint init_alloc,uint alloc_increment);
extern my_bool dynstr_append(DYNAMIC_STRING *str, const char *append); extern my_bool dynstr_append(DYNAMIC_STRING *str, const char *append);
......
...@@ -56,6 +56,7 @@ typedef int my_socket; ...@@ -56,6 +56,7 @@ typedef int my_socket;
#include "mysql_com.h" #include "mysql_com.h"
#include "mysql_version.h" #include "mysql_version.h"
#include "typelib.h"
extern unsigned int mysql_port; extern unsigned int mysql_port;
extern char *mysql_unix_port; extern char *mysql_unix_port;
...@@ -137,24 +138,36 @@ struct st_mysql_options { ...@@ -137,24 +138,36 @@ struct st_mysql_options {
a read that is replication-aware a read that is replication-aware
*/ */
my_bool no_master_reads; my_bool no_master_reads;
char *shared_memory_base_name;
unsigned int protocol;
}; };
enum mysql_option { MYSQL_OPT_CONNECT_TIMEOUT, MYSQL_OPT_COMPRESS, enum mysql_option
MYSQL_OPT_NAMED_PIPE, MYSQL_INIT_COMMAND, {
MYSQL_READ_DEFAULT_FILE, MYSQL_READ_DEFAULT_GROUP, MYSQL_OPT_CONNECT_TIMEOUT, MYSQL_OPT_COMPRESS, MYSQL_OPT_NAMED_PIPE, MYSQL_INIT_COMMAND,
MYSQL_SET_CHARSET_DIR, MYSQL_SET_CHARSET_NAME, MYSQL_READ_DEFAULT_FILE, MYSQL_READ_DEFAULT_GROUP,MYSQL_SET_CHARSET_DIR, MYSQL_SET_CHARSET_NAME,
MYSQL_OPT_LOCAL_INFILE}; MYSQL_OPT_LOCAL_INFILE, MYSQL_OPT_PROTOCOL, MYSQL_SHARED_MEMORY_BASE_NAME
};
enum mysql_status { MYSQL_STATUS_READY,MYSQL_STATUS_GET_RESULT, enum mysql_status
MYSQL_STATUS_USE_RESULT}; {
MYSQL_STATUS_READY,MYSQL_STATUS_GET_RESULT,MYSQL_STATUS_USE_RESULT
};
enum mysql_protocol_type
{
MYSQL_PROTOCOL_DEFAULT, MYSQL_PROTOCOL_TCP, MYSQL_PROTOCOL_SOCKET, MYSQL_PROTOCOL_PIPE,
MYSQL_PROTOCOL_MEMORY
};
/* /*
There are three types of queries - the ones that have to go to There are three types of queries - the ones that have to go to
the master, the ones that go to a slave, and the adminstrative the master, the ones that go to a slave, and the adminstrative
type which must happen on the pivot connectioin type which must happen on the pivot connectioin
*/ */
enum mysql_rpl_type { MYSQL_RPL_MASTER, MYSQL_RPL_SLAVE, enum mysql_rpl_type
MYSQL_RPL_ADMIN }; {
MYSQL_RPL_MASTER, MYSQL_RPL_SLAVE, MYSQL_RPL_ADMIN
};
typedef struct st_mysql typedef struct st_mysql
......
/* Copyright (C) 2000 MySQL AB
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; either version 2 of the License, or
(at your option) any later version.
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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#ifndef _typelib_h
#define _typelib_h
typedef struct st_typelib { /* Different types saved here */
uint count; /* How many types */
const char *name; /* Name of typelib */
const char **type_names;
} TYPELIB;
extern int find_type(char *x,TYPELIB *typelib,uint full_name);
extern void make_type(char *to,uint nr,TYPELIB *typelib);
extern const char *get_type(TYPELIB *typelib,uint nr);
extern TYPELIB sql_protocol_typelib;
#endif /* _typelib_h */
...@@ -32,7 +32,7 @@ extern "C" { ...@@ -32,7 +32,7 @@ extern "C" {
#endif /* __cplusplus */ #endif /* __cplusplus */
enum enum_vio_type { VIO_CLOSED, VIO_TYPE_TCPIP, VIO_TYPE_SOCKET, enum enum_vio_type { VIO_CLOSED, VIO_TYPE_TCPIP, VIO_TYPE_SOCKET,
VIO_TYPE_NAMEDPIPE, VIO_TYPE_SSL}; VIO_TYPE_NAMEDPIPE, VIO_TYPE_SSL,VIO_TYPE_SHARED_MEMORY};
#ifndef __WIN__ #ifndef __WIN__
#define HANDLE void * #define HANDLE void *
...@@ -41,6 +41,9 @@ enum enum_vio_type { VIO_CLOSED, VIO_TYPE_TCPIP, VIO_TYPE_SOCKET, ...@@ -41,6 +41,9 @@ enum enum_vio_type { VIO_CLOSED, VIO_TYPE_TCPIP, VIO_TYPE_SOCKET,
Vio* vio_new(my_socket sd, enum enum_vio_type type, my_bool localhost); Vio* vio_new(my_socket sd, enum enum_vio_type type, my_bool localhost);
#ifdef __WIN__ #ifdef __WIN__
Vio* vio_new_win32pipe(HANDLE hPipe); Vio* vio_new_win32pipe(HANDLE hPipe);
Vio* vio_new_win32shared_memory(NET *net,HANDLE handle_file_map, HANDLE handle_map,
HANDLE event_server_wrote, HANDLE event_server_read,
HANDLE event_client_wrote, HANDLE event_client_read);
#endif #endif
void vio_delete(Vio* vio); void vio_delete(Vio* vio);
...@@ -107,6 +110,17 @@ my_bool vio_poll_read(Vio *vio,uint timeout); ...@@ -107,6 +110,17 @@ my_bool vio_poll_read(Vio *vio,uint timeout);
} }
#endif #endif
#ifdef HAVE_SMEM
int vio_read_shared_memory(Vio *vio, gptr buf, int size);
int vio_write_shared_memory(Vio *vio, const gptr buf, int size);
int vio_close_shared_memory(Vio * vio);
#endif
#ifdef __WIN__
int vio_read_pipe(Vio *vio, gptr buf, int size);
int vio_write_pipe(Vio *vio, const gptr buf, int size);
int vio_close_pipe(Vio * vio);
#endif
#if defined(HAVE_VIO) && !defined(DONT_MAP_VIO) #if defined(HAVE_VIO) && !defined(DONT_MAP_VIO)
#define vio_delete(vio) (vio)->viodelete(vio) #define vio_delete(vio) (vio)->viodelete(vio)
#define vio_errno(vio) (vio)->vioerrno(vio) #define vio_errno(vio) (vio)->vioerrno(vio)
...@@ -233,6 +247,17 @@ struct st_vio ...@@ -233,6 +247,17 @@ struct st_vio
SSL* ssl_; SSL* ssl_;
my_bool open_; my_bool open_;
#endif /* HAVE_OPENSSL */ #endif /* HAVE_OPENSSL */
#ifdef HAVE_SMEM
HANDLE handle_file_map;
char *handle_map;
HANDLE event_server_wrote;
HANDLE event_server_read;
HANDLE event_client_wrote;
HANDLE event_client_read;
long shared_memory_remain;
char *shared_memory_pos;
NET *net;
#endif /* HAVE_SMEM */
#endif /* HAVE_VIO */ #endif /* HAVE_VIO */
}; };
#endif /* EMBEDDED_LIBRARY */ #endif /* EMBEDDED_LIBRARY */
......
...@@ -59,6 +59,17 @@ const char *client_errors[]= ...@@ -59,6 +59,17 @@ const char *client_errors[]=
"Invalid parameter number", "Invalid parameter number",
"Can't send long data for non string or binary data types (parameter: %d)", "Can't send long data for non string or binary data types (parameter: %d)",
"Using not supported parameter type: %d (parameter: %d)" "Using not supported parameter type: %d (parameter: %d)"
"Shared memory (%lu)",
"Can't open shared memory. Request event don't create (%lu)",
"Can't open shared memory. Answer event don't create (%lu)",
"Can't open shared memory. File mapping don't create (%lu)",
"Can't open shared memory. Map of memory don't create (%lu)",
"Can't open shared memory. File mapping don't create for client (%lu)",
"Can't open shared memory. Map of memory don't create for client (%lu)",
"Can't open shared memory. %s event don't create for client (%lu)",
"Can't open shared memory. Server abandoded and don't sent the answer event (%lu)",
"Can't open shared memory. Can't send the request event to server (%lu)"
"Wrong or unknow protocol"
}; };
/* Start of code added by Roberto M. Serqueira - martinsc@uol.com.br - 05.24.2001 */ /* Start of code added by Roberto M. Serqueira - martinsc@uol.com.br - 05.24.2001 */
...@@ -101,6 +112,17 @@ const char *client_errors[]= ...@@ -101,6 +112,17 @@ const char *client_errors[]=
"Invalid parameter number", "Invalid parameter number",
"Can't send long data for non string or binary data types (parameter: %d)", "Can't send long data for non string or binary data types (parameter: %d)",
"Using not supported parameter type: %d (parameter: %d)" "Using not supported parameter type: %d (parameter: %d)"
"Shared memory (%lu)",
"Can't open shared memory. Request event don't create (%lu)",
"Can't open shared memory. Answer event don't create (%lu)",
"Can't open shared memory. File mapping don't create (%lu)",
"Can't open shared memory. Map of memory don't create (%lu)",
"Can't open shared memory. File mapping don't create for client (%lu)",
"Can't open shared memory. Map of memory don't create for client (%lu)",
"Can't open shared memory. %s event don't create for client (%lu)",
"Can't open shared memory. Server abandoded and don't sent the answer event (%lu)",
"Can't open shared memory. Can't send the request event to server (%lu)"
"Wrong or unknow protocol"
}; };
#else /* ENGLISH */ #else /* ENGLISH */
...@@ -141,6 +163,17 @@ const char *client_errors[]= ...@@ -141,6 +163,17 @@ const char *client_errors[]=
"Invalid parameter number", "Invalid parameter number",
"Can't send long data for non string or binary data types (parameter: %d)", "Can't send long data for non string or binary data types (parameter: %d)",
"Using not supported parameter type: %d (parameter: %d)" "Using not supported parameter type: %d (parameter: %d)"
"Shared memory (%lu)",
"Can't open shared memory. Request event don't create (%lu)",
"Can't open shared memory. Answer event don't create (%lu)",
"Can't open shared memory. File mapping don't create (%lu)",
"Can't open shared memory. Map of memory don't create (%lu)",
"Can't open shared memory. File mapping don't create for client (%lu)",
"Can't open shared memory. Map of memory don't create for client (%lu)",
"Can't open shared memory. %s event don't create for client (%lu)",
"Can't open shared memory. Server abandoded and don't sent the answer event (%lu)",
"Can't open shared memory. Can't send the request event to server (%lu)"
"Wrong or unknow protocol"
}; };
#endif #endif
......
...@@ -84,6 +84,15 @@ ulong net_write_timeout= NET_WRITE_TIMEOUT; ...@@ -84,6 +84,15 @@ ulong net_write_timeout= NET_WRITE_TIMEOUT;
#define SOCKET_ERROR -1 #define SOCKET_ERROR -1
#endif /* __WIN__ */ #endif /* __WIN__ */
#ifdef HAVE_SMEM
char *shared_memory_base_name=0;
const char *def_shared_memory_base_name=default_shared_memory_base_name;
#endif
const char *sql_protocol_names_lib[] =
{ "TCP", "SOCKET", "PIPE", "MEMORY",NullS };
TYPELIB sql_protocol_typelib = {array_elements(sql_protocol_names_lib)-1,"",
sql_protocol_names_lib};
/* /*
If allowed through some configuration, then this needs to If allowed through some configuration, then this needs to
be changed be changed
...@@ -336,6 +345,190 @@ HANDLE create_named_pipe(NET *net, uint connect_timeout, char **arg_host, ...@@ -336,6 +345,190 @@ HANDLE create_named_pipe(NET *net, uint connect_timeout, char **arg_host,
} }
#endif #endif
/*
Create new shared memory connection, return handler of connection
SYNOPSIS
create_shared_memory()
mysql Pointer of mysql structure
net Pointer of net structure
connect_timeout Timeout of connection
*/
#ifdef HAVE_SMEM
HANDLE create_shared_memory(MYSQL *mysql,NET *net, uint connect_timeout)
{
ulong smem_buffer_length = shared_memory_buffer_length + 4;
/*
event_connect_request is event object for start connection actions
event_connect_answer is event object for confirm, that server put data
handle_connect_file_map is file-mapping object, use for create shared memory
handle_connect_map is pointer on shared memory
handle_map is pointer on shared memory for client
event_server_wrote,
event_server_read,
event_client_wrote,
event_client_read are events for transfer data between server and client
handle_file_map is file-mapping object, use for create shared memory
*/
HANDLE event_connect_request = NULL;
HANDLE event_connect_answer = NULL;
HANDLE handle_connect_file_map = NULL;
char *handle_connect_map = NULL;
char *handle_map = NULL;
HANDLE event_server_wrote = NULL;
HANDLE event_server_read = NULL;
HANDLE event_client_wrote = NULL;
HANDLE event_client_read = NULL;
HANDLE handle_file_map = NULL;
ulong connect_number;
char connect_number_char[22], *p;
char tmp[64];
char *suffix_pos;
DWORD error_allow = 0;
DWORD error_code = 0;
char *shared_memory_base_name = mysql->options.shared_memory_base_name;
/*
The name of event and file-mapping events create agree next rule:
shared_memory_base_name+unique_part
Where:
shared_memory_base_name is unique value for each server
unique_part is uniquel value for each object (events and file-mapping)
*/
suffix_pos = strxmov(tmp,shared_memory_base_name,"_",NullS);
strmov(suffix_pos, "CONNECT_REQUEST");
if ((event_connect_request = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_CONNECT_REQUEST_ERROR;
goto err;
}
strmov(suffix_pos, "CONNECT_ANSWER");
if ((event_connect_answer = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_CONNECT_ANSWER_ERROR;
goto err;
}
strmov(suffix_pos, "CONNECT_DATA");
if ((handle_connect_file_map = OpenFileMapping(FILE_MAP_WRITE,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_CONNECT_FILE_MAP_ERROR;
goto err;
}
if ((handle_connect_map = MapViewOfFile(handle_connect_file_map,FILE_MAP_WRITE,0,0,sizeof(DWORD))) == NULL)
{
error_allow = CR_SHARED_MEMORY_CONNECT_MAP_ERROR;
goto err;
}
/*
Send to server request of connection
*/
if (!SetEvent(event_connect_request))
{
error_allow = CR_SHARED_MEMORY_CONNECT_SET_ERROR;
goto err;
}
/*
Wait of answer from server
*/
if (WaitForSingleObject(event_connect_answer,connect_timeout*1000) != WAIT_OBJECT_0)
{
error_allow = CR_SHARED_MEMORY_CONNECT_ABANDODED_ERROR;
goto err;
}
/*
Get number of connection
*/
connect_number = uint4korr(handle_connect_map);/*WAX2*/
p = int2str(connect_number, connect_number_char, 10);
/*
The name of event and file-mapping events create agree next rule:
shared_memory_base_name+unique_part+number_of_connection
Where:
shared_memory_base_name is uniquel value for each server
unique_part is uniquel value for each object (events and file-mapping)
number_of_connection is number of connection between server and client
*/
suffix_pos = strxmov(tmp,shared_memory_base_name,"_",connect_number_char,"_",NullS);
strmov(suffix_pos, "DATA");
if ((handle_file_map = OpenFileMapping(FILE_MAP_WRITE,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_FILE_MAP_ERROR;
goto err2;
}
if ((handle_map = MapViewOfFile(handle_file_map,FILE_MAP_WRITE,0,0,smem_buffer_length)) == NULL)
{
error_allow = CR_SHARED_MEMORY_MAP_ERROR;
goto err2;
}
strmov(suffix_pos, "SERVER_WROTE");
if ((event_server_wrote = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_EVENT_ERROR;
goto err2;
}
strmov(suffix_pos, "SERVER_READ");
if ((event_server_read = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_EVENT_ERROR;
goto err2;
}
strmov(suffix_pos, "CLIENT_WROTE");
if ((event_client_wrote = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_EVENT_ERROR;
goto err2;
}
strmov(suffix_pos, "CLIENT_READ");
if ((event_client_read = OpenEvent(EVENT_ALL_ACCESS,FALSE,tmp)) == NULL)
{
error_allow = CR_SHARED_MEMORY_EVENT_ERROR;
goto err2;
}
/*
Set event that server should send data
*/
SetEvent(event_server_read);
err2:
if (error_allow == 0)
{
net->vio = vio_new_win32shared_memory(net,handle_file_map,handle_map,event_server_wrote,
event_server_read,event_client_wrote,event_client_read);
}
else
{
error_code = GetLastError();
if (event_server_read) CloseHandle(event_server_read);
if (event_server_wrote) CloseHandle(event_server_wrote);
if (event_client_read) CloseHandle(event_client_read);
if (event_client_wrote) CloseHandle(event_client_wrote);
if (handle_map) UnmapViewOfFile(handle_map);
if (handle_file_map) CloseHandle(handle_file_map);
}
err:
if (error_allow) error_code = GetLastError();
if (event_connect_request) CloseHandle(event_connect_request);
if (event_connect_answer) CloseHandle(event_connect_answer);
if (handle_connect_map) UnmapViewOfFile(handle_connect_map);
if (handle_connect_file_map) CloseHandle(handle_connect_file_map);
if (error_allow)
{
net->last_errno=error_allow;
if (error_allow == CR_SHARED_MEMORY_EVENT_ERROR)
sprintf(net->last_error,ER(net->last_errno),suffix_pos,error_code);
else
sprintf(net->last_error,ER(net->last_errno),error_code);
return(INVALID_HANDLE_VALUE);
}
return(handle_map);
};
#endif
/***************************************************************************** /*****************************************************************************
read a packet from server. Give error message if socket was down read a packet from server. Give error message if socket was down
...@@ -734,7 +927,7 @@ static const char *default_options[]= ...@@ -734,7 +927,7 @@ static const char *default_options[]=
"character-sets-dir", "default-character-set", "interactive-timeout", "character-sets-dir", "default-character-set", "interactive-timeout",
"connect-timeout", "local-infile", "disable-local-infile", "connect-timeout", "local-infile", "disable-local-infile",
"replication-probe", "enable-reads-from-master", "repl-parse-query", "replication-probe", "enable-reads-from-master", "repl-parse-query",
"ssl-cipher", "ssl-cipher","protocol","shared_memory_base_name",
NullS NullS
}; };
...@@ -794,9 +987,8 @@ static void mysql_read_default_options(struct st_mysql_options *options, ...@@ -794,9 +987,8 @@ static void mysql_read_default_options(struct st_mysql_options *options,
options->password=my_strdup(opt_arg,MYF(MY_WME)); options->password=my_strdup(opt_arg,MYF(MY_WME));
} }
break; break;
case 5: /* pipe */ case 5:
options->named_pipe=1; /* Force named pipe */ options->protocol = MYSQL_PROTOCOL_PIPE;
break;
case 20: /* connect_timeout */ case 20: /* connect_timeout */
case 6: /* timeout */ case 6: /* timeout */
if (opt_arg) if (opt_arg)
...@@ -889,6 +1081,20 @@ static void mysql_read_default_options(struct st_mysql_options *options, ...@@ -889,6 +1081,20 @@ static void mysql_read_default_options(struct st_mysql_options *options,
case 25: /* repl-parse-query */ case 25: /* repl-parse-query */
options->rpl_parse= 1; options->rpl_parse= 1;
break; break;
case 27:/* protocol */
if ((options->protocol = find_type(opt_arg, &sql_protocol_typelib,0)) == ~(ulong) 0)
{
fprintf(stderr, "Unknown option to protocol: %s\n", opt_arg);
exit(1);
}
break;
case 28: /*shared_memory_base_name*/
#ifdef HAVE_SMEM
if (options->shared_memory_base_name != def_shared_memory_base_name)
my_free(options->shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
options->shared_memory_base_name=my_strdup(opt_arg,MYF(MY_WME));
#endif
break;
default: default:
DBUG_PRINT("warning",("unknown option: %s",option[0])); DBUG_PRINT("warning",("unknown option: %s",option[0]));
} }
...@@ -1449,6 +1655,9 @@ mysql_init(MYSQL *mysql) ...@@ -1449,6 +1655,9 @@ mysql_init(MYSQL *mysql)
#ifdef ENABLED_LOCAL_INFILE #ifdef ENABLED_LOCAL_INFILE
mysql->options.client_flag|= CLIENT_LOCAL_FILES; mysql->options.client_flag|= CLIENT_LOCAL_FILES;
#endif #endif
#ifdef HAVE_SMEM
mysql->options.shared_memory_base_name=(char*)def_shared_memory_base_name;
#endif
return mysql; return mysql;
} }
...@@ -1645,9 +1854,38 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user, ...@@ -1645,9 +1854,38 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
/* /*
** Grab a socket and connect it to the server ** Grab a socket and connect it to the server
*/ */
#if defined(HAVE_SMEM)
if ((!mysql->options.protocol || mysql->options.protocol == MYSQL_PROTOCOL_MEMORY)&&
(!host || !strcmp(host,LOCAL_HOST)))
{
if ((create_shared_memory(mysql,net, mysql->options.connect_timeout)) ==
INVALID_HANDLE_VALUE)
{
DBUG_PRINT("error",
("host: '%s' socket: '%s' shared memory: %s have_tcpip: %d",
host ? host : "<null>",
unix_socket ? unix_socket : "<null>",
(int) mysql->options.shared_memory_base_name,
(int) have_tcpip));
if (mysql->options.protocol == MYSQL_PROTOCOL_MEMORY)
goto error;
/*
Try also with PIPE or TCP/IP
*/
}
else
{
mysql->options.protocol=MYSQL_PROTOCOL_MEMORY;
sock=0;
unix_socket = 0;
host=mysql->options.shared_memory_base_name;
host_info=(char*) ER(CR_SHARED_MEMORY_CONNECTION);
}
} else
#endif //HAVE_SMEM
#if defined(HAVE_SYS_UN_H) #if defined(HAVE_SYS_UN_H)
if ((!host || !strcmp(host,LOCAL_HOST)) && (unix_socket || mysql_unix_port)) if ((!mysql->options.protocol || mysql->options.protocol == MYSQL_PROTOCOL_SOCKET)&&
(!host || !strcmp(host,LOCAL_HOST)) && (unix_socket || mysql_unix_port))
{ {
host=LOCAL_HOST; host=LOCAL_HOST;
if (!unix_socket) if (!unix_socket)
...@@ -1672,46 +1910,42 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user, ...@@ -1672,46 +1910,42 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
sprintf(net->last_error,ER(net->last_errno),unix_socket,socket_errno); sprintf(net->last_error,ER(net->last_errno),unix_socket,socket_errno);
goto error; goto error;
} }
else
mysql->options.protocol=MYSQL_PROTOCOL_SOCKET;
} }
else else
#elif defined(__WIN__) #elif defined(__WIN__)
if ((!mysql->options.protocol || mysql->options.protocol == MYSQL_PROTOCOL_PIPE)&&
((unix_socket || !host && is_NT() ||
host && !strcmp(host,LOCAL_HOST_NAMEDPIPE) ||!have_tcpip))&&(!net->vio))
{ {
if ((unix_socket || sock=0;
!host && is_NT() || if ((hPipe=create_named_pipe(net, mysql->options.connect_timeout,
host && !strcmp(host,LOCAL_HOST_NAMEDPIPE) || (char**) &host, (char**) &unix_socket)) ==
mysql->options.named_pipe || !have_tcpip)) INVALID_HANDLE_VALUE)
{ {
sock=0; DBUG_PRINT("error",
if ((hPipe=create_named_pipe(net, mysql->options.connect_timeout, ("host: '%s' socket: '%s' have_tcpip: %d",
(char**) &host, (char**) &unix_socket)) == host ? host : "<null>",
INVALID_HANDLE_VALUE) unix_socket ? unix_socket : "<null>",
{ (int) have_tcpip));
DBUG_PRINT("error", if (mysql->options.protocol == MYSQL_PROTOCOL_PIPE ||
("host: '%s' socket: '%s' named_pipe: %d have_tcpip: %d", (host && !strcmp(host,LOCAL_HOST_NAMEDPIPE)) ||
host ? host : "<null>", (unix_socket && !strcmp(unix_socket,MYSQL_NAMEDPIPE)))
unix_socket ? unix_socket : "<null>", goto error;
(int) mysql->options.named_pipe, /*
(int) have_tcpip)); Try also with TCP/IP
if (mysql->options.named_pipe || */
(host && !strcmp(host,LOCAL_HOST_NAMEDPIPE)) || }
(unix_socket && !strcmp(unix_socket,MYSQL_NAMEDPIPE))) else
{ {
net->last_errno= CR_SERVER_LOST; net->vio=vio_new_win32pipe(hPipe);
strmov(net->last_error,ER(net->last_errno)); sprintf(host_info=buff, ER(CR_NAMEDPIPE_CONNECTION), host,
goto error; /* User only requested named pipes */ unix_socket);
}
/* Try also with TCP/IP */
}
else
{
net->vio=vio_new_win32pipe(hPipe);
sprintf(host_info=buff, ER(CR_NAMEDPIPE_CONNECTION), host,
unix_socket);
}
} }
} }
if (hPipe == INVALID_HANDLE_VALUE)
#endif #endif
if ((!mysql->options.protocol || mysql->options.protocol == MYSQL_PROTOCOL_TCP)&&(!net->vio))
{ {
unix_socket=0; /* This is not used */ unix_socket=0; /* This is not used */
if (!port) if (!port)
...@@ -1766,6 +2000,14 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user, ...@@ -1766,6 +2000,14 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
goto error; goto error;
} }
} }
else
if (!net->vio)
{
DBUG_PRINT("error",("Unknow protocol %d ",mysql->options.protocol));
net->last_errno= CR_CONN_UNKNOW_PROTOCOL;
sprintf(net->last_error ,ER(CR_CONN_UNKNOW_PROTOCOL));
goto error;
};
if (!net->vio || my_net_init(net, net->vio)) if (!net->vio || my_net_init(net, net->vio))
{ {
...@@ -2169,6 +2411,10 @@ mysql_close(MYSQL *mysql) ...@@ -2169,6 +2411,10 @@ mysql_close(MYSQL *mysql)
#ifdef HAVE_OPENSSL #ifdef HAVE_OPENSSL
mysql_ssl_free(mysql); mysql_ssl_free(mysql);
#endif /* HAVE_OPENSSL */ #endif /* HAVE_OPENSSL */
#ifdef HAVE_SMEM
if (mysql->options.shared_memory_base_name != def_shared_memory_base_name)
my_free(mysql->options.shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
#endif /* HAVE_SMEM */
/* Clear pointers for better safety */ /* Clear pointers for better safety */
mysql->host_info=mysql->user=mysql->passwd=mysql->db=0; mysql->host_info=mysql->user=mysql->passwd=mysql->db=0;
bzero((char*) &mysql->options,sizeof(mysql->options)); bzero((char*) &mysql->options,sizeof(mysql->options));
...@@ -2888,7 +3134,7 @@ mysql_options(MYSQL *mysql,enum mysql_option option, const char *arg) ...@@ -2888,7 +3134,7 @@ mysql_options(MYSQL *mysql,enum mysql_option option, const char *arg)
mysql->options.compress= 1; /* Remember for connect */ mysql->options.compress= 1; /* Remember for connect */
break; break;
case MYSQL_OPT_NAMED_PIPE: case MYSQL_OPT_NAMED_PIPE:
mysql->options.named_pipe=1; /* Force named pipe */ mysql->options.protocol=MYSQL_PROTOCOL_PIPE; /* Force named pipe */
break; break;
case MYSQL_OPT_LOCAL_INFILE: /* Allow LOAD DATA LOCAL ?*/ case MYSQL_OPT_LOCAL_INFILE: /* Allow LOAD DATA LOCAL ?*/
if (!arg || test(*(uint*) arg)) if (!arg || test(*(uint*) arg))
...@@ -2916,6 +3162,16 @@ mysql_options(MYSQL *mysql,enum mysql_option option, const char *arg) ...@@ -2916,6 +3162,16 @@ mysql_options(MYSQL *mysql,enum mysql_option option, const char *arg)
my_free(mysql->options.charset_name,MYF(MY_ALLOW_ZERO_PTR)); my_free(mysql->options.charset_name,MYF(MY_ALLOW_ZERO_PTR));
mysql->options.charset_name=my_strdup(arg,MYF(MY_WME)); mysql->options.charset_name=my_strdup(arg,MYF(MY_WME));
break; break;
case MYSQL_OPT_PROTOCOL:
mysql->options.protocol= *(uint*) arg;
break;
case MYSQL_SHARED_MEMORY_BASE_NAME:
#ifdef HAVE_SMEM
if (mysql->options.shared_memory_base_name != def_shared_memory_base_name)
my_free(mysql->options.shared_memory_base_name,MYF(MY_ALLOW_ZERO_PTR));
mysql->options.shared_memory_base_name=my_strdup(arg,MYF(MY_WME));
#endif
break;
default: default:
DBUG_RETURN(1); DBUG_RETURN(1);
} }
......
...@@ -179,10 +179,13 @@ static char szPipeName [ 257 ]; ...@@ -179,10 +179,13 @@ static char szPipeName [ 257 ];
static SECURITY_ATTRIBUTES saPipeSecurity; static SECURITY_ATTRIBUTES saPipeSecurity;
static SECURITY_DESCRIPTOR sdPipeDescriptor; static SECURITY_DESCRIPTOR sdPipeDescriptor;
static HANDLE hPipe = INVALID_HANDLE_VALUE; static HANDLE hPipe = INVALID_HANDLE_VALUE;
static pthread_cond_t COND_handler_count;
static uint handler_count; static uint handler_count;
static bool opt_enable_named_pipe = 0;
#endif #endif
#ifdef __WIN__ #ifdef __WIN__
static bool opt_console=0,start_mode=0;
static pthread_cond_t COND_handler_count;
static uint handler_count;
static bool opt_console=0, start_mode=0, use_opt_args; static bool opt_console=0, start_mode=0, use_opt_args;
static int opt_argc; static int opt_argc;
static char **opt_argv; static char **opt_argv;
...@@ -335,6 +338,11 @@ ulong query_cache_limit=0; ...@@ -335,6 +338,11 @@ ulong query_cache_limit=0;
Query_cache query_cache; Query_cache query_cache;
#endif #endif
#ifdef HAVE_SMEM
static char *shared_memory_base_name=default_shared_memory_base_name;
static bool opt_enable_shared_memory = 0;
#endif
volatile ulong cached_thread_count=0; volatile ulong cached_thread_count=0;
// replication parameters, if master_host is not NULL, we are a slave // replication parameters, if master_host is not NULL, we are a slave
...@@ -459,6 +467,9 @@ static bool read_init_file(char *file_name); ...@@ -459,6 +467,9 @@ static bool read_init_file(char *file_name);
#ifdef __NT__ #ifdef __NT__
static pthread_handler_decl(handle_connections_namedpipes,arg); static pthread_handler_decl(handle_connections_namedpipes,arg);
#endif #endif
#ifdef HAVE_SMEM
static pthread_handler_decl(handle_connections_shared_memory,arg);
#endif
extern pthread_handler_decl(handle_slave,arg); extern pthread_handler_decl(handle_slave,arg);
#ifdef SET_RLIMIT_NOFILE #ifdef SET_RLIMIT_NOFILE
static uint set_maximum_open_files(uint max_file_limit); static uint set_maximum_open_files(uint max_file_limit);
...@@ -2123,21 +2134,24 @@ The server will not act as a slave."); ...@@ -2123,21 +2134,24 @@ The server will not act as a slave.");
printf(ER(ER_READY),my_progname,server_version,""); printf(ER(ER_READY),my_progname,server_version,"");
fflush(stdout); fflush(stdout);
#if defined(__NT__) || defined(HAVE_SMEM)
#ifdef __NT__ #ifdef __NT__
if (hPipe == INVALID_HANDLE_VALUE && if (hPipe == INVALID_HANDLE_VALUE &&
(!have_tcpip || opt_disable_networking)) (!have_tcpip || opt_disable_networking) &&
!opt_enable_shared_memory)
{ {
sql_print_error("TCP/IP or --enable-named-pipe should be configured on NT OS"); sql_print_error("TCP/IP,--shared-memory or --named-pipe should be configured on NT OS");
unireg_abort(1); unireg_abort(1);
} }
else else
#endif
{ {
pthread_mutex_lock(&LOCK_thread_count); pthread_mutex_lock(&LOCK_thread_count);
(void) pthread_cond_init(&COND_handler_count,NULL); (void) pthread_cond_init(&COND_handler_count,NULL);
{ {
pthread_t hThread; pthread_t hThread;
handler_count=0; handler_count=0;
#ifdef __NT__
if (hPipe != INVALID_HANDLE_VALUE && opt_enable_named_pipe) if (hPipe != INVALID_HANDLE_VALUE && opt_enable_named_pipe)
{ {
handler_count++; handler_count++;
...@@ -2148,18 +2162,33 @@ The server will not act as a slave."); ...@@ -2148,18 +2162,33 @@ The server will not act as a slave.");
handler_count--; handler_count--;
} }
} }
#endif
#ifdef HAVE_SMEM
if (opt_enable_shared_memory)
{
handler_count++;
if (pthread_create(&hThread,&connection_attrib,
handle_connections_shared_memory, 0))
{
sql_print_error("Warning: Can't create thread to handle shared memory");
handler_count--;
}
}
#endif
if (have_tcpip && !opt_disable_networking) if (have_tcpip && !opt_disable_networking)
{ {
handler_count++; handler_count++;
if (pthread_create(&hThread,&connection_attrib, if (pthread_create(&hThread,&connection_attrib,
handle_connections_sockets, 0)) handle_connections_sockets, 0))
{ {
sql_print_error("Warning: Can't create thread to handle named pipes"); sql_print_error("Warning: Can't create thread to handle tcp/ip");
handler_count--; handler_count--;
} }
} }
while (handler_count > 0) while (handler_count > 0)
{
pthread_cond_wait(&COND_handler_count,&LOCK_thread_count); pthread_cond_wait(&COND_handler_count,&LOCK_thread_count);
}
} }
pthread_mutex_unlock(&LOCK_thread_count); pthread_mutex_unlock(&LOCK_thread_count);
} }
...@@ -2777,6 +2806,219 @@ pthread_handler_decl(handle_connections_namedpipes,arg) ...@@ -2777,6 +2806,219 @@ pthread_handler_decl(handle_connections_namedpipes,arg)
} }
#endif /* __NT__ */ #endif /* __NT__ */
/*
Thread of shared memory's service
SYNOPSIS
pthread_handler_decl()
handle_connections_shared_memory Thread handle
arg Arguments of thread
*/
#ifdef HAVE_SMEM
pthread_handler_decl(handle_connections_shared_memory,arg)
{
/*
event_connect_request is event object for start connection actions
event_connect_answer is event object for confirm, that server put data
handle_connect_file_map is file-mapping object, use for create shared memory
handle_connect_map is pointer on shared memory
handle_map is pointer on shared memory for client
event_server_wrote,
event_server_read,
event_client_wrote,
event_client_read are events for transfer data between server and client
handle_file_map is file-mapping object, use for create shared memory
*/
HANDLE handle_connect_file_map = NULL;
char *handle_connect_map = NULL;
HANDLE event_connect_request = NULL;
HANDLE event_connect_answer = NULL;
ulong smem_buffer_length = shared_memory_buffer_length + 4;
ulong connect_number = 1;
my_bool error_allow;
THD *thd;
char tmp[63];
char *suffix_pos;
char connect_number_char[22], *p;
my_thread_init();
DBUG_ENTER("handle_connections_shared_memorys");
DBUG_PRINT("general",("Waiting for allocated shared memory."));
/*
The name of event and file-mapping events create agree next rule:
shared_memory_base_name+unique_part
Where:
shared_memory_base_name is unique value for each server
unique_part is unique value for each object (events and file-mapping)
*/
suffix_pos = strxmov(tmp,shared_memory_base_name,"_",NullS);
strmov(suffix_pos, "CONNECT_REQUEST");
if ((event_connect_request = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create shared memory service ! The request event don't create.");
goto error;
}
strmov(suffix_pos, "CONNECT_ANSWER");
if ((event_connect_answer = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create shared memory service ! The answer event don't create.");
goto error;
}
strmov(suffix_pos, "CONNECT_DATA");
if ((handle_connect_file_map = CreateFileMapping(INVALID_HANDLE_VALUE,NULL,PAGE_READWRITE,
0,sizeof(connect_number),tmp)) == 0)
{
sql_perror("Can't create shared memory service ! File mapping don't create.");
goto error;
}
if ((handle_connect_map = (char *)MapViewOfFile(handle_connect_file_map,FILE_MAP_WRITE,0,0,
sizeof(DWORD))) == 0)
{
sql_perror("Can't create shared memory service ! Map of memory don't create.");
goto error;
}
while (!abort_loop)
{
/*
Wait a request from client
*/
WaitForSingleObject(event_connect_request,INFINITE);
error_allow = FALSE;
HANDLE handle_client_file_map = NULL;
char *handle_client_map = NULL;
HANDLE event_client_wrote = NULL;
HANDLE event_client_read = NULL;
HANDLE event_server_wrote = NULL;
HANDLE event_server_read = NULL;
p = int2str(connect_number, connect_number_char, 10);
/*
The name of event and file-mapping events create agree next rule:
shared_memory_base_name+unique_part+number_of_connection
Where:
shared_memory_base_name is uniquel value for each server
unique_part is unique value for each object (events and file-mapping)
number_of_connection is number of connection between server and client
*/
suffix_pos = strxmov(tmp,shared_memory_base_name,"_",connect_number_char,"_",NullS);
strmov(suffix_pos, "DATA");
if ((handle_client_file_map = CreateFileMapping(INVALID_HANDLE_VALUE,NULL,
PAGE_READWRITE,0,smem_buffer_length,tmp)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! File mapping don't create.");
error_allow = TRUE;
goto errorconn;
}
if ((handle_client_map = (char*)MapViewOfFile(handle_client_file_map,FILE_MAP_WRITE,0,0,smem_buffer_length)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! Map of memory don't create.");
error_allow = TRUE;
goto errorconn;
}
strmov(suffix_pos, "CLIENT_WROTE");
if ((event_client_wrote = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! CW event don't create.");
error_allow = TRUE;
goto errorconn;
}
strmov(suffix_pos, "CLIENT_READ");
if ((event_client_read = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! CR event don't create.");
error_allow = TRUE;
goto errorconn;
}
strmov(suffix_pos, "SERVER_READ");
if ((event_server_read = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! SR event don't create.");
error_allow = TRUE;
goto errorconn;
}
strmov(suffix_pos, "SERVER_WROTE");
if ((event_server_wrote = CreateEvent(NULL,FALSE,FALSE,tmp)) == 0)
{
sql_perror("Can't create connection with client in shared memory service ! SW event don't create.");
error_allow = TRUE;
goto errorconn;
}
if (abort_loop) break;
if ( !(thd = new THD))
{
error_allow = TRUE;
goto errorconn;
}
/*
Send number of connection to client
*/
int4store(handle_connect_map, connect_number);
/*
Send number of connection to client
*/
if (!SetEvent(event_connect_answer))
{
sql_perror("Can't create connection with client in shared memory service ! Can't send answer event.");
error_allow = TRUE;
goto errorconn;
}
/*
Set event that client should receive data
*/
if (!SetEvent(event_client_read))
{
sql_perror("Can't create connection with client in shared memory service ! Can't set client to read's mode.");
error_allow = TRUE;
goto errorconn;
}
if (!(thd->net.vio = vio_new_win32shared_memory(&thd->net,handle_client_file_map,handle_client_map,event_client_wrote,
event_client_read,event_server_wrote,event_server_read)) ||
my_net_init(&thd->net, thd->net.vio))
{
close_connection(&thd->net,ER_OUT_OF_RESOURCES);
delete thd;
error_allow = TRUE;
}
/* host name is unknown */
errorconn:
if (error_allow)
{
if (!handle_client_map) UnmapViewOfFile(handle_client_map);
if (!handle_client_file_map) CloseHandle(handle_client_file_map);
if (!event_server_wrote) CloseHandle(event_server_wrote);
if (!event_server_read) CloseHandle(event_server_read);
if (!event_client_wrote) CloseHandle(event_client_wrote);
if (!event_client_read) CloseHandle(event_client_read);
continue;
}
thd->host = my_strdup(localhost,MYF(0)); /* Host is unknown */
create_new_thread(thd);
uint4korr(connect_number++);
}
error:
if (!handle_connect_map) UnmapViewOfFile(handle_connect_map);
if (!handle_connect_file_map) CloseHandle(handle_connect_file_map);
if (!event_connect_answer) CloseHandle(event_connect_answer);
if (!event_connect_request) CloseHandle(event_connect_request);
pthread_mutex_lock(&LOCK_thread_count);
pthread_mutex_unlock(&LOCK_thread_count);
DBUG_RETURN(0);
}
#endif /* HAVE_SMEM */
/****************************************************************************** /******************************************************************************
** handle start options ** handle start options
...@@ -2886,7 +3128,9 @@ enum options { ...@@ -2886,7 +3128,9 @@ enum options {
OPT_INNODB_FORCE_RECOVERY, OPT_INNODB_FORCE_RECOVERY,
OPT_BDB_CACHE_SIZE, OPT_BDB_CACHE_SIZE,
OPT_BDB_LOG_BUFFER_SIZE, OPT_BDB_LOG_BUFFER_SIZE,
OPT_BDB_MAX_LOCK OPT_BDB_MAX_LOCK,
OPT_ENABLE_SHARED_MEMORY,
OPT_SHARED_MEMORY_BASE_NAME
}; };
...@@ -2993,6 +3237,11 @@ struct my_option my_long_options[] = ...@@ -2993,6 +3237,11 @@ struct my_option my_long_options[] =
{"enable-pstack", OPT_DO_PSTACK, "Print a symbolic stack trace on failure", {"enable-pstack", OPT_DO_PSTACK, "Print a symbolic stack trace on failure",
(gptr*) &opt_do_pstack, (gptr*) &opt_do_pstack, 0, GET_BOOL, NO_ARG, 0, 0, (gptr*) &opt_do_pstack, (gptr*) &opt_do_pstack, 0, GET_BOOL, NO_ARG, 0, 0,
0, 0, 0, 0}, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared-memory", OPT_ENABLE_SHARED_MEMORY,
"Enable the shared memory.",(gptr*) &opt_enable_shared_memory, (gptr*) &opt_enable_shared_memory,
0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"exit-info", 'T', "Used for debugging; Use at your own risk!", 0, 0, 0, {"exit-info", 'T', "Used for debugging; Use at your own risk!", 0, 0, 0,
GET_LONG, OPT_ARG, 0, 0, 0, 0, 0, 0}, GET_LONG, OPT_ARG, 0, 0, 0, 0, 0, 0},
{"flush", OPT_FLUSH, "Flush tables to disk between SQL commands", 0, 0, 0, {"flush", OPT_FLUSH, "Flush tables to disk between SQL commands", 0, 0, 0,
...@@ -3234,6 +3483,11 @@ struct my_option my_long_options[] = ...@@ -3234,6 +3483,11 @@ struct my_option my_long_options[] =
{"set-variable", 'O', {"set-variable", 'O',
"Change the value of a variable. Please note that this option is deprecated;you can set variables directly with --variable-name=value.", "Change the value of a variable. Please note that this option is deprecated;you can set variables directly with --variable-name=value.",
0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#ifdef HAVE_SMEM
{"shared_memory_base_name",OPT_SHARED_MEMORY_BASE_NAME,
"Base name of shared memory", (gptr*) &shared_memory_base_name, (gptr*) &shared_memory_base_name,
0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0},
#endif
{"show-slave-auth-info", OPT_SHOW_SLAVE_AUTH_INFO, {"show-slave-auth-info", OPT_SHOW_SLAVE_AUTH_INFO,
"Show user and password in SHOW SLAVE STATUS", "Show user and password in SHOW SLAVE STATUS",
(gptr*) &opt_show_slave_auth_info, (gptr*) &opt_show_slave_auth_info, 0, (gptr*) &opt_show_slave_auth_info, (gptr*) &opt_show_slave_auth_info, 0,
......
...@@ -520,6 +520,10 @@ struct show_var_st init_vars[]= { ...@@ -520,6 +520,10 @@ struct show_var_st init_vars[]= {
{sys_query_cache_type.name, (char*) &sys_query_cache_type, SHOW_SYS}, {sys_query_cache_type.name, (char*) &sys_query_cache_type, SHOW_SYS},
#endif /* HAVE_QUERY_CACHE */ #endif /* HAVE_QUERY_CACHE */
{sys_safe_show_db.name, (char*) &sys_safe_show_db, SHOW_SYS}, {sys_safe_show_db.name, (char*) &sys_safe_show_db, SHOW_SYS},
#ifdef HAVE_SMEM
{"shared_memory", (char*) &opt_enable_shared_memory, SHOW_MY_BOOL},
{"shared_memory_base_name", (char*) &shared_memory_base_name, SHOW_CHAR_PTR},
#endif
{sys_server_id.name, (char*) &sys_server_id, SHOW_SYS}, {sys_server_id.name, (char*) &sys_server_id, SHOW_SYS},
{sys_slave_net_timeout.name,(char*) &sys_slave_net_timeout, SHOW_SYS}, {sys_slave_net_timeout.name,(char*) &sys_slave_net_timeout, SHOW_SYS},
{"skip_external_locking", (char*) &my_disable_locking, SHOW_MY_BOOL}, {"skip_external_locking", (char*) &my_disable_locking, SHOW_MY_BOOL},
......
...@@ -45,7 +45,43 @@ void vio_reset(Vio* vio, enum enum_vio_type type, ...@@ -45,7 +45,43 @@ void vio_reset(Vio* vio, enum enum_vio_type type,
vio->sd = sd; vio->sd = sd;
vio->hPipe = hPipe; vio->hPipe = hPipe;
vio->localhost= localhost; vio->localhost= localhost;
#ifdef HAVE_VIO #ifdef HAVE_VIO
#ifdef __WIN__
if (type == VIO_TYPE_NAMEDPIPE)
{
vio->viodelete =vio_delete;
vio->vioerrno =vio_errno;
vio->read =vio_read_pipe;
vio->write =vio_write_pipe;
vio->fastsend =vio_fastsend;
vio->viokeepalive =vio_keepalive;
vio->should_retry =vio_should_retry;
vio->vioclose =vio_close_pipe;
vio->peer_addr =vio_peer_addr;
vio->in_addr =vio_in_addr;
vio->vioblocking =vio_blocking;
vio->is_blocking =vio_is_blocking;
}
else /* default is VIO_TYPE_TCPIP */
#endif
#ifdef HAVE_SMEM
if (type == VIO_TYPE_SHARED_MEMORY)
{
vio->viodelete =vio_delete;
vio->vioerrno =vio_errno;
vio->read =vio_read_shared_memory;
vio->write =vio_write_shared_memory;
vio->fastsend =vio_fastsend;
vio->viokeepalive =vio_keepalive;
vio->should_retry =vio_should_retry;
vio->vioclose =vio_close_shared_memory;
vio->peer_addr =vio_peer_addr;
vio->in_addr =vio_in_addr;
vio->vioblocking =vio_blocking;
vio->is_blocking =vio_is_blocking;
}
else
#endif
#ifdef HAVE_OPENSSL #ifdef HAVE_OPENSSL
if (type == VIO_TYPE_SSL) if (type == VIO_TYPE_SSL)
{ {
...@@ -131,4 +167,44 @@ Vio *vio_new_win32pipe(HANDLE hPipe) ...@@ -131,4 +167,44 @@ Vio *vio_new_win32pipe(HANDLE hPipe)
DBUG_RETURN(vio); DBUG_RETURN(vio);
} }
#ifdef HAVE_SMEM
Vio *vio_new_win32shared_memory(NET *net,HANDLE handle_file_map, HANDLE handle_map,
HANDLE event_server_wrote, HANDLE event_server_read,
HANDLE event_client_wrote, HANDLE event_client_read)
{
Vio *vio;
DBUG_ENTER("vio_new_win32shared_memory");
if ((vio = (Vio*) my_malloc(sizeof(Vio),MYF(MY_WME))))
{
vio_reset(vio, VIO_TYPE_SHARED_MEMORY, 0, 0, TRUE);
vio->handle_file_map = handle_file_map;
vio->handle_map = handle_map;
vio->event_server_wrote = event_server_wrote;
vio->event_server_read = event_server_read;
vio->event_client_wrote = event_client_wrote;
vio->event_client_read = event_client_read;
vio->shared_memory_remain = 0;
vio->shared_memory_pos = handle_map;
vio->net = net;
strmov(vio->desc, "shared memory");
}
DBUG_RETURN(vio);
}
#endif
#endif #endif
void vio_delete(Vio* vio)
{
/* It must be safe to delete null pointers. */
/* This matches the semantics of C++'s delete operator. */
if (vio)
{
if (vio->type != VIO_CLOSED)
#ifdef HAVE_VIO /*WAX*/
vio->vioclose(vio);
#else
vio_close(vio);
#endif
my_free((gptr) vio,MYF(0));
}
}
...@@ -35,18 +35,6 @@ ...@@ -35,18 +35,6 @@
#define HANDLE void * #define HANDLE void *
#endif #endif
void vio_delete(Vio* vio)
{
/* It must be safe to delete null pointers. */
/* This matches the semantics of C++'s delete operator. */
if (vio)
{
if (vio->type != VIO_CLOSED)
vio_close(vio);
my_free((gptr) vio,MYF(0));
}
}
int vio_errno(Vio *vio __attribute__((unused))) int vio_errno(Vio *vio __attribute__((unused)))
{ {
return socket_errno; /* On Win32 this mapped to WSAGetLastError() */ return socket_errno; /* On Win32 this mapped to WSAGetLastError() */
...@@ -58,14 +46,8 @@ int vio_read(Vio * vio, gptr buf, int size) ...@@ -58,14 +46,8 @@ int vio_read(Vio * vio, gptr buf, int size)
int r; int r;
DBUG_ENTER("vio_read"); DBUG_ENTER("vio_read");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
#ifdef __WIN__ #ifdef __WIN__
if (vio->type == VIO_TYPE_NAMEDPIPE)
{
DWORD length;
if (!ReadFile(vio->hPipe, buf, size, &length, NULL))
DBUG_RETURN(-1);
DBUG_RETURN(length);
}
r = recv(vio->sd, buf, size,0); r = recv(vio->sd, buf, size,0);
#else #else
errno=0; /* For linux */ errno=0; /* For linux */
...@@ -87,15 +69,8 @@ int vio_write(Vio * vio, const gptr buf, int size) ...@@ -87,15 +69,8 @@ int vio_write(Vio * vio, const gptr buf, int size)
int r; int r;
DBUG_ENTER("vio_write"); DBUG_ENTER("vio_write");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size)); DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
#if defined( __WIN__) #ifdef __WIN__
if ( vio->type == VIO_TYPE_NAMEDPIPE) r = send(vio->sd, buf, size,0);
{
DWORD length;
if (!WriteFile(vio->hPipe, (char*) buf, size, &length, NULL))
DBUG_RETURN(-1);
DBUG_RETURN(length);
}
r = send(vio->sd, buf, size, 0);
#else #else
r = write(vio->sd, buf, size); r = write(vio->sd, buf, size);
#endif /* __WIN__ */ #endif /* __WIN__ */
...@@ -109,7 +84,6 @@ int vio_write(Vio * vio, const gptr buf, int size) ...@@ -109,7 +84,6 @@ int vio_write(Vio * vio, const gptr buf, int size)
DBUG_RETURN(r); DBUG_RETURN(r);
} }
int vio_blocking(Vio * vio __attribute__((unused)), my_bool set_blocking_mode, int vio_blocking(Vio * vio __attribute__((unused)), my_bool set_blocking_mode,
my_bool *old_mode) my_bool *old_mode)
{ {
...@@ -332,3 +306,155 @@ my_bool vio_poll_read(Vio *vio,uint timeout) ...@@ -332,3 +306,155 @@ my_bool vio_poll_read(Vio *vio,uint timeout)
DBUG_RETURN(fds.revents & POLLIN ? 0 : 1); DBUG_RETURN(fds.revents & POLLIN ? 0 : 1);
#endif #endif
} }
#ifdef __WIN__
int vio_read_pipe(Vio * vio, gptr buf, int size)
{
DWORD length;
DBUG_ENTER("vio_read_pipe");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
if (!ReadFile(vio->hPipe, buf, size, &length, NULL))
DBUG_RETURN(-1);
DBUG_PRINT("exit", ("%d", length));
DBUG_RETURN(length);
}
int vio_write_pipe(Vio * vio, const gptr buf, int size)
{
DWORD length;
DBUG_ENTER("vio_write_pipe");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
if (!WriteFile(vio->hPipe, (char*) buf, size, &length, NULL))
DBUG_RETURN(-1);
DBUG_PRINT("exit", ("%d", length));
DBUG_RETURN(length);
}
int vio_close_pipe(Vio * vio)
{
int r;
DBUG_ENTER("vio_close_pipe");
#if defined(__NT__) && defined(MYSQL_SERVER)
CancelIo(vio->hPipe);
DisconnectNamedPipe(vio->hPipe);
#endif
r=CloseHandle(vio->hPipe);
if (r)
{
DBUG_PRINT("vio_error", ("close() failed, error: %d",GetLastError()));
/* FIXME: error handling (not critical for MySQL) */
}
vio->type= VIO_CLOSED;
vio->sd= -1;
DBUG_RETURN(r);
}
#ifdef HAVE_SMEM
int vio_read_shared_memory(Vio * vio, gptr buf, int size)
{
int length;
int remain_local;
char *current_postion;
DBUG_ENTER("vio_read_shared_memory");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
remain_local = size;
current_postion=buf;
do
{
if (vio->shared_memory_remain == 0)
{
if (WaitForSingleObject(vio->event_server_wrote,vio->net->read_timeout*1000) != WAIT_OBJECT_0)
{
DBUG_RETURN(-1);
};
vio->shared_memory_pos = vio->handle_map;
vio->shared_memory_remain = uint4korr((ulong*)vio->shared_memory_pos);
vio->shared_memory_pos+=4;
}
length = size;
if (vio->shared_memory_remain < length)
length = vio->shared_memory_remain;
if (length > remain_local)
length = remain_local;
memcpy(current_postion,vio->shared_memory_pos,length);
vio->shared_memory_remain-=length;
vio->shared_memory_pos+=length;
current_postion+=length;
remain_local-=length;
if (!vio->shared_memory_remain)
if (!SetEvent(vio->event_client_read)) DBUG_RETURN(-1);
} while (remain_local);
length = size;
DBUG_PRINT("exit", ("%d", length));
DBUG_RETURN(length);
}
int vio_write_shared_memory(Vio * vio, const gptr buf, int size)
{
int length;
uint remain;
HANDLE pos;
int sz;
char *current_postion;
DBUG_ENTER("vio_write_shared_memory");
DBUG_PRINT("enter", ("sd=%d, buf=%p, size=%d", vio->sd, buf, size));
remain = size;
current_postion = buf;
while (remain != 0)
{
if (WaitForSingleObject(vio->event_server_read,vio->net->write_timeout*1000) != WAIT_OBJECT_0)
{
DBUG_RETURN(-1);
};
sz = remain > shared_memory_buffer_length ? shared_memory_buffer_length: remain;
int4store(vio->handle_map,sz);
pos = vio->handle_map + 4;
memcpy(pos,current_postion,sz);
remain-=sz;
current_postion+=sz;
if (!SetEvent(vio->event_client_wrote)) DBUG_RETURN(-1);
}
length = size;
DBUG_PRINT("exit", ("%d", length));
DBUG_RETURN(length);
}
int vio_close_shared_memory(Vio * vio)
{
int r;
DBUG_ENTER("vio_close_shared_memory");
r=UnmapViewOfFile(vio->handle_map) || CloseHandle(vio->event_server_wrote) ||
CloseHandle(vio->event_server_read) || CloseHandle(vio->event_client_wrote) ||
CloseHandle(vio->event_client_read) || CloseHandle(vio->handle_file_map);
if (r)
{
DBUG_PRINT("vio_error", ("close() failed, error: %d",r));
/* FIXME: error handling (not critical for MySQL) */
}
vio->type= VIO_CLOSED;
vio->sd= -1;
DBUG_RETURN(r);
}
#endif
#endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment