You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

5068 lines
135 KiB

18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
18 years ago
Fixed compiler warnings Fixed compile-pentium64 scripts Fixed wrong estimate of update_with_key_prefix in sql-bench Merge bk-internal.mysql.com:/home/bk/mysql-5.1 into mysql.com:/home/my/mysql-5.1 Fixed unsafe define of uint4korr() Fixed that --extern works with mysql-test-run.pl Small trivial cleanups This also fixes a bug in counting number of rows that are updated when we have many simultanous queries Move all connection handling and command exectuion main loop from sql_parse.cc to sql_connection.cc Split handle_one_connection() into reusable sub functions. Split create_new_thread() into reusable sub functions. Added thread_scheduler; Preliminary interface code for future thread_handling code. Use 'my_thread_id' for internal thread id's Make thr_alarm_kill() to depend on thread_id instead of thread Make thr_abort_locks_for_thread() depend on thread_id instead of thread In store_globals(), set my_thread_var->id to be thd->thread_id. Use my_thread_var->id as basis for my_thread_name() The above changes makes the connection we have between THD and threads more soft. Added a lot of DBUG_PRINT() and DBUG_ASSERT() functions Fixed compiler warnings Fixed core dumps when running with --debug Removed setting of signal masks (was never used) Made event code call pthread_exit() (portability fix) Fixed that event code doesn't call DBUG_xxx functions before my_thread_init() is called. Made handling of thread_id and thd->variables.pseudo_thread_id uniform. Removed one common 'not freed memory' warning from mysqltest Fixed a couple of usage of not initialized warnings (unlikely cases) Suppress compiler warnings from bdb and (for the moment) warnings from ndb
19 years ago
18 years ago
18 years ago
18 years ago
Fixed compiler warnings Fixed compile-pentium64 scripts Fixed wrong estimate of update_with_key_prefix in sql-bench Merge bk-internal.mysql.com:/home/bk/mysql-5.1 into mysql.com:/home/my/mysql-5.1 Fixed unsafe define of uint4korr() Fixed that --extern works with mysql-test-run.pl Small trivial cleanups This also fixes a bug in counting number of rows that are updated when we have many simultanous queries Move all connection handling and command exectuion main loop from sql_parse.cc to sql_connection.cc Split handle_one_connection() into reusable sub functions. Split create_new_thread() into reusable sub functions. Added thread_scheduler; Preliminary interface code for future thread_handling code. Use 'my_thread_id' for internal thread id's Make thr_alarm_kill() to depend on thread_id instead of thread Make thr_abort_locks_for_thread() depend on thread_id instead of thread In store_globals(), set my_thread_var->id to be thd->thread_id. Use my_thread_var->id as basis for my_thread_name() The above changes makes the connection we have between THD and threads more soft. Added a lot of DBUG_PRINT() and DBUG_ASSERT() functions Fixed compiler warnings Fixed core dumps when running with --debug Removed setting of signal masks (was never used) Made event code call pthread_exit() (portability fix) Fixed that event code doesn't call DBUG_xxx functions before my_thread_init() is called. Made handling of thread_id and thd->variables.pseudo_thread_id uniform. Removed one common 'not freed memory' warning from mysqltest Fixed a couple of usage of not initialized warnings (unlikely cases) Suppress compiler warnings from bdb and (for the moment) warnings from ndb
19 years ago
20 years ago
20 years ago
20 years ago
20 years ago
20 years ago
20 years ago
20 years ago
20 years ago
20 years ago
18 years ago
17 years ago
18 years ago
18 years ago
18 years ago
20 years ago
20 years ago
Fixed compiler warnings Fixed compile-pentium64 scripts Fixed wrong estimate of update_with_key_prefix in sql-bench Merge bk-internal.mysql.com:/home/bk/mysql-5.1 into mysql.com:/home/my/mysql-5.1 Fixed unsafe define of uint4korr() Fixed that --extern works with mysql-test-run.pl Small trivial cleanups This also fixes a bug in counting number of rows that are updated when we have many simultanous queries Move all connection handling and command exectuion main loop from sql_parse.cc to sql_connection.cc Split handle_one_connection() into reusable sub functions. Split create_new_thread() into reusable sub functions. Added thread_scheduler; Preliminary interface code for future thread_handling code. Use 'my_thread_id' for internal thread id's Make thr_alarm_kill() to depend on thread_id instead of thread Make thr_abort_locks_for_thread() depend on thread_id instead of thread In store_globals(), set my_thread_var->id to be thd->thread_id. Use my_thread_var->id as basis for my_thread_name() The above changes makes the connection we have between THD and threads more soft. Added a lot of DBUG_PRINT() and DBUG_ASSERT() functions Fixed compiler warnings Fixed core dumps when running with --debug Removed setting of signal masks (was never used) Made event code call pthread_exit() (portability fix) Fixed that event code doesn't call DBUG_xxx functions before my_thread_init() is called. Made handling of thread_id and thd->variables.pseudo_thread_id uniform. Removed one common 'not freed memory' warning from mysqltest Fixed a couple of usage of not initialized warnings (unlikely cases) Suppress compiler warnings from bdb and (for the moment) warnings from ndb
19 years ago
Fixed compiler warnings Fixed compile-pentium64 scripts Fixed wrong estimate of update_with_key_prefix in sql-bench Merge bk-internal.mysql.com:/home/bk/mysql-5.1 into mysql.com:/home/my/mysql-5.1 Fixed unsafe define of uint4korr() Fixed that --extern works with mysql-test-run.pl Small trivial cleanups This also fixes a bug in counting number of rows that are updated when we have many simultanous queries Move all connection handling and command exectuion main loop from sql_parse.cc to sql_connection.cc Split handle_one_connection() into reusable sub functions. Split create_new_thread() into reusable sub functions. Added thread_scheduler; Preliminary interface code for future thread_handling code. Use 'my_thread_id' for internal thread id's Make thr_alarm_kill() to depend on thread_id instead of thread Make thr_abort_locks_for_thread() depend on thread_id instead of thread In store_globals(), set my_thread_var->id to be thd->thread_id. Use my_thread_var->id as basis for my_thread_name() The above changes makes the connection we have between THD and threads more soft. Added a lot of DBUG_PRINT() and DBUG_ASSERT() functions Fixed compiler warnings Fixed core dumps when running with --debug Removed setting of signal masks (was never used) Made event code call pthread_exit() (portability fix) Fixed that event code doesn't call DBUG_xxx functions before my_thread_init() is called. Made handling of thread_id and thd->variables.pseudo_thread_id uniform. Removed one common 'not freed memory' warning from mysqltest Fixed a couple of usage of not initialized warnings (unlikely cases) Suppress compiler warnings from bdb and (for the moment) warnings from ndb
19 years ago
18 years ago
  1. #!/usr/bin/perl
  2. # -*- cperl -*-
  3. #
  4. ##############################################################################
  5. #
  6. # mysql-test-run.pl
  7. #
  8. # Tool used for executing a suite of .test files
  9. #
  10. # See the "MySQL Test framework manual" for more information
  11. # http://dev.mysql.com/doc/mysqltest/en/index.html
  12. #
  13. #
  14. ##############################################################################
  15. use strict;
  16. use warnings;
  17. BEGIN {
  18. # Check that mysql-test-run.pl is started from mysql-test/
  19. unless ( -f "mysql-test-run.pl" )
  20. {
  21. print "**** ERROR **** ",
  22. "You must start mysql-test-run from the mysql-test/ directory\n";
  23. exit(1);
  24. }
  25. # Check that lib exist
  26. unless ( -d "lib/" )
  27. {
  28. print "**** ERROR **** ",
  29. "Could not find the lib/ directory \n";
  30. exit(1);
  31. }
  32. }
  33. BEGIN {
  34. # Check backward compatibility support
  35. # By setting the environment variable MTR_VERSION
  36. # it's possible to use a previous version of
  37. # mysql-test-run.pl
  38. my $version= $ENV{MTR_VERSION} || 2;
  39. if ( $version == 1 )
  40. {
  41. print "=======================================================\n";
  42. print " WARNING: Using mysql-test-run.pl version 1! \n";
  43. print "=======================================================\n";
  44. # Should use exec() here on *nix but this appears not to work on Windows
  45. exit(system($^X, "lib/v1/mysql-test-run.pl", @ARGV) >> 8);
  46. }
  47. elsif ( $version == 2 )
  48. {
  49. # This is the current version, just continue
  50. ;
  51. }
  52. else
  53. {
  54. print "ERROR: Version $version of mysql-test-run does not exist!\n";
  55. exit(1);
  56. }
  57. }
  58. use lib "lib";
  59. use Cwd;
  60. use Getopt::Long;
  61. use My::File::Path; # Patched version of File::Path
  62. use File::Basename;
  63. use File::Copy;
  64. use File::Find;
  65. use File::Temp qw / tempdir /;
  66. use File::Spec::Functions qw / splitdir /;
  67. use My::Platform;
  68. use My::SafeProcess;
  69. use My::ConfigFactory;
  70. use My::Options;
  71. use My::Find;
  72. use My::SysInfo;
  73. use My::CoreDump;
  74. use mtr_cases;
  75. use mtr_report;
  76. use mtr_match;
  77. use mtr_unique;
  78. use IO::Socket::INET;
  79. use IO::Select;
  80. require "lib/mtr_process.pl";
  81. require "lib/mtr_io.pl";
  82. require "lib/mtr_gcov.pl";
  83. require "lib/mtr_misc.pl";
  84. $SIG{INT}= sub { mtr_error("Got ^C signal"); };
  85. our $mysql_version_id;
  86. our $glob_mysql_test_dir;
  87. our $basedir;
  88. our $path_charsetsdir;
  89. our $path_client_bindir;
  90. our $path_client_libdir;
  91. our $path_language;
  92. our $path_current_testlog;
  93. our $path_testlog;
  94. our $default_vardir;
  95. our $opt_vardir; # Path to use for var/ dir
  96. my $path_vardir_trace; # unix formatted opt_vardir for trace files
  97. my $opt_tmpdir; # Path to use for tmp/ dir
  98. my $opt_tmpdir_pid;
  99. END {
  100. if (defined $opt_tmpdir_pid and
  101. $opt_tmpdir_pid == $$){
  102. # Remove the tempdir this process has created
  103. mtr_verbose("Removing tmpdir '$opt_tmpdir");
  104. rmtree($opt_tmpdir);
  105. }
  106. }
  107. my $path_config_file; # The generated config file, var/my.cnf
  108. # Visual Studio produces executables in different sub-directories based on the
  109. # configuration used to build them. To make life easier, an environment
  110. # variable or command-line option may be specified to control which set of
  111. # executables will be used by the test suite.
  112. our $opt_vs_config = $ENV{'MTR_VS_CONFIG'};
  113. my $DEFAULT_SUITES= "main,binlog,federated,rpl,rpl_ndb,ndb";
  114. my $opt_suites;
  115. our $opt_verbose= 0; # Verbose output, enable with --verbose
  116. our $exe_mysql;
  117. our $exe_mysqladmin;
  118. our $exe_mysqltest;
  119. our $exe_libtool;
  120. our $opt_big_test= 0;
  121. our @opt_combinations;
  122. our @opt_extra_mysqld_opt;
  123. my $opt_compress;
  124. my $opt_ssl;
  125. my $opt_skip_ssl;
  126. my $opt_ssl_supported;
  127. my $opt_ps_protocol;
  128. my $opt_sp_protocol;
  129. my $opt_cursor_protocol;
  130. my $opt_view_protocol;
  131. our $opt_debug;
  132. our @opt_cases; # The test cases names in argv
  133. our $opt_embedded_server;
  134. # Options used when connecting to an already running server
  135. my %opts_extern;
  136. sub using_extern { return (keys %opts_extern > 0);};
  137. our $opt_fast= 0;
  138. our $opt_force;
  139. our $opt_mem= $ENV{'MTR_MEM'};
  140. our $opt_gcov;
  141. our $opt_gcov_exe= "gcov";
  142. our $opt_gcov_err= "mysql-test-gcov.msg";
  143. our $opt_gcov_msg= "mysql-test-gcov.err";
  144. our $glob_debugger= 0;
  145. our $opt_gdb;
  146. our $opt_client_gdb;
  147. our $opt_ddd;
  148. our $opt_client_ddd;
  149. our $opt_manual_gdb;
  150. our $opt_manual_ddd;
  151. our $opt_manual_debug;
  152. our $opt_debugger;
  153. our $opt_client_debugger;
  154. my $config; # The currently running config
  155. my $current_config_name; # The currently running config file template
  156. my $baseport;
  157. my $opt_build_thread= $ENV{'MTR_BUILD_THREAD'} || "auto";
  158. my $opt_record;
  159. my $opt_report_features;
  160. our $opt_check_testcases= 1;
  161. my $opt_mark_progress;
  162. my $opt_sleep;
  163. my $opt_testcase_timeout= 15; # minutes
  164. my $opt_suite_timeout = 300; # minutes
  165. my $opt_shutdown_timeout= 10; # seconds
  166. my $opt_start_timeout = 180; # seconds
  167. sub testcase_timeout { return $opt_testcase_timeout * 60; };
  168. sub suite_timeout { return $opt_suite_timeout * 60; };
  169. sub check_timeout { return $opt_testcase_timeout * 6; };
  170. my $opt_start;
  171. my $opt_start_dirty;
  172. my $opt_repeat= 1;
  173. my $opt_retry= 3;
  174. my $opt_retry_failure= 2;
  175. my $opt_strace_client;
  176. our $opt_user = "root";
  177. my $opt_valgrind= 0;
  178. my $opt_valgrind_mysqld= 0;
  179. my $opt_valgrind_mysqltest= 0;
  180. my @default_valgrind_args= ("--show-reachable=yes");
  181. my @valgrind_args;
  182. my $opt_valgrind_path;
  183. my $opt_callgrind;
  184. our $opt_warnings= 1;
  185. our $opt_skip_ndbcluster= 0;
  186. my $exe_ndbd;
  187. my $exe_ndb_mgmd;
  188. my $exe_ndb_waiter;
  189. our $debug_compiled_binaries;
  190. our %mysqld_variables;
  191. my $source_dist= 0;
  192. my $opt_max_save_core= $ENV{MTR_MAX_SAVE_CORE} || 5;
  193. my $opt_max_save_datadir= $ENV{MTR_MAX_SAVE_DATADIR} || 20;
  194. my $opt_max_test_fail= $ENV{MTR_MAX_TEST_FAIL} || 10;
  195. my $opt_parallel= $ENV{MTR_PARALLEL} || 1;
  196. select(STDOUT);
  197. $| = 1; # Automatically flush STDOUT
  198. main();
  199. sub main {
  200. # Default, verbosity on
  201. report_option('verbose', 0);
  202. # This is needed for test log evaluation in "gen-build-status-page"
  203. # in all cases where the calling tool does not log the commands
  204. # directly before it executes them, like "make test-force-pl" in RPM builds.
  205. mtr_report("Logging: $0 ", join(" ", @ARGV));
  206. command_line_setup();
  207. if ( $opt_gcov ) {
  208. gcov_prepare($basedir);
  209. }
  210. if (!$opt_suites) {
  211. $opt_suites= $DEFAULT_SUITES;
  212. # Check for any extra suites to enable based on the path name
  213. my %extra_suites=
  214. (
  215. "mysql-5.1-new-ndb" => "ndb_team",
  216. "mysql-5.1-new-ndb-merge" => "ndb_team",
  217. "mysql-5.1-telco-6.2" => "ndb_team",
  218. "mysql-5.1-telco-6.2-merge" => "ndb_team",
  219. "mysql-5.1-telco-6.3" => "ndb_team",
  220. "mysql-6.0-ndb" => "ndb_team",
  221. );
  222. foreach my $dir ( reverse splitdir($basedir) ) {
  223. my $extra_suite= $extra_suites{$dir};
  224. if (defined $extra_suite) {
  225. mtr_report("Found extra suite: $extra_suite");
  226. $opt_suites= "$extra_suite,$opt_suites";
  227. last;
  228. }
  229. }
  230. }
  231. mtr_report("Collecting tests...");
  232. my $tests= collect_test_cases($opt_suites, \@opt_cases);
  233. if ( $opt_report_features ) {
  234. # Put "report features" as the first test to run
  235. my $tinfo = My::Test->new
  236. (
  237. name => 'report_features',
  238. # No result_file => Prints result
  239. path => 'include/report-features.test',
  240. template_path => "include/default_my.cnf",
  241. master_opt => [],
  242. slave_opt => [],
  243. );
  244. unshift(@$tests, $tinfo);
  245. }
  246. print "vardir: $opt_vardir\n";
  247. initialize_servers();
  248. #######################################################################
  249. my $num_tests= @$tests;
  250. if ( not defined $opt_parallel ) {
  251. # Try to find a suitable value for number of workers
  252. my $sys_info= My::SysInfo->new();
  253. $opt_parallel= $sys_info->num_cpus();
  254. for my $limit (2000, 1500, 1000, 500){
  255. $opt_parallel-- if ($sys_info->min_bogomips() < $limit);
  256. }
  257. $opt_parallel= 8 if ($opt_parallel > 8);
  258. $opt_parallel= $num_tests if ($opt_parallel > $num_tests);
  259. $opt_parallel= 1 if (IS_WINDOWS and $sys_info->isvm());
  260. $opt_parallel= 1 if ($opt_parallel < 1);
  261. mtr_report("Using parallel: $opt_parallel");
  262. }
  263. # Create server socket on any free port
  264. my $server = new IO::Socket::INET
  265. (
  266. LocalAddr => 'localhost',
  267. Proto => 'tcp',
  268. Listen => $opt_parallel,
  269. );
  270. mtr_error("Could not create testcase server port: $!") unless $server;
  271. my $server_port = $server->sockport();
  272. mtr_report("Using server port $server_port");
  273. # Create child processes
  274. my %children;
  275. for my $child_num (1..$opt_parallel){
  276. my $child_pid= My::SafeProcess::Base::_safe_fork();
  277. if ($child_pid == 0){
  278. $server= undef; # Close the server port in child
  279. $tests= {}; # Don't need the tests list in child
  280. # Use subdir of var and tmp unless only one worker
  281. if ($opt_parallel > 1) {
  282. set_vardir("$opt_vardir/$child_num");
  283. $opt_tmpdir= "$opt_tmpdir/$child_num";
  284. }
  285. run_worker($server_port, $child_num);
  286. exit(1);
  287. }
  288. $children{$child_pid}= 1;
  289. }
  290. #######################################################################
  291. mtr_report();
  292. mtr_print_thick_line();
  293. mtr_print_header();
  294. my $completed= run_test_server($server, $tests, $opt_parallel);
  295. # Send Ctrl-C to any children still running
  296. kill("INT", keys(%children));
  297. # Wait for childs to exit
  298. foreach my $pid (keys %children)
  299. {
  300. my $ret_pid= waitpid($pid, 0);
  301. if ($ret_pid != $pid){
  302. mtr_report("Unknown process $ret_pid exited");
  303. }
  304. else {
  305. delete $children{$ret_pid};
  306. }
  307. }
  308. if ( not defined @$completed ) {
  309. mtr_error("Test suite aborted");
  310. }
  311. if ( @$completed != $num_tests){
  312. if ($opt_force){
  313. # All test should have been run, print any that are still in $tests
  314. #foreach my $test ( @$tests ){
  315. # $test->print_test();
  316. #}
  317. }
  318. # Not all tests completed, failure
  319. mtr_report();
  320. mtr_report("Only ", int(@$completed), " of $num_tests completed.");
  321. mtr_error("Not all tests completed");
  322. }
  323. mtr_print_line();
  324. if ( $opt_gcov ) {
  325. gcov_collect($basedir, $opt_gcov_exe,
  326. $opt_gcov_msg, $opt_gcov_err);
  327. }
  328. mtr_report_stats($completed);
  329. exit(0);
  330. }
  331. sub run_test_server ($$$) {
  332. my ($server, $tests, $childs) = @_;
  333. my $num_saved_cores= 0; # Number of core files saved in vardir/log/ so far.
  334. my $num_saved_datadir= 0; # Number of datadirs saved in vardir/log/ so far.
  335. my $num_failed_test= 0; # Number of tests failed so far
  336. # Scheduler variables
  337. my $max_ndb= $childs / 2;
  338. $max_ndb = 4 if $max_ndb > 4;
  339. $max_ndb = 1 if $max_ndb < 1;
  340. my $num_ndb_tests= 0;
  341. my $completed= [];
  342. my %running;
  343. my $result;
  344. my $suite_timeout_proc= My::SafeProcess->timer(suite_timeout());
  345. my $s= IO::Select->new();
  346. $s->add($server);
  347. while (1) {
  348. my @ready = $s->can_read(1); # Wake up once every second
  349. foreach my $sock (@ready) {
  350. if ($sock == $server) {
  351. # New client connected
  352. my $child= $sock->accept();
  353. mtr_verbose("Client connected");
  354. $s->add($child);
  355. print $child "HELLO\n";
  356. }
  357. else {
  358. my $line= <$sock>;
  359. if (!defined $line) {
  360. # Client disconnected
  361. mtr_verbose("Child closed socket");
  362. $s->remove($sock);
  363. if (--$childs == 0){
  364. $suite_timeout_proc->kill();
  365. return $completed;
  366. }
  367. next;
  368. }
  369. chomp($line);
  370. if ($line eq 'TESTRESULT'){
  371. $result= My::Test::read_test($sock);
  372. # $result->print_test();
  373. # Report test status
  374. mtr_report_test($result);
  375. if ( $result->is_failed() ) {
  376. # Save the workers "savedir" in var/log
  377. my $worker_savedir= $result->{savedir};
  378. my $worker_savename= basename($worker_savedir);
  379. my $savedir= "$opt_vardir/log/$worker_savename";
  380. if ($opt_max_save_datadir > 0 &&
  381. $num_saved_datadir >= $opt_max_save_datadir)
  382. {
  383. mtr_report(" - skipping '$worker_savedir/'");
  384. rmtree($worker_savedir);
  385. }
  386. else {
  387. mtr_report(" - saving '$worker_savedir/' to '$savedir/'");
  388. rename($worker_savedir, $savedir);
  389. # Move any core files from e.g. mysqltest
  390. foreach my $coref (glob("core*"), glob("*.dmp"))
  391. {
  392. mtr_report(" - found '$coref', moving it to '$savedir'");
  393. move($coref, $savedir);
  394. }
  395. if ($opt_max_save_core > 0) {
  396. # Limit number of core files saved
  397. find({ no_chdir => 1,
  398. wanted => sub {
  399. my $core_file= $File::Find::name;
  400. my $core_name= basename($core_file);
  401. if ($core_name =~ /^core/ or # Starting with core
  402. (IS_WINDOWS and $core_name =~ /\.dmp$/)){
  403. # Ending with .dmp
  404. mtr_report(" - found '$core_name'",
  405. "($num_saved_cores/$opt_max_save_core)");
  406. My::CoreDump->show($core_file);
  407. if ($num_saved_cores >= $opt_max_save_core) {
  408. mtr_report(" - deleting it, already saved",
  409. "$opt_max_save_core");
  410. unlink("$core_file");
  411. }
  412. ++$num_saved_cores;
  413. }
  414. }
  415. },
  416. $savedir);
  417. }
  418. }
  419. $num_saved_datadir++;
  420. if ( !$opt_force ) {
  421. # Test has failed, force is off
  422. $suite_timeout_proc->kill();
  423. push(@$completed, $result);
  424. return $completed;
  425. }
  426. elsif ($opt_max_test_fail > 0 and
  427. $num_failed_test >= $opt_max_test_fail) {
  428. $suite_timeout_proc->kill();
  429. mtr_report("Too many tests($num_failed_test) failed!",
  430. "Terminating...");
  431. return undef;
  432. }
  433. $num_failed_test++;
  434. }
  435. # Retry test run after test failure
  436. my $retries= $result->{retries} || 2;
  437. my $test_has_failed= $result->{failures} || 0;
  438. if ($test_has_failed and $retries <= $opt_retry){
  439. # Test should be run one more time unless it has failed
  440. # too many times already
  441. my $failures= $result->{failures};
  442. if ($opt_retry > 1 and $failures >= $opt_retry_failure){
  443. mtr_report("\nTest has failed $failures times,",
  444. "no more retries!\n");
  445. }
  446. else {
  447. mtr_report("\nRetrying test, attempt($retries/$opt_retry)...\n");
  448. delete($result->{result});
  449. $result->{retries}= $retries+1;
  450. $result->write_test($sock, 'TESTCASE');
  451. next;
  452. }
  453. }
  454. # Repeat test $opt_repeat number of times
  455. my $repeat= $result->{repeat} || 1;
  456. if ($repeat < $opt_repeat)
  457. {
  458. $result->{retries}= 0;
  459. $result->{failures}= 0;
  460. delete($result->{result});
  461. $result->{repeat}= $repeat+1;
  462. $result->write_test($sock, 'TESTCASE');
  463. next;
  464. }
  465. # Remove from list of running
  466. mtr_error("'", $result->{name},"' is not known to be running")
  467. unless delete $running{$result->key()};
  468. # Update scheduler variables
  469. $num_ndb_tests-- if ($result->{ndb_test});
  470. # Save result in completed list
  471. push(@$completed, $result);
  472. }
  473. elsif ($line eq 'START'){
  474. ; # Send first test
  475. }
  476. else {
  477. mtr_error("Unknown response: '$line' from client");
  478. }
  479. # Find next test to schedule
  480. # - Try to use same configuration as worker used last time
  481. # - Limit number of parallel ndb tests
  482. my $next;
  483. my $second_best;
  484. for(my $i= 0; $i <= @$tests; $i++)
  485. {
  486. my $t= $tests->[$i];
  487. last unless defined $t;
  488. if (run_testcase_check_skip_test($t)){
  489. # Move the test to completed list
  490. #mtr_report("skip - Moving test $i to completed");
  491. push(@$completed, splice(@$tests, $i, 1));
  492. # Since the test at pos $i was taken away, next
  493. # test will also be at $i -> redo
  494. redo;
  495. }
  496. # Limit number of parallell NDB tests
  497. if ($t->{ndb_test} and $num_ndb_tests >= $max_ndb){
  498. #mtr_report("Skipping, num ndb is already at max, $num_ndb_tests");
  499. next;
  500. }
  501. # Prefer same configuration
  502. if (defined $result and
  503. $result->{template_path} eq $t->{template_path})
  504. {
  505. #mtr_report("Test uses same config => good match");
  506. # Test uses same config => good match
  507. $next= splice(@$tests, $i, 1);
  508. last;
  509. }
  510. # Second best choice is the first that does not fulfill
  511. # any of the above conditions
  512. if (!defined $second_best){
  513. #mtr_report("Setting second_best to $i");
  514. $second_best= $i;
  515. }
  516. }
  517. # Use second best choice if no other test has been found
  518. if (!$next and defined $second_best){
  519. #mtr_report("Take second best choice $second_best");
  520. mtr_error("Internal error, second best too large($second_best)")
  521. if $second_best > $#$tests;
  522. $next= splice(@$tests, $second_best, 1);
  523. }
  524. if ($next) {
  525. #$next->print_test();
  526. $next->write_test($sock, 'TESTCASE');
  527. $running{$next->key()}= $next;
  528. $num_ndb_tests++ if ($next->{ndb_test});
  529. }
  530. else {
  531. # No more test, tell child to exit
  532. #mtr_report("Saying BYE to child");
  533. print $sock "BYE\n";
  534. }
  535. }
  536. }
  537. # ----------------------------------------------------
  538. # Check if test suite timer expired
  539. # ----------------------------------------------------
  540. if ( ! $suite_timeout_proc->wait_one(0) )
  541. {
  542. mtr_report("Test suite timeout! Terminating...");
  543. return undef;
  544. }
  545. }
  546. }
  547. sub run_worker ($) {
  548. my ($server_port, $thread_num)= @_;
  549. $SIG{INT}= sub { exit(1); };
  550. # Connect to server
  551. my $server = new IO::Socket::INET
  552. (
  553. PeerAddr => 'localhost',
  554. PeerPort => $server_port,
  555. Proto => 'tcp'
  556. );
  557. mtr_error("Could not connect to server at port $server_port: $!")
  558. unless $server;
  559. # --------------------------------------------------------------------------
  560. # Set worker name
  561. # --------------------------------------------------------------------------
  562. report_option('name',"worker[$thread_num]");
  563. # --------------------------------------------------------------------------
  564. # Use auto build thread in all but first worker
  565. # --------------------------------------------------------------------------
  566. set_build_thread_ports($thread_num > 1 ? 'auto' : $opt_build_thread);
  567. if (check_ports_free()){
  568. # Some port was not free(which one has already been printed)
  569. mtr_error("Some port(s) was not free")
  570. }
  571. # --------------------------------------------------------------------------
  572. # Turn off verbosity in workers, unless explicitly specified
  573. # --------------------------------------------------------------------------
  574. report_option('verbose', undef) if ($opt_verbose == 0);
  575. environment_setup();
  576. # Read hello from server which it will send when shared
  577. # resources have been setup
  578. my $hello= <$server>;
  579. setup_vardir();
  580. check_running_as_root();
  581. if ( using_extern() ) {
  582. create_config_file_for_extern(%opts_extern);
  583. }
  584. # Ask server for first test
  585. print $server "START\n";
  586. while(my $line= <$server>){
  587. chomp($line);
  588. if ($line eq 'TESTCASE'){
  589. my $test= My::Test::read_test($server);
  590. #$test->print_test();
  591. # Clear comment and logfile, to avoid
  592. # reusing them from previous test
  593. delete($test->{'comment'});
  594. delete($test->{'logfile'});
  595. run_testcase($test);
  596. #$test->{result}= 'MTR_RES_PASSED';
  597. # Send it back, now with results set
  598. #$test->print_test();
  599. $test->write_test($server, 'TESTRESULT');
  600. }
  601. elsif ($line eq 'BYE'){
  602. mtr_report("Server said BYE");
  603. exit(0);
  604. }
  605. else {
  606. mtr_error("Could not understand server, '$line'");
  607. }
  608. }
  609. stop_all_servers();
  610. exit(1);
  611. }
  612. sub ignore_option {
  613. my ($opt, $value)= @_;
  614. mtr_report("Ignoring option '$opt'");
  615. }
  616. # Setup any paths that are $opt_vardir related
  617. sub set_vardir {
  618. my ($vardir)= @_;
  619. $opt_vardir= $vardir;
  620. $path_vardir_trace= $opt_vardir;
  621. # Chop off any "c:", DBUG likes a unix path ex: c:/src/... => /src/...
  622. $path_vardir_trace=~ s/^\w://;
  623. # Location of my.cnf that all clients use
  624. $path_config_file= "$opt_vardir/my.cnf";
  625. $path_testlog= "$opt_vardir/log/mysqltest.log";
  626. $path_current_testlog= "$opt_vardir/log/current_test";
  627. }
  628. sub command_line_setup {
  629. my $opt_comment;
  630. my $opt_usage;
  631. # Read the command line options
  632. # Note: Keep list, and the order, in sync with usage at end of this file
  633. Getopt::Long::Configure("pass_through");
  634. GetOptions(
  635. # Control what engine/variation to run
  636. 'embedded-server' => \$opt_embedded_server,
  637. 'ps-protocol' => \$opt_ps_protocol,
  638. 'sp-protocol' => \$opt_sp_protocol,
  639. 'view-protocol' => \$opt_view_protocol,
  640. 'cursor-protocol' => \$opt_cursor_protocol,
  641. 'ssl|with-openssl' => \$opt_ssl,
  642. 'skip-ssl' => \$opt_skip_ssl,
  643. 'compress' => \$opt_compress,
  644. 'vs-config' => \$opt_vs_config,
  645. # Max number of parallel threads to use
  646. 'parallel=i' => \$opt_parallel,
  647. # Config file to use as template for all tests
  648. 'defaults-file=s' => \&collect_option,
  649. # Extra config file to append to all generated configs
  650. 'defaults-extra-file=s' => \&collect_option,
  651. # Control what test suites or cases to run
  652. 'force' => \$opt_force,
  653. 'with-ndbcluster-only' => \&collect_option,
  654. 'skip-ndbcluster|skip-ndb' => \$opt_skip_ndbcluster,
  655. 'suite|suites=s' => \$opt_suites,
  656. 'skip-rpl' => \&collect_option,
  657. 'skip-test=s' => \&collect_option,
  658. 'do-test=s' => \&collect_option,
  659. 'start-from=s' => \&collect_option,
  660. 'big-test' => \$opt_big_test,
  661. 'combination=s' => \@opt_combinations,
  662. 'skip-combinations' => \&collect_option,
  663. 'skip-im' => \&ignore_option,
  664. # Specify ports
  665. 'build-thread|mtr-build-thread=i' => \$opt_build_thread,
  666. # Test case authoring
  667. 'record' => \$opt_record,
  668. 'check-testcases!' => \$opt_check_testcases,
  669. 'mark-progress' => \$opt_mark_progress,
  670. # Extra options used when starting mysqld
  671. 'mysqld=s' => \@opt_extra_mysqld_opt,
  672. # Run test on running server
  673. 'extern=s' => \%opts_extern, # Append to hash
  674. # Debugging
  675. 'debug' => \$opt_debug,
  676. 'gdb' => \$opt_gdb,
  677. 'client-gdb' => \$opt_client_gdb,
  678. 'manual-gdb' => \$opt_manual_gdb,
  679. 'manual-debug' => \$opt_manual_debug,
  680. 'ddd' => \$opt_ddd,
  681. 'client-ddd' => \$opt_client_ddd,
  682. 'manual-ddd' => \$opt_manual_ddd,
  683. 'debugger=s' => \$opt_debugger,
  684. 'client-debugger=s' => \$opt_client_debugger,
  685. 'strace-client:s' => \$opt_strace_client,
  686. 'max-save-core=i' => \$opt_max_save_core,
  687. 'max-save-datadir=i' => \$opt_max_save_datadir,
  688. 'max-test-fail=i' => \$opt_max_test_fail,
  689. # Coverage, profiling etc
  690. 'gcov' => \$opt_gcov,
  691. 'valgrind|valgrind-all' => \$opt_valgrind,
  692. 'valgrind-mysqltest' => \$opt_valgrind_mysqltest,
  693. 'valgrind-mysqld' => \$opt_valgrind_mysqld,
  694. 'valgrind-options=s' => sub {
  695. my ($opt, $value)= @_;
  696. # Deprecated option unless it's what we know pushbuild uses
  697. if ($value eq "--gen-suppressions=all --show-reachable=yes") {
  698. push(@valgrind_args, $_) for (split(' ', $value));
  699. return;
  700. }
  701. die("--valgrind-options=s is deprecated. Use ",
  702. "--valgrind-option=s, to be specified several",
  703. " times if necessary");
  704. },
  705. 'valgrind-option=s' => \@valgrind_args,
  706. 'valgrind-path=s' => \$opt_valgrind_path,
  707. 'callgrind' => \$opt_callgrind,
  708. # Directories
  709. 'tmpdir=s' => \$opt_tmpdir,
  710. 'vardir=s' => \$opt_vardir,
  711. 'mem' => \$opt_mem,
  712. 'client-bindir=s' => \$path_client_bindir,
  713. 'client-libdir=s' => \$path_client_libdir,
  714. # Misc
  715. 'report-features' => \$opt_report_features,
  716. 'comment=s' => \$opt_comment,
  717. 'fast' => \$opt_fast,
  718. 'reorder!' => \&collect_option,
  719. 'enable-disabled' => \&collect_option,
  720. 'verbose+' => \$opt_verbose,
  721. 'verbose-restart' => \&report_option,
  722. 'sleep=i' => \$opt_sleep,
  723. 'start-dirty' => \$opt_start_dirty,
  724. 'start' => \$opt_start,
  725. 'print-testcases' => \&collect_option,
  726. 'repeat=i' => \$opt_repeat,
  727. 'retry=i' => \$opt_retry,
  728. 'retry-failure=i' => \$opt_retry_failure,
  729. 'timer!' => \&report_option,
  730. 'user=s' => \$opt_user,
  731. 'testcase-timeout=i' => \$opt_testcase_timeout,
  732. 'suite-timeout=i' => \$opt_suite_timeout,
  733. 'shutdown-timeout=i' => \$opt_shutdown_timeout,
  734. 'warnings!' => \$opt_warnings,
  735. 'timestamp' => \&report_option,
  736. 'timediff' => \&report_option,
  737. 'help|h' => \$opt_usage,
  738. ) or usage("Can't read options");
  739. usage("") if $opt_usage;
  740. # --------------------------------------------------------------------------
  741. # Setup verbosity
  742. # --------------------------------------------------------------------------
  743. if ($opt_verbose != 0){
  744. report_option('verbose', $opt_verbose);
  745. }
  746. if ( -d "../sql" )
  747. {
  748. $source_dist= 1;
  749. }
  750. # Find the absolute path to the test directory
  751. $glob_mysql_test_dir= cwd();
  752. if (IS_CYGWIN)
  753. {
  754. # Use mixed path format i.e c:/path/to/
  755. $glob_mysql_test_dir= mixed_path($glob_mysql_test_dir);
  756. }
  757. # In most cases, the base directory we find everything relative to,
  758. # is the parent directory of the "mysql-test" directory. For source
  759. # distributions, TAR binary distributions and some other packages.
  760. $basedir= dirname($glob_mysql_test_dir);
  761. # In the RPM case, binaries and libraries are installed in the
  762. # default system locations, instead of having our own private base
  763. # directory. And we install "/usr/share/mysql-test". Moving up one
  764. # more directory relative to "mysql-test" gives us a usable base
  765. # directory for RPM installs.
  766. if ( ! $source_dist and ! -d "$basedir/bin" )
  767. {
  768. $basedir= dirname($basedir);
  769. }
  770. # Look for the client binaries directory
  771. if ($path_client_bindir)
  772. {
  773. # --client-bindir=path set on command line, check that the path exists
  774. $path_client_bindir= mtr_path_exists($path_client_bindir);
  775. }
  776. else
  777. {
  778. $path_client_bindir= mtr_path_exists("$basedir/client_release",
  779. "$basedir/client_debug",
  780. vs_config_dirs('client', ''),
  781. "$basedir/client",
  782. "$basedir/bin");
  783. }
  784. # Look for language files and charsetsdir, use same share
  785. my $path_share= mtr_path_exists("$basedir/share/mysql",
  786. "$basedir/sql/share",
  787. "$basedir/share");
  788. $path_language= mtr_path_exists("$path_share/english");
  789. $path_charsetsdir= mtr_path_exists("$path_share/charsets");
  790. if (using_extern())
  791. {
  792. # Connect to the running mysqld and find out what it supports
  793. collect_mysqld_features_from_running_server();
  794. }
  795. else
  796. {
  797. # Run the mysqld to find out what features are available
  798. collect_mysqld_features();
  799. }
  800. if ( $opt_comment )
  801. {
  802. mtr_report();
  803. mtr_print_thick_line('#');
  804. mtr_report("# $opt_comment");
  805. mtr_print_thick_line('#');
  806. }
  807. foreach my $arg ( @ARGV )
  808. {
  809. if ( $arg =~ /^--skip-/ )
  810. {
  811. push(@opt_extra_mysqld_opt, $arg);
  812. }
  813. elsif ( $arg =~ /^--$/ )
  814. {
  815. # It is an effect of setting 'pass_through' in option processing
  816. # that the lone '--' separating options from arguments survives,
  817. # simply ignore it.
  818. }
  819. elsif ( $arg =~ /^-/ )
  820. {
  821. usage("Invalid option \"$arg\"");
  822. }
  823. else
  824. {
  825. push(@opt_cases, $arg);
  826. }
  827. }
  828. # --------------------------------------------------------------------------
  829. # Find out type of logging that are being used
  830. # --------------------------------------------------------------------------
  831. foreach my $arg ( @opt_extra_mysqld_opt )
  832. {
  833. if ( $arg =~ /binlog[-_]format=(\S+)/ )
  834. {
  835. # Save this for collect phase
  836. collect_option('binlog-format', $1);
  837. mtr_report("Using binlog format '$1'");
  838. }
  839. }
  840. # --------------------------------------------------------------------------
  841. # Find out default storage engine being used(if any)
  842. # --------------------------------------------------------------------------
  843. foreach my $arg ( @opt_extra_mysqld_opt )
  844. {
  845. if ( $arg =~ /default-storage-engine=(\S+)/ )
  846. {
  847. # Save this for collect phase
  848. collect_option('default-storage-engine', $1);
  849. mtr_report("Using default engine '$1'")
  850. }
  851. }
  852. # --------------------------------------------------------------------------
  853. # Check if we should speed up tests by trying to run on tmpfs
  854. # --------------------------------------------------------------------------
  855. if ( defined $opt_mem)
  856. {
  857. mtr_error("Can't use --mem and --vardir at the same time ")
  858. if $opt_vardir;
  859. mtr_error("Can't use --mem and --tmpdir at the same time ")
  860. if $opt_tmpdir;
  861. # Search through list of locations that are known
  862. # to be "fast disks" to find a suitable location
  863. # Use --mem=<dir> as first location to look.
  864. my @tmpfs_locations= ($opt_mem, "/dev/shm", "/tmp");
  865. foreach my $fs (@tmpfs_locations)
  866. {
  867. if ( -d $fs )
  868. {
  869. my $template= "var_${opt_build_thread}_XXXX";
  870. $opt_mem= tempdir( $template, DIR => $fs, CLEANUP => 0);
  871. last;
  872. }
  873. }
  874. }
  875. # --------------------------------------------------------------------------
  876. # Set the "var/" directory, the base for everything else
  877. # --------------------------------------------------------------------------
  878. $default_vardir= "$glob_mysql_test_dir/var";
  879. if ( ! $opt_vardir )
  880. {
  881. $opt_vardir= $default_vardir;
  882. }
  883. # We make the path absolute, as the server will do a chdir() before usage
  884. unless ( $opt_vardir =~ m,^/, or
  885. (IS_WINDOWS and $opt_vardir =~ m,^[a-z]:/,i) )
  886. {
  887. # Make absolute path, relative test dir
  888. $opt_vardir= "$glob_mysql_test_dir/$opt_vardir";
  889. }
  890. set_vardir($opt_vardir);
  891. # --------------------------------------------------------------------------
  892. # Set the "tmp" directory
  893. # --------------------------------------------------------------------------
  894. if ( ! $opt_tmpdir )
  895. {
  896. $opt_tmpdir= "$opt_vardir/tmp" unless $opt_tmpdir;
  897. if (check_socket_path_length("$opt_tmpdir/mysql_testsocket.sock"))
  898. {
  899. mtr_report("Too long tmpdir path '$opt_tmpdir'",
  900. " creating a shorter one...");
  901. # Create temporary directory in standard location for temporary files
  902. $opt_tmpdir= tempdir( TMPDIR => 1, CLEANUP => 0 );
  903. mtr_report(" - using tmpdir: '$opt_tmpdir'\n");
  904. # Remember pid that created dir so it's removed by correct process
  905. $opt_tmpdir_pid= $$;
  906. }
  907. }
  908. $opt_tmpdir =~ s,/+$,,; # Remove ending slash if any
  909. # --------------------------------------------------------------------------
  910. # fast option
  911. # --------------------------------------------------------------------------
  912. if ($opt_fast){
  913. $opt_shutdown_timeout= 0; # Kill processes instead of nice shutdown
  914. }
  915. # --------------------------------------------------------------------------
  916. # Record flag
  917. # --------------------------------------------------------------------------
  918. if ( $opt_record and ! @opt_cases )
  919. {
  920. mtr_error("Will not run in record mode without a specific test case");
  921. }
  922. if ( $opt_record ) {
  923. # Use only one worker with --record
  924. $opt_parallel= 1;
  925. }
  926. # --------------------------------------------------------------------------
  927. # Embedded server flag
  928. # --------------------------------------------------------------------------
  929. if ( $opt_embedded_server )
  930. {
  931. if ( IS_WINDOWS )
  932. {
  933. # Add the location for libmysqld.dll to the path.
  934. my $separator= ";";
  935. my $lib_mysqld=
  936. mtr_path_exists(vs_config_dirs('libmysqld',''));
  937. if ( IS_CYGWIN )
  938. {
  939. $lib_mysqld= posix_path($lib_mysqld);
  940. $separator= ":";
  941. }
  942. $ENV{'PATH'}= "$ENV{'PATH'}".$separator.$lib_mysqld;
  943. }
  944. $opt_skip_ndbcluster= 1; # Turn off use of NDB cluster
  945. $opt_skip_ssl= 1; # Turn off use of SSL
  946. # Turn off use of bin log
  947. push(@opt_extra_mysqld_opt, "--skip-log-bin");
  948. if ( using_extern() )
  949. {
  950. mtr_error("Can't use --extern with --embedded-server");
  951. }
  952. if ($opt_gdb)
  953. {
  954. mtr_warning("Silently converting --gdb to --client-gdb in embedded mode");
  955. $opt_client_gdb= $opt_gdb;
  956. $opt_gdb= undef;
  957. }
  958. if ($opt_ddd)
  959. {
  960. mtr_warning("Silently converting --ddd to --client-ddd in embedded mode");
  961. $opt_client_ddd= $opt_ddd;
  962. $opt_ddd= undef;
  963. }
  964. if ($opt_debugger)
  965. {
  966. mtr_warning("Silently converting --debugger to --client-debugger in embedded mode");
  967. $opt_client_debugger= $opt_debugger;
  968. $opt_debugger= undef;
  969. }
  970. if ( $opt_gdb || $opt_ddd || $opt_manual_gdb || $opt_manual_ddd ||
  971. $opt_manual_debug || $opt_debugger )
  972. {
  973. mtr_error("You need to use the client debug options for the",
  974. "embedded server. Ex: --client-gdb");
  975. }
  976. }
  977. # --------------------------------------------------------------------------
  978. # Big test flags
  979. # --------------------------------------------------------------------------
  980. if ( $opt_big_test )
  981. {
  982. $ENV{'BIG_TEST'}= 1;
  983. }
  984. # --------------------------------------------------------------------------
  985. # Gcov flag
  986. # --------------------------------------------------------------------------
  987. if ( $opt_gcov and ! $source_dist )
  988. {
  989. mtr_error("Coverage test needs the source - please use source dist");
  990. }
  991. # --------------------------------------------------------------------------
  992. # Check debug related options
  993. # --------------------------------------------------------------------------
  994. if ( $opt_gdb || $opt_client_gdb || $opt_ddd || $opt_client_ddd ||
  995. $opt_manual_gdb || $opt_manual_ddd || $opt_manual_debug ||
  996. $opt_debugger || $opt_client_debugger )
  997. {
  998. # Indicate that we are using debugger
  999. $glob_debugger= 1;
  1000. if ( using_extern() )
  1001. {
  1002. mtr_error("Can't use --extern when using debugger");
  1003. }
  1004. }
  1005. # --------------------------------------------------------------------------
  1006. # Check timeout arguments
  1007. # --------------------------------------------------------------------------
  1008. mtr_error("Invalid value '$opt_testcase_timeout' supplied ".
  1009. "for option --testcase-timeout")
  1010. if ($opt_testcase_timeout <= 0);
  1011. mtr_error("Invalid value '$opt_suite_timeout' supplied ".
  1012. "for option --testsuite-timeout")
  1013. if ($opt_suite_timeout <= 0);
  1014. # --------------------------------------------------------------------------
  1015. # Check valgrind arguments
  1016. # --------------------------------------------------------------------------
  1017. if ( $opt_valgrind or $opt_valgrind_path or @valgrind_args)
  1018. {
  1019. mtr_report("Turning on valgrind for all executables");
  1020. $opt_valgrind= 1;
  1021. $opt_valgrind_mysqld= 1;
  1022. $opt_valgrind_mysqltest= 1;
  1023. # Increase the timeouts when running with valgrind
  1024. $opt_testcase_timeout*= 10;
  1025. $opt_suite_timeout*= 6;
  1026. $opt_start_timeout*= 10;
  1027. }
  1028. elsif ( $opt_valgrind_mysqld )
  1029. {
  1030. mtr_report("Turning on valgrind for mysqld(s) only");
  1031. $opt_valgrind= 1;
  1032. }
  1033. elsif ( $opt_valgrind_mysqltest )
  1034. {
  1035. mtr_report("Turning on valgrind for mysqltest and mysql_client_test only");
  1036. $opt_valgrind= 1;
  1037. }
  1038. if ( $opt_callgrind )
  1039. {
  1040. mtr_report("Turning on valgrind with callgrind for mysqld(s)");
  1041. $opt_valgrind= 1;
  1042. $opt_valgrind_mysqld= 1;
  1043. # Set special valgrind options unless options passed on command line
  1044. push(@valgrind_args, "--trace-children=yes")
  1045. unless @valgrind_args;
  1046. }
  1047. if ( $opt_valgrind )
  1048. {
  1049. # Set valgrind_options to default unless already defined
  1050. push(@valgrind_args, @default_valgrind_args)
  1051. unless @valgrind_args;
  1052. mtr_report("Running valgrind with options \"",
  1053. join(" ", @valgrind_args), "\"");
  1054. }
  1055. mtr_report("Checking supported features...");
  1056. check_ndbcluster_support(\%mysqld_variables);
  1057. check_ssl_support(\%mysqld_variables);
  1058. check_debug_support(\%mysqld_variables);
  1059. executable_setup();
  1060. }
  1061. #
  1062. # To make it easier for different devs to work on the same host,
  1063. # an environment variable can be used to control all ports. A small
  1064. # number is to be used, 0 - 16 or similar.
  1065. #
  1066. # Note the MASTER_MYPORT has to be set the same in all 4.x and 5.x
  1067. # versions of this script, else a 4.0 test run might conflict with a
  1068. # 5.1 test run, even if different MTR_BUILD_THREAD is used. This means
  1069. # all port numbers might not be used in this version of the script.
  1070. #
  1071. # Also note the limitation of ports we are allowed to hand out. This
  1072. # differs between operating systems and configuration, see
  1073. # http://www.ncftp.com/ncftpd/doc/misc/ephemeral_ports.html
  1074. # But a fairly safe range seems to be 5001 - 32767
  1075. #
  1076. sub set_build_thread_ports($) {
  1077. my $build_thread= shift || 0;
  1078. if ( lc($build_thread) eq 'auto' ) {
  1079. #mtr_report("Requesting build thread... ");
  1080. $build_thread= mtr_get_unique_id(250, 299);
  1081. if ( !defined $build_thread ) {
  1082. mtr_error("Could not get a unique build thread id");
  1083. }
  1084. #mtr_report(" - got $build_thread");
  1085. }
  1086. $ENV{MTR_BUILD_THREAD}= $build_thread;
  1087. $opt_build_thread= $build_thread;
  1088. # Calculate baseport
  1089. $baseport= $build_thread * 10 + 10000;
  1090. if ( $baseport < 5001 or $baseport + 9 >= 32767 )
  1091. {
  1092. mtr_error("MTR_BUILD_THREAD number results in a port",
  1093. "outside 5001 - 32767",
  1094. "($baseport - $baseport + 9)");
  1095. }
  1096. mtr_report("Using MTR_BUILD_THREAD $build_thread,",
  1097. "with reserved ports $baseport..".($baseport+9));
  1098. }
  1099. sub collect_mysqld_features {
  1100. my $found_variable_list_start= 0;
  1101. my $use_tmpdir;
  1102. if ( defined $opt_tmpdir and -d $opt_tmpdir){
  1103. # Create the tempdir in $opt_tmpdir
  1104. $use_tmpdir= $opt_tmpdir;
  1105. }
  1106. my $tmpdir= tempdir(CLEANUP => 0, # Directory removed by this function
  1107. DIR => $use_tmpdir);
  1108. #
  1109. # Execute "mysqld --no-defaults --help --verbose" to get a
  1110. # list of all features and settings
  1111. #
  1112. # --no-defaults and --skip-grant-tables are to avoid loading
  1113. # system-wide configs and plugins
  1114. #
  1115. # --datadir must exist, mysqld will chdir into it
  1116. #
  1117. my $args;
  1118. mtr_init_args(\$args);
  1119. mtr_add_arg($args, "--no-defaults");
  1120. mtr_add_arg($args, "--datadir=%s", mixed_path($tmpdir));
  1121. mtr_add_arg($args, "--language=%s", $path_language);
  1122. mtr_add_arg($args, "--skip-grant-tables");
  1123. mtr_add_arg($args, "--verbose");
  1124. mtr_add_arg($args, "--help");
  1125. my $exe_mysqld= find_mysqld($basedir);
  1126. my $cmd= join(" ", $exe_mysqld, @$args);
  1127. my $list= `$cmd`;
  1128. foreach my $line (split('\n', $list))
  1129. {
  1130. # First look for version
  1131. if ( !$mysql_version_id )
  1132. {
  1133. # Look for version
  1134. my $exe_name= basename($exe_mysqld);
  1135. mtr_verbose("exe_name: $exe_name");
  1136. if ( $line =~ /^\S*$exe_name\s\sVer\s([0-9]*)\.([0-9]*)\.([0-9]*)/ )
  1137. {
  1138. #print "Major: $1 Minor: $2 Build: $3\n";
  1139. $mysql_version_id= $1*10000 + $2*100 + $3;
  1140. #print "mysql_version_id: $mysql_version_id\n";
  1141. mtr_report("MySQL Version $1.$2.$3");
  1142. }
  1143. }
  1144. else
  1145. {
  1146. if (!$found_variable_list_start)
  1147. {
  1148. # Look for start of variables list
  1149. if ( $line =~ /[\-]+\s[\-]+/ )
  1150. {
  1151. $found_variable_list_start= 1;
  1152. }
  1153. }
  1154. else
  1155. {
  1156. # Put variables into hash
  1157. if ( $line =~ /^([\S]+)[ \t]+(.*?)\r?$/ )
  1158. {
  1159. # print "$1=\"$2\"\n";
  1160. $mysqld_variables{$1}= $2;
  1161. }
  1162. else
  1163. {
  1164. # The variable list is ended with a blank line
  1165. if ( $line =~ /^[\s]*$/ )
  1166. {
  1167. last;
  1168. }
  1169. else
  1170. {
  1171. # Send out a warning, we should fix the variables that has no
  1172. # space between variable name and it's value
  1173. # or should it be fixed width column parsing? It does not
  1174. # look like that in function my_print_variables in my_getopt.c
  1175. mtr_warning("Could not parse variable list line : $line");
  1176. }
  1177. }
  1178. }
  1179. }
  1180. }
  1181. rmtree($tmpdir);
  1182. mtr_error("Could not find version of MySQL") unless $mysql_version_id;
  1183. mtr_error("Could not find variabes list") unless $found_variable_list_start;
  1184. }
  1185. sub collect_mysqld_features_from_running_server ()
  1186. {
  1187. my $mysql= mtr_exe_exists("$path_client_bindir/mysql");
  1188. my $args;
  1189. mtr_init_args(\$args);
  1190. mtr_add_arg($args, "--no-defaults");
  1191. mtr_add_arg($args, "--user=%s", $opt_user);
  1192. while (my ($option, $value)= each( %opts_extern )) {
  1193. mtr_add_arg($args, "--$option=$value");
  1194. }
  1195. mtr_add_arg($args, "--silent"); # Tab separated output
  1196. mtr_add_arg($args, "-e '%s'", "use mysql; SHOW VARIABLES");
  1197. my $cmd= "$mysql " . join(' ', @$args);
  1198. mtr_verbose("cmd: $cmd");
  1199. my $list = `$cmd` or
  1200. mtr_error("Could not connect to extern server using command: '$cmd'");
  1201. foreach my $line (split('\n', $list ))
  1202. {
  1203. # Put variables into hash
  1204. if ( $line =~ /^([\S]+)[ \t]+(.*?)\r?$/ )
  1205. {
  1206. # print "$1=\"$2\"\n";
  1207. $mysqld_variables{$1}= $2;
  1208. }
  1209. }
  1210. # Parse version
  1211. my $version_str= $mysqld_variables{'version'};
  1212. if ( $version_str =~ /^([0-9]*)\.([0-9]*)\.([0-9]*)/ )
  1213. {
  1214. #print "Major: $1 Minor: $2 Build: $3\n";
  1215. $mysql_version_id= $1*10000 + $2*100 + $3;
  1216. #print "mysql_version_id: $mysql_version_id\n";
  1217. mtr_report("MySQL Version $1.$2.$3");
  1218. }
  1219. mtr_error("Could not find version of MySQL") unless $mysql_version_id;
  1220. }
  1221. sub find_mysqld {
  1222. my ($mysqld_basedir)= @_;
  1223. my @mysqld_names= ("mysqld", "mysqld-max-nt", "mysqld-max",
  1224. "mysqld-nt");
  1225. if ( $opt_debug ){
  1226. # Put mysqld-debug first in the list of binaries to look for
  1227. mtr_verbose("Adding mysqld-debug first in list of binaries to look for");
  1228. unshift(@mysqld_names, "mysqld-debug");
  1229. }
  1230. return my_find_bin($mysqld_basedir,
  1231. ["sql", "libexec", "sbin", "bin"],
  1232. [@mysqld_names]);
  1233. }
  1234. sub executable_setup () {
  1235. #
  1236. # Check if libtool is available in this distribution/clone
  1237. # we need it when valgrinding or debugging non installed binary
  1238. # Otherwise valgrind will valgrind the libtool wrapper or bash
  1239. # and gdb will not find the real executable to debug
  1240. #
  1241. if ( -x "../libtool")
  1242. {
  1243. $exe_libtool= "../libtool";
  1244. if ($opt_valgrind or $glob_debugger)
  1245. {
  1246. mtr_report("Using \"$exe_libtool\" when running valgrind or debugger");
  1247. }
  1248. }
  1249. # Look for the client binaries
  1250. $exe_mysqladmin= mtr_exe_exists("$path_client_bindir/mysqladmin");
  1251. $exe_mysql= mtr_exe_exists("$path_client_bindir/mysql");
  1252. if ( ! $opt_skip_ndbcluster )
  1253. {
  1254. $exe_ndbd=
  1255. my_find_bin($basedir,
  1256. ["storage/ndb/src/kernel", "libexec", "sbin", "bin"],
  1257. "ndbd");
  1258. $exe_ndb_mgmd=
  1259. my_find_bin($basedir,
  1260. ["storage/ndb/src/mgmsrv", "libexec", "sbin", "bin"],
  1261. "ndb_mgmd");
  1262. $exe_ndb_waiter=
  1263. my_find_bin($basedir,
  1264. ["storage/ndb/tools/", "bin"],
  1265. "ndb_waiter");
  1266. }
  1267. # Look for mysqltest executable
  1268. if ( $opt_embedded_server )
  1269. {
  1270. $exe_mysqltest=
  1271. mtr_exe_exists(vs_config_dirs('libmysqld/examples','mysqltest_embedded'),
  1272. "$basedir/libmysqld/examples/mysqltest_embedded",
  1273. "$path_client_bindir/mysqltest_embedded");
  1274. }
  1275. else
  1276. {
  1277. $exe_mysqltest= mtr_exe_exists("$path_client_bindir/mysqltest");
  1278. }
  1279. }
  1280. sub client_debug_arg($$) {
  1281. my ($args, $client_name)= @_;
  1282. if ( $opt_debug ) {
  1283. mtr_add_arg($args,
  1284. "--debug=d:t:A,%s/log/%s.trace",
  1285. $path_vardir_trace, $client_name)
  1286. }
  1287. }
  1288. sub mysql_fix_arguments () {
  1289. return "" if ( IS_WINDOWS );
  1290. my $exe=
  1291. mtr_script_exists("$basedir/scripts/mysql_fix_privilege_tables",
  1292. "$path_client_bindir/mysql_fix_privilege_tables");
  1293. my $args;
  1294. mtr_init_args(\$args);
  1295. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1296. mtr_add_arg($args, "--basedir=%s", $basedir);
  1297. mtr_add_arg($args, "--bindir=%s", $path_client_bindir);
  1298. mtr_add_arg($args, "--verbose");
  1299. return mtr_args2str($exe, @$args);
  1300. }
  1301. sub client_arguments ($) {
  1302. my $client_name= shift;
  1303. my $client_exe= mtr_exe_exists("$path_client_bindir/$client_name");
  1304. my $args;
  1305. mtr_init_args(\$args);
  1306. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1307. client_debug_arg($args, $client_name);
  1308. return mtr_args2str($client_exe, @$args);
  1309. }
  1310. sub mysqlslap_arguments () {
  1311. my $exe= mtr_exe_maybe_exists("$path_client_bindir/mysqlslap");
  1312. if ( $exe eq "" ) {
  1313. # mysqlap was not found
  1314. if (defined $mysql_version_id and $mysql_version_id >= 50100 ) {
  1315. mtr_error("Could not find the mysqlslap binary");
  1316. }
  1317. return ""; # Don't care about mysqlslap
  1318. }
  1319. my $args;
  1320. mtr_init_args(\$args);
  1321. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1322. client_debug_arg($args, "mysqlslap");
  1323. return mtr_args2str($exe, @$args);
  1324. }
  1325. sub mysqldump_arguments ($) {
  1326. my($group_suffix) = @_;
  1327. my $exe= mtr_exe_exists("$path_client_bindir/mysqldump");
  1328. my $args;
  1329. mtr_init_args(\$args);
  1330. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1331. mtr_add_arg($args, "--defaults-group-suffix=%s", $group_suffix);
  1332. client_debug_arg($args, "mysqldump-$group_suffix");
  1333. return mtr_args2str($exe, @$args);
  1334. }
  1335. sub mysql_client_test_arguments(){
  1336. my $exe;
  1337. # mysql_client_test executable may _not_ exist
  1338. if ( $opt_embedded_server ) {
  1339. $exe= mtr_exe_maybe_exists(
  1340. vs_config_dirs('libmysqld/examples','mysql_client_test_embedded'),
  1341. "$basedir/libmysqld/examples/mysql_client_test_embedded",
  1342. "$basedir/bin/mysql_client_test_embedded");
  1343. } else {
  1344. $exe= mtr_exe_maybe_exists(vs_config_dirs('tests', 'mysql_client_test'),
  1345. "$basedir/tests/mysql_client_test",
  1346. "$basedir/bin/mysql_client_test");
  1347. }
  1348. my $args;
  1349. mtr_init_args(\$args);
  1350. if ( $opt_valgrind_mysqltest ) {
  1351. valgrind_arguments($args, \$exe);
  1352. }
  1353. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1354. mtr_add_arg($args, "--testcase");
  1355. mtr_add_arg($args, "--vardir=$opt_vardir");
  1356. client_debug_arg($args,"mysql_client_test");
  1357. return mtr_args2str($exe, @$args);
  1358. }
  1359. #
  1360. # Set environment to be used by childs of this process for
  1361. # things that are constant during the whole lifetime of mysql-test-run
  1362. #
  1363. sub environment_setup {
  1364. umask(022);
  1365. my @ld_library_paths;
  1366. if ($path_client_libdir)
  1367. {
  1368. # Use the --client-libdir passed on commandline
  1369. push(@ld_library_paths, "$path_client_libdir");
  1370. }
  1371. else
  1372. {
  1373. # Setup LD_LIBRARY_PATH so the libraries from this distro/clone
  1374. # are used in favor of the system installed ones
  1375. if ( $source_dist )
  1376. {
  1377. push(@ld_library_paths, "$basedir/libmysql/.libs/",
  1378. "$basedir/libmysql_r/.libs/",
  1379. "$basedir/zlib.libs/");
  1380. }
  1381. else
  1382. {
  1383. push(@ld_library_paths, "$basedir/lib");
  1384. }
  1385. }
  1386. # --------------------------------------------------------------------------
  1387. # Add the path where libndbclient can be found
  1388. # --------------------------------------------------------------------------
  1389. if ( !$opt_skip_ndbcluster )
  1390. {
  1391. push(@ld_library_paths, "$basedir/storage/ndb/src/.libs");
  1392. }
  1393. # --------------------------------------------------------------------------
  1394. # Add the path where mysqld will find udf_example.so
  1395. # --------------------------------------------------------------------------
  1396. my $lib_udf_example=
  1397. mtr_file_exists(vs_config_dirs('sql', 'udf_example.dll'),
  1398. "$basedir/sql/.libs/udf_example.so",);
  1399. if ( $lib_udf_example )
  1400. {
  1401. push(@ld_library_paths, dirname($lib_udf_example));
  1402. }
  1403. $ENV{'UDF_EXAMPLE_LIB'}=
  1404. ($lib_udf_example ? basename($lib_udf_example) : "");
  1405. $ENV{'UDF_EXAMPLE_LIB_OPT'}= "--plugin-dir=".
  1406. ($lib_udf_example ? dirname($lib_udf_example) : "");
  1407. # --------------------------------------------------------------------------
  1408. # Add the path where mysqld will find ha_example.so
  1409. # --------------------------------------------------------------------------
  1410. if ($mysql_version_id >= 50100) {
  1411. my $lib_example_plugin=
  1412. mtr_file_exists(vs_config_dirs('storage/example', 'ha_example.dll'),
  1413. "$basedir/storage/example/.libs/ha_example.so",);
  1414. $ENV{'EXAMPLE_PLUGIN'}=
  1415. ($lib_example_plugin ? basename($lib_example_plugin) : "");
  1416. $ENV{'EXAMPLE_PLUGIN_OPT'}= "--plugin-dir=".
  1417. ($lib_example_plugin ? dirname($lib_example_plugin) : "");
  1418. }
  1419. # ----------------------------------------------------
  1420. # Add the path where mysqld will find mypluglib.so
  1421. # ----------------------------------------------------
  1422. my $lib_simple_parser=
  1423. mtr_file_exists(vs_config_dirs('plugin/fulltext', 'mypluglib.dll'),
  1424. "$basedir/plugin/fulltext/.libs/mypluglib.so",);
  1425. $ENV{'SIMPLE_PARSER'}=
  1426. ($lib_simple_parser ? basename($lib_simple_parser) : "");
  1427. $ENV{'SIMPLE_PARSER_OPT'}= "--plugin-dir=".
  1428. ($lib_simple_parser ? dirname($lib_simple_parser) : "");
  1429. # --------------------------------------------------------------------------
  1430. # Valgrind need to be run with debug libraries otherwise it's almost
  1431. # impossible to add correct supressions, that means if "/usr/lib/debug"
  1432. # is available, it should be added to
  1433. # LD_LIBRARY_PATH
  1434. #
  1435. # But pthread is broken in libc6-dbg on Debian <= 3.1 (see Debian
  1436. # bug 399035, http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=399035),
  1437. # so don't change LD_LIBRARY_PATH on that platform.
  1438. # --------------------------------------------------------------------------
  1439. my $debug_libraries_path= "/usr/lib/debug";
  1440. my $deb_version;
  1441. if ( $opt_valgrind and -d $debug_libraries_path and
  1442. (! -e '/etc/debian_version' or
  1443. ($deb_version=
  1444. mtr_grab_file('/etc/debian_version')) !~ /^[0-9]+\.[0-9]$/ or
  1445. $deb_version > 3.1 ) )
  1446. {
  1447. push(@ld_library_paths, $debug_libraries_path);
  1448. }
  1449. $ENV{'LD_LIBRARY_PATH'}= join(":", @ld_library_paths,
  1450. $ENV{'LD_LIBRARY_PATH'} ?
  1451. split(':', $ENV{'LD_LIBRARY_PATH'}) : ());
  1452. mtr_debug("LD_LIBRARY_PATH: $ENV{'LD_LIBRARY_PATH'}");
  1453. $ENV{'DYLD_LIBRARY_PATH'}= join(":", @ld_library_paths,
  1454. $ENV{'DYLD_LIBRARY_PATH'} ?
  1455. split(':', $ENV{'DYLD_LIBRARY_PATH'}) : ());
  1456. mtr_debug("DYLD_LIBRARY_PATH: $ENV{'DYLD_LIBRARY_PATH'}");
  1457. # The environment variable used for shared libs on AIX
  1458. $ENV{'SHLIB_PATH'}= join(":", @ld_library_paths,
  1459. $ENV{'SHLIB_PATH'} ?
  1460. split(':', $ENV{'SHLIB_PATH'}) : ());
  1461. mtr_debug("SHLIB_PATH: $ENV{'SHLIB_PATH'}");
  1462. # The environment variable used for shared libs on hp-ux
  1463. $ENV{'LIBPATH'}= join(":", @ld_library_paths,
  1464. $ENV{'LIBPATH'} ?
  1465. split(':', $ENV{'LIBPATH'}) : ());
  1466. mtr_debug("LIBPATH: $ENV{'LIBPATH'}");
  1467. $ENV{'CHARSETSDIR'}= $path_charsetsdir;
  1468. $ENV{'UMASK'}= "0660"; # The octal *string*
  1469. $ENV{'UMASK_DIR'}= "0770"; # The octal *string*
  1470. #
  1471. # MySQL tests can produce output in various character sets
  1472. # (especially, ctype_xxx.test). To avoid confusing Perl
  1473. # with output which is incompatible with the current locale
  1474. # settings, we reset the current values of LC_ALL and LC_CTYPE to "C".
  1475. # For details, please see
  1476. # Bug#27636 tests fails if LC_* variables set to *_*.UTF-8
  1477. #
  1478. $ENV{'LC_ALL'}= "C";
  1479. $ENV{'LC_CTYPE'}= "C";
  1480. $ENV{'LC_COLLATE'}= "C";
  1481. $ENV{'USE_RUNNING_SERVER'}= using_extern();
  1482. $ENV{'MYSQL_TEST_DIR'}= $glob_mysql_test_dir;
  1483. $ENV{'DEFAULT_MASTER_PORT'}= $mysqld_variables{'master-port'} || 3306;
  1484. $ENV{'MYSQL_TMP_DIR'}= $opt_tmpdir;
  1485. $ENV{'MYSQLTEST_VARDIR'}= $opt_vardir;
  1486. # ----------------------------------------------------
  1487. # Setup env for NDB
  1488. # ----------------------------------------------------
  1489. if ( ! $opt_skip_ndbcluster )
  1490. {
  1491. $ENV{'NDB_MGM'}=
  1492. my_find_bin($basedir,
  1493. ["storage/ndb/src/mgmclient", "bin"],
  1494. "ndb_mgm");
  1495. $ENV{'NDB_TOOLS_DIR'}=
  1496. my_find_dir($basedir,
  1497. ["storage/ndb/tools", "bin"]);
  1498. $ENV{'NDB_EXAMPLES_DIR'}=
  1499. my_find_dir($basedir,
  1500. ["storage/ndb/ndbapi-examples", "bin"]);
  1501. $ENV{'NDB_EXAMPLES_BINARY'}=
  1502. my_find_bin($basedir,
  1503. ["storage/ndb/ndbapi-examples/ndbapi_simple", "bin"],
  1504. "ndbapi_simple", NOT_REQUIRED);
  1505. my $path_ndb_testrun_log= "$opt_vardir/log/ndb_testrun.log";
  1506. $ENV{'NDB_TOOLS_OUTPUT'}= $path_ndb_testrun_log;
  1507. $ENV{'NDB_EXAMPLES_OUTPUT'}= $path_ndb_testrun_log;
  1508. }
  1509. # ----------------------------------------------------
  1510. # mysql clients
  1511. # ----------------------------------------------------
  1512. $ENV{'MYSQL_CHECK'}= client_arguments("mysqlcheck");
  1513. $ENV{'MYSQL_DUMP'}= mysqldump_arguments(".1");
  1514. $ENV{'MYSQL_DUMP_SLAVE'}= mysqldump_arguments(".2");
  1515. $ENV{'MYSQL_SLAP'}= mysqlslap_arguments();
  1516. $ENV{'MYSQL_IMPORT'}= client_arguments("mysqlimport");
  1517. $ENV{'MYSQL_SHOW'}= client_arguments("mysqlshow");
  1518. $ENV{'MYSQL_BINLOG'}= client_arguments("mysqlbinlog");
  1519. $ENV{'MYSQL'}= client_arguments("mysql");
  1520. $ENV{'MYSQL_UPGRADE'}= client_arguments("mysql_upgrade");
  1521. $ENV{'MYSQLADMIN'}= native_path($exe_mysqladmin);
  1522. $ENV{'MYSQL_CLIENT_TEST'}= mysql_client_test_arguments();
  1523. $ENV{'MYSQL_FIX_SYSTEM_TABLES'}= mysql_fix_arguments();
  1524. $ENV{'EXE_MYSQL'}= $exe_mysql;
  1525. # ----------------------------------------------------
  1526. # bug25714 executable may _not_ exist in
  1527. # some versions, test using it should be skipped
  1528. # ----------------------------------------------------
  1529. my $exe_bug25714=
  1530. mtr_exe_maybe_exists(vs_config_dirs('tests', 'bug25714'),
  1531. "$basedir/tests/bug25714");
  1532. $ENV{'MYSQL_BUG25714'}= native_path($exe_bug25714);
  1533. # ----------------------------------------------------
  1534. # mysql_fix_privilege_tables.sql
  1535. # ----------------------------------------------------
  1536. my $file_mysql_fix_privilege_tables=
  1537. mtr_file_exists("$basedir/scripts/mysql_fix_privilege_tables.sql",
  1538. "$basedir/share/mysql_fix_privilege_tables.sql",
  1539. "$basedir/share/mysql/mysql_fix_privilege_tables.sql");
  1540. $ENV{'MYSQL_FIX_PRIVILEGE_TABLES'}= $file_mysql_fix_privilege_tables;
  1541. # ----------------------------------------------------
  1542. # my_print_defaults
  1543. # ----------------------------------------------------
  1544. my $exe_my_print_defaults=
  1545. mtr_exe_exists(vs_config_dirs('extra', 'my_print_defaults'),
  1546. "$path_client_bindir/my_print_defaults",
  1547. "$basedir/extra/my_print_defaults");
  1548. $ENV{'MYSQL_MY_PRINT_DEFAULTS'}= native_path($exe_my_print_defaults);
  1549. # ----------------------------------------------------
  1550. # Setup env so childs can execute myisampack and myisamchk
  1551. # ----------------------------------------------------
  1552. $ENV{'MYISAMCHK'}= native_path(mtr_exe_exists(
  1553. vs_config_dirs('storage/myisam', 'myisamchk'),
  1554. vs_config_dirs('myisam', 'myisamchk'),
  1555. "$path_client_bindir/myisamchk",
  1556. "$basedir/storage/myisam/myisamchk",
  1557. "$basedir/myisam/myisamchk"));
  1558. $ENV{'MYISAMPACK'}= native_path(mtr_exe_exists(
  1559. vs_config_dirs('storage/myisam', 'myisampack'),
  1560. vs_config_dirs('myisam', 'myisampack'),
  1561. "$path_client_bindir/myisampack",
  1562. "$basedir/storage/myisam/myisampack",
  1563. "$basedir/myisam/myisampack"));
  1564. # ----------------------------------------------------
  1565. # perror
  1566. # ----------------------------------------------------
  1567. my $exe_perror= mtr_exe_exists(vs_config_dirs('extra', 'perror'),
  1568. "$basedir/extra/perror",
  1569. "$path_client_bindir/perror");
  1570. $ENV{'MY_PERROR'}= native_path($exe_perror);
  1571. # Create an environment variable to make it possible
  1572. # to detect that valgrind is being used from test cases
  1573. $ENV{'VALGRIND_TEST'}= $opt_valgrind;
  1574. }
  1575. #
  1576. # Remove var and any directories in var/ created by previous
  1577. # tests
  1578. #
  1579. sub remove_stale_vardir () {
  1580. mtr_report("Removing old var directory...");
  1581. # Safety!
  1582. mtr_error("No, don't remove the vardir when running with --extern")
  1583. if using_extern();
  1584. mtr_verbose("opt_vardir: $opt_vardir");
  1585. if ( $opt_vardir eq $default_vardir )
  1586. {
  1587. #
  1588. # Running with "var" in mysql-test dir
  1589. #
  1590. if ( -l $opt_vardir)
  1591. {
  1592. # var is a symlink
  1593. if ( $opt_mem )
  1594. {
  1595. # Remove the directory which the link points at
  1596. mtr_verbose("Removing " . readlink($opt_vardir));
  1597. rmtree(readlink($opt_vardir));
  1598. # Remove the "var" symlink
  1599. mtr_verbose("unlink($opt_vardir)");
  1600. unlink($opt_vardir);
  1601. }
  1602. else
  1603. {
  1604. # Some users creates a soft link in mysql-test/var to another area
  1605. # - allow it, but remove all files in it
  1606. mtr_report(" - WARNING: Using the 'mysql-test/var' symlink");
  1607. # Make sure the directory where it points exist
  1608. mtr_error("The destination for symlink $opt_vardir does not exist")
  1609. if ! -d readlink($opt_vardir);
  1610. foreach my $bin ( glob("$opt_vardir/*") )
  1611. {
  1612. mtr_verbose("Removing bin $bin");
  1613. rmtree($bin);
  1614. }
  1615. }
  1616. }
  1617. else
  1618. {
  1619. # Remove the entire "var" dir
  1620. mtr_verbose("Removing $opt_vardir/");
  1621. rmtree("$opt_vardir/");
  1622. }
  1623. if ( $opt_mem )
  1624. {
  1625. # A symlink from var/ to $opt_mem will be set up
  1626. # remove the $opt_mem dir to assure the symlink
  1627. # won't point at an old directory
  1628. mtr_verbose("Removing $opt_mem");
  1629. rmtree($opt_mem);
  1630. }
  1631. }
  1632. else
  1633. {
  1634. #
  1635. # Running with "var" in some other place
  1636. #
  1637. # Remove the var/ dir in mysql-test dir if any
  1638. # this could be an old symlink that shouldn't be there
  1639. mtr_verbose("Removing $default_vardir");
  1640. rmtree($default_vardir);
  1641. # Remove the "var" dir
  1642. mtr_verbose("Removing $opt_vardir/");
  1643. rmtree("$opt_vardir/");
  1644. }
  1645. # Remove the "tmp" dir
  1646. mtr_verbose("Removing $opt_tmpdir/");
  1647. rmtree("$opt_tmpdir/");
  1648. }
  1649. #
  1650. # Create var and the directories needed in var
  1651. #
  1652. sub setup_vardir() {
  1653. mtr_report("Creating var directory '$opt_vardir'...");
  1654. if ( $opt_vardir eq $default_vardir )
  1655. {
  1656. #
  1657. # Running with "var" in mysql-test dir
  1658. #
  1659. if ( -l $opt_vardir )
  1660. {
  1661. # it's a symlink
  1662. # Make sure the directory where it points exist
  1663. mtr_error("The destination for symlink $opt_vardir does not exist")
  1664. if ! -d readlink($opt_vardir);
  1665. }
  1666. elsif ( $opt_mem )
  1667. {
  1668. # Runinng with "var" as a link to some "memory" location, normally tmpfs
  1669. mtr_verbose("Creating $opt_mem");
  1670. mkpath($opt_mem);
  1671. mtr_report(" - symlinking 'var' to '$opt_mem'");
  1672. symlink($opt_mem, $opt_vardir);
  1673. }
  1674. }
  1675. if ( ! -d $opt_vardir )
  1676. {
  1677. mtr_verbose("Creating $opt_vardir");
  1678. mkpath($opt_vardir);
  1679. }
  1680. # Ensure a proper error message if vardir couldn't be created
  1681. unless ( -d $opt_vardir and -w $opt_vardir )
  1682. {
  1683. mtr_error("Writable 'var' directory is needed, use the " .
  1684. "'--vardir=<path>' option");
  1685. }
  1686. mkpath("$opt_vardir/log");
  1687. mkpath("$opt_vardir/run");
  1688. # Create var/tmp and tmp - they might be different
  1689. mkpath("$opt_vardir/tmp");
  1690. mkpath($opt_tmpdir) if ($opt_tmpdir ne "$opt_vardir/tmp");
  1691. # On some operating systems, there is a limit to the length of a
  1692. # UNIX domain socket's path far below PATH_MAX.
  1693. # Don't allow that to happen
  1694. if (check_socket_path_length("$opt_tmpdir/testsocket.sock")){
  1695. mtr_error("Socket path '$opt_tmpdir' too long, it would be ",
  1696. "truncated and thus not possible to use for connection to ",
  1697. "MySQL Server. Set a shorter with --tmpdir=<path> option");
  1698. }
  1699. # copy all files from std_data into var/std_data
  1700. # and make them world readable
  1701. copytree("$glob_mysql_test_dir/std_data", "$opt_vardir/std_data", "0022");
  1702. # Remove old log files
  1703. foreach my $name (glob("r/*.progress r/*.log r/*.warnings"))
  1704. {
  1705. unlink($name);
  1706. }
  1707. }
  1708. #
  1709. # Check if running as root
  1710. # i.e a file can be read regardless what mode we set it to
  1711. #
  1712. sub check_running_as_root () {
  1713. my $test_file= "$opt_vardir/test_running_as_root.txt";
  1714. mtr_tofile($test_file, "MySQL");
  1715. chmod(oct("0000"), $test_file);
  1716. my $result="";
  1717. if (open(FILE,"<",$test_file))
  1718. {
  1719. $result= join('', <FILE>);
  1720. close FILE;
  1721. }
  1722. # Some filesystems( for example CIFS) allows reading a file
  1723. # although mode was set to 0000, but in that case a stat on
  1724. # the file will not return 0000
  1725. my $file_mode= (stat($test_file))[2] & 07777;
  1726. mtr_verbose("result: $result, file_mode: $file_mode");
  1727. if ($result eq "MySQL" && $file_mode == 0)
  1728. {
  1729. mtr_warning("running this script as _root_ will cause some " .
  1730. "tests to be skipped");
  1731. $ENV{'MYSQL_TEST_ROOT'}= "YES";
  1732. }
  1733. chmod(oct("0755"), $test_file);
  1734. unlink($test_file);
  1735. }
  1736. sub check_ssl_support ($) {
  1737. my $mysqld_variables= shift;
  1738. if ($opt_skip_ssl)
  1739. {
  1740. mtr_report(" - skipping SSL");
  1741. $opt_ssl_supported= 0;
  1742. $opt_ssl= 0;
  1743. return;
  1744. }
  1745. if ( ! $mysqld_variables->{'ssl'} )
  1746. {
  1747. if ( $opt_ssl)
  1748. {
  1749. mtr_error("Couldn't find support for SSL");
  1750. return;
  1751. }
  1752. mtr_report(" - skipping SSL, mysqld not compiled with SSL");
  1753. $opt_ssl_supported= 0;
  1754. $opt_ssl= 0;
  1755. return;
  1756. }
  1757. mtr_report(" - SSL connections supported");
  1758. $opt_ssl_supported= 1;
  1759. }
  1760. sub check_debug_support ($) {
  1761. my $mysqld_variables= shift;
  1762. if ( ! $mysqld_variables->{'debug'} )
  1763. {
  1764. #mtr_report(" - binaries are not debug compiled");
  1765. $debug_compiled_binaries= 0;
  1766. if ( $opt_debug )
  1767. {
  1768. mtr_error("Can't use --debug, binaries does not support it");
  1769. }
  1770. return;
  1771. }
  1772. mtr_report(" - binaries are debug compiled");
  1773. $debug_compiled_binaries= 1;
  1774. }
  1775. #
  1776. # Helper function to handle configuration-based subdirectories which Visual
  1777. # Studio uses for storing binaries. If opt_vs_config is set, this returns
  1778. # a path based on that setting; if not, it returns paths for the default
  1779. # /release/ and /debug/ subdirectories.
  1780. #
  1781. # $exe can be undefined, if the directory itself will be used
  1782. #
  1783. sub vs_config_dirs ($$) {
  1784. my ($path_part, $exe) = @_;
  1785. $exe = "" if not defined $exe;
  1786. # Don't look in these dirs when not on windows
  1787. return () unless IS_WINDOWS;
  1788. if ($opt_vs_config)
  1789. {
  1790. return ("$basedir/$path_part/$opt_vs_config/$exe");
  1791. }
  1792. return ("$basedir/$path_part/release/$exe",
  1793. "$basedir/$path_part/relwithdebinfo/$exe",
  1794. "$basedir/$path_part/debug/$exe");
  1795. }
  1796. sub check_ndbcluster_support ($) {
  1797. my $mysqld_variables= shift;
  1798. if ($opt_skip_ndbcluster)
  1799. {
  1800. mtr_report(" - skipping ndbcluster");
  1801. return;
  1802. }
  1803. if ( ! $mysqld_variables{'ndb-connectstring'} )
  1804. {
  1805. mtr_report(" - skipping ndbcluster, mysqld not compiled with ndbcluster");
  1806. $opt_skip_ndbcluster= 2;
  1807. return;
  1808. }
  1809. mtr_report(" - using ndbcluster when necessary, mysqld supports it");
  1810. return;
  1811. }
  1812. sub ndbcluster_wait_started($$){
  1813. my $cluster= shift;
  1814. my $ndb_waiter_extra_opt= shift;
  1815. my $path_waitlog= join('/', $opt_vardir, $cluster->name(), "ndb_waiter.log");
  1816. my $args;
  1817. mtr_init_args(\$args);
  1818. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1819. mtr_add_arg($args, "--defaults-group-suffix=%s", $cluster->suffix());
  1820. mtr_add_arg($args, "--timeout=%d", $opt_start_timeout);
  1821. if ($ndb_waiter_extra_opt)
  1822. {
  1823. mtr_add_arg($args, "$ndb_waiter_extra_opt");
  1824. }
  1825. # Start the ndb_waiter which will connect to the ndb_mgmd
  1826. # and poll it for state of the ndbd's, will return when
  1827. # all nodes in the cluster is started
  1828. my $res= My::SafeProcess->run
  1829. (
  1830. name => "ndb_waiter ".$cluster->name(),
  1831. path => $exe_ndb_waiter,
  1832. args => \$args,
  1833. output => $path_waitlog,
  1834. error => $path_waitlog,
  1835. append => 1,
  1836. );
  1837. # Check that ndb_mgmd(s) are still alive
  1838. foreach my $ndb_mgmd ( in_cluster($cluster, ndb_mgmds()) )
  1839. {
  1840. my $proc= $ndb_mgmd->{proc};
  1841. if ( ! $proc->wait_one(0) )
  1842. {
  1843. mtr_warning("$proc died");
  1844. return 2;
  1845. }
  1846. }
  1847. # Check that all started ndbd(s) are still alive
  1848. foreach my $ndbd ( in_cluster($cluster, ndbds()) )
  1849. {
  1850. my $proc= $ndbd->{proc};
  1851. next unless defined $proc;
  1852. if ( ! $proc->wait_one(0) )
  1853. {
  1854. mtr_warning("$proc died");
  1855. return 3;
  1856. }
  1857. }
  1858. if ($res)
  1859. {
  1860. mtr_verbose("ndbcluster_wait_started failed");
  1861. return 1;
  1862. }
  1863. return 0;
  1864. }
  1865. sub ndb_mgmd_wait_started($) {
  1866. my ($cluster)= @_;
  1867. my $retries= 100;
  1868. while ($retries)
  1869. {
  1870. my $result= ndbcluster_wait_started($cluster, "--no-contact");
  1871. if ($result == 0)
  1872. {
  1873. # ndb_mgmd is started
  1874. mtr_verbose("ndb_mgmd is started");
  1875. return 0;
  1876. }
  1877. elsif ($result > 1)
  1878. {
  1879. mtr_warning("Cluster process failed while waiting for start");
  1880. return $result;
  1881. }
  1882. mtr_milli_sleep(100);
  1883. $retries--;
  1884. }
  1885. return 1;
  1886. }
  1887. sub ndb_mgmd_start ($$) {
  1888. my ($cluster, $ndb_mgmd)= @_;
  1889. mtr_verbose("ndb_mgmd_start");
  1890. my $dir= $ndb_mgmd->value("DataDir");
  1891. mkpath($dir) unless -d $dir;
  1892. my $args;
  1893. mtr_init_args(\$args);
  1894. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1895. mtr_add_arg($args, "--defaults-group-suffix=%s", $cluster->suffix());
  1896. mtr_add_arg($args, "--mycnf");
  1897. mtr_add_arg($args, "--nodaemon");
  1898. my $path_ndb_mgmd_log= "$dir/ndb_mgmd.log";
  1899. $ndb_mgmd->{'proc'}= My::SafeProcess->new
  1900. (
  1901. name => $ndb_mgmd->after('cluster_config.'),
  1902. path => $exe_ndb_mgmd,
  1903. args => \$args,
  1904. output => $path_ndb_mgmd_log,
  1905. error => $path_ndb_mgmd_log,
  1906. append => 1,
  1907. verbose => $opt_verbose,
  1908. );
  1909. mtr_verbose("Started $ndb_mgmd->{proc}");
  1910. # FIXME Should not be needed
  1911. # Unfortunately the cluster nodes will fail to start
  1912. # if ndb_mgmd has not started properly
  1913. if (ndb_mgmd_wait_started($cluster))
  1914. {
  1915. mtr_warning("Failed to wait for start of ndb_mgmd");
  1916. return 1;
  1917. }
  1918. return 0;
  1919. }
  1920. sub ndbd_start {
  1921. my ($cluster, $ndbd)= @_;
  1922. mtr_verbose("ndbd_start");
  1923. my $dir= $ndbd->value("DataDir");
  1924. mkpath($dir) unless -d $dir;
  1925. my $args;
  1926. mtr_init_args(\$args);
  1927. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  1928. mtr_add_arg($args, "--defaults-group-suffix=%s", $cluster->suffix());
  1929. mtr_add_arg($args, "--nodaemon");
  1930. # > 5.0 { 'character-sets-dir' => \&fix_charset_dir },
  1931. my $path_ndbd_log= "$dir/ndbd.log";
  1932. my $proc= My::SafeProcess->new
  1933. (
  1934. name => $ndbd->after('cluster_config.'),
  1935. path => $exe_ndbd,
  1936. args => \$args,
  1937. output => $path_ndbd_log,
  1938. error => $path_ndbd_log,
  1939. append => 1,
  1940. verbose => $opt_verbose,
  1941. );
  1942. mtr_verbose("Started $proc");
  1943. $ndbd->{proc}= $proc;
  1944. return;
  1945. }
  1946. sub ndbcluster_start ($) {
  1947. my $cluster= shift;
  1948. mtr_verbose("ndbcluster_start '".$cluster->name()."'");
  1949. foreach my $ndb_mgmd ( in_cluster($cluster, ndb_mgmds()) )
  1950. {
  1951. next if started($ndb_mgmd);
  1952. ndb_mgmd_start($cluster, $ndb_mgmd);
  1953. }
  1954. foreach my $ndbd ( in_cluster($cluster, ndbds()) )
  1955. {
  1956. next if started($ndbd);
  1957. ndbd_start($cluster, $ndbd);
  1958. }
  1959. return 0;
  1960. }
  1961. sub create_config_file_for_extern {
  1962. my %opts=
  1963. (
  1964. socket => '/tmp/mysqld.sock',
  1965. port => 3306,
  1966. user => $opt_user,
  1967. password => '',
  1968. @_
  1969. );
  1970. mtr_report("Creating my.cnf file for extern server...");
  1971. my $F= IO::File->new($path_config_file, "w")
  1972. or mtr_error("Can't write to $path_config_file: $!");
  1973. print $F "[client]\n";
  1974. while (my ($option, $value)= each( %opts )) {
  1975. print $F "$option= $value\n";
  1976. mtr_report(" $option= $value");
  1977. }
  1978. print $F <<EOF
  1979. # binlog reads from [client] and [mysqlbinlog]
  1980. [mysqlbinlog]
  1981. character-sets-dir= $path_charsetsdir
  1982. # mysql_fix_privilege_tables.sh don't read from [client]
  1983. [mysql_fix_privilege_tables]
  1984. socket = $opts{'socket'}
  1985. port = $opts{'port'}
  1986. user = $opts{'user'}
  1987. password = $opts{'password'}
  1988. EOF
  1989. ;
  1990. $F= undef; # Close file
  1991. }
  1992. #
  1993. # Kill processes left from previous runs, normally
  1994. # there should be none so make sure to warn
  1995. # if there is one
  1996. #
  1997. sub kill_leftovers ($) {
  1998. my $rundir= shift;
  1999. return unless ( -d $rundir );
  2000. mtr_report("Checking leftover processes...");
  2001. # Scan the "run" directory for process id's to kill
  2002. opendir(RUNDIR, $rundir)
  2003. or mtr_error("kill_leftovers, can't open dir \"$rundir\": $!");
  2004. while ( my $elem= readdir(RUNDIR) )
  2005. {
  2006. # Only read pid from files that end with .pid
  2007. if ( $elem =~ /.*[.]pid$/ )
  2008. {
  2009. my $pidfile= "$rundir/$elem";
  2010. next unless -f $pidfile;
  2011. my $pid= mtr_fromfile($pidfile);
  2012. unlink($pidfile);
  2013. unless ($pid=~ /^(\d+)/){
  2014. # The pid was not a valid number
  2015. mtr_warning("Got invalid pid '$pid' from '$elem'");
  2016. next;
  2017. }
  2018. mtr_report(" - found old pid $pid in '$elem', killing it...");
  2019. my $ret= kill("KILL", $pid);
  2020. if ($ret == 0) {
  2021. mtr_report(" process did not exist!");
  2022. next;
  2023. }
  2024. my $check_counter= 100;
  2025. while ($ret > 0 and $check_counter--) {
  2026. mtr_milli_sleep(100);
  2027. $ret= kill(0, $pid);
  2028. }
  2029. mtr_report($check_counter ? " ok!" : " failed!");
  2030. }
  2031. else
  2032. {
  2033. mtr_warning("Found non pid file '$elem' in '$rundir'")
  2034. if -f "$rundir/$elem";
  2035. }
  2036. }
  2037. closedir(RUNDIR);
  2038. }
  2039. #
  2040. # Check that all the ports that are going to
  2041. # be used are free
  2042. #
  2043. sub check_ports_free
  2044. {
  2045. my @ports_to_check;
  2046. for ($baseport..$baseport+9){
  2047. push(@ports_to_check, $_);
  2048. }
  2049. #mtr_report("Checking ports...");
  2050. # print "@ports_to_check\n";
  2051. foreach my $port (@ports_to_check){
  2052. if (mtr_ping_port($port)){
  2053. mtr_report(" - 'localhost:$port' was not free");
  2054. return 1; # One port was not free
  2055. }
  2056. }
  2057. return 0; # All ports free
  2058. }
  2059. sub initialize_servers {
  2060. if ( using_extern() )
  2061. {
  2062. # Running against an already started server, if the specified
  2063. # vardir does not already exist it should be created
  2064. if ( ! -d $opt_vardir )
  2065. {
  2066. setup_vardir();
  2067. }
  2068. else
  2069. {
  2070. mtr_verbose("No need to create '$opt_vardir' it already exists");
  2071. }
  2072. }
  2073. else
  2074. {
  2075. # Kill leftovers from previous run
  2076. # using any pidfiles found in var/run
  2077. kill_leftovers("$opt_vardir/run");
  2078. if ( ! $opt_start_dirty )
  2079. {
  2080. remove_stale_vardir();
  2081. setup_vardir();
  2082. mysql_install_db(default_mysqld(), "$opt_vardir/install.db");
  2083. }
  2084. }
  2085. }
  2086. #
  2087. # Remove all newline characters expect after semicolon
  2088. #
  2089. sub sql_to_bootstrap {
  2090. my ($sql) = @_;
  2091. my @lines= split(/\n/, $sql);
  2092. my $result= "\n";
  2093. my $delimiter= ';';
  2094. foreach my $line (@lines) {
  2095. # Change current delimiter if line starts with "delimiter"
  2096. if ( $line =~ /^delimiter (.*)/ ) {
  2097. my $new= $1;
  2098. # Remove old delimiter from end of new
  2099. $new=~ s/\Q$delimiter\E$//;
  2100. $delimiter = $new;
  2101. mtr_debug("changed delimiter to $delimiter");
  2102. # No need to add the delimiter to result
  2103. next;
  2104. }
  2105. # Add newline if line ends with $delimiter
  2106. # and convert the current delimiter to semicolon
  2107. if ( $line =~ /\Q$delimiter\E$/ ){
  2108. $line =~ s/\Q$delimiter\E$/;/;
  2109. $result.= "$line\n";
  2110. mtr_debug("Added default delimiter");
  2111. next;
  2112. }
  2113. # Remove comments starting with --
  2114. if ( $line =~ /^\s*--/ ) {
  2115. mtr_debug("Discarded $line");
  2116. next;
  2117. }
  2118. # Replace @HOSTNAME with localhost
  2119. $line=~ s/\'\@HOSTNAME\@\'/localhost/;
  2120. # Default, just add the line without newline
  2121. # but with a space as separator
  2122. $result.= "$line ";
  2123. }
  2124. return $result;
  2125. }
  2126. sub default_mysqld {
  2127. # Generate new config file from template
  2128. my $config= My::ConfigFactory->new_config
  2129. ( {
  2130. basedir => $basedir,
  2131. template_path => "include/default_my.cnf",
  2132. vardir => $opt_vardir,
  2133. tmpdir => $opt_tmpdir,
  2134. baseport => 0,
  2135. user => $opt_user,
  2136. password => '',
  2137. }
  2138. );
  2139. my $mysqld= $config->group('mysqld.1')
  2140. or mtr_error("Couldn't find mysqld.1 in default config");
  2141. return $mysqld;
  2142. }
  2143. sub mysql_install_db {
  2144. my ($mysqld, $datadir)= @_;
  2145. my $install_datadir= $datadir || $mysqld->value('datadir');
  2146. my $install_basedir= $mysqld->value('basedir');
  2147. my $install_lang= $mysqld->value('language');
  2148. my $install_chsdir= $mysqld->value('character-sets-dir');
  2149. mtr_report("Installing system database...");
  2150. my $args;
  2151. mtr_init_args(\$args);
  2152. mtr_add_arg($args, "--no-defaults");
  2153. mtr_add_arg($args, "--bootstrap");
  2154. mtr_add_arg($args, "--basedir=%s", $install_basedir);
  2155. mtr_add_arg($args, "--datadir=%s", $install_datadir);
  2156. mtr_add_arg($args, "--loose-skip-innodb");
  2157. mtr_add_arg($args, "--loose-skip-falcon");
  2158. mtr_add_arg($args, "--loose-skip-ndbcluster");
  2159. mtr_add_arg($args, "--tmpdir=%s", "$opt_vardir/tmp/");
  2160. mtr_add_arg($args, "--core-file");
  2161. if ( $opt_debug )
  2162. {
  2163. mtr_add_arg($args, "--debug=d:t:i:A,%s/log/bootstrap.trace",
  2164. $path_vardir_trace);
  2165. }
  2166. mtr_add_arg($args, "--language=%s", $install_lang);
  2167. mtr_add_arg($args, "--character-sets-dir=%s", $install_chsdir);
  2168. # If DISABLE_GRANT_OPTIONS is defined when the server is compiled (e.g.,
  2169. # configure --disable-grant-options), mysqld will not recognize the
  2170. # --bootstrap or --skip-grant-tables options. The user can set
  2171. # MYSQLD_BOOTSTRAP to the full path to a mysqld which does accept
  2172. # --bootstrap, to accommodate this.
  2173. my $exe_mysqld_bootstrap =
  2174. $ENV{'MYSQLD_BOOTSTRAP'} || find_mysqld($install_basedir);
  2175. # ----------------------------------------------------------------------
  2176. # export MYSQLD_BOOTSTRAP_CMD variable containing <path>/mysqld <args>
  2177. # ----------------------------------------------------------------------
  2178. $ENV{'MYSQLD_BOOTSTRAP_CMD'}= "$exe_mysqld_bootstrap " . join(" ", @$args);
  2179. # ----------------------------------------------------------------------
  2180. # Create the bootstrap.sql file
  2181. # ----------------------------------------------------------------------
  2182. my $bootstrap_sql_file= "$opt_vardir/tmp/bootstrap.sql";
  2183. my $path_sql= my_find_file($install_basedir,
  2184. ["mysql", "sql/share", "share/mysql",
  2185. "share", "scripts"],
  2186. "mysql_system_tables.sql",
  2187. NOT_REQUIRED);
  2188. if (-f $path_sql )
  2189. {
  2190. my $sql_dir= dirname($path_sql);
  2191. # Use the mysql database for system tables
  2192. mtr_tofile($bootstrap_sql_file, "use mysql\n");
  2193. # Add the offical mysql system tables
  2194. # for a production system
  2195. mtr_appendfile_to_file("$sql_dir/mysql_system_tables.sql",
  2196. $bootstrap_sql_file);
  2197. # Add the mysql system tables initial data
  2198. # for a production system
  2199. mtr_appendfile_to_file("$sql_dir/mysql_system_tables_data.sql",
  2200. $bootstrap_sql_file);
  2201. # Add test data for timezone - this is just a subset, on a real
  2202. # system these tables will be populated either by mysql_tzinfo_to_sql
  2203. # or by downloading the timezone table package from our website
  2204. mtr_appendfile_to_file("$sql_dir/mysql_test_data_timezone.sql",
  2205. $bootstrap_sql_file);
  2206. # Fill help tables, just an empty file when running from bk repo
  2207. # but will be replaced by a real fill_help_tables.sql when
  2208. # building the source dist
  2209. mtr_appendfile_to_file("$sql_dir/fill_help_tables.sql",
  2210. $bootstrap_sql_file);
  2211. }
  2212. else
  2213. {
  2214. # Install db from init_db.sql that exist in early 5.1 and 5.0
  2215. # versions of MySQL
  2216. my $init_file= "$install_basedir/mysql-test/lib/init_db.sql";
  2217. mtr_report(" - from '$init_file'");
  2218. my $text= mtr_grab_file($init_file) or
  2219. mtr_error("Can't open '$init_file': $!");
  2220. mtr_tofile($bootstrap_sql_file,
  2221. sql_to_bootstrap($text));
  2222. }
  2223. # Remove anonymous users
  2224. mtr_tofile($bootstrap_sql_file,
  2225. "DELETE FROM mysql.user where user= '';\n");
  2226. # Create mtr database
  2227. mtr_tofile($bootstrap_sql_file,
  2228. "CREATE DATABASE mtr;\n");
  2229. # Add help tables and data for warning detection and supression
  2230. mtr_tofile($bootstrap_sql_file,
  2231. sql_to_bootstrap(mtr_grab_file("include/mtr_warnings.sql")));
  2232. # Add procedures for checking server is restored after testcase
  2233. mtr_tofile($bootstrap_sql_file,
  2234. sql_to_bootstrap(mtr_grab_file("include/mtr_check.sql")));
  2235. # Log bootstrap command
  2236. my $path_bootstrap_log= "$opt_vardir/log/bootstrap.log";
  2237. mtr_tofile($path_bootstrap_log,
  2238. "$exe_mysqld_bootstrap " . join(" ", @$args) . "\n");
  2239. # Create directories mysql and test
  2240. mkpath("$install_datadir/mysql");
  2241. mkpath("$install_datadir/test");
  2242. if ( My::SafeProcess->run
  2243. (
  2244. name => "bootstrap",
  2245. path => $exe_mysqld_bootstrap,
  2246. args => \$args,
  2247. input => $bootstrap_sql_file,
  2248. output => $path_bootstrap_log,
  2249. error => $path_bootstrap_log,
  2250. append => 1,
  2251. verbose => $opt_verbose,
  2252. ) != 0)
  2253. {
  2254. mtr_error("Error executing mysqld --bootstrap\n" .
  2255. "Could not install system database from $bootstrap_sql_file\n" .
  2256. "see $path_bootstrap_log for errors");
  2257. }
  2258. }
  2259. sub run_testcase_check_skip_test($)
  2260. {
  2261. my ($tinfo)= @_;
  2262. # ----------------------------------------------------------------------
  2263. # If marked to skip, just print out and return.
  2264. # Note that a test case not marked as 'skip' can still be
  2265. # skipped later, because of the test case itself in cooperation
  2266. # with the mysqltest program tells us so.
  2267. # ----------------------------------------------------------------------
  2268. if ( $tinfo->{'skip'} )
  2269. {
  2270. mtr_report_test_skipped($tinfo);
  2271. return 1;
  2272. }
  2273. return 0;
  2274. }
  2275. sub run_query {
  2276. my ($tinfo, $mysqld, $query)= @_;
  2277. my $args;
  2278. mtr_init_args(\$args);
  2279. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  2280. mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld'));
  2281. mtr_add_arg($args, "-e %s", $query);
  2282. my $res= My::SafeProcess->run
  2283. (
  2284. name => "run_query -> ".$mysqld->name(),
  2285. path => $exe_mysql,
  2286. args => \$args,
  2287. output => '/dev/null',
  2288. error => '/dev/null'
  2289. );
  2290. return $res
  2291. }
  2292. sub do_before_run_mysqltest($)
  2293. {
  2294. my $tinfo= shift;
  2295. # Remove old files produced by mysqltest
  2296. my $base_file= mtr_match_extension($tinfo->{result_file},
  2297. "result"); # Trim extension
  2298. if (defined $base_file ){
  2299. unlink("$base_file.reject");
  2300. unlink("$base_file.progress");
  2301. unlink("$base_file.log");
  2302. unlink("$base_file.warnings");
  2303. }
  2304. if ( $mysql_version_id < 50000 ) {
  2305. # Set environment variable NDB_STATUS_OK to 1
  2306. # if script decided to run mysqltest cluster _is_ installed ok
  2307. $ENV{'NDB_STATUS_OK'} = "1";
  2308. } elsif ( $mysql_version_id < 50100 ) {
  2309. # Set environment variable NDB_STATUS_OK to YES
  2310. # if script decided to run mysqltest cluster _is_ installed ok
  2311. $ENV{'NDB_STATUS_OK'} = "YES";
  2312. }
  2313. }
  2314. #
  2315. # Check all server for sideffects
  2316. #
  2317. # RETURN VALUE
  2318. # 0 ok
  2319. # 1 Check failed
  2320. # >1 Fatal errro
  2321. sub check_testcase($$)
  2322. {
  2323. my ($tinfo, $mode)= @_;
  2324. my $tname= $tinfo->{name};
  2325. # Start the mysqltest processes in parallel to save time
  2326. # also makes it possible to wait for any process to exit during the check
  2327. my %started;
  2328. foreach my $mysqld ( mysqlds() )
  2329. {
  2330. if ( defined $mysqld->{'proc'} )
  2331. {
  2332. my $proc= start_check_testcase($tinfo, $mode, $mysqld);
  2333. $started{$proc->pid()}= $proc;
  2334. }
  2335. }
  2336. # Return immediately if no check proceess was started
  2337. return 0 unless ( keys %started );
  2338. my $timeout_proc= My::SafeProcess->timer(check_timeout());
  2339. while (1){
  2340. my $result;
  2341. my $proc= My::SafeProcess->wait_any();
  2342. mtr_report("Got $proc");
  2343. if ( delete $started{$proc->pid()} ) {
  2344. my $err_file= $proc->user_data();
  2345. my $base_file= mtr_match_extension($err_file, "err"); # Trim extension
  2346. # One check testcase process returned
  2347. my $res= $proc->exit_status();
  2348. if ( $res == 0){
  2349. # Check completed without problem
  2350. # Remove the .err file the check generated
  2351. unlink($err_file);
  2352. # Remove the .result file the check generated
  2353. if ( $mode eq 'after' ){
  2354. unlink("$base_file.result");
  2355. }
  2356. if ( keys(%started) == 0){
  2357. # All checks completed
  2358. $timeout_proc->kill();
  2359. return 0;
  2360. }
  2361. # Wait for next process to exit
  2362. next;
  2363. }
  2364. else
  2365. {
  2366. if ( $mode eq "after" and $res == 1 )
  2367. {
  2368. # Test failed, grab the report mysqltest has created
  2369. my $report= mtr_grab_file($err_file);
  2370. $tinfo->{check}.=
  2371. "\nMTR's internal check of the test case '$tname' failed.
  2372. This means that the test case does not preserve the state that existed
  2373. before the test case was executed. Most likely the test case did not
  2374. do a proper clean-up.
  2375. This is the diff of the states of the servers before and after the
  2376. test case was executed:\n";
  2377. $tinfo->{check}.= $report;
  2378. # Check failed, mark the test case with that info
  2379. $tinfo->{'check_testcase_failed'}= 1;
  2380. $result= 1;
  2381. }
  2382. elsif ( $res )
  2383. {
  2384. my $report= mtr_grab_file($err_file);
  2385. $tinfo->{comment}.=
  2386. "Could not execute 'check-testcase' $mode ".
  2387. "testcase '$tname' (res: $res):\n";
  2388. $tinfo->{comment}.= $report;
  2389. $result= 2;
  2390. }
  2391. # Remove the .result file the check generated
  2392. unlink("$base_file.result");
  2393. }
  2394. }
  2395. elsif ( $proc eq $timeout_proc ) {
  2396. $tinfo->{comment}.= "Timeout $timeout_proc for ".
  2397. "'check-testcase' expired after ".check_timeout().
  2398. " seconds";
  2399. $result= 4;
  2400. }
  2401. else {
  2402. # Unknown process returned, most likley a crash, abort everything
  2403. $tinfo->{comment}=
  2404. "The server $proc crashed while running ".
  2405. "'check testcase $mode test'";
  2406. $result= 3;
  2407. }
  2408. # Kill any check processes still running
  2409. map($_->kill(), values(%started));
  2410. $timeout_proc->kill();
  2411. return $result;
  2412. }
  2413. mtr_error("INTERNAL_ERROR: check_testcase");
  2414. }
  2415. # Start run mysqltest on one server
  2416. #
  2417. # RETURN VALUE
  2418. # 0 OK
  2419. # 1 Check failed
  2420. #
  2421. sub start_run_one ($$) {
  2422. my ($mysqld, $run)= @_;
  2423. my $name= "$run-".$mysqld->name();
  2424. my $args;
  2425. mtr_init_args(\$args);
  2426. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  2427. mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld'));
  2428. mtr_add_arg($args, "--silent");
  2429. mtr_add_arg($args, "--skip-safemalloc");
  2430. mtr_add_arg($args, "--test-file=%s", "include/$run.test");
  2431. my $errfile= "$opt_vardir/tmp/$name.err";
  2432. my $proc= My::SafeProcess->new
  2433. (
  2434. name => $name,
  2435. path => $exe_mysqltest,
  2436. error => $errfile,
  2437. output => $errfile,
  2438. args => \$args,
  2439. user_data => $errfile,
  2440. verbose => $opt_verbose,
  2441. );
  2442. mtr_verbose("Started $proc");
  2443. return $proc;
  2444. }
  2445. #
  2446. # Run script on all servers, collect results
  2447. #
  2448. # RETURN VALUE
  2449. # 0 ok
  2450. # 1 Failure
  2451. sub run_on_all($$)
  2452. {
  2453. my ($tinfo, $run)= @_;
  2454. # Start the mysqltest processes in parallel to save time
  2455. # also makes it possible to wait for any process to exit during the check
  2456. # and to have a timeout process
  2457. my %started;
  2458. foreach my $mysqld ( mysqlds() )
  2459. {
  2460. if ( defined $mysqld->{'proc'} )
  2461. {
  2462. my $proc= start_run_one($mysqld, $run);
  2463. $started{$proc->pid()}= $proc;
  2464. }
  2465. }
  2466. # Return immediately if no check proceess was started
  2467. return 0 unless ( keys %started );
  2468. my $timeout_proc= My::SafeProcess->timer(check_timeout());
  2469. while (1){
  2470. my $result;
  2471. my $proc= My::SafeProcess->wait_any();
  2472. mtr_report("Got $proc");
  2473. if ( delete $started{$proc->pid()} ) {
  2474. # One mysqltest process returned
  2475. my $err_file= $proc->user_data();
  2476. my $res= $proc->exit_status();
  2477. # Append the report from .err file
  2478. $tinfo->{comment}.= " == $err_file ==\n";
  2479. $tinfo->{comment}.= mtr_grab_file($err_file);
  2480. $tinfo->{comment}.= "\n";
  2481. # Remove the .err file
  2482. unlink($err_file);
  2483. if ( keys(%started) == 0){
  2484. # All completed
  2485. $timeout_proc->kill();
  2486. return 0;
  2487. }
  2488. # Wait for next process to exit
  2489. next;
  2490. }
  2491. elsif ( $proc eq $timeout_proc ) {
  2492. $tinfo->{comment}.= "Timeout $timeout_proc for '$run' ".
  2493. "expired after ". check_timeout().
  2494. " seconds";
  2495. }
  2496. else {
  2497. # Unknown process returned, most likley a crash, abort everything
  2498. $tinfo->{comment}.=
  2499. "The server $proc crashed while running '$run'";
  2500. }
  2501. # Kill any check processes still running
  2502. map($_->kill(), values(%started));
  2503. $timeout_proc->kill();
  2504. return 1;
  2505. }
  2506. mtr_error("INTERNAL_ERROR: run_on_all");
  2507. }
  2508. sub mark_log {
  2509. my ($log, $tinfo)= @_;
  2510. my $log_msg= "CURRENT_TEST: $tinfo->{name}\n";
  2511. mtr_tofile($log, $log_msg);
  2512. }
  2513. sub find_testcase_skipped_reason($)
  2514. {
  2515. my ($tinfo)= @_;
  2516. # Set default message
  2517. $tinfo->{'comment'}= "Detected by testcase(no log file)";
  2518. # Open the test log file
  2519. my $F= IO::File->new($path_current_testlog)
  2520. or return;
  2521. my $reason;
  2522. while ( my $line= <$F> )
  2523. {
  2524. # Look for "reason: <reason for skipping test>"
  2525. if ( $line =~ /reason: (.*)/ )
  2526. {
  2527. $reason= $1;
  2528. }
  2529. }
  2530. if ( ! $reason )
  2531. {
  2532. mtr_warning("Could not find reason for skipping test in $path_current_testlog");
  2533. $reason= "Detected by testcase(reason unknown) ";
  2534. }
  2535. $tinfo->{'comment'}= $reason;
  2536. }
  2537. sub find_analyze_request
  2538. {
  2539. # Open the test log file
  2540. my $F= IO::File->new($path_current_testlog)
  2541. or return;
  2542. my $analyze;
  2543. while ( my $line= <$F> )
  2544. {
  2545. # Look for "reason: <reason for skipping test>"
  2546. if ( $line =~ /analyze: (.*)/ )
  2547. {
  2548. $analyze= $1;
  2549. }
  2550. }
  2551. return $analyze;
  2552. }
  2553. # Return timezone value of tinfo or default value
  2554. sub timezone {
  2555. my ($tinfo)= @_;
  2556. return $tinfo->{timezone} || "GMT-3";
  2557. }
  2558. # Storage for changed environment variables
  2559. my %old_env;
  2560. #
  2561. # Run a single test case
  2562. #
  2563. # RETURN VALUE
  2564. # 0 OK
  2565. # > 0 failure
  2566. #
  2567. sub run_testcase ($) {
  2568. my $tinfo= shift;
  2569. mtr_verbose("Running test:", $tinfo->{name});
  2570. # -------------------------------------------------------
  2571. # Init variables that can change between each test case
  2572. # -------------------------------------------------------
  2573. my $timezone= timezone($tinfo);
  2574. $ENV{'TZ'}= $timezone;
  2575. mtr_verbose("Setting timezone: $timezone");
  2576. if ( ! using_extern() )
  2577. {
  2578. my @restart= servers_need_restart($tinfo);
  2579. if ( @restart != 0) {
  2580. stop_servers($tinfo, @restart );
  2581. }
  2582. if ( started(all_servers()) == 0 )
  2583. {
  2584. # Remove old datadirs
  2585. clean_datadir();
  2586. # Restore old ENV
  2587. while (my ($option, $value)= each( %old_env )) {
  2588. if (defined $value){
  2589. mtr_verbose("Restoring $option to $value");
  2590. $ENV{$option}= $value;
  2591. } else {
  2592. mtr_verbose("Removing $option");
  2593. delete($ENV{$option});
  2594. }
  2595. }
  2596. %old_env= ();
  2597. mtr_verbose("Generating my.cnf from '$tinfo->{template_path}'");
  2598. # Generate new config file from template
  2599. $config= My::ConfigFactory->new_config
  2600. ( {
  2601. basedir => $basedir,
  2602. template_path => $tinfo->{template_path},
  2603. extra_template_path => $tinfo->{extra_template_path},
  2604. vardir => $opt_vardir,
  2605. tmpdir => $opt_tmpdir,
  2606. baseport => $baseport,
  2607. #hosts => [ 'host1', 'host2' ],
  2608. user => $opt_user,
  2609. password => '',
  2610. ssl => $opt_ssl_supported,
  2611. embedded => $opt_embedded_server,
  2612. }
  2613. );
  2614. # Write the new my.cnf
  2615. $config->save($path_config_file);
  2616. # Remember current config so a restart can occur when a test need
  2617. # to use a different one
  2618. $current_config_name= $tinfo->{template_path};
  2619. #
  2620. # Set variables in the ENV section
  2621. #
  2622. foreach my $option ($config->options_in_group("ENV"))
  2623. {
  2624. # Save old value to restore it before next time
  2625. $old_env{$option->name()}= $ENV{$option->name()};
  2626. mtr_verbose($option->name(), "=",$option->value());
  2627. $ENV{$option->name()}= $option->value();
  2628. }
  2629. }
  2630. # Write start of testcase to log
  2631. mark_log($path_current_testlog, $tinfo);
  2632. if (start_servers($tinfo))
  2633. {
  2634. report_failure_and_restart($tinfo);
  2635. return 1;
  2636. }
  2637. }
  2638. # --------------------------------------------------------------------
  2639. # If --start or --start-dirty given, stop here to let user manually
  2640. # run tests
  2641. # ----------------------------------------------------------------------
  2642. if ( $opt_start or $opt_start_dirty )
  2643. {
  2644. mtr_print("\nStarted", started(all_servers()));
  2645. mtr_print("Waiting for server(s) to exit...");
  2646. my $proc= My::SafeProcess->wait_any();
  2647. if ( grep($proc eq $_, started(all_servers())) )
  2648. {
  2649. mtr_print("Server $proc died");
  2650. exit(1);
  2651. }
  2652. mtr_print("Unknown process $proc died");
  2653. exit(1);
  2654. }
  2655. my $test_timeout_proc= My::SafeProcess->timer(testcase_timeout());
  2656. do_before_run_mysqltest($tinfo);
  2657. if ( $opt_check_testcases and check_testcase($tinfo, "before") ){
  2658. # Failed to record state of server or server crashed
  2659. report_failure_and_restart($tinfo);
  2660. # Stop the test case timer
  2661. $test_timeout_proc->kill();
  2662. return 1;
  2663. }
  2664. my $test= start_mysqltest($tinfo);
  2665. while (1)
  2666. {
  2667. my $proc= My::SafeProcess->wait_any();
  2668. unless ( defined $proc )
  2669. {
  2670. mtr_error("wait_any failed");
  2671. }
  2672. mtr_verbose("Got $proc");
  2673. # ----------------------------------------------------
  2674. # Was it the test program that exited
  2675. # ----------------------------------------------------
  2676. if ($proc eq $test)
  2677. {
  2678. # Stop the test case timer
  2679. $test_timeout_proc->kill();
  2680. my $res= $test->exit_status();
  2681. if ($res == 0 and $opt_warnings and check_warnings($tinfo) )
  2682. {
  2683. # Test case suceeded, but it has produced unexpected
  2684. # warnings, continue in $res == 1
  2685. $res= 1;
  2686. }
  2687. if ( $res == 0 )
  2688. {
  2689. my $check_res;
  2690. if ( $opt_check_testcases and
  2691. $check_res= check_testcase($tinfo, "after"))
  2692. {
  2693. if ($check_res == 1) {
  2694. # Test case had sideeffects, not fatal error, just continue
  2695. stop_all_servers();
  2696. mtr_report("Resuming tests...\n");
  2697. }
  2698. else {
  2699. # Test case check failed fatally, probably a server crashed
  2700. report_failure_and_restart($tinfo);
  2701. return 1;
  2702. }
  2703. }
  2704. mtr_report_test_passed($tinfo);
  2705. }
  2706. elsif ( $res == 62 )
  2707. {
  2708. # Testcase itself tell us to skip this one
  2709. $tinfo->{skip_detected_by_test}= 1;
  2710. # Try to get reason from test log file
  2711. find_testcase_skipped_reason($tinfo);
  2712. mtr_report_test_skipped($tinfo);
  2713. }
  2714. elsif ( $res == 65 )
  2715. {
  2716. # Testprogram killed by signal
  2717. $tinfo->{comment}=
  2718. "testprogram crashed(returned code $res)";
  2719. report_failure_and_restart($tinfo);
  2720. }
  2721. elsif ( $res == 1 )
  2722. {
  2723. # Check if the test tool requests that
  2724. # an analyze script should be run
  2725. my $analyze= find_analyze_request();
  2726. if ($analyze){
  2727. run_on_all($tinfo, "analyze-$analyze");
  2728. }
  2729. # Test case failure reported by mysqltest
  2730. report_failure_and_restart($tinfo);
  2731. }
  2732. else
  2733. {
  2734. # mysqltest failed, probably crashed
  2735. $tinfo->{comment}=
  2736. "mysqltest failed with unexpected return code $res";
  2737. report_failure_and_restart($tinfo);
  2738. }
  2739. # Save info from this testcase run to mysqltest.log
  2740. if( -f $path_current_testlog)
  2741. {
  2742. mtr_appendfile_to_file($path_current_testlog, $path_testlog);
  2743. unlink($path_current_testlog);
  2744. }
  2745. return ($res == 62) ? 0 : $res;
  2746. }
  2747. # ----------------------------------------------------
  2748. # Check if it was an expected crash
  2749. # ----------------------------------------------------
  2750. if ( check_expected_crash_and_restart($proc) )
  2751. {
  2752. next;
  2753. }
  2754. # ----------------------------------------------------
  2755. # Stop the test case timer
  2756. # ----------------------------------------------------
  2757. $test_timeout_proc->kill();
  2758. # ----------------------------------------------------
  2759. # Check if it was a server that died
  2760. # ----------------------------------------------------
  2761. if ( grep($proc eq $_, started(all_servers())) )
  2762. {
  2763. # Server failed, probably crashed
  2764. $tinfo->{comment}=
  2765. "Server $proc failed during test run";
  2766. # ----------------------------------------------------
  2767. # It's not mysqltest that has exited, kill it
  2768. # ----------------------------------------------------
  2769. $test->kill();
  2770. report_failure_and_restart($tinfo);
  2771. return 1;
  2772. }
  2773. # Try to dump core for mysqltest and all servers
  2774. foreach my $proc ($test, started(all_servers()))
  2775. {
  2776. mtr_print("Trying to dump core for $proc");
  2777. if ($proc->dump_core())
  2778. {
  2779. $proc->wait_one(20);
  2780. }
  2781. }
  2782. # ----------------------------------------------------
  2783. # It's not mysqltest that has exited, kill it
  2784. # ----------------------------------------------------
  2785. $test->kill();
  2786. # ----------------------------------------------------
  2787. # Check if testcase timer expired
  2788. # ----------------------------------------------------
  2789. if ( $proc eq $test_timeout_proc )
  2790. {
  2791. my $log_file_name= $opt_vardir."/log/".$tinfo->{shortname}.".log";
  2792. $tinfo->{comment}=
  2793. "Test case timeout after ".testcase_timeout().
  2794. " seconds\n\n";
  2795. # Add 20 last executed commands from test case log file
  2796. if (-e $log_file_name)
  2797. {
  2798. $tinfo->{comment}.=
  2799. "== $log_file_name == \n".
  2800. mtr_lastlinesfromfile($log_file_name, 20)."\n";
  2801. }
  2802. $tinfo->{'timeout'}= testcase_timeout(); # Mark as timeout
  2803. run_on_all($tinfo, 'analyze-timeout');
  2804. report_failure_and_restart($tinfo);
  2805. return 1;
  2806. }
  2807. mtr_error("Unhandled process $proc exited");
  2808. }
  2809. mtr_error("Should never come here");
  2810. }
  2811. #
  2812. # Perform a rough examination of the servers
  2813. # error log and write all lines that look
  2814. # suspicious into $error_log.warnings
  2815. #
  2816. sub extract_warning_lines ($) {
  2817. my ($error_log) = @_;
  2818. # Open the servers .err log file and read all lines
  2819. # belonging to current tets into @lines
  2820. my $Ferr = IO::File->new($error_log)
  2821. or mtr_error("Could not open file '$error_log' for reading: $!");
  2822. my @lines;
  2823. while ( my $line = <$Ferr> )
  2824. {
  2825. if ( $line =~ /^CURRENT_TEST:/ )
  2826. {
  2827. # Throw away lines from previous tests
  2828. @lines = ();
  2829. }
  2830. push(@lines, $line);
  2831. }
  2832. $Ferr = undef; # Close error log file
  2833. # mysql_client_test.test sends a COM_DEBUG packet to the server
  2834. # to provoke a SAFEMALLOC leak report, ignore any warnings
  2835. # between "Begin/end safemalloc memory dump"
  2836. if ( grep(/Begin safemalloc memory dump:/, @lines) > 0)
  2837. {
  2838. my $discard_lines= 1;
  2839. foreach my $line ( @lines )
  2840. {
  2841. if ($line =~ /Begin safemalloc memory dump:/){
  2842. $discard_lines = 1;
  2843. } elsif ($line =~ /End safemalloc memory dump./){
  2844. $discard_lines = 0;
  2845. }
  2846. if ($discard_lines){
  2847. $line = "ignored";
  2848. }
  2849. }
  2850. }
  2851. # Write all suspicious lines to $error_log.warnings file
  2852. my $warning_log = "$error_log.warnings";
  2853. my $Fwarn = IO::File->new($warning_log, "w")
  2854. or die("Could not open file '$warning_log' for writing: $!");
  2855. print $Fwarn "Suspicious lines from $error_log\n";
  2856. my @patterns =
  2857. (
  2858. # The patterns for detection of [Warning] and [ERROR]
  2859. # in the server log files have been faulty for a longer period
  2860. # and correcting them shows a few additional harmless warnings.
  2861. # Thus those patterns are temporarily removed from the list
  2862. # of patterns. For more info see BUG#42408
  2863. # qr/^Warning:|mysqld: Warning|\[Warning\]/,
  2864. # qr/^Error:|\[ERROR\]/,
  2865. qr/^Warning:|mysqld: Warning/,
  2866. qr/^Error:/,
  2867. qr/^==.* at 0x/,
  2868. qr/InnoDB: Warning|InnoDB: Error/,
  2869. qr/^safe_mutex:|allocated at line/,
  2870. qr/missing DBUG_RETURN/,
  2871. qr/Attempting backtrace/,
  2872. qr/Assertion .* failed/,
  2873. );
  2874. foreach my $line ( @lines )
  2875. {
  2876. foreach my $pat ( @patterns )
  2877. {
  2878. if ( $line =~ /$pat/ )
  2879. {
  2880. print $Fwarn $line;
  2881. last;
  2882. }
  2883. }
  2884. }
  2885. $Fwarn = undef; # Close file
  2886. }
  2887. # Run include/check-warnings.test
  2888. #
  2889. # RETURN VALUE
  2890. # 0 OK
  2891. # 1 Check failed
  2892. #
  2893. sub start_check_warnings ($$) {
  2894. my $tinfo= shift;
  2895. my $mysqld= shift;
  2896. my $name= "warnings-".$mysqld->name();
  2897. extract_warning_lines($mysqld->value('log-error'));
  2898. my $args;
  2899. mtr_init_args(\$args);
  2900. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  2901. mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld'));
  2902. mtr_add_arg($args, "--skip-safemalloc");
  2903. mtr_add_arg($args, "--test-file=%s", "include/check-warnings.test");
  2904. mtr_add_arg($args, "--verbose");
  2905. if ( $opt_embedded_server )
  2906. {
  2907. # Get the args needed for the embedded server
  2908. # and append them to args prefixed
  2909. # with --sever-arg=
  2910. my $mysqld= $config->group('embedded')
  2911. or mtr_error("Could not get [embedded] section");
  2912. my $mysqld_args;
  2913. mtr_init_args(\$mysqld_args);
  2914. my $extra_opts= get_extra_opts($mysqld, $tinfo);
  2915. mysqld_arguments($mysqld_args, $mysqld, $extra_opts);
  2916. mtr_add_arg($args, "--server-arg=%s", $_) for @$mysqld_args;
  2917. }
  2918. my $errfile= "$opt_vardir/tmp/$name.err";
  2919. my $proc= My::SafeProcess->new
  2920. (
  2921. name => $name,
  2922. path => $exe_mysqltest,
  2923. error => $errfile,
  2924. output => $errfile,
  2925. args => \$args,
  2926. user_data => $errfile,
  2927. verbose => $opt_verbose,
  2928. );
  2929. mtr_verbose("Started $proc");
  2930. return $proc;
  2931. }
  2932. #
  2933. # Loop through our list of processes and check the error log
  2934. # for unexepcted errors and warnings
  2935. #
  2936. sub check_warnings ($) {
  2937. my ($tinfo)= @_;
  2938. my $res= 0;
  2939. my $tname= $tinfo->{name};
  2940. # Clear previous warnings
  2941. delete($tinfo->{warnings});
  2942. # Start the mysqltest processes in parallel to save time
  2943. # also makes it possible to wait for any process to exit during the check
  2944. my %started;
  2945. foreach my $mysqld ( mysqlds() )
  2946. {
  2947. if ( defined $mysqld->{'proc'} )
  2948. {
  2949. my $proc= start_check_warnings($tinfo, $mysqld);
  2950. $started{$proc->pid()}= $proc;
  2951. }
  2952. }
  2953. # Return immediately if no check proceess was started
  2954. return 0 unless ( keys %started );
  2955. my $timeout_proc= My::SafeProcess->timer(check_timeout());
  2956. while (1){
  2957. my $result= 0;
  2958. my $proc= My::SafeProcess->wait_any();
  2959. mtr_report("Got $proc");
  2960. if ( delete $started{$proc->pid()} ) {
  2961. # One check warning process returned
  2962. my $res= $proc->exit_status();
  2963. my $err_file= $proc->user_data();
  2964. if ( $res == 0 or $res == 62 ){
  2965. if ( $res == 0 ) {
  2966. # Check completed with problem
  2967. my $report= mtr_grab_file($err_file);
  2968. # Log to var/log/warnings file
  2969. mtr_tofile("$opt_vardir/log/warnings",
  2970. $tname."\n".$report);
  2971. $tinfo->{'warnings'}.= $report;
  2972. $result= 1;
  2973. }
  2974. if ( $res == 62 ) {
  2975. # Test case was ok and called "skip"
  2976. # Remove the .err file the check generated
  2977. unlink($err_file);
  2978. }
  2979. if ( keys(%started) == 0){
  2980. # All checks completed
  2981. $timeout_proc->kill();
  2982. return $result;
  2983. }
  2984. # Wait for next process to exit
  2985. next;
  2986. }
  2987. else
  2988. {
  2989. my $report= mtr_grab_file($err_file);
  2990. $tinfo->{comment}.=
  2991. "Could not execute 'check-warnings' for ".
  2992. "testcase '$tname' (res: $res):\n";
  2993. $tinfo->{comment}.= $report;
  2994. $result= 2;
  2995. }
  2996. }
  2997. elsif ( $proc eq $timeout_proc ) {
  2998. $tinfo->{comment}.= "Timeout $timeout_proc for ".
  2999. "'check warnings' expired after ".check_timeout().
  3000. " seconds";
  3001. $result= 4;
  3002. }
  3003. else {
  3004. # Unknown process returned, most likley a crash, abort everything
  3005. $tinfo->{comment}=
  3006. "The server $proc crashed while running 'check warnings'";
  3007. $result= 3;
  3008. }
  3009. # Kill any check processes still running
  3010. map($_->kill(), values(%started));
  3011. $timeout_proc->kill();
  3012. return $result;
  3013. }
  3014. mtr_error("INTERNAL_ERROR: check_warnings");
  3015. }
  3016. #
  3017. # Loop through our list of processes and look for and entry
  3018. # with the provided pid, if found check for the file indicating
  3019. # expected crash and restart it.
  3020. #
  3021. sub check_expected_crash_and_restart {
  3022. my ($proc)= @_;
  3023. foreach my $mysqld ( mysqlds() )
  3024. {
  3025. next unless ( $mysqld->{proc} eq $proc );
  3026. # Check if crash expected by looking at the .expect file
  3027. # in var/tmp
  3028. my $expect_file= "$opt_vardir/tmp/".$mysqld->name().".expect";
  3029. if ( -f $expect_file )
  3030. {
  3031. mtr_verbose("Crash was expected, file '$expect_file' exists");
  3032. while (1){
  3033. # If last line in expect file starts with "wait"
  3034. # sleep a little and try again, thus allowing the
  3035. # test script to control when the server should start
  3036. # up again
  3037. my $last_line= mtr_lastlinesfromfile($expect_file, 1);
  3038. if ($last_line =~ /^wait/ )
  3039. {
  3040. mtr_verbose("Test says wait before restart");
  3041. mtr_milli_sleep(100);
  3042. next;
  3043. }
  3044. unlink($expect_file);
  3045. # Start server with same settings as last time
  3046. mysqld_start($mysqld, $mysqld->{'started_opts'});
  3047. last;
  3048. }
  3049. }
  3050. return 1;
  3051. }
  3052. # Not an expected crash
  3053. return 0;
  3054. }
  3055. # Remove all files and subdirectories of a directory
  3056. sub clean_dir {
  3057. my ($dir)= @_;
  3058. mtr_verbose("clean_dir: $dir");
  3059. finddepth(
  3060. { no_chdir => 1,
  3061. wanted => sub {
  3062. if (-d $_){
  3063. # A dir
  3064. if ($_ eq $dir){
  3065. # The dir to clean
  3066. return;
  3067. } else {
  3068. mtr_verbose("rmdir: '$_'");
  3069. rmdir($_) or mtr_warning("rmdir($_) failed: $!");
  3070. }
  3071. } else {
  3072. # Hopefully a file
  3073. mtr_verbose("unlink: '$_'");
  3074. unlink($_) or mtr_warning("unlink($_) failed: $!");
  3075. }
  3076. }
  3077. },
  3078. $dir);
  3079. }
  3080. sub clean_datadir {
  3081. mtr_verbose("Cleaning datadirs...");
  3082. if (started(all_servers()) != 0){
  3083. mtr_error("Trying to clean datadir before all servers stopped");
  3084. }
  3085. foreach my $cluster ( clusters() )
  3086. {
  3087. my $cluster_dir= "$opt_vardir/".$cluster->{name};
  3088. mtr_verbose(" - removing '$cluster_dir'");
  3089. rmtree($cluster_dir);
  3090. }
  3091. foreach my $mysqld ( mysqlds() )
  3092. {
  3093. my $mysqld_dir= dirname($mysqld->value('datadir'));
  3094. if (-d $mysqld_dir ) {
  3095. mtr_verbose(" - removing '$mysqld_dir'");
  3096. rmtree($mysqld_dir);
  3097. }
  3098. }
  3099. # Remove all files in tmp and var/tmp
  3100. clean_dir("$opt_vardir/tmp");
  3101. if ($opt_tmpdir ne "$opt_vardir/tmp"){
  3102. clean_dir($opt_tmpdir);
  3103. }
  3104. }
  3105. #
  3106. # Save datadir before it's removed
  3107. #
  3108. sub save_datadir_after_failure($$) {
  3109. my ($dir, $savedir)= @_;
  3110. mtr_report(" - saving '$dir'");
  3111. my $dir_name= basename($dir);
  3112. rename("$dir", "$savedir/$dir_name");
  3113. }
  3114. sub remove_ndbfs_from_ndbd_datadir {
  3115. my ($ndbd_datadir)= @_;
  3116. # Remove the ndb_*_fs directory from ndbd.X/ dir
  3117. foreach my $ndbfs_dir ( glob("$ndbd_datadir/ndb_*_fs") )
  3118. {
  3119. next unless -d $ndbfs_dir; # Skip if not a directory
  3120. rmtree($ndbfs_dir);
  3121. }
  3122. }
  3123. sub after_failure ($) {
  3124. my ($tinfo)= @_;
  3125. mtr_report("Saving datadirs...");
  3126. my $save_dir= "$opt_vardir/log/";
  3127. $save_dir.= $tinfo->{name};
  3128. # Add combination name if any
  3129. $save_dir.= "-$tinfo->{combination}"
  3130. if defined $tinfo->{combination};
  3131. # Save savedir path for server
  3132. $tinfo->{savedir}= $save_dir;
  3133. mkpath($save_dir) if ! -d $save_dir;
  3134. # Save the used my.cnf file
  3135. copy($path_config_file, $save_dir);
  3136. # Copy the tmp dir
  3137. copytree("$opt_vardir/tmp/", "$save_dir/tmp/");
  3138. if ( clusters() ) {
  3139. foreach my $cluster ( clusters() ) {
  3140. my $cluster_dir= "$opt_vardir/".$cluster->{name};
  3141. # Remove the fileystem of each ndbd
  3142. foreach my $ndbd ( in_cluster($cluster, ndbds()) )
  3143. {
  3144. my $ndbd_datadir= $ndbd->value("DataDir");
  3145. remove_ndbfs_from_ndbd_datadir($ndbd_datadir);
  3146. }
  3147. save_datadir_after_failure($cluster_dir, $save_dir);
  3148. }
  3149. }
  3150. else {
  3151. foreach my $mysqld ( mysqlds() ) {
  3152. my $data_dir= $mysqld->value('datadir');
  3153. save_datadir_after_failure(dirname($data_dir), $save_dir);
  3154. }
  3155. }
  3156. }
  3157. sub report_failure_and_restart ($) {
  3158. my $tinfo= shift;
  3159. stop_all_servers();
  3160. $tinfo->{'result'}= 'MTR_RES_FAILED';
  3161. my $test_failures= $tinfo->{'failures'} || 0;
  3162. $tinfo->{'failures'}= $test_failures + 1;
  3163. if ( $tinfo->{comment} )
  3164. {
  3165. # The test failure has been detected by mysql-test-run.pl
  3166. # when starting the servers or due to other error, the reason for
  3167. # failing the test is saved in "comment"
  3168. ;
  3169. }
  3170. if ( !defined $tinfo->{logfile} )
  3171. {
  3172. my $logfile= $path_current_testlog;
  3173. if ( defined $logfile )
  3174. {
  3175. if ( -f $logfile )
  3176. {
  3177. # Test failure was detected by test tool and its report
  3178. # about what failed has been saved to file. Save the report
  3179. # in tinfo
  3180. $tinfo->{logfile}= mtr_fromfile($logfile);
  3181. }
  3182. else
  3183. {
  3184. # The test tool report didn't exist, display an
  3185. # error message
  3186. $tinfo->{logfile}= "Could not open test tool report '$logfile'";
  3187. }
  3188. }
  3189. }
  3190. after_failure($tinfo);
  3191. mtr_report_test($tinfo);
  3192. }
  3193. sub run_sh_script {
  3194. my ($script)= @_;
  3195. return 0 unless defined $script;
  3196. mtr_verbose("Running '$script'");
  3197. my $ret= system("/bin/sh $script") >> 8;
  3198. return $ret;
  3199. }
  3200. sub mysqld_stop {
  3201. my $mysqld= shift or die "usage: mysqld_stop(<mysqld>)";
  3202. my $args;
  3203. mtr_init_args(\$args);
  3204. mtr_add_arg($args, "--no-defaults");
  3205. mtr_add_arg($args, "--user=%s", $opt_user);
  3206. mtr_add_arg($args, "--password=");
  3207. mtr_add_arg($args, "--port=%d", $mysqld->value('port'));
  3208. mtr_add_arg($args, "--host=%s", $mysqld->value('#host'));
  3209. mtr_add_arg($args, "--connect_timeout=20");
  3210. mtr_add_arg($args, "--protocol=tcp");
  3211. mtr_add_arg($args, "shutdown");
  3212. My::SafeProcess->run
  3213. (
  3214. name => "mysqladmin shutdown ".$mysqld->name(),
  3215. path => $exe_mysqladmin,
  3216. args => \$args,
  3217. error => "/dev/null",
  3218. );
  3219. }
  3220. sub mysqld_arguments ($$$) {
  3221. my $args= shift;
  3222. my $mysqld= shift;
  3223. my $extra_opts= shift;
  3224. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  3225. # When mysqld is run by a root user(euid is 0), it will fail
  3226. # to start unless we specify what user to run as, see BUG#30630
  3227. my $euid= $>;
  3228. if (!IS_WINDOWS and $euid == 0 and
  3229. (grep(/^--user/, @$extra_opts)) == 0) {
  3230. mtr_add_arg($args, "--user=root");
  3231. }
  3232. if ( $opt_valgrind_mysqld )
  3233. {
  3234. mtr_add_arg($args, "--skip-safemalloc");
  3235. if ( $mysql_version_id < 50100 )
  3236. {
  3237. mtr_add_arg($args, "--skip-bdb");
  3238. }
  3239. }
  3240. if ( $mysql_version_id >= 50106 )
  3241. {
  3242. # Turn on logging to both tables and file
  3243. mtr_add_arg($args, "--log-output=table,file");
  3244. }
  3245. # Check if "extra_opt" contains skip-log-bin
  3246. my $skip_binlog= grep(/^(--|--loose-)skip-log-bin/, @$extra_opts);
  3247. # Indicate to mysqld it will be debugged in debugger
  3248. if ( $glob_debugger )
  3249. {
  3250. mtr_add_arg($args, "--gdb");
  3251. }
  3252. my $found_skip_core= 0;
  3253. foreach my $arg ( @$extra_opts )
  3254. {
  3255. # Allow --skip-core-file to be set in <testname>-[master|slave].opt file
  3256. if ($arg eq "--skip-core-file")
  3257. {
  3258. $found_skip_core= 1;
  3259. }
  3260. elsif ($skip_binlog and mtr_match_prefix($arg, "--binlog-format"))
  3261. {
  3262. ; # Dont add --binlog-format when running without binlog
  3263. }
  3264. elsif ($arg eq "--loose-skip-log-bin" and
  3265. $mysqld->option("log-slave-updates"))
  3266. {
  3267. ; # Dont add --skip-log-bin when mysqld have --log-slave-updates in config
  3268. }
  3269. else
  3270. {
  3271. mtr_add_arg($args, "%s", $arg);
  3272. }
  3273. }
  3274. if ( !$found_skip_core )
  3275. {
  3276. mtr_add_arg($args, "%s", "--core-file");
  3277. }
  3278. return $args;
  3279. }
  3280. sub mysqld_start ($$) {
  3281. my $mysqld= shift;
  3282. my $extra_opts= shift;
  3283. mtr_verbose(My::Options::toStr("mysqld_start", @$extra_opts));
  3284. my $exe= find_mysqld($mysqld->value('basedir'));
  3285. my $wait_for_pid_file= 1;
  3286. mtr_error("Internal error: mysqld should never be started for embedded")
  3287. if $opt_embedded_server;
  3288. my $args;
  3289. mtr_init_args(\$args);
  3290. if ( $opt_valgrind_mysqld )
  3291. {
  3292. valgrind_arguments($args, \$exe);
  3293. }
  3294. mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld'));
  3295. mysqld_arguments($args,$mysqld,$extra_opts);
  3296. if ( $opt_debug )
  3297. {
  3298. mtr_add_arg($args, "--debug=d:t:i:A,%s/log/%s.trace",
  3299. $path_vardir_trace, $mysqld->name());
  3300. }
  3301. if ( $opt_gdb || $opt_manual_gdb )
  3302. {
  3303. gdb_arguments(\$args, \$exe, $mysqld->name());
  3304. }
  3305. elsif ( $opt_ddd || $opt_manual_ddd )
  3306. {
  3307. ddd_arguments(\$args, \$exe, $mysqld->name());
  3308. }
  3309. elsif ( $opt_debugger )
  3310. {
  3311. debugger_arguments(\$args, \$exe, $mysqld->name());
  3312. }
  3313. elsif ( $opt_manual_debug )
  3314. {
  3315. print "\nStart " .$mysqld->name()." in your debugger\n" .
  3316. "dir: $glob_mysql_test_dir\n" .
  3317. "exe: $exe\n" .
  3318. "args: " . join(" ", @$args) . "\n\n" .
  3319. "Waiting ....\n";
  3320. # Indicate the exe should not be started
  3321. $exe= undef;
  3322. }
  3323. else
  3324. {
  3325. # Default to not wait until pid file has been created
  3326. $wait_for_pid_file= 0;
  3327. }
  3328. # Remove the old pidfile if any
  3329. unlink($mysqld->value('pid-file'));
  3330. my $output= $mysqld->value('log-error');
  3331. if ( $opt_valgrind and $opt_debug )
  3332. {
  3333. # When both --valgrind and --debug is selected, send
  3334. # all output to the trace file, making it possible to
  3335. # see the exact location where valgrind complains
  3336. $output= "$opt_vardir/log/".$mysqld->name().".trace";
  3337. }
  3338. if ( defined $exe )
  3339. {
  3340. $mysqld->{'proc'}= My::SafeProcess->new
  3341. (
  3342. name => $mysqld->name(),
  3343. path => $exe,
  3344. args => \$args,
  3345. output => $output,
  3346. error => $output,
  3347. append => 1,
  3348. verbose => $opt_verbose,
  3349. host => undef,
  3350. shutdown => sub { mysqld_stop($mysqld) },
  3351. );
  3352. mtr_verbose("Started $mysqld->{proc}");
  3353. }
  3354. if ( $wait_for_pid_file &&
  3355. !sleep_until_file_created($mysqld->value('pid-file'),
  3356. $opt_start_timeout,
  3357. $mysqld->{'proc'}))
  3358. {
  3359. mtr_error("Failed to start mysqld $mysqld->name()");
  3360. }
  3361. # Remember options used when starting
  3362. $mysqld->{'started_opts'}= $extra_opts;
  3363. return;
  3364. }
  3365. sub stop_all_servers () {
  3366. mtr_verbose("Stopping all servers...");
  3367. # Kill all started servers
  3368. My::SafeProcess::shutdown(0, # shutdown timeout 0 => kill
  3369. started(all_servers()));
  3370. # Remove pidfiles
  3371. foreach my $server ( all_servers() )
  3372. {
  3373. my $pid_file= $server->if_exist('pid-file');
  3374. unlink($pid_file) if defined $pid_file;
  3375. }
  3376. # Mark servers as stopped
  3377. map($_->{proc}= undef, all_servers());
  3378. }
  3379. # Find out if server should be restarted for this test
  3380. sub server_need_restart {
  3381. my ($tinfo, $server)= @_;
  3382. if ( using_extern() )
  3383. {
  3384. mtr_verbose_restart($server, "no restart for --extern server");
  3385. return 0;
  3386. }
  3387. if ( $opt_embedded_server )
  3388. {
  3389. mtr_verbose_restart($server, "no start or restart for embedded server");
  3390. return 0;
  3391. }
  3392. if ( $tinfo->{'force_restart'} ) {
  3393. mtr_verbose_restart($server, "forced in .opt file");
  3394. return 1;
  3395. }
  3396. if ( $tinfo->{template_path} ne $current_config_name)
  3397. {
  3398. mtr_verbose_restart($server, "using different config file");
  3399. return 1;
  3400. }
  3401. if ( $tinfo->{'master_sh'} || $tinfo->{'slave_sh'} )
  3402. {
  3403. mtr_verbose_restart($server, "sh script to run");
  3404. return 1;
  3405. }
  3406. if ( ! started($server) )
  3407. {
  3408. mtr_verbose_restart($server, "not started");
  3409. return 1;
  3410. }
  3411. my $started_tinfo= $server->{'started_tinfo'};
  3412. if ( defined $started_tinfo )
  3413. {
  3414. # Check if timezone of test that server was started
  3415. # with differs from timezone of next test
  3416. if ( timezone($started_tinfo) ne timezone($tinfo) )
  3417. {
  3418. mtr_verbose_restart($server, "different timezone");
  3419. return 1;
  3420. }
  3421. }
  3422. # Temporary re-enable the "always restart slave" hack
  3423. # this should be removed asap, but will require that each rpl
  3424. # testcase cleanup better after itself - ie. stop and reset
  3425. # replication
  3426. # Use the "#!use-slave-opt" marker to detect that this is a "slave"
  3427. # server
  3428. if ( $server->option("#!use-slave-opt") ){
  3429. mtr_verbose_restart($server, "Always restart slave(s)");
  3430. return 1;
  3431. }
  3432. my $is_mysqld= grep ($server eq $_, mysqlds());
  3433. if ($is_mysqld)
  3434. {
  3435. # Check that running process was started with same options
  3436. # as the current test requires
  3437. my $extra_opts= get_extra_opts($server, $tinfo);
  3438. my $started_opts= $server->{'started_opts'};
  3439. if (!My::Options::same($started_opts, $extra_opts) )
  3440. {
  3441. my $use_dynamic_option_switch= 0;
  3442. if (!$use_dynamic_option_switch)
  3443. {
  3444. mtr_verbose_restart($server, "running with different options '" .
  3445. join(" ", @{$extra_opts}) . "' != '" .
  3446. join(" ", @{$started_opts}) . "'" );
  3447. return 1;
  3448. }
  3449. mtr_verbose(My::Options::toStr("started_opts", @$started_opts));
  3450. mtr_verbose(My::Options::toStr("extra_opts", @$extra_opts));
  3451. # Get diff and check if dynamic switch is possible
  3452. my @diff_opts= My::Options::diff($started_opts, $extra_opts);
  3453. mtr_verbose(My::Options::toStr("diff_opts", @diff_opts));
  3454. my $query= My::Options::toSQL(@diff_opts);
  3455. mtr_verbose("Attempting dynamic switch '$query'");
  3456. if (run_query($tinfo, $server, $query)){
  3457. mtr_verbose("Restart: running with different options '" .
  3458. join(" ", @{$extra_opts}) . "' != '" .
  3459. join(" ", @{$started_opts}) . "'" );
  3460. return 1;
  3461. }
  3462. # Remember the dynamically set options
  3463. $server->{'started_opts'}= $extra_opts;
  3464. }
  3465. }
  3466. # Default, no restart
  3467. return 0;
  3468. }
  3469. sub servers_need_restart($) {
  3470. my ($tinfo)= @_;
  3471. return grep { server_need_restart($tinfo, $_); } all_servers();
  3472. }
  3473. #
  3474. # Return list of specific servers
  3475. # - there is no servers in an empty config
  3476. #
  3477. sub _like { return $config ? $config->like($_[0]) : (); }
  3478. sub mysqlds { return _like('mysqld.'); }
  3479. sub ndbds { return _like('cluster_config.ndbd.');}
  3480. sub ndb_mgmds { return _like('cluster_config.ndb_mgmd.'); }
  3481. sub clusters { return _like('mysql_cluster.'); }
  3482. sub all_servers { return ( mysqlds(), ndb_mgmds(), ndbds() ); }
  3483. #
  3484. # Filter a list of servers and return only those that are part
  3485. # of the specified cluster
  3486. #
  3487. sub in_cluster {
  3488. my ($cluster)= shift;
  3489. # Return only processes for a specific cluster
  3490. return grep { $_->suffix() eq $cluster->suffix() } @_;
  3491. }
  3492. #
  3493. # Filter a list of servers and return the SafeProcess
  3494. # for only those that are started or stopped
  3495. #
  3496. sub started { return grep(defined $_, map($_->{proc}, @_)); }
  3497. sub stopped { return grep(!defined $_, map($_->{proc}, @_)); }
  3498. sub envsubst {
  3499. my $string= shift;
  3500. if ( ! defined $ENV{$string} )
  3501. {
  3502. mtr_error(".opt file references '$string' which is not set");
  3503. }
  3504. return $ENV{$string};
  3505. }
  3506. sub get_extra_opts {
  3507. my ($mysqld, $tinfo)= @_;
  3508. my $opts=
  3509. $mysqld->option("#!use-slave-opt") ?
  3510. $tinfo->{slave_opt} : $tinfo->{master_opt};
  3511. # Expand environment variables
  3512. foreach my $opt ( @$opts )
  3513. {
  3514. $opt =~ s/\$\{(\w+)\}/envsubst($1)/ge;
  3515. $opt =~ s/\$(\w+)/envsubst($1)/ge;
  3516. }
  3517. return $opts;
  3518. }
  3519. sub stop_servers($$) {
  3520. my ($tinfo, @servers)= @_;
  3521. # Remember if we restarted for this test case (count restarts)
  3522. $tinfo->{'restarted'}= 1;
  3523. if ( join('|', @servers) eq join('|', all_servers()) )
  3524. {
  3525. # All servers are going down, use some kind of order to
  3526. # avoid too many warnings in the log files
  3527. mtr_report("Restarting all servers");
  3528. # mysqld processes
  3529. My::SafeProcess::shutdown( $opt_shutdown_timeout, started(mysqlds()) );
  3530. # cluster processes
  3531. My::SafeProcess::shutdown( $opt_shutdown_timeout,
  3532. started(ndbds(), ndb_mgmds()) );
  3533. }
  3534. else
  3535. {
  3536. mtr_report("Restarting ", started(@servers));
  3537. # Stop only some servers
  3538. My::SafeProcess::shutdown( $opt_shutdown_timeout,
  3539. started(@servers) );
  3540. }
  3541. foreach my $server (@servers)
  3542. {
  3543. # Mark server as stopped
  3544. $server->{proc}= undef;
  3545. # Forget history
  3546. delete $server->{'started_tinfo'};
  3547. delete $server->{'started_opts'};
  3548. delete $server->{'started_cnf'};
  3549. }
  3550. }
  3551. #
  3552. # start_servers
  3553. #
  3554. # Start servers not already started
  3555. #
  3556. # RETURN
  3557. # 0 OK
  3558. # 1 Start failed
  3559. #
  3560. sub start_servers($) {
  3561. my ($tinfo)= @_;
  3562. # Start clusters
  3563. foreach my $cluster ( clusters() )
  3564. {
  3565. ndbcluster_start($cluster);
  3566. }
  3567. # Start mysqlds
  3568. foreach my $mysqld ( mysqlds() )
  3569. {
  3570. if ( $mysqld->{proc} )
  3571. {
  3572. # Already started
  3573. # Write start of testcase to log file
  3574. mark_log($mysqld->value('log-error'), $tinfo);
  3575. next;
  3576. }
  3577. my $datadir= $mysqld->value('datadir');
  3578. if ($opt_start_dirty)
  3579. {
  3580. # Don't delete anything if starting dirty
  3581. ;
  3582. }
  3583. else
  3584. {
  3585. my @options= ('log-bin', 'relay-log');
  3586. foreach my $option_name ( @options ) {
  3587. next unless $mysqld->option($option_name);
  3588. my $file_name= $mysqld->value($option_name);
  3589. next unless
  3590. defined $file_name and
  3591. -e $file_name;
  3592. mtr_debug(" -removing '$file_name'");
  3593. unlink($file_name) or die ("unable to remove file '$file_name'");
  3594. }
  3595. if (-d $datadir ) {
  3596. mtr_verbose(" - removing '$datadir'");
  3597. rmtree($datadir);
  3598. }
  3599. }
  3600. my $mysqld_basedir= $mysqld->value('basedir');
  3601. if ( $basedir eq $mysqld_basedir )
  3602. {
  3603. # Copy datadir from installed system db
  3604. for my $path ( "$opt_vardir", "$opt_vardir/..") {
  3605. my $install_db= "$path/install.db";
  3606. copytree($install_db, $datadir)
  3607. if -d $install_db;
  3608. }
  3609. mtr_error("Failed to copy system db to '$datadir'")
  3610. unless -d $datadir;
  3611. }
  3612. else
  3613. {
  3614. mysql_install_db($mysqld); # For versional testing
  3615. mtr_error("Failed to install system db to '$datadir'")
  3616. unless -d $datadir;
  3617. }
  3618. # Create the servers tmpdir
  3619. my $tmpdir= $mysqld->value('tmpdir');
  3620. mkpath($tmpdir) unless -d $tmpdir;
  3621. # Write start of testcase to log file
  3622. mark_log($mysqld->value('log-error'), $tinfo);
  3623. # Run <tname>-master.sh
  3624. if ($mysqld->option('#!run-master-sh') and
  3625. run_sh_script($tinfo->{master_sh}) )
  3626. {
  3627. $tinfo->{'comment'}= "Failed to execute '$tinfo->{master_sh}'";
  3628. return 1;
  3629. }
  3630. # Run <tname>-slave.sh
  3631. if ($mysqld->option('#!run-slave-sh') and
  3632. run_sh_script($tinfo->{slave_sh}))
  3633. {
  3634. $tinfo->{'comment'}= "Failed to execute '$tinfo->{slave_sh}'";
  3635. return 1;
  3636. }
  3637. if (!$opt_embedded_server)
  3638. {
  3639. my $extra_opts= get_extra_opts($mysqld, $tinfo);
  3640. mysqld_start($mysqld,$extra_opts);
  3641. # Save this test case information, so next can examine it
  3642. $mysqld->{'started_tinfo'}= $tinfo;
  3643. }
  3644. }
  3645. # Wait for clusters to start
  3646. foreach my $cluster ( clusters() )
  3647. {
  3648. if (ndbcluster_wait_started($cluster, ""))
  3649. {
  3650. # failed to start
  3651. $tinfo->{'comment'}= "Start of '".$cluster->name()."' cluster failed";
  3652. return 1;
  3653. }
  3654. }
  3655. # Wait for mysqlds to start
  3656. foreach my $mysqld ( mysqlds() )
  3657. {
  3658. next if !started($mysqld);
  3659. if (sleep_until_file_created($mysqld->value('pid-file'),
  3660. $opt_start_timeout,
  3661. $mysqld->{'proc'}) == 0) {
  3662. $tinfo->{comment}=
  3663. "Failed to start ".$mysqld->name();
  3664. my $logfile= $mysqld->value('log-error');
  3665. if ( defined $logfile and -f $logfile )
  3666. {
  3667. $tinfo->{logfile}= mtr_fromfile($logfile);
  3668. }
  3669. else
  3670. {
  3671. $tinfo->{logfile}= "Could not open server logfile: '$logfile'";
  3672. }
  3673. return 1;
  3674. }
  3675. }
  3676. return 0;
  3677. }
  3678. #
  3679. # Run include/check-testcase.test
  3680. # Before a testcase, run in record mode and save result file to var/tmp
  3681. # After testcase, run and compare with the recorded file, they should be equal!
  3682. #
  3683. # RETURN VALUE
  3684. # The newly started process
  3685. #
  3686. sub start_check_testcase ($$$) {
  3687. my $tinfo= shift;
  3688. my $mode= shift;
  3689. my $mysqld= shift;
  3690. my $name= "check-".$mysqld->name();
  3691. # Replace dots in name with underscore to avoid that mysqltest
  3692. # misinterpret's what the filename extension is :(
  3693. $name=~ s/\./_/g;
  3694. my $args;
  3695. mtr_init_args(\$args);
  3696. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  3697. mtr_add_arg($args, "--defaults-group-suffix=%s", $mysqld->after('mysqld'));
  3698. mtr_add_arg($args, "--skip-safemalloc");
  3699. mtr_add_arg($args, "--result-file=%s", "$opt_vardir/tmp/$name.result");
  3700. mtr_add_arg($args, "--test-file=%s", "include/check-testcase.test");
  3701. mtr_add_arg($args, "--verbose");
  3702. if ( $mode eq "before" )
  3703. {
  3704. mtr_add_arg($args, "--record");
  3705. }
  3706. my $errfile= "$opt_vardir/tmp/$name.err";
  3707. my $proc= My::SafeProcess->new
  3708. (
  3709. name => $name,
  3710. path => $exe_mysqltest,
  3711. error => $errfile,
  3712. output => $errfile,
  3713. args => \$args,
  3714. user_data => $errfile,
  3715. verbose => $opt_verbose,
  3716. );
  3717. mtr_report("Started $proc");
  3718. return $proc;
  3719. }
  3720. sub run_mysqltest ($) {
  3721. my $proc= start_mysqltest(@_);
  3722. $proc->wait();
  3723. }
  3724. sub start_mysqltest ($) {
  3725. my ($tinfo)= @_;
  3726. my $exe= $exe_mysqltest;
  3727. my $args;
  3728. mtr_init_args(\$args);
  3729. mtr_add_arg($args, "--defaults-file=%s", $path_config_file);
  3730. mtr_add_arg($args, "--silent");
  3731. mtr_add_arg($args, "--skip-safemalloc");
  3732. mtr_add_arg($args, "--tmpdir=%s", $opt_tmpdir);
  3733. mtr_add_arg($args, "--character-sets-dir=%s", $path_charsetsdir);
  3734. mtr_add_arg($args, "--logdir=%s/log", $opt_vardir);
  3735. # Log line number and time for each line in .test file
  3736. mtr_add_arg($args, "--mark-progress")
  3737. if $opt_mark_progress;
  3738. mtr_add_arg($args, "--database=test");
  3739. if ( $opt_ps_protocol )
  3740. {
  3741. mtr_add_arg($args, "--ps-protocol");
  3742. }
  3743. if ( $opt_sp_protocol )
  3744. {
  3745. mtr_add_arg($args, "--sp-protocol");
  3746. }
  3747. if ( $opt_view_protocol )
  3748. {
  3749. mtr_add_arg($args, "--view-protocol");
  3750. }
  3751. if ( $opt_cursor_protocol )
  3752. {
  3753. mtr_add_arg($args, "--cursor-protocol");
  3754. }
  3755. if ( $opt_strace_client )
  3756. {
  3757. $exe= $opt_strace_client || "strace";
  3758. mtr_add_arg($args, "-o");
  3759. mtr_add_arg($args, "%s/log/mysqltest.strace", $opt_vardir);
  3760. mtr_add_arg($args, "$exe_mysqltest");
  3761. }
  3762. mtr_add_arg($args, "--timer-file=%s/log/timer", $opt_vardir);
  3763. if ( $opt_compress )
  3764. {
  3765. mtr_add_arg($args, "--compress");
  3766. }
  3767. if ( $opt_sleep )
  3768. {
  3769. mtr_add_arg($args, "--sleep=%d", $opt_sleep);
  3770. }
  3771. if ( $opt_ssl )
  3772. {
  3773. # Turn on SSL for _all_ test cases if option --ssl was used
  3774. mtr_add_arg($args, "--ssl");
  3775. }
  3776. if ( $opt_embedded_server )
  3777. {
  3778. # Get the args needed for the embedded server
  3779. # and append them to args prefixed
  3780. # with --sever-arg=
  3781. my $mysqld= $config->group('embedded')
  3782. or mtr_error("Could not get [embedded] section");
  3783. my $mysqld_args;
  3784. mtr_init_args(\$mysqld_args);
  3785. my $extra_opts= get_extra_opts($mysqld, $tinfo);
  3786. mysqld_arguments($mysqld_args, $mysqld, $extra_opts);
  3787. mtr_add_arg($args, "--server-arg=%s", $_) for @$mysqld_args;
  3788. if (IS_WINDOWS)
  3789. {
  3790. # Trick the server to send output to stderr, with --console
  3791. mtr_add_arg($args, "--server-arg=--console");
  3792. }
  3793. }
  3794. # ----------------------------------------------------------------------
  3795. # export MYSQL_TEST variable containing <path>/mysqltest <args>
  3796. # ----------------------------------------------------------------------
  3797. $ENV{'MYSQL_TEST'}= mtr_args2str($exe_mysqltest, @$args);
  3798. # ----------------------------------------------------------------------
  3799. # Add arguments that should not go into the MYSQL_TEST env var
  3800. # ----------------------------------------------------------------------
  3801. if ( $opt_valgrind_mysqltest )
  3802. {
  3803. # Prefix the Valgrind options to the argument list.
  3804. # We do this here, since we do not want to Valgrind the nested invocations
  3805. # of mysqltest; that would mess up the stderr output causing test failure.
  3806. my @args_saved = @$args;
  3807. mtr_init_args(\$args);
  3808. valgrind_arguments($args, \$exe);
  3809. mtr_add_arg($args, "%s", $_) for @args_saved;
  3810. }
  3811. mtr_add_arg($args, "--test-file=%s", $tinfo->{'path'});
  3812. # Number of lines of resut to include in failure report
  3813. mtr_add_arg($args, "--tail-lines=20");
  3814. if ( defined $tinfo->{'result_file'} ) {
  3815. mtr_add_arg($args, "--result-file=%s", $tinfo->{'result_file'});
  3816. }
  3817. client_debug_arg($args, "mysqltest");
  3818. if ( $opt_record )
  3819. {
  3820. mtr_add_arg($args, "--record");
  3821. # When recording to a non existing result file
  3822. # the name of that file is in "record_file"
  3823. if ( defined $tinfo->{'record_file'} ) {
  3824. mtr_add_arg($args, "--result-file=%s", $tinfo->{record_file});
  3825. }
  3826. }
  3827. if ( $opt_client_gdb )
  3828. {
  3829. gdb_arguments(\$args, \$exe, "client");
  3830. }
  3831. elsif ( $opt_client_ddd )
  3832. {
  3833. ddd_arguments(\$args, \$exe, "client");
  3834. }
  3835. elsif ( $opt_client_debugger )
  3836. {
  3837. debugger_arguments(\$args, \$exe, "client");
  3838. }
  3839. my $proc= My::SafeProcess->new
  3840. (
  3841. name => "mysqltest",
  3842. path => $exe,
  3843. args => \$args,
  3844. append => 1,
  3845. error => $path_current_testlog,
  3846. verbose => $opt_verbose,
  3847. );
  3848. mtr_verbose("Started $proc");
  3849. return $proc;
  3850. }
  3851. #
  3852. # Modify the exe and args so that program is run in gdb in xterm
  3853. #
  3854. sub gdb_arguments {
  3855. my $args= shift;
  3856. my $exe= shift;
  3857. my $type= shift;
  3858. # Write $args to gdb init file
  3859. my $str= join(" ", @$$args);
  3860. my $gdb_init_file= "$opt_vardir/tmp/gdbinit.$type";
  3861. # Remove the old gdbinit file
  3862. unlink($gdb_init_file);
  3863. if ( $type eq "client" )
  3864. {
  3865. # write init file for client
  3866. mtr_tofile($gdb_init_file,
  3867. "set args $str\n" .
  3868. "break main\n");
  3869. }
  3870. else
  3871. {
  3872. # write init file for mysqld
  3873. mtr_tofile($gdb_init_file,
  3874. "set args $str\n" .
  3875. "break mysql_parse\n" .
  3876. "commands 1\n" .
  3877. "disable 1\n" .
  3878. "end\n" .
  3879. "run");
  3880. }
  3881. if ( $opt_manual_gdb )
  3882. {
  3883. print "\nTo start gdb for $type, type in another window:\n";
  3884. print "gdb -cd $glob_mysql_test_dir -x $gdb_init_file $$exe\n";
  3885. # Indicate the exe should not be started
  3886. $$exe= undef;
  3887. return;
  3888. }
  3889. $$args= [];
  3890. mtr_add_arg($$args, "-title");
  3891. mtr_add_arg($$args, "$type");
  3892. mtr_add_arg($$args, "-e");
  3893. if ( $exe_libtool )
  3894. {
  3895. mtr_add_arg($$args, $exe_libtool);
  3896. mtr_add_arg($$args, "--mode=execute");
  3897. }
  3898. mtr_add_arg($$args, "gdb");
  3899. mtr_add_arg($$args, "-x");
  3900. mtr_add_arg($$args, "$gdb_init_file");
  3901. mtr_add_arg($$args, "$$exe");
  3902. $$exe= "xterm";
  3903. }
  3904. #
  3905. # Modify the exe and args so that program is run in ddd
  3906. #
  3907. sub ddd_arguments {
  3908. my $args= shift;
  3909. my $exe= shift;
  3910. my $type= shift;
  3911. # Write $args to ddd init file
  3912. my $str= join(" ", @$$args);
  3913. my $gdb_init_file= "$opt_vardir/tmp/gdbinit.$type";
  3914. # Remove the old gdbinit file
  3915. unlink($gdb_init_file);
  3916. if ( $type eq "client" )
  3917. {
  3918. # write init file for client
  3919. mtr_tofile($gdb_init_file,
  3920. "set args $str\n" .
  3921. "break main\n");
  3922. }
  3923. else
  3924. {
  3925. # write init file for mysqld
  3926. mtr_tofile($gdb_init_file,
  3927. "file $$exe\n" .
  3928. "set args $str\n" .
  3929. "break mysql_parse\n" .
  3930. "commands 1\n" .
  3931. "disable 1\n" .
  3932. "end");
  3933. }
  3934. if ( $opt_manual_ddd )
  3935. {
  3936. print "\nTo start ddd for $type, type in another window:\n";
  3937. print "ddd -cd $glob_mysql_test_dir -x $gdb_init_file $$exe\n";
  3938. # Indicate the exe should not be started
  3939. $$exe= undef;
  3940. return;
  3941. }
  3942. my $save_exe= $$exe;
  3943. $$args= [];
  3944. if ( $exe_libtool )
  3945. {
  3946. $$exe= $exe_libtool;
  3947. mtr_add_arg($$args, "--mode=execute");
  3948. mtr_add_arg($$args, "ddd");
  3949. }
  3950. else
  3951. {
  3952. $$exe= "ddd";
  3953. }
  3954. mtr_add_arg($$args, "--command=$gdb_init_file");
  3955. mtr_add_arg($$args, "$save_exe");
  3956. }
  3957. #
  3958. # Modify the exe and args so that program is run in the selected debugger
  3959. #
  3960. sub debugger_arguments {
  3961. my $args= shift;
  3962. my $exe= shift;
  3963. my $debugger= $opt_debugger || $opt_client_debugger;
  3964. if ( $debugger =~ /vcexpress|vc|devenv/ )
  3965. {
  3966. # vc[express] /debugexe exe arg1 .. argn
  3967. # Add /debugexe and name of the exe before args
  3968. unshift(@$$args, "/debugexe");
  3969. unshift(@$$args, "$$exe");
  3970. # Set exe to debuggername
  3971. $$exe= $debugger;
  3972. }
  3973. elsif ( $debugger =~ /windbg/ )
  3974. {
  3975. # windbg exe arg1 .. argn
  3976. # Add name of the exe before args
  3977. unshift(@$$args, "$$exe");
  3978. # Set exe to debuggername
  3979. $$exe= $debugger;
  3980. }
  3981. elsif ( $debugger eq "dbx" )
  3982. {
  3983. # xterm -e dbx -r exe arg1 .. argn
  3984. unshift(@$$args, $$exe);
  3985. unshift(@$$args, "-r");
  3986. unshift(@$$args, $debugger);
  3987. unshift(@$$args, "-e");
  3988. $$exe= "xterm";
  3989. }
  3990. else
  3991. {
  3992. mtr_error("Unknown argument \"$debugger\" passed to --debugger");
  3993. }
  3994. }
  3995. #
  3996. # Modify the exe and args so that program is run in valgrind
  3997. #
  3998. sub valgrind_arguments {
  3999. my $args= shift;
  4000. my $exe= shift;
  4001. if ( $opt_callgrind)
  4002. {
  4003. mtr_add_arg($args, "--tool=callgrind");
  4004. mtr_add_arg($args, "--base=$opt_vardir/log");
  4005. }
  4006. else
  4007. {
  4008. mtr_add_arg($args, "--tool=memcheck"); # From >= 2.1.2 needs this option
  4009. mtr_add_arg($args, "--alignment=8");
  4010. mtr_add_arg($args, "--leak-check=yes");
  4011. mtr_add_arg($args, "--num-callers=16");
  4012. mtr_add_arg($args, "--suppressions=%s/valgrind.supp", $glob_mysql_test_dir)
  4013. if -f "$glob_mysql_test_dir/valgrind.supp";
  4014. }
  4015. # Add valgrind options, can be overriden by user
  4016. mtr_add_arg($args, '%s', $_) for (@valgrind_args);
  4017. mtr_add_arg($args, $$exe);
  4018. $$exe= $opt_valgrind_path || "valgrind";
  4019. if ($exe_libtool)
  4020. {
  4021. # Add "libtool --mode-execute" before the test to execute
  4022. # if running in valgrind(to avoid valgrinding bash)
  4023. unshift(@$args, "--mode=execute", $$exe);
  4024. $$exe= $exe_libtool;
  4025. }
  4026. }
  4027. #
  4028. # Usage
  4029. #
  4030. sub usage ($) {
  4031. my ($message)= @_;
  4032. if ( $message )
  4033. {
  4034. print STDERR "$message\n";
  4035. }
  4036. print <<HERE;
  4037. $0 [ OPTIONS ] [ TESTCASE ]
  4038. Options to control what engine/variation to run
  4039. embedded-server Use the embedded server, i.e. no mysqld daemons
  4040. ps-protocol Use the binary protocol between client and server
  4041. cursor-protocol Use the cursor protocol between client and server
  4042. (implies --ps-protocol)
  4043. view-protocol Create a view to execute all non updating queries
  4044. sp-protocol Create a stored procedure to execute all queries
  4045. compress Use the compressed protocol between client and server
  4046. ssl Use ssl protocol between client and server
  4047. skip-ssl Dont start server with support for ssl connections
  4048. vs-config Visual Studio configuration used to create executables
  4049. (default: MTR_VS_CONFIG environment variable)
  4050. config|defaults-file=<config template> Use fixed config template for all
  4051. tests
  4052. defaults_extra_file=<config template> Extra config template to add to
  4053. all generated configs
  4054. Options to control directories to use
  4055. tmpdir=DIR The directory where temporary files are stored
  4056. (default: ./var/tmp).
  4057. vardir=DIR The directory where files generated from the test run
  4058. is stored (default: ./var). Specifying a ramdisk or
  4059. tmpfs will speed up tests.
  4060. mem Run testsuite in "memory" using tmpfs or ramdisk
  4061. Attempts to find a suitable location
  4062. using a builtin list of standard locations
  4063. for tmpfs (/dev/shm)
  4064. The option can also be set using environment
  4065. variable MTR_MEM=[DIR]
  4066. client-bindir=PATH Path to the directory where client binaries are located
  4067. client-libdir=PATH Path to the directory where client libraries are located
  4068. Options to control what test suites or cases to run
  4069. force Continue to run the suite after failure
  4070. with-ndbcluster-only Run only tests that include "ndb" in the filename
  4071. skip-ndb[cluster] Skip all tests that need cluster
  4072. skip-ndb[cluster]-slave Skip all tests that need a slave cluster
  4073. do-test=PREFIX or REGEX
  4074. Run test cases which name are prefixed with PREFIX
  4075. or fulfills REGEX
  4076. skip-test=PREFIX or REGEX
  4077. Skip test cases which name are prefixed with PREFIX
  4078. or fulfills REGEX
  4079. start-from=PREFIX Run test cases starting test prefixed with PREFIX where
  4080. prefix may be suite.testname or just testname
  4081. suite[s]=NAME1,..,NAMEN
  4082. Collect tests in suites from the comma separated
  4083. list of suite names.
  4084. The default is: "$DEFAULT_SUITES"
  4085. skip-rpl Skip the replication test cases.
  4086. big-test Also run tests marked as "big"
  4087. Options that specify ports
  4088. mtr-build-thread=# Specify unique number to calculate port number(s) from.
  4089. build-thread=# Can be set in environment variable MTR_BUILD_THREAD.
  4090. Set MTR_BUILD_THREAD="auto" to automatically aquire
  4091. a build thread id that is unique to current host
  4092. Options for test case authoring
  4093. record TESTNAME (Re)genereate the result file for TESTNAME
  4094. check-testcases Check testcases for sideeffects
  4095. mark-progress Log line number and elapsed time to <testname>.progress
  4096. Options that pass on options
  4097. mysqld=ARGS Specify additional arguments to "mysqld"
  4098. Options to run test on running server
  4099. extern option=value Run only the tests against an already started server
  4100. the options to use for connection to the extern server
  4101. must be specified using name-value pair notation
  4102. For example:
  4103. ./$0 --extern socket=/tmp/mysqld.sock
  4104. Options for debugging the product
  4105. client-ddd Start mysqltest client in ddd
  4106. client-debugger=NAME Start mysqltest in the selected debugger
  4107. client-gdb Start mysqltest client in gdb
  4108. ddd Start mysqld in ddd
  4109. debug Dump trace output for all servers and client programs
  4110. debugger=NAME Start mysqld in the selected debugger
  4111. gdb Start the mysqld(s) in gdb
  4112. manual-debug Let user manually start mysqld in debugger, before
  4113. running test(s)
  4114. manual-gdb Let user manually start mysqld in gdb, before running
  4115. test(s)
  4116. manual-ddd Let user manually start mysqld in ddd, before running
  4117. test(s)
  4118. strace-client=[path] Create strace output for mysqltest client, optionally
  4119. specifying name and path to the trace program to use.
  4120. Example: $0 --strace-client=ktrace
  4121. max-save-core Limit the number of core files saved (to avoid filling
  4122. up disks for heavily crashing server). Defaults to
  4123. $opt_max_save_core, set to 0 for no limit. Set
  4124. it's default with MTR_MAX_SAVE_CORE
  4125. max-save-datadir Limit the number of datadir saved (to avoid filling
  4126. up disks for heavily crashing server). Defaults to
  4127. $opt_max_save_datadir, set to 0 for no limit. Set
  4128. it's default with MTR_MAX_SAVE_DATDIR
  4129. max-test-fail Limit the number of test failurs before aborting
  4130. the current test run. Defaults to
  4131. $opt_max_test_fail, set to 0 for no limit. Set
  4132. it's default with MTR_MAX_TEST_FAIL
  4133. Options for valgrind
  4134. valgrind Run the "mysqltest" and "mysqld" executables using
  4135. valgrind with default options
  4136. valgrind-all Synonym for --valgrind
  4137. valgrind-mysqltest Run the "mysqltest" and "mysql_client_test" executable
  4138. with valgrind
  4139. valgrind-mysqld Run the "mysqld" executable with valgrind
  4140. valgrind-options=ARGS Deprecated, use --valgrind-option
  4141. valgrind-option=ARGS Option to give valgrind, replaces default option(s),
  4142. can be specified more then once
  4143. valgrind-path=[EXE] Path to the valgrind executable
  4144. callgrind Instruct valgrind to use callgrind
  4145. Misc options
  4146. user=USER User for connecting to mysqld(default: $opt_user)
  4147. comment=STR Write STR to the output
  4148. notimer Don't show test case execution time
  4149. verbose More verbose output(use multiple times for even more)
  4150. start Only initialize and start the servers, using the
  4151. startup settings for the first specified test case
  4152. Example:
  4153. $0 --start alias &
  4154. start-dirty Only start the servers (without initialization) for
  4155. the first specified test case
  4156. fast Run as fast as possible, dont't wait for servers
  4157. to shutdown etc.
  4158. repeat=N Run each test N number of times
  4159. retry=N Retry tests that fail N times, limit number of failures
  4160. to $opt_retry_failure
  4161. retry-failure=N Limit number of retries for a failed test
  4162. reorder Reorder tests to get fewer server restarts
  4163. help Get this help text
  4164. testcase-timeout=MINUTES Max test case run time (default $opt_testcase_timeout)
  4165. suite-timeout=MINUTES Max test suite run time (default $opt_suite_timeout)
  4166. shutdown-timeout=SECONDS Max number of seconds to wait for server shutdown
  4167. before killing servers (default $opt_shutdown_timeout)
  4168. warnings Scan the log files for warnings. Use --nowarnings
  4169. to turn off.
  4170. sleep=SECONDS Passed to mysqltest, will be used as fixed sleep time
  4171. gcov Collect coverage information after the test.
  4172. The result is a gcov file per source and header file.
  4173. HERE
  4174. exit(1);
  4175. }