summaryrefslogtreecommitdiff
path: root/mysql-test/lib
diff options
context:
space:
mode:
Diffstat (limited to 'mysql-test/lib')
-rw-r--r--mysql-test/lib/My/CoreDump.pm39
-rw-r--r--mysql-test/lib/My/Platform.pm2
-rw-r--r--mysql-test/lib/My/SafeProcess/safe_kill_win.cc23
-rw-r--r--mysql-test/lib/My/SafeProcess/safe_process.cc50
-rw-r--r--mysql-test/lib/My/SafeProcess/safe_process_win.cc10
-rw-r--r--mysql-test/lib/mtr_cases.pm13
-rw-r--r--mysql-test/lib/mtr_report.pm2
7 files changed, 116 insertions, 23 deletions
diff --git a/mysql-test/lib/My/CoreDump.pm b/mysql-test/lib/My/CoreDump.pm
index 1ba94223b68..ae30f4f6074 100644
--- a/mysql-test/lib/My/CoreDump.pm
+++ b/mysql-test/lib/My/CoreDump.pm
@@ -264,6 +264,44 @@ EOF
}
+sub _lldb
+{
+ my ($core_name)= @_;
+
+ print "\nTrying 'lldb' to get a backtrace from coredump $core_name\n";
+
+ # Create tempfile containing lldb commands
+ my ($tmp, $tmp_name)= tempfile();
+ print $tmp
+ "bt\n",
+ "thread backtrace all\n",
+ "quit\n";
+ close $tmp or die "Error closing $tmp_name: $!";
+
+ my $lldb_output= `lldb -c '$core_name' -s '$tmp_name' 2>&1`;
+
+ unlink $tmp_name or die "Error removing $tmp_name: $!";
+
+ if ($? == 127)
+ {
+ print "lldb not found, cannot get the stack trace\n";
+ return;
+ }
+
+ return if $?;
+ return unless $lldb_output;
+
+ resfile_print <<EOF . $lldb_output . "\n";
+Output from lldb follows. The first stack trace is from the failing thread.
+The following stack traces are from all threads (so the failing one is
+duplicated).
+--------------------------
+EOF
+ return 1;
+}
+
+
+
sub show {
my ($class, $core_name, $exe_mysqld, $parallel)= @_;
$hint_mysqld= $exe_mysqld;
@@ -282,6 +320,7 @@ sub show {
(
\&_dbx,
\&_gdb,
+ \&_lldb,
# TODO...
);
diff --git a/mysql-test/lib/My/Platform.pm b/mysql-test/lib/My/Platform.pm
index cb2ac3895e3..db1206f187e 100644
--- a/mysql-test/lib/My/Platform.pm
+++ b/mysql-test/lib/My/Platform.pm
@@ -112,6 +112,8 @@ sub check_socket_path_length {
return 0 if ($^O eq 'aix');
# See Debian bug #670722 - failing on kFreeBSD even after setting short path
return 0 if $^O eq 'gnukfreebsd' and length $path < 40;
+ # GNU/Hurd doesn't have hostpath(), but no limitation either
+ return 0 if $^O eq 'gnu';
require IO::Socket::UNIX;
diff --git a/mysql-test/lib/My/SafeProcess/safe_kill_win.cc b/mysql-test/lib/My/SafeProcess/safe_kill_win.cc
index bfd38928679..4a9d5f2b8cc 100644
--- a/mysql-test/lib/My/SafeProcess/safe_kill_win.cc
+++ b/mysql-test/lib/My/SafeProcess/safe_kill_win.cc
@@ -72,23 +72,24 @@ void dump_single_process(DWORD pid)
char path[MAX_PATH];
char working_dir[MAX_PATH];
char tmpname[MAX_PATH];
+ char *filename= 0;
process= OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, pid);
if (!process)
{
- fprintf(stderr, "safe_kill : cannot open process pid=%u to create dump, last error %u\n",
+ fprintf(stderr, "safe_kill : cannot open process pid=%lu to create dump, last error %lu\n",
pid, GetLastError());
goto exit;
}
if (QueryFullProcessImageName(process, 0, path, &size) == 0)
{
- fprintf(stderr, "safe_kill : cannot read process path for pid %u, last error %u\n",
+ fprintf(stderr, "safe_kill : cannot read process path for pid %lu, last error %lu\n",
pid, GetLastError());
goto exit;
}
- char *filename= strrchr(path, '\\');
+ filename= strrchr(path, '\\');
if (filename)
{
filename++;
@@ -115,17 +116,17 @@ void dump_single_process(DWORD pid)
{
if (!GetTempFileName(".", filename, 0, tmpname))
{
- fprintf(stderr, "GetTempFileName failed, last error %u", GetLastError());
+ fprintf(stderr, "GetTempFileName failed, last error %lu", GetLastError());
goto exit;
}
- strncat(tmpname, ".dmp", sizeof(tmpname));
+ strncat_s(tmpname, ".dmp", sizeof(tmpname));
filename= tmpname;
}
if (!GetCurrentDirectory(MAX_PATH, working_dir))
{
- fprintf(stderr, "GetCurrentDirectory failed, last error %u", GetLastError());
+ fprintf(stderr, "GetCurrentDirectory failed, last error %lu", GetLastError());
goto exit;
}
@@ -134,14 +135,14 @@ void dump_single_process(DWORD pid)
if (file == INVALID_HANDLE_VALUE)
{
- fprintf(stderr, "safe_kill : CreateFile() failed for file %s, working dir %s, last error = %u\n",
+ fprintf(stderr, "safe_kill : CreateFile() failed for file %s, working dir %s, last error = %lu\n",
filename, working_dir, GetLastError());
goto exit;
}
if (!MiniDumpWriteDump(process, pid, file, MiniDumpNormal, 0, 0, 0))
{
- fprintf(stderr, "Failed to write minidump to %s, working dir %s, last error %u\n",
+ fprintf(stderr, "Failed to write minidump to %s, working dir %s, last error %lu\n",
filename, working_dir, GetLastError());
goto exit;
}
@@ -213,7 +214,7 @@ int main(int argc, const char** argv )
if (!GetExitCodeProcess(process,&exit_code))
{
- fprintf(stderr, "GetExitCodeProcess failed, pid= %d, err= %d\n",
+ fprintf(stderr, "GetExitCodeProcess failed, pid= %lu, err= %lu\n",
pid, GetLastError());
exit(1);
}
@@ -231,7 +232,7 @@ int main(int argc, const char** argv )
Sleep(100);
else
{
- fprintf(stderr, "Failed to open shutdown_event '%s', error: %d\n",
+ fprintf(stderr, "Failed to open shutdown_event '%s', error: %lu\n",
safe_process_name, GetLastError());
exit(3);
}
@@ -239,7 +240,7 @@ int main(int argc, const char** argv )
if(SetEvent(shutdown_event) == 0)
{
- fprintf(stderr, "Failed to signal shutdown_event '%s', error: %d\n",
+ fprintf(stderr, "Failed to signal shutdown_event '%s', error: %lu\n",
safe_process_name, GetLastError());
CloseHandle(shutdown_event);
exit(4);
diff --git a/mysql-test/lib/My/SafeProcess/safe_process.cc b/mysql-test/lib/My/SafeProcess/safe_process.cc
index 13d09198a0c..4d0d1e2a3a0 100644
--- a/mysql-test/lib/My/SafeProcess/safe_process.cc
+++ b/mysql-test/lib/My/SafeProcess/safe_process.cc
@@ -90,6 +90,53 @@ static void die(const char* fmt, ...)
}
+#ifdef __APPLE__
+#include <sys/sysctl.h>
+
+
+/*
+ Eventually we may want to adopt kern.corefile parsing code from
+ https://opensource.apple.com/source/xnu/xnu-3247.1.106/bsd/kern/kern_proc.c
+*/
+
+void handle_core(pid_t pid)
+{
+ char corefile[256];
+ int coredump;
+ size_t corefile_size= sizeof(corefile);
+ size_t coredump_size= sizeof(coredump);
+
+ if (sysctlbyname("kern.coredump", &coredump, &coredump_size, 0, 0) ||
+ sysctlbyname("kern.corefile", corefile, &corefile_size, 0, 0))
+ {
+ message("sysctlbyname failed: %d (%s)", errno, strerror(errno));
+ return;
+ }
+
+ if (!coredump)
+ {
+ message("core dumps disabled, to enable run sudo sysctl kern.coredump=1");
+ return;
+ }
+
+ if (!strncmp(corefile, "/cores/core.%P", corefile_size))
+ {
+ char from[256];
+ char *to= from + 7;
+
+ snprintf(from, sizeof(from), "/cores/core.%u", pid);
+ if (!access(from, R_OK))
+ {
+ if (symlink(from, to))
+ message("symlink failed: %d (%s)", errno, strerror(errno));
+ }
+ }
+}
+#else
+void handle_core(pid_t pid __attribute__((unused))) {}
+#endif
+
+
static int kill_child(bool was_killed)
{
int status= 0;
@@ -113,7 +160,10 @@ static int kill_child(bool was_killed)
}
if (WIFSIGNALED(status))
+ {
message("Child killed by signal: %d", WTERMSIG(status));
+ handle_core(child_pid);
+ }
return exit_code;
}
diff --git a/mysql-test/lib/My/SafeProcess/safe_process_win.cc b/mysql-test/lib/My/SafeProcess/safe_process_win.cc
index 4dd4e24f30d..8a5bb60a3f5 100644
--- a/mysql-test/lib/My/SafeProcess/safe_process_win.cc
+++ b/mysql-test/lib/My/SafeProcess/safe_process_win.cc
@@ -75,7 +75,7 @@ static void message(const char* fmt, ...)
static void die(const char* fmt, ...)
{
- DWORD last_err= GetLastError();
+ int last_err= GetLastError();
va_list args;
fprintf(stderr, "%s: FATAL ERROR, ", safe_process_name);
va_start(args, fmt);
@@ -106,7 +106,7 @@ static void die(const char* fmt, ...)
DWORD get_parent_pid(DWORD pid)
{
HANDLE snapshot;
- DWORD parent_pid= -1;
+ DWORD parent_pid= 0;
PROCESSENTRY32 pe32;
pe32.dwSize= sizeof(PROCESSENTRY32);
@@ -127,7 +127,7 @@ DWORD get_parent_pid(DWORD pid)
} while(Process32Next( snapshot, &pe32));
CloseHandle(snapshot);
- if (parent_pid == -1)
+ if (parent_pid == 0)
die("Could not find parent pid");
return parent_pid;
@@ -163,7 +163,7 @@ int main(int argc, const char** argv )
PROCESS_INFORMATION process_info= {0};
BOOL nocore= FALSE;
- sprintf(safe_process_name, "safe_process[%d]", pid);
+ sprintf(safe_process_name, "safe_process[%lu]", pid);
/* Create an event for the signal handler */
if ((shutdown_event=
@@ -298,7 +298,7 @@ int main(int argc, const char** argv )
BOOL process_created= FALSE;
BOOL jobobject_assigned= FALSE;
- for (int i=0; i < sizeof(create_flags)/sizeof(create_flags[0]); i++)
+ for (size_t i=0; i < sizeof(create_flags)/sizeof(create_flags[0]); i++)
{
process_created= CreateProcess(NULL, (LPSTR)child_args,
NULL,
diff --git a/mysql-test/lib/mtr_cases.pm b/mysql-test/lib/mtr_cases.pm
index 8c94c281edf..5958849da09 100644
--- a/mysql-test/lib/mtr_cases.pm
+++ b/mysql-test/lib/mtr_cases.pm
@@ -292,7 +292,7 @@ sub combinations_from_file($$)
} else {
return () if @::opt_combinations or not -f $filename;
# Read combinations file in my.cnf format
- mtr_verbose("Read combinations file");
+ mtr_verbose("Read combinations file $filename");
my $config= My::Config->new($filename);
foreach my $group ($config->option_groups()) {
my $comb= { name => $group->name(), comb_opt => [] };
@@ -398,7 +398,7 @@ sub collect_suite_name($$)
}
}
} else {
- $suites{$suitename} = [ $::glob_mysql_test_dir,
+ $suites{$suitename} = [ $::glob_mysql_test_dir . "/main",
my_find_dir(dirname($::glob_mysql_test_dir),
[ @plugin_suitedirs ],
'main', NOT_REQUIRED) ];
@@ -470,7 +470,9 @@ sub process_suite {
$suitename = $basename;
}
- my $suite = load_suite_object($suitename, $suitedir);
+ my $suite = load_suite_object($suitename, (($suitename eq "main") ?
+ $::glob_mysql_test_dir :
+ $suitedir));
#
# Read suite config files, unless it was done aleady
@@ -647,7 +649,7 @@ sub make_combinations($$@)
{
# Copy test options
my $new_test= $test->copy();
-
+
# Prepend the combination options to master_opt and slave_opt
# (on the command line combinations go *before* .opt files)
unshift @{$new_test->{master_opt}}, @{$comb->{comb_opt}};
@@ -693,8 +695,6 @@ sub collect_one_test_case {
my $tpath = shift;
my $tname = shift;
my %test_combs = map { $_ => 1 } @_;
-
-
my $suitename = $suite->{name};
my $name = "$suitename.$tname";
my $filename = "$tpath/${tname}.test";
@@ -1096,6 +1096,7 @@ sub get_tags_from_file($$) {
$file_to_slave_opts{$file}= $slave_opts;
$file_combinations{$file}= [ ::uniq(@combinations) ];
$file_in_overlay{$file} = 1 if $in_overlay;
+
return @{$tags};
}
diff --git a/mysql-test/lib/mtr_report.pm b/mysql-test/lib/mtr_report.pm
index 0b99eafa4cf..25d3256ca4e 100644
--- a/mysql-test/lib/mtr_report.pm
+++ b/mysql-test/lib/mtr_report.pm
@@ -135,7 +135,7 @@ sub mtr_report_test ($) {
my $logfile= $tinfo->{'logfile'};
my $warnings= $tinfo->{'warnings'};
my $result= $tinfo->{'result'};
- my $retry= $tinfo->{'retries'} ? "retry-" : "";
+ my $retry= $tinfo->{'retries'} ? "retry-" : $tinfo->{'repeat'} ? "$tinfo->{'repeat'} " : "";
if ($result eq 'MTR_RES_FAILED'){