Commit e9bce6c9 authored by Michael Widenius's avatar Michael Widenius

Patch set contributed by Alex Budovski (MCA)

Fix for Bug#31173: mysqlslap.exe crashes if called without any parameters

.bzrignore:
  Fixed .bzrignore rules. Many were simply not ignoring what they were meant to.
client/mysqlslap.c:
  Fixed bug for Bug#31173: mysqlslap.exe crashes if called without any parameters
  The original patch could cause memory leaks and odd problems depending on how connection was made.
  This code ensures that all mysql_options() are set for each mysql_real_connect().
  (This patch by Monty)
mysys/my_thr_init.c:
  Fixed multiply-initialized critical section on Windows, due to code incorrectly
  checking the wrong field in an attempt to prevent multiple-initialization.
sql-common/client.c:
  Don't use shared memory if it's not set (for example after failed mysql_real_connect).
  Ensure that mysql_close() resets all resources so that it's safe to call it twice.
  (Patch by monty, related to Bug#31173: mysqlslap.exe crashes if called without any parameters)
sql/CMakeLists.txt:
   Added page fault counters for SHOW PROFILE on Windows.
sql/mysqld.cc:
  Fixed attempt to set a NULL event. The code now only sets the event if appropriate (i.e. shared memory is being used)
sql/sql_profile.cc:
  Added page fault counters for SHOW PROFILE on Windows.
sql/sql_profile.h:
  Added page fault counters for SHOW PROFILE on Windows.
sql/udf_example.def:
  Some cleanup functions were not exported from udf_example.dll, causing them to
  never be executed, and as a result multiple-initialization of kernel objects
  occurred and resources were not being freed correctly.
storage/maria/ma_close.c:
  Condition variable share->key_del_cond was never being destroyed, while its
  containing heap block was being freed in maria_close(), leaking kernel
  resources.
parent ea0380f4
...@@ -40,15 +40,15 @@ ...@@ -40,15 +40,15 @@
*.dsp *.dsp
*.Po *.Po
*.Plo *.Plo
*/*.dir/* *.dir/
*/*_pure_*warnings */*_pure_*warnings
*/.deps */.deps
*/.libs/* */.libs/*
*/.pure */.pure
*/debug/* debug/
*/minsizerel/* MinSizeRel/
*/release/* Release/
*/relwithdebinfo/* RelWithDebInfo/
*~ *~
.*.swp .*.swp
./CMakeCache.txt ./CMakeCache.txt
...@@ -96,7 +96,7 @@ BitKeeper/tmp/gone ...@@ -96,7 +96,7 @@ BitKeeper/tmp/gone
BitKeeper/tmp BitKeeper/tmp
BitKeeper/log BitKeeper/log
BitKeeper/etc/SCCS BitKeeper/etc/SCCS
CMakeFiles/* CMakeFiles/
COPYING COPYING
COPYING.LIB COPYING.LIB
Docs/#manual.texi# Docs/#manual.texi#
......
...@@ -292,6 +292,25 @@ static int gettimeofday(struct timeval *tp, void *tzp) ...@@ -292,6 +292,25 @@ static int gettimeofday(struct timeval *tp, void *tzp)
} }
#endif #endif
void set_mysql_connect_options(MYSQL *mysql)
{
if (opt_compress)
mysql_options(mysql,MYSQL_OPT_COMPRESS,NullS);
#ifdef HAVE_OPENSSL
if (opt_use_ssl)
mysql_ssl_set(mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
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
mysql_options(mysql, MYSQL_SET_CHARSET_NAME, default_charset);
}
int main(int argc, char **argv) int main(int argc, char **argv)
{ {
MYSQL mysql; MYSQL mysql;
...@@ -323,20 +342,7 @@ int main(int argc, char **argv) ...@@ -323,20 +342,7 @@ int main(int argc, char **argv)
exit(1); exit(1);
} }
mysql_init(&mysql); mysql_init(&mysql);
if (opt_compress) set_mysql_connect_options(&mysql);
mysql_options(&mysql,MYSQL_OPT_COMPRESS,NullS);
#ifdef HAVE_OPENSSL
if (opt_use_ssl)
mysql_ssl_set(&mysql, opt_ssl_key, opt_ssl_cert, opt_ssl_ca,
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
mysql_options(&mysql, MYSQL_SET_CHARSET_NAME, default_charset);
if (!opt_only_print) if (!opt_only_print)
{ {
...@@ -1815,6 +1821,7 @@ pthread_handler_t run_task(void *p) ...@@ -1815,6 +1821,7 @@ pthread_handler_t run_task(void *p)
my_progname, mysql_error(mysql)); my_progname, mysql_error(mysql));
exit(0); exit(0);
} }
set_mysql_connect_options(mysql);
if (mysql_thread_init()) if (mysql_thread_init())
{ {
...@@ -1855,7 +1862,6 @@ limit_not_met: ...@@ -1855,7 +1862,6 @@ limit_not_met:
my_progname, mysql_error(mysql)); my_progname, mysql_error(mysql));
exit(0); exit(0);
} }
if (slap_connect(mysql)) if (slap_connect(mysql))
goto end; goto end;
} }
...@@ -2223,6 +2229,7 @@ slap_connect(MYSQL *mysql) ...@@ -2223,6 +2229,7 @@ slap_connect(MYSQL *mysql)
int x, connect_error= 1; int x, connect_error= 1;
for (x= 0; x < 10; x++) for (x= 0; x < 10; x++)
{ {
set_mysql_connect_options(mysql);
if (mysql_real_connect(mysql, host, user, opt_password, if (mysql_real_connect(mysql, host, user, opt_password,
create_schema_string, create_schema_string,
opt_mysql_port, opt_mysql_port,
......
...@@ -317,7 +317,7 @@ my_bool my_thread_init(void) ...@@ -317,7 +317,7 @@ my_bool my_thread_init(void)
/* /*
Skip initialization if the thread specific variable is already initialized Skip initialization if the thread specific variable is already initialized
*/ */
if (THR_KEY_mysys.id) if (THR_KEY_mysys.init)
goto end; goto end;
tmp= &THR_KEY_mysys; tmp= &THR_KEY_mysys;
#endif #endif
......
...@@ -1940,7 +1940,8 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user, ...@@ -1940,7 +1940,8 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
#if defined(HAVE_SMEM) #if defined(HAVE_SMEM)
if ((!mysql->options.protocol || if ((!mysql->options.protocol ||
mysql->options.protocol == MYSQL_PROTOCOL_MEMORY) && mysql->options.protocol == MYSQL_PROTOCOL_MEMORY) &&
(!host || !strcmp(host,LOCAL_HOST))) (!host || !strcmp(host,LOCAL_HOST)) &&
mysql->options.shared_memory_base_name)
{ {
if ((create_shared_memory(mysql,net, mysql->options.connect_timeout)) == if ((create_shared_memory(mysql,net, mysql->options.connect_timeout)) ==
INVALID_HANDLE_VALUE) INVALID_HANDLE_VALUE)
...@@ -1949,7 +1950,7 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user, ...@@ -1949,7 +1950,7 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
("host: '%s' socket: '%s' shared memory: %s have_tcpip: %d", ("host: '%s' socket: '%s' shared memory: %s have_tcpip: %d",
host ? host : "<null>", host ? host : "<null>",
unix_socket ? unix_socket : "<null>", unix_socket ? unix_socket : "<null>",
(int) mysql->options.shared_memory_base_name, mysql->options.shared_memory_base_name,
(int) have_tcpip)); (int) have_tcpip));
if (mysql->options.protocol == MYSQL_PROTOCOL_MEMORY) if (mysql->options.protocol == MYSQL_PROTOCOL_MEMORY)
goto error; goto error;
...@@ -2752,6 +2753,13 @@ void mysql_detach_stmt_list(LIST **stmt_list __attribute__((unused)), ...@@ -2752,6 +2753,13 @@ void mysql_detach_stmt_list(LIST **stmt_list __attribute__((unused)),
} }
/*
Close a MySQL connection and free all resources attached to it.
This function is coded in such that it can be called multiple times
(As some clients call this after mysql_real_connect() fails)
*/
void STDCALL mysql_close(MYSQL *mysql) void STDCALL mysql_close(MYSQL *mysql)
{ {
DBUG_ENTER("mysql_close"); DBUG_ENTER("mysql_close");
...@@ -2785,10 +2793,16 @@ void STDCALL mysql_close(MYSQL *mysql) ...@@ -2785,10 +2793,16 @@ void STDCALL mysql_close(MYSQL *mysql)
} }
#endif #endif
if (mysql != mysql->master) if (mysql != mysql->master)
{
mysql_close(mysql->master); mysql_close(mysql->master);
mysql->master= 0;
}
#ifndef MYSQL_SERVER #ifndef MYSQL_SERVER
if (mysql->thd) if (mysql->thd)
{
(*mysql->methods->free_embedded_thd)(mysql); (*mysql->methods->free_embedded_thd)(mysql);
mysql->thd= 0;
}
#endif #endif
if (mysql->free_me) if (mysql->free_me)
my_free((uchar*) mysql,MYF(0)); my_free((uchar*) mysql,MYF(0));
......
...@@ -97,7 +97,7 @@ SET_TARGET_PROPERTIES(mysqld PROPERTIES ENABLE_EXPORTS TRUE) ...@@ -97,7 +97,7 @@ SET_TARGET_PROPERTIES(mysqld PROPERTIES ENABLE_EXPORTS TRUE)
SET (MYSQLD_CORE_LIBS mysys zlib dbug strings yassl taocrypt vio regex sql libevent) SET (MYSQLD_CORE_LIBS mysys zlib dbug strings yassl taocrypt vio regex sql libevent)
TARGET_LINK_LIBRARIES(mysqld ${MYSQLD_CORE_LIBS} ${MYSQLD_STATIC_ENGINE_LIBS}) TARGET_LINK_LIBRARIES(mysqld ${MYSQLD_CORE_LIBS} ${MYSQLD_STATIC_ENGINE_LIBS})
TARGET_LINK_LIBRARIES(mysqld ws2_32.lib) TARGET_LINK_LIBRARIES(mysqld ws2_32.lib psapi.lib)
IF(MSVC AND NOT WITHOUT_DYNAMIC_PLUGINS) IF(MSVC AND NOT WITHOUT_DYNAMIC_PLUGINS)
......
...@@ -1173,11 +1173,14 @@ static void __cdecl kill_server(int sig_ptr) ...@@ -1173,11 +1173,14 @@ static void __cdecl kill_server(int sig_ptr)
/* /*
Send event to smem_event_connect_request for aborting Send event to smem_event_connect_request for aborting
*/ */
if (!SetEvent(smem_event_connect_request)) if (opt_enable_shared_memory)
{ {
DBUG_PRINT("error", if (!SetEvent(smem_event_connect_request))
("Got error: %ld from SetEvent of smem_event_connect_request", {
GetLastError())); DBUG_PRINT("error",
("Got error: %ld from SetEvent of smem_event_connect_request",
GetLastError()));
}
} }
#endif #endif
......
...@@ -131,6 +131,23 @@ int make_profile_table_for_show(THD *thd, ST_SCHEMA_TABLE *schema_table) ...@@ -131,6 +131,23 @@ int make_profile_table_for_show(THD *thd, ST_SCHEMA_TABLE *schema_table)
#define RUSAGE_USEC(tv) ((tv).tv_sec*1000*1000 + (tv).tv_usec) #define RUSAGE_USEC(tv) ((tv).tv_sec*1000*1000 + (tv).tv_usec)
#define RUSAGE_DIFF_USEC(tv1, tv2) (RUSAGE_USEC((tv1))-RUSAGE_USEC((tv2))) #define RUSAGE_DIFF_USEC(tv1, tv2) (RUSAGE_USEC((tv1))-RUSAGE_USEC((tv2)))
#ifdef __WIN__
inline ULONGLONG FileTimeToQuadWord(FILETIME *ft)
{
ULONGLONG nrv = 0;
nrv |= ft->dwHighDateTime;
nrv <<= 32;
nrv |= ft->dwLowDateTime;
return nrv;
}
// Get time difference between to FILETIME objects in seconds.
inline double GetTimeDiffInSeconds(FILETIME *a, FILETIME *b)
{
return ((FileTimeToQuadWord(a) - FileTimeToQuadWord(b)) / 1e7);
}
#endif /* __WIN__ */
PROF_MEASUREMENT::PROF_MEASUREMENT(QUERY_PROFILE *profile_arg, const char PROF_MEASUREMENT::PROF_MEASUREMENT(QUERY_PROFILE *profile_arg, const char
*status_arg) *status_arg)
...@@ -221,6 +238,11 @@ void PROF_MEASUREMENT::collect() ...@@ -221,6 +238,11 @@ void PROF_MEASUREMENT::collect()
time_usecs= (double) my_getsystime() / 10.0; /* 1 sec was 1e7, now is 1e6 */ time_usecs= (double) my_getsystime() / 10.0; /* 1 sec was 1e7, now is 1e6 */
#ifdef HAVE_GETRUSAGE #ifdef HAVE_GETRUSAGE
getrusage(RUSAGE_SELF, &rusage); getrusage(RUSAGE_SELF, &rusage);
#elif defined(__WIN__)
FILETIME ftDummy;
GetProcessTimes(GetCurrentProcess(), &ftDummy, &ftDummy, &ftKernel, &ftUser);
GetProcessIoCounters(GetCurrentProcess(), &io_count);
GetProcessMemoryInfo(GetCurrentProcess(), &mem_count, sizeof(mem_count));
#endif #endif
} }
...@@ -586,6 +608,23 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond) ...@@ -586,6 +608,23 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond)
(1000.0*1000), (1000.0*1000),
&cpu_stime_decimal); &cpu_stime_decimal);
table->field[4]->store_decimal(&cpu_utime_decimal);
table->field[5]->store_decimal(&cpu_stime_decimal);
table->field[4]->set_notnull();
table->field[5]->set_notnull();
#elif defined(__WIN__)
my_decimal cpu_utime_decimal, cpu_stime_decimal;
double2my_decimal(E_DEC_FATAL_ERROR,
GetTimeDiffInSeconds(&entry->ftUser,
&previous->ftUser),
&cpu_utime_decimal);
double2my_decimal(E_DEC_FATAL_ERROR,
GetTimeDiffInSeconds(&entry->ftKernel,
&previous->ftKernel),
&cpu_stime_decimal);
// Store the result.
table->field[4]->store_decimal(&cpu_utime_decimal); table->field[4]->store_decimal(&cpu_utime_decimal);
table->field[5]->store_decimal(&cpu_stime_decimal); table->field[5]->store_decimal(&cpu_stime_decimal);
table->field[4]->set_notnull(); table->field[4]->set_notnull();
...@@ -612,6 +651,17 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond) ...@@ -612,6 +651,17 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond)
table->field[9]->store((uint32)(entry->rusage.ru_oublock - table->field[9]->store((uint32)(entry->rusage.ru_oublock -
previous->rusage.ru_oublock)); previous->rusage.ru_oublock));
table->field[9]->set_notnull(); table->field[9]->set_notnull();
#elif defined(__WIN__)
ULONGLONG reads_delta = entry->io_count.ReadOperationCount -
previous->io_count.ReadOperationCount;
ULONGLONG writes_delta = entry->io_count.WriteOperationCount -
previous->io_count.WriteOperationCount;
table->field[8]->store((uint32)reads_delta);
table->field[8]->set_notnull();
table->field[9]->store((uint32)writes_delta);
table->field[9]->set_notnull();
#else #else
/* TODO: Add block IO info for non-BSD systems */ /* TODO: Add block IO info for non-BSD systems */
#endif #endif
...@@ -634,6 +684,13 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond) ...@@ -634,6 +684,13 @@ int PROFILING::fill_statistics_info(THD *thd, TABLE_LIST *tables, Item *cond)
table->field[13]->store((uint32)(entry->rusage.ru_minflt - table->field[13]->store((uint32)(entry->rusage.ru_minflt -
previous->rusage.ru_minflt), true); previous->rusage.ru_minflt), true);
table->field[13]->set_notnull(); table->field[13]->set_notnull();
#elif defined(__WIN__)
/* Windows APIs don't easily distinguish between hard and soft page
faults, so we just fill the 'major' column and leave the second NULL.
*/
table->field[12]->store((uint32)(entry->mem_count.PageFaultCount -
previous->mem_count.PageFaultCount), true);
table->field[12]->set_notnull();
#else #else
/* TODO: Add page fault info for non-BSD systems */ /* TODO: Add page fault info for non-BSD systems */
#endif #endif
......
...@@ -36,6 +36,10 @@ int make_profile_table_for_show(THD *thd, ST_SCHEMA_TABLE *schema_table); ...@@ -36,6 +36,10 @@ int make_profile_table_for_show(THD *thd, ST_SCHEMA_TABLE *schema_table);
#if defined(ENABLED_PROFILING) && defined(COMMUNITY_SERVER) #if defined(ENABLED_PROFILING) && defined(COMMUNITY_SERVER)
#include "mysql_priv.h" #include "mysql_priv.h"
#ifdef __WIN__
#include <psapi.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H #ifdef HAVE_SYS_RESOURCE_H
#include <sys/resource.h> #include <sys/resource.h>
#endif #endif
...@@ -165,6 +169,10 @@ private: ...@@ -165,6 +169,10 @@ private:
char *status; char *status;
#ifdef HAVE_GETRUSAGE #ifdef HAVE_GETRUSAGE
struct rusage rusage; struct rusage rusage;
#elif defined(__WIN__)
FILETIME ftKernel, ftUser;
IO_COUNTERS io_count;
PROCESS_MEMORY_COUNTERS mem_count;
#endif #endif
char *function; char *function;
......
...@@ -3,8 +3,10 @@ VERSION 1.0 ...@@ -3,8 +3,10 @@ VERSION 1.0
EXPORTS EXPORTS
lookup lookup
lookup_init lookup_init
lookup_deinit
reverse_lookup reverse_lookup
reverse_lookup_init reverse_lookup_init
reverse_lookup_deinit
metaphon_init metaphon_init
metaphon_deinit metaphon_deinit
metaphon metaphon
......
...@@ -177,6 +177,7 @@ int maria_close(register MARIA_HA *info) ...@@ -177,6 +177,7 @@ int maria_close(register MARIA_HA *info)
{ {
(void) pthread_mutex_destroy(&share->intern_lock); (void) pthread_mutex_destroy(&share->intern_lock);
(void) pthread_mutex_destroy(&share->close_lock); (void) pthread_mutex_destroy(&share->close_lock);
(void) pthread_cond_destroy(&share->key_del_cond);
my_free((uchar *)share, MYF(0)); my_free((uchar *)share, MYF(0));
/* /*
If share cannot be freed, it's because checkpoint has previously If share cannot be freed, it's because checkpoint has previously
......
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