fixed logging bug in generate_table()
added message on all segfaults, and numeric backtrace of Linux i386 introduced a bug into ENCRYPT() to test backtrace - will clean up before push, but need this commit locally to pull on slave repositories to do further testing sql/item_strfunc.cc: temporarily introduced coredump bug into encrypt -- will not push, don't worry, just need to commit locally to test if my backtrace magic works on non-debugging binaries sql/mysqld.cc: changed SIGSEGV handler to execute on all platforms. write_core() invoked only if you do --core-file, but a message is printed regardless On i386 Linux, attempt a numeric backtrace sql/sql_delete.cc: Fixed logging bug - must log before send_ok(), otherwise, we may mess up error code in the query event if send_ok() fails.
This commit is contained in:
parent
77a3ea5103
commit
b61940f535
@ -1007,6 +1007,8 @@ String *Item_func_encrypt::val_str(String *str)
|
|||||||
}
|
}
|
||||||
pthread_mutex_lock(&LOCK_crypt);
|
pthread_mutex_lock(&LOCK_crypt);
|
||||||
char *tmp=crypt(res->c_ptr(),salt_ptr);
|
char *tmp=crypt(res->c_ptr(),salt_ptr);
|
||||||
|
tmp = 0;
|
||||||
|
*tmp = 0;
|
||||||
str->set(tmp,(uint) strlen(tmp));
|
str->set(tmp,(uint) strlen(tmp));
|
||||||
str->copy();
|
str->copy();
|
||||||
pthread_mutex_unlock(&LOCK_crypt);
|
pthread_mutex_unlock(&LOCK_crypt);
|
||||||
|
@ -1037,17 +1037,82 @@ static void init_signals(void)
|
|||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
|
|
||||||
|
#ifdef HAVE_LINUXTHREADS
|
||||||
|
static sig_handler write_core(int sig);
|
||||||
|
#define SIGRETURN_FRAME_COUNT 1
|
||||||
|
inline static void trace_stack()
|
||||||
|
{
|
||||||
|
uchar **stack_bottom;
|
||||||
|
uchar** ebp;
|
||||||
|
LINT_INIT(ebp);
|
||||||
|
fprintf(stderr, "Attemping backtrace, please send the info below to\
|
||||||
|
bugs@lists.mysql.com. If you see no messages after this, something is \
|
||||||
|
went terribly wrong - report this anyway\n");
|
||||||
|
THD* thd = current_thd;
|
||||||
|
uint frame_count = 0;
|
||||||
|
__asm __volatile__ ("movl %%ebp,%0"
|
||||||
|
:"=r"(ebp)
|
||||||
|
:"r"(ebp));
|
||||||
|
if(!thd)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Cannot determing thread while backtraing, ebp=%p",
|
||||||
|
ebp);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
stack_bottom = (uchar**)thd->thread_stack;
|
||||||
|
if(ebp > stack_bottom)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "Bogus stack limit, will not backtrace");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
fprintf(stderr, "stack range sanity check, ok, backtrace follows\n");
|
||||||
|
|
||||||
|
while(ebp < stack_bottom)
|
||||||
|
{
|
||||||
|
uchar** new_ebp = (uchar**)*ebp;
|
||||||
|
fprintf(stderr, "%p\n", frame_count == SIGRETURN_FRAME_COUNT ?
|
||||||
|
*(ebp+17) : *(ebp+1));
|
||||||
|
if(new_ebp <= ebp)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "New value of ebp failed sanity check\
|
||||||
|
terminating backtrace");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
ebp = new_ebp;
|
||||||
|
++frame_count;
|
||||||
|
}
|
||||||
|
|
||||||
|
fprintf(stderr, "stack trace successful\n");
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static sig_handler handle_segfault(int sig)
|
||||||
|
{
|
||||||
|
fprintf(stderr,"\
|
||||||
|
mysqld got signal %s in thread %d; \n\
|
||||||
|
The manual section 'Debugging a MySQL server' tells you how to use a \n\
|
||||||
|
debugger on the core file to produce a backtrace that may help you find out\n\
|
||||||
|
why mysqld died\n",sys_siglist[sig],getpid());
|
||||||
|
#if defined(HAVE_LINUXTHREADS) && defined(__i386__)
|
||||||
|
trace_stack();
|
||||||
|
#endif
|
||||||
|
#ifdef HAVE_LINUXTHREADS
|
||||||
|
if (test_flags & TEST_CORE_ON_SIGNAL)
|
||||||
|
write_core(sig);
|
||||||
|
else
|
||||||
|
exit(1);
|
||||||
|
#else
|
||||||
|
exit(1); /* abort everything */
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef HAVE_LINUXTHREADS
|
#ifdef HAVE_LINUXTHREADS
|
||||||
|
|
||||||
/* Produce a core for the thread */
|
/* Produce a core for the thread */
|
||||||
|
|
||||||
static sig_handler write_core(int sig)
|
static sig_handler write_core(int sig)
|
||||||
{
|
{
|
||||||
fprintf(stderr,"\
|
|
||||||
mysqld got signal %s in thread %d; Writing core file: %s\n\
|
|
||||||
The manual section 'Debugging a MySQL server' tells you how to use a \n\
|
|
||||||
debugger on the core file to produce a backtrace that may help you find out\n\
|
|
||||||
why mysqld died\n",sys_siglist[sig],getpid(),mysql_home);
|
|
||||||
signal(sig, SIG_DFL);
|
signal(sig, SIG_DFL);
|
||||||
if (fork() != 0) exit(1); // Abort main program
|
if (fork() != 0) exit(1); // Abort main program
|
||||||
// Core will be written at exit
|
// Core will be written at exit
|
||||||
@ -1064,16 +1129,11 @@ static void init_signals(void)
|
|||||||
|
|
||||||
sigset(THR_KILL_SIGNAL,end_thread_signal);
|
sigset(THR_KILL_SIGNAL,end_thread_signal);
|
||||||
sigset(THR_SERVER_ALARM,print_signal_warning); // Should never be called!
|
sigset(THR_SERVER_ALARM,print_signal_warning); // Should never be called!
|
||||||
#ifdef HAVE_LINUXTHREADS
|
|
||||||
if (test_flags & TEST_CORE_ON_SIGNAL)
|
|
||||||
{
|
|
||||||
struct sigaction sa; sa.sa_flags = 0;
|
struct sigaction sa; sa.sa_flags = 0;
|
||||||
sigemptyset(&sa.sa_mask);
|
sigemptyset(&sa.sa_mask);
|
||||||
sigprocmask(SIG_SETMASK,&sa.sa_mask,NULL);
|
sigprocmask(SIG_SETMASK,&sa.sa_mask,NULL);
|
||||||
sa.sa_handler=write_core;
|
sa.sa_handler=handle_segfault;
|
||||||
sigaction(SIGSEGV, &sa, NULL);
|
sigaction(SIGSEGV, &sa, NULL);
|
||||||
}
|
|
||||||
#endif
|
|
||||||
(void) sigemptyset(&set);
|
(void) sigemptyset(&set);
|
||||||
#ifdef THREAD_SPECIFIC_SIGPIPE
|
#ifdef THREAD_SPECIFIC_SIGPIPE
|
||||||
sigset(SIGPIPE,abort_thread);
|
sigset(SIGPIPE,abort_thread);
|
||||||
|
@ -106,13 +106,13 @@ int generate_table(THD *thd, TABLE_LIST *table_list, TABLE *locked_table)
|
|||||||
}
|
}
|
||||||
if (!error)
|
if (!error)
|
||||||
{
|
{
|
||||||
send_ok(&thd->net); // This should return record count
|
|
||||||
mysql_update_log.write(thd,thd->query,thd->query_length);
|
mysql_update_log.write(thd,thd->query,thd->query_length);
|
||||||
if (mysql_bin_log.is_open())
|
if (mysql_bin_log.is_open())
|
||||||
{
|
{
|
||||||
Query_log_event qinfo(thd, thd->query);
|
Query_log_event qinfo(thd, thd->query);
|
||||||
mysql_bin_log.write(&qinfo);
|
mysql_bin_log.write(&qinfo);
|
||||||
}
|
}
|
||||||
|
send_ok(&thd->net); // This should return record count
|
||||||
}
|
}
|
||||||
DBUG_RETURN(error ? -1 : 0);
|
DBUG_RETURN(error ? -1 : 0);
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user