~mathiaz/ubuntu/lucid/mysql-dfsg-5.1/zap-bug-552053

« back to all changes in this revision

Viewing changes to mysql-test/lib/mtr_cases.pl

  • Committer: Bazaar Package Importer
  • Author(s): Mathias Gug
  • Date: 2009-06-25 12:55:45 UTC
  • mfrom: (1.1.2 upstream) (0.1.3 experimental)
  • Revision ID: james.westby@ubuntu.com-20090625125545-m8ogs96zzsri74xe
Tags: 5.1.34-1ubuntu1
* Merge from debian experimental (and 5.0 from main), remaining changes:
  - debian/mysql-server-5.1.config:
    + ask for MySQL root password at priority high instead of medium so
      that the password prompt is seen on a default install. (LP: #319843)
    + don't ask for root password when upgrading from a 5.0 install.
  - debian/control:
    + Make libmysqlclient16-dev a transitional package depending on
      libmysqlclient-dev.
    + Make libmysqlclient-dev conflict with libmysqlclient15-dev.
    + Don't build mysql-server, mysql-client, mysql-common and
      libmysqlclient15-dev binary packages since they're still provided
      by mysql-dfsg-5.0.
    + Make mysql-{client,server}-5.1 packages conflict and
      replace mysql-{client,server}-5.0, but not provide
      mysql-{client,server}.
    + Depend on a specific version of mysql-common rather than the src
      version of mysql-dfsg-5.1 since mysql-common is currently part of
      mysql-dfsg-5.0.
    + Lower mailx from a Recommends to a Suggests to avoid pulling in
      a full MTA on all installs of mysql-server. (LP: #259477)
  - debian/rules:
    + added -fno-strict-aliasing to CFLAGS to get around mysql testsuite
      build failures.
    + install mysql-test and sql-bench to /usr/share/mysql/ rather than
      /usr/.
  - debian/additions/debian-start.inc.sh: support ANSI mode (LP: #310211)
  - Add AppArmor profile:
    - debian/apparmor-profile: apparmor profile.
    - debian/rules, debian/mysql-server-5.0.files: install apparmor profile.
    - debian/mysql-server-5.0.dirs: add etc/apparmor.d/force-complain
    - debian/mysql-server-5.0.postrm: remove symlink in force-complain/ on
      purge.
    - debian/mysql-server-5.1.README.Debian: add apparmor documentation.
    - debian/additions/my.cnf: Add warning about apparmor. (LP: #201799)
    - debian/mysql-server-5.1.postinst: reload apparmor profiles.
  - debian/additions/my.cnf: remove language option. Error message files are
    located in a different directory in MySQL 5.0. Setting the language
    option to use /usr/share/mysql/english breaks 5.0. Both 5.0 and 5.1
    use a default value that works. (LP: #316974)
  - debian/mysql-server-5.1.mysql.init:
    + Clearly indicate that we do not support running multiple instances
      of mysqld by duplicating the init script.
      (closes: #314785, #324834, #435165, #444216)
    + Properly parameterize all existing references to the mysql config
      file (/etc/mysql/my.cnf).
  - debian/mysql-server-5.0.postinst: Clear out the second password
    when setting up mysql. (LP: #344816)
  - mysql-server-core-5.1 package for files needed by Akonadi:
    + debian/control: create mysql-server-core-5.1 package.
    + debian/mysql-server-core-5.1.files, debian/mysql-server-5.1.files:
      move core mysqld files to mysql-server-core-5.1 package.
  - Don't package sql-bench and mysql-test file.
* Dropped changes:
  - debian/patches/92_ssl_test_cert.dpatch: certificate expiration in
    test suite (LP: #323755). Included upstream.
* Dropped from 5.0:
  - apparmor profile:
    - debian/control: Recommends apparmor >= 2.1+1075-0ubuntu6. All version
      of apparmor-profile (>hardy) are higher than this version.
    - debian/mysql-server-5.0.preinst: create symlink for force-complain/
      on pre-feisty upgrades, upgrades where apparmor-profiles profile is
      unchanged (ie non-enforcing) and upgrades where the profile
      doesn't exist. Support for pre-hardy upgrades is no longer needed.
* debian/mysql-server-5.1.postinst: fix debian-sys-maint user creation.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# -*- cperl -*-
2
 
# Copyright (C) 2005-2006 MySQL AB
3
 
4
 
# This program is free software; you can redistribute it and/or modify
5
 
# it under the terms of the GNU General Public License as published by
6
 
# the Free Software Foundation; version 2 of the License.
7
 
8
 
# This program is distributed in the hope that it will be useful,
9
 
# but WITHOUT ANY WARRANTY; without even the implied warranty of
10
 
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
 
# GNU General Public License for more details.
12
 
13
 
# You should have received a copy of the GNU General Public License
14
 
# along with this program; if not, write to the Free Software
15
 
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
16
 
 
17
 
# This is a library file used by the Perl version of mysql-test-run,
18
 
# and is part of the translation of the Bourne shell script with the
19
 
# same name.
20
 
 
21
 
use File::Basename;
22
 
use IO::File();
23
 
use strict;
24
 
 
25
 
use My::Config;
26
 
 
27
 
sub collect_test_cases ($);
28
 
sub collect_one_suite ($);
29
 
sub collect_one_test_case ($$$$$$$$$);
30
 
 
31
 
sub mtr_options_from_test_file($$);
32
 
 
33
 
my $do_test;
34
 
my $skip_test;
35
 
 
36
 
sub init_pattern {
37
 
  my ($from, $what)= @_;
38
 
  if ( $from =~ /^[a-z0-9]$/ ) {
39
 
    # Does not contain any regex, make the pattern match
40
 
    # beginning of string
41
 
    $from= "^$from";
42
 
  }
43
 
  # Check that pattern is a valid regex
44
 
  eval { "" =~/$from/; 1 } or
45
 
    mtr_error("Invalid regex '$from' passed to $what\nPerl says: $@");
46
 
  return $from;
47
 
}
48
 
 
49
 
 
50
 
 
51
 
##############################################################################
52
 
#
53
 
#  Collect information about test cases we are to run
54
 
#
55
 
##############################################################################
56
 
 
57
 
sub collect_test_cases ($) {
58
 
  $do_test= init_pattern($::opt_do_test, "--do-test");
59
 
  $skip_test= init_pattern($::opt_skip_test, "--skip-test");
60
 
 
61
 
  my $suites= shift; # Semicolon separated list of test suites
62
 
  my $cases = [];    # Array of hash
63
 
 
64
 
  foreach my $suite (split(",", $suites))
65
 
  {
66
 
    push(@$cases, collect_one_suite($suite));
67
 
  }
68
 
 
69
 
 
70
 
  if ( @::opt_cases )
71
 
  {
72
 
    # Check that the tests specified was found
73
 
    # in at least one suite
74
 
    foreach my $test_name_spec ( @::opt_cases )
75
 
    {
76
 
      my $found= 0;
77
 
      my ($sname, $tname, $extension)= split_testname($test_name_spec);
78
 
      foreach my $test ( @$cases )
79
 
      {
80
 
        # test->{name} is always in suite.name format
81
 
        if ( $test->{name} =~ /.*\.$tname/ )
82
 
        {
83
 
          $found= 1;
84
 
        }
85
 
      }
86
 
      if ( not $found )
87
 
      {
88
 
        mtr_error("Could not find $tname in any suite");
89
 
      }
90
 
    }
91
 
  }
92
 
 
93
 
  if ( $::opt_reorder )
94
 
  {
95
 
    # Reorder the test cases in an order that will make them faster to run
96
 
    my %sort_criteria;
97
 
 
98
 
    # Make a mapping of test name to a string that represents how that test
99
 
    # should be sorted among the other tests.  Put the most important criterion
100
 
    # first, then a sub-criterion, then sub-sub-criterion, et c.
101
 
    foreach my $tinfo (@$cases)
102
 
    {
103
 
      my @criteria = ();
104
 
 
105
 
      # Look for tests that muct be in run in a defined order
106
 
      # that is defined by test having the same name except for
107
 
      # the ending digit
108
 
 
109
 
      # Put variables into hash
110
 
      my $test_name= $tinfo->{'name'};
111
 
      my $depend_on_test_name;
112
 
      if ( $test_name =~ /^([\D]+)([0-9]{1})$/ )
113
 
      {
114
 
        my $base_name= $1;
115
 
        my $idx= $2;
116
 
        mtr_verbose("$test_name =>  $base_name idx=$idx");
117
 
        if ( $idx > 1 )
118
 
        {
119
 
          $idx-= 1;
120
 
          $base_name= "$base_name$idx";
121
 
          mtr_verbose("New basename $base_name");
122
 
        }
123
 
 
124
 
        foreach my $tinfo2 (@$cases)
125
 
        {
126
 
          if ( $tinfo2->{'name'} eq $base_name )
127
 
          {
128
 
            mtr_verbose("found dependent test $tinfo2->{'name'}");
129
 
            $depend_on_test_name=$base_name;
130
 
          }
131
 
        }
132
 
      }
133
 
 
134
 
      if ( defined $depend_on_test_name )
135
 
      {
136
 
        mtr_verbose("Giving $test_name same critera as $depend_on_test_name");
137
 
        $sort_criteria{$test_name} = $sort_criteria{$depend_on_test_name};
138
 
      }
139
 
      else
140
 
      {
141
 
        #
142
 
        # Append the criteria for sorting, in order of importance.
143
 
        #
144
 
        push(@criteria, "ndb=" . ($tinfo->{'ndb_test'} ? "1" : "0"));
145
 
        # Group test with equal options together.
146
 
        # Ending with "~" makes empty sort later than filled
147
 
        push(@criteria, join("!", sort @{$tinfo->{'master_opt'}}) . "~");
148
 
 
149
 
        $sort_criteria{$test_name} = join(" ", @criteria);
150
 
      }
151
 
    }
152
 
 
153
 
    @$cases = sort {
154
 
      $sort_criteria{$a->{'name'}} . $a->{'name'} cmp
155
 
        $sort_criteria{$b->{'name'}} . $b->{'name'}; } @$cases;
156
 
 
157
 
    if ( $::opt_script_debug )
158
 
    {
159
 
      # For debugging the sort-order
160
 
      foreach my $tinfo (@$cases)
161
 
      {
162
 
        print("$sort_criteria{$tinfo->{'name'}} -> \t$tinfo->{'name'}\n");
163
 
      }
164
 
    }
165
 
  }
166
 
 
167
 
  return $cases;
168
 
 
169
 
}
170
 
 
171
 
# Valid extensions and their corresonding component id
172
 
my %exts = ( 'test' => 'mysqld',
173
 
             'imtest' => 'im'
174
 
           );
175
 
 
176
 
 
177
 
# Returns (suitename, testname, extension)
178
 
sub split_testname {
179
 
  my ($test_name)= @_;
180
 
 
181
 
  # Get rid of directory part and split name on .'s
182
 
  my @parts= split(/\./, basename($test_name));
183
 
 
184
 
  if (@parts == 1){
185
 
    # Only testname given, ex: alias
186
 
    return (undef , $parts[0], undef);
187
 
  } elsif (@parts == 2) {
188
 
    # Either testname.test or suite.testname given
189
 
    # Ex. main.alias or alias.test
190
 
 
191
 
    if (defined $exts{$parts[1]})
192
 
    {
193
 
      return (undef , $parts[0], $parts[1]);
194
 
    }
195
 
    else
196
 
    {
197
 
      return ($parts[0], $parts[1], undef);
198
 
    }
199
 
 
200
 
  } elsif (@parts == 3) {
201
 
    # Fully specified suitename.testname.test
202
 
    # ex main.alias.test
203
 
    return ( $parts[0], $parts[1], $parts[2]);
204
 
  }
205
 
 
206
 
  mtr_error("Illegal format of test name: $test_name");
207
 
}
208
 
 
209
 
 
210
 
sub collect_one_suite($)
211
 
{
212
 
  my $suite= shift;  # Test suite name
213
 
  my @cases;  # Array of hash
214
 
 
215
 
  mtr_verbose("Collecting: $suite");
216
 
 
217
 
  my $suitedir= "$::glob_mysql_test_dir"; # Default
218
 
  if ( $suite ne "main" )
219
 
  {
220
 
    $suitedir= mtr_path_exists("$suitedir/suite/$suite",
221
 
                               "$suitedir/$suite");
222
 
    mtr_verbose("suitedir: $suitedir");
223
 
  }
224
 
 
225
 
  my $testdir= "$suitedir/t";
226
 
  my $resdir=  "$suitedir/r";
227
 
 
228
 
  # ----------------------------------------------------------------------
229
 
  # Build a hash of disabled testcases for this suite
230
 
  # ----------------------------------------------------------------------
231
 
  my %disabled;
232
 
  if ( open(DISABLED, "$testdir/disabled.def" ) )
233
 
  {
234
 
    while ( <DISABLED> )
235
 
      {
236
 
        chomp;
237
 
        if ( /^\s*(\S+)\s*:\s*(.*?)\s*$/ )
238
 
          {
239
 
            $disabled{$1}= $2;
240
 
          }
241
 
      }
242
 
    close DISABLED;
243
 
  }
244
 
 
245
 
  # Read suite.opt file
246
 
  my $suite_opt_file=  "$testdir/suite.opt";
247
 
  my $suite_opts= [];
248
 
  if ( -f $suite_opt_file )
249
 
  {
250
 
    $suite_opts= mtr_get_opts_from_file($suite_opt_file);
251
 
  }
252
 
 
253
 
  if ( @::opt_cases )
254
 
  {
255
 
    # Collect in specified order
256
 
    foreach my $test_name_spec ( @::opt_cases )
257
 
    {
258
 
      my ($sname, $tname, $extension)= split_testname($test_name_spec);
259
 
 
260
 
      # The test name parts have now been defined
261
 
      #print "  suite_name: $sname\n";
262
 
      #print "  tname:      $tname\n";
263
 
      #print "  extension:  $extension\n";
264
 
 
265
 
      # Check cirrect suite if suitename is defined
266
 
      next if (defined $sname and $suite ne $sname);
267
 
 
268
 
      my $component_id;
269
 
      if ( defined $extension )
270
 
      {
271
 
        my $full_name= "$testdir/$tname.$extension";
272
 
        # Extension was specified, check if the test exists
273
 
        if ( ! -f $full_name)
274
 
        {
275
 
          # This is only an error if suite was specified, otherwise it
276
 
          # could exist in another suite
277
 
          mtr_error("Test '$full_name' was not found in suite '$sname'")
278
 
            if $sname;
279
 
 
280
 
          next;
281
 
        }
282
 
        $component_id= $exts{$extension};
283
 
      }
284
 
      else
285
 
      {
286
 
        # No extension was specified
287
 
        my ($ext, $component);
288
 
        while (($ext, $component)= each %exts) {
289
 
          my $full_name= "$testdir/$tname.$ext";
290
 
 
291
 
          if ( ! -f $full_name ) {
292
 
            next;
293
 
          }
294
 
          $component_id= $component;
295
 
          $extension= $ext;
296
 
        }
297
 
        # Test not found here, could exist in other suite
298
 
        next unless $component_id;
299
 
      }
300
 
 
301
 
      collect_one_test_case($testdir,$resdir,$suite,$tname,
302
 
                            "$tname.$extension",\@cases,\%disabled,
303
 
                            $component_id,$suite_opts);
304
 
    }
305
 
  }
306
 
  else
307
 
  {
308
 
    opendir(TESTDIR, $testdir) or mtr_error("Can't open dir \"$testdir\": $!");
309
 
 
310
 
    foreach my $elem ( sort readdir(TESTDIR) )
311
 
    {
312
 
      my $component_id= undef;
313
 
      my $tname= undef;
314
 
 
315
 
      if ($tname= mtr_match_extension($elem, 'test'))
316
 
      {
317
 
        $component_id = 'mysqld';
318
 
      }
319
 
      elsif ($tname= mtr_match_extension($elem, 'imtest'))
320
 
      {
321
 
        $component_id = 'im';
322
 
      }
323
 
      else
324
 
      {
325
 
        next;
326
 
      }
327
 
 
328
 
      # Skip tests that does not match the --do-test= filter
329
 
      next if ($do_test and not $tname =~ /$do_test/o);
330
 
 
331
 
      collect_one_test_case($testdir,$resdir,$suite,$tname,
332
 
                            $elem,\@cases,\%disabled,$component_id,
333
 
                            $suite_opts);
334
 
    }
335
 
    closedir TESTDIR;
336
 
  }
337
 
 
338
 
 
339
 
  #  Return empty list if no testcases found
340
 
  return if (@cases == 0);
341
 
 
342
 
  # ----------------------------------------------------------------------
343
 
  # Read combinations for this suite and build testcases x combinations
344
 
  # if any combinations exists
345
 
  # ----------------------------------------------------------------------
346
 
  if ( ! $::opt_skip_combination )
347
 
  {
348
 
    my @combinations;
349
 
    my $combination_file= "$suitedir/combinations";
350
 
    #print "combination_file: $combination_file\n";
351
 
    if (@::opt_combinations)
352
 
    {
353
 
      # take the combination from command-line
354
 
      mtr_verbose("Take the combination from command line");
355
 
      foreach my $combination (@::opt_combinations) {
356
 
        my $comb= {};
357
 
        $comb->{name}= $combination;
358
 
        push(@{$comb->{comb_opt}}, $combination);
359
 
        push(@combinations, $comb);
360
 
      }
361
 
    }
362
 
    elsif (-f $combination_file )
363
 
    {
364
 
      # Read combinations file in my.cnf format
365
 
      mtr_verbose("Read combinations file");
366
 
      my $config= My::Config->new($combination_file);
367
 
 
368
 
      foreach my $group ($config->groups()) {
369
 
        my $comb= {};
370
 
        $comb->{name}= $group->name();
371
 
        foreach my $option ( $group->options() ) {
372
 
          push(@{$comb->{comb_opt}}, $option->name()."=".$option->value());
373
 
        }
374
 
        push(@combinations, $comb);
375
 
      }
376
 
    }
377
 
 
378
 
    if (@combinations)
379
 
    {
380
 
      print " - adding combinations\n";
381
 
      #print_testcases(@cases);
382
 
 
383
 
      my @new_cases;
384
 
      foreach my $comb (@combinations)
385
 
      {
386
 
        foreach my $test (@cases)
387
 
        {
388
 
          #print $test->{name}, " ", $comb, "\n";
389
 
          my $new_test= {};
390
 
 
391
 
          while (my ($key, $value) = each(%$test)) {
392
 
            if (ref $value eq "ARRAY") {
393
 
              push(@{$new_test->{$key}}, @$value);
394
 
            } else {
395
 
              $new_test->{$key}= $value;
396
 
            }
397
 
          }
398
 
 
399
 
          # Append the combination options to master_opt and slave_opt
400
 
          push(@{$new_test->{master_opt}}, @{$comb->{comb_opt}});
401
 
          push(@{$new_test->{slave_opt}}, @{$comb->{comb_opt}});
402
 
 
403
 
          # Add combination name shrt name
404
 
          $new_test->{combination}= $comb->{name};
405
 
 
406
 
          # Add the new test to new test cases list
407
 
          push(@new_cases, $new_test);
408
 
        }
409
 
      }
410
 
      #print_testcases(@new_cases);
411
 
      @cases= @new_cases;
412
 
      #print_testcases(@cases);
413
 
    }
414
 
  }
415
 
 
416
 
  optimize_cases(\@cases);
417
 
  #print_testcases(@cases);
418
 
 
419
 
  return @cases;
420
 
}
421
 
 
422
 
 
423
 
#
424
 
# Loop through all test cases
425
 
# - optimize which test to run by skipping unnecessary ones
426
 
# - update settings if necessary
427
 
#
428
 
sub optimize_cases {
429
 
  my ($cases)= @_;
430
 
 
431
 
  foreach my $tinfo ( @$cases )
432
 
  {
433
 
    # Skip processing if already marked as skipped
434
 
    next if $tinfo->{skip};
435
 
 
436
 
    # =======================================================
437
 
    # If a special binlog format was selected with
438
 
    # --mysqld=--binlog-format=x, skip all test that does not
439
 
    # support it
440
 
    # =======================================================
441
 
    #print "used_binlog_format: $::used_binlog_format\n";
442
 
    if (defined $::used_binlog_format )
443
 
    {
444
 
      # =======================================================
445
 
      # Fixed --binlog-format=x specified on command line
446
 
      # =======================================================
447
 
      if ( defined $tinfo->{'binlog_formats'} )
448
 
      {
449
 
        #print "binlog_formats: ". join(", ", @{$tinfo->{binlog_formats}})."\n";
450
 
 
451
 
        # The test supports different binlog formats
452
 
        # check if the selected one is ok
453
 
        my $supported=
454
 
          grep { $_ eq $::used_binlog_format } @{$tinfo->{'binlog_formats'}};
455
 
        if ( !$supported )
456
 
        {
457
 
          $tinfo->{'skip'}= 1;
458
 
          $tinfo->{'comment'}=
459
 
            "Doesn't support --binlog-format='$::used_binlog_format'";
460
 
        }
461
 
      }
462
 
    }
463
 
    else
464
 
    {
465
 
      # =======================================================
466
 
      # Use dynamic switching of binlog format
467
 
      # =======================================================
468
 
 
469
 
      # Get binlog-format used by this test from master_opt
470
 
      my $test_binlog_format;
471
 
      foreach my $opt ( @{$tinfo->{master_opt}} ) {
472
 
        $test_binlog_format=
473
 
          mtr_match_prefix($opt, "--binlog-format=") || $test_binlog_format;
474
 
      }
475
 
 
476
 
      if (defined $test_binlog_format and
477
 
          defined $tinfo->{binlog_formats} )
478
 
      {
479
 
        my $supported=
480
 
          grep { $_ eq $test_binlog_format } @{$tinfo->{'binlog_formats'}};
481
 
        if ( !$supported )
482
 
        {
483
 
          $tinfo->{'skip'}= 1;
484
 
          $tinfo->{'comment'}=
485
 
            "Doesn't support --binlog-format='$test_binlog_format'";
486
 
          next;
487
 
        }
488
 
      }
489
 
    }
490
 
 
491
 
  }
492
 
}
493
 
 
494
 
 
495
 
##############################################################################
496
 
#
497
 
#  Collect information about a single test case
498
 
#
499
 
##############################################################################
500
 
 
501
 
 
502
 
sub collect_one_test_case($$$$$$$$$) {
503
 
  my $testdir= shift;
504
 
  my $resdir=  shift;
505
 
  my $suite=   shift;
506
 
  my $tname=   shift;
507
 
  my $elem=    shift;
508
 
  my $cases=   shift;
509
 
  my $disabled=shift;
510
 
  my $component_id= shift;
511
 
  my $suite_opts= shift;
512
 
 
513
 
  my $path= "$testdir/$elem";
514
 
 
515
 
  # ----------------------------------------------------------------------
516
 
  # Skip some tests silently
517
 
  # ----------------------------------------------------------------------
518
 
 
519
 
  if ( $::opt_start_from and $tname lt $::opt_start_from )
520
 
  {
521
 
    return;
522
 
  }
523
 
 
524
 
 
525
 
  my $tinfo= {};
526
 
  $tinfo->{'name'}= basename($suite) . ".$tname";
527
 
  $tinfo->{'result_file'}= "$resdir/$tname.result";
528
 
  $tinfo->{'component_id'} = $component_id;
529
 
  push(@$cases, $tinfo);
530
 
 
531
 
  # ----------------------------------------------------------------------
532
 
  # Skip some tests but include in list, just mark them to skip
533
 
  # ----------------------------------------------------------------------
534
 
 
535
 
  if ( $skip_test and $tname =~ /$skip_test/o )
536
 
  {
537
 
    $tinfo->{'skip'}= 1;
538
 
    return;
539
 
  }
540
 
 
541
 
  # ----------------------------------------------------------------------
542
 
  # Collect information about test case
543
 
  # ----------------------------------------------------------------------
544
 
 
545
 
  $tinfo->{'path'}= $path;
546
 
  $tinfo->{'timezone'}= "GMT-3"; # for UNIX_TIMESTAMP tests to work
547
 
 
548
 
  $tinfo->{'slave_num'}= 0; # Default, no slave
549
 
  $tinfo->{'master_num'}= 1; # Default, 1 master
550
 
  if ( defined mtr_match_prefix($tname,"rpl") )
551
 
  {
552
 
    if ( $::opt_skip_rpl )
553
 
    {
554
 
      $tinfo->{'skip'}= 1;
555
 
      $tinfo->{'comment'}= "No replication tests(--skip-rpl)";
556
 
      return;
557
 
    }
558
 
 
559
 
    $tinfo->{'slave_num'}= 1; # Default for rpl* tests, use one slave
560
 
 
561
 
  }
562
 
 
563
 
  if ( defined mtr_match_prefix($tname,"federated") )
564
 
  {
565
 
    # Default, federated uses the first slave as it's federated database
566
 
    $tinfo->{'slave_num'}= 1;
567
 
  }
568
 
 
569
 
  my $master_opt_file= "$testdir/$tname-master.opt";
570
 
  my $slave_opt_file=  "$testdir/$tname-slave.opt";
571
 
  my $slave_mi_file=   "$testdir/$tname.slave-mi";
572
 
  my $master_sh=       "$testdir/$tname-master.sh";
573
 
  my $slave_sh=        "$testdir/$tname-slave.sh";
574
 
  my $disabled_file=   "$testdir/$tname.disabled";
575
 
  my $im_opt_file=     "$testdir/$tname-im.opt";
576
 
 
577
 
  $tinfo->{'master_opt'}= [];
578
 
  $tinfo->{'slave_opt'}=  [];
579
 
  $tinfo->{'slave_mi'}=   [];
580
 
 
581
 
 
582
 
  # Add suite opts
583
 
  foreach my $opt ( @$suite_opts )
584
 
  {
585
 
    mtr_verbose($opt);
586
 
    push(@{$tinfo->{'master_opt'}}, $opt);
587
 
    push(@{$tinfo->{'slave_opt'}}, $opt);
588
 
  }
589
 
 
590
 
  # Add master opts
591
 
  if ( -f $master_opt_file )
592
 
  {
593
 
 
594
 
    my $master_opt= mtr_get_opts_from_file($master_opt_file);
595
 
 
596
 
    foreach my $opt ( @$master_opt )
597
 
    {
598
 
      my $value;
599
 
 
600
 
      # The opt file is used both to send special options to the mysqld
601
 
      # as well as pass special test case specific options to this
602
 
      # script
603
 
 
604
 
      $value= mtr_match_prefix($opt, "--timezone=");
605
 
      if ( defined $value )
606
 
      {
607
 
        $tinfo->{'timezone'}= $value;
608
 
        next;
609
 
      }
610
 
 
611
 
      $value= mtr_match_prefix($opt, "--slave-num=");
612
 
      if ( defined $value )
613
 
      {
614
 
        $tinfo->{'slave_num'}= $value;
615
 
        next;
616
 
      }
617
 
 
618
 
      $value= mtr_match_prefix($opt, "--result-file=");
619
 
      if ( defined $value )
620
 
      {
621
 
        # Specifies the file mysqltest should compare
622
 
        # output against
623
 
        $tinfo->{'result_file'}= "r/$value.result";
624
 
        next;
625
 
      }
626
 
 
627
 
      # If we set default time zone, remove the one we have
628
 
      $value= mtr_match_prefix($opt, "--default-time-zone=");
629
 
      if ( defined $value )
630
 
      {
631
 
        # Set timezone for this test case to something different
632
 
        $tinfo->{'timezone'}= "GMT-8";
633
 
        # Fallthrough, add the --default-time-zone option
634
 
      }
635
 
 
636
 
      # The --restart option forces a restart even if no special
637
 
      # option is set. If the options are the same as next testcase
638
 
      # there is no need to restart after the testcase
639
 
      # has completed
640
 
      if ( $opt eq "--force-restart" )
641
 
      {
642
 
        $tinfo->{'force_restart'}= 1;
643
 
        next;
644
 
      }
645
 
 
646
 
      # Ok, this was a real option, add it
647
 
      push(@{$tinfo->{'master_opt'}}, $opt);
648
 
    }
649
 
  }
650
 
 
651
 
  # Add slave opts
652
 
  if ( -f $slave_opt_file )
653
 
  {
654
 
    my $slave_opt= mtr_get_opts_from_file($slave_opt_file);
655
 
 
656
 
    foreach my $opt ( @$slave_opt )
657
 
    {
658
 
      # If we set default time zone, remove the one we have
659
 
      my $value= mtr_match_prefix($opt, "--default-time-zone=");
660
 
      $tinfo->{'slave_opt'}= [] if defined $value;
661
 
    }
662
 
    push(@{$tinfo->{'slave_opt'}}, @$slave_opt);
663
 
  }
664
 
 
665
 
  if ( -f $slave_mi_file )
666
 
  {
667
 
    $tinfo->{'slave_mi'}= mtr_get_opts_from_file($slave_mi_file);
668
 
  }
669
 
 
670
 
  if ( -f $master_sh )
671
 
  {
672
 
    if ( $::glob_win32_perl )
673
 
    {
674
 
      $tinfo->{'skip'}= 1;
675
 
      $tinfo->{'comment'}= "No tests with sh scripts on Windows";
676
 
      return;
677
 
    }
678
 
    else
679
 
    {
680
 
      $tinfo->{'master_sh'}= $master_sh;
681
 
    }
682
 
  }
683
 
 
684
 
  if ( -f $slave_sh )
685
 
  {
686
 
    if ( $::glob_win32_perl )
687
 
    {
688
 
      $tinfo->{'skip'}= 1;
689
 
      $tinfo->{'comment'}= "No tests with sh scripts on Windows";
690
 
      return;
691
 
    }
692
 
    else
693
 
    {
694
 
      $tinfo->{'slave_sh'}= $slave_sh;
695
 
    }
696
 
  }
697
 
 
698
 
  if ( -f $im_opt_file )
699
 
  {
700
 
    $tinfo->{'im_opts'} = mtr_get_opts_from_file($im_opt_file);
701
 
  }
702
 
  else
703
 
  {
704
 
    $tinfo->{'im_opts'} = [];
705
 
  }
706
 
 
707
 
  # FIXME why this late?
708
 
  my $marked_as_disabled= 0;
709
 
  if ( $disabled->{$tname} )
710
 
  {
711
 
    $marked_as_disabled= 1;
712
 
    $tinfo->{'comment'}= $disabled->{$tname};
713
 
  }
714
 
 
715
 
  if ( -f $disabled_file )
716
 
  {
717
 
    $marked_as_disabled= 1;
718
 
    $tinfo->{'comment'}= mtr_fromfile($disabled_file);
719
 
  }
720
 
 
721
 
  # If test was marked as disabled, either opt_enable_disabled is off and then
722
 
  # we skip this test, or it is on and then we run this test but warn
723
 
 
724
 
  if ( $marked_as_disabled )
725
 
  {
726
 
    if ( $::opt_enable_disabled )
727
 
    {
728
 
      $tinfo->{'dont_skip_though_disabled'}= 1;
729
 
    }
730
 
    else
731
 
    {
732
 
      $tinfo->{'skip'}= 1;
733
 
      $tinfo->{'disable'}= 1;   # Sub type of 'skip'
734
 
      return;
735
 
    }
736
 
  }
737
 
 
738
 
  if ( $component_id eq 'im' )
739
 
  {
740
 
    if ( $::glob_use_embedded_server )
741
 
    {
742
 
      $tinfo->{'skip'}= 1;
743
 
      $tinfo->{'comment'}= "No IM with embedded server";
744
 
      return;
745
 
    }
746
 
    elsif ( $::opt_ps_protocol )
747
 
    {
748
 
      $tinfo->{'skip'}= 1;
749
 
      $tinfo->{'comment'}= "No IM with --ps-protocol";
750
 
      return;
751
 
    }
752
 
    elsif ( $::opt_skip_im )
753
 
    {
754
 
      $tinfo->{'skip'}= 1;
755
 
      $tinfo->{'comment'}= "No IM tests(--skip-im)";
756
 
      return;
757
 
    }
758
 
  }
759
 
  else
760
 
  {
761
 
    mtr_options_from_test_file($tinfo,"$testdir/${tname}.test");
762
 
 
763
 
    if ( defined $::used_default_engine )
764
 
    {
765
 
      # Different default engine is used
766
 
      # tag test to require that engine
767
 
      $tinfo->{'ndb_test'}= 1
768
 
        if ( $::used_default_engine =~ /^ndb/i );
769
 
 
770
 
      $tinfo->{'innodb_test'}= 1
771
 
        if ( $::used_default_engine =~ /^innodb/i );
772
 
    }
773
 
 
774
 
    #enable federated for this test
775
 
    if ($tinfo->{'federated_test'})
776
 
    {
777
 
      push(@{$tinfo->{'master_opt'}}, "--loose-federated");
778
 
      push(@{$tinfo->{'slave_opt'}}, "--loose-federated");
779
 
    }
780
 
 
781
 
    if ( $tinfo->{'big_test'} and ! $::opt_big_test )
782
 
    {
783
 
      $tinfo->{'skip'}= 1;
784
 
      $tinfo->{'comment'}= "Test need 'big-test' option";
785
 
      return;
786
 
    }
787
 
 
788
 
    if ( $tinfo->{'ndb_extra'} and ! $::opt_ndb_extra_test )
789
 
    {
790
 
      $tinfo->{'skip'}= 1;
791
 
      $tinfo->{'comment'}= "Test need 'ndb_extra' option";
792
 
      return;
793
 
    }
794
 
 
795
 
    if ( $tinfo->{'require_manager'} )
796
 
    {
797
 
      $tinfo->{'skip'}= 1;
798
 
      $tinfo->{'comment'}= "Test need the _old_ manager(to be removed)";
799
 
      return;
800
 
    }
801
 
 
802
 
    if ( $tinfo->{'need_debug'} && ! $::debug_compiled_binaries )
803
 
    {
804
 
      $tinfo->{'skip'}= 1;
805
 
      $tinfo->{'comment'}= "Test need debug binaries";
806
 
      return;
807
 
    }
808
 
 
809
 
    if ( $tinfo->{'ndb_test'} )
810
 
    {
811
 
      # This is a NDB test
812
 
      if ( ! $::glob_ndbcluster_supported )
813
 
      {
814
 
        # Ndb is not supported, skip it
815
 
        $tinfo->{'skip'}= 1;
816
 
        $tinfo->{'comment'}= "No ndbcluster support";
817
 
        return;
818
 
      }
819
 
      elsif ( $::opt_skip_ndbcluster )
820
 
      {
821
 
        # All ndb test's should be skipped
822
 
        $tinfo->{'skip'}= 1;
823
 
        $tinfo->{'comment'}= "No ndbcluster tests(--skip-ndbcluster)";
824
 
        return;
825
 
      }
826
 
      # Ndb tests run with two mysqld masters
827
 
      $tinfo->{'master_num'}= 2;
828
 
    }
829
 
    else
830
 
    {
831
 
      # This is not a ndb test
832
 
      if ( $::opt_with_ndbcluster_only )
833
 
      {
834
 
        # Only the ndb test should be run, all other should be skipped
835
 
        $tinfo->{'skip'}= 1;
836
 
        $tinfo->{'comment'}= "Only ndbcluster tests(--with-ndbcluster-only)";
837
 
        return;
838
 
      }
839
 
    }
840
 
 
841
 
    if ( $tinfo->{'innodb_test'} )
842
 
    {
843
 
      # This is a test that need innodb
844
 
      if ( $::mysqld_variables{'innodb'} ne "TRUE" )
845
 
      {
846
 
        # innodb is not supported, skip it
847
 
        $tinfo->{'skip'}= 1;
848
 
        $tinfo->{'comment'}= "No innodb support";
849
 
        return;
850
 
      }
851
 
    }
852
 
 
853
 
    if ( $tinfo->{'need_binlog'} )
854
 
    {
855
 
      if (grep(/^--skip-log-bin/,  @::opt_extra_mysqld_opt) )
856
 
      {
857
 
        $tinfo->{'skip'}= 1;
858
 
        $tinfo->{'comment'}= "Test need binlog";
859
 
        return;
860
 
      }
861
 
    }
862
 
    else
863
 
    {
864
 
      if ( $::mysql_version_id >= 50100 )
865
 
      {
866
 
        # Test does not need binlog, add --skip-binlog to
867
 
        # the options used when starting it
868
 
        push(@{$tinfo->{'master_opt'}}, "--skip-log-bin");
869
 
      }
870
 
    }
871
 
 
872
 
  }
873
 
}
874
 
 
875
 
 
876
 
# List of tags in the .test files that if found should set
877
 
# the specified value in "tinfo"
878
 
our @tags=
879
 
(
880
 
 
881
 
 ["include/have_binlog_format_row.inc", "binlog_formats", ["row"]],
882
 
 ["include/have_binlog_format_statement.inc", "binlog_formats", ["statement"]],
883
 
 ["include/have_binlog_format_mixed.inc", "binlog_formats", ["mixed"]],
884
 
 ["include/have_binlog_format_mixed_or_row.inc",
885
 
  "binlog_formats", ["mixed", "row"]],
886
 
 ["include/have_binlog_format_mixed_or_statement.inc",
887
 
  "binlog_formats", ["mixed", "statement"]],
888
 
 ["include/have_binlog_format_row_or_statement.inc",
889
 
  "binlog_formats", ["row", "statement"]],
890
 
 
891
 
 ["include/have_innodb.inc", "innodb_test", 1],
892
 
 ["include/have_log_bin.inc", "need_binlog", 1],
893
 
 ["include/big_test.inc", "big_test", 1],
894
 
 ["include/have_debug.inc", "need_debug", 1],
895
 
 ["include/have_ndb.inc", "ndb_test", 1],
896
 
 ["include/have_multi_ndb.inc", "ndb_test", 1],
897
 
 ["include/have_ndb_extra.inc", "ndb_extra", 1],
898
 
 ["include/ndb_master-slave.inc", "ndb_test", 1],
899
 
 ["require_manager", "require_manager", 1],
900
 
 ["include/federated.inc", "federated_test", 1],
901
 
 ["include/have_federated_db.inc", "federated_test", 1],
902
 
);
903
 
 
904
 
sub mtr_options_from_test_file($$) {
905
 
  my $tinfo= shift;
906
 
  my $file= shift;
907
 
  #mtr_verbose("$file");
908
 
  my $F= IO::File->new($file) or mtr_error("can't open file \"$file\": $!");
909
 
 
910
 
  while ( my $line= <$F> )
911
 
  {
912
 
 
913
 
    # Skip line if it start's with #
914
 
    next if ( $line =~ /^#/ );
915
 
 
916
 
    # Match this line against tag in "tags" array
917
 
    foreach my $tag (@tags)
918
 
    {
919
 
      if ( index($line, $tag->[0]) >= 0 )
920
 
      {
921
 
          # Tag matched, assign value to "tinfo"
922
 
        $tinfo->{"$tag->[1]"}= $tag->[2];
923
 
      }
924
 
    }
925
 
 
926
 
    # If test sources another file, open it as well
927
 
    if ( $line =~ /^\-\-([[:space:]]*)source(.*)$/ or
928
 
         $line =~ /^([[:space:]]*)source(.*);$/ )
929
 
    {
930
 
      my $value= $2;
931
 
      $value =~ s/^\s+//;  # Remove leading space
932
 
      $value =~ s/[[:space:]]+$//;  # Remove ending space
933
 
 
934
 
      my $sourced_file= "$::glob_mysql_test_dir/$value";
935
 
      if ( -f $sourced_file )
936
 
      {
937
 
        # Only source the file if it exists, we may get
938
 
        # false positives in the regexes above if someone
939
 
        # writes "source nnnn;" in a test case(such as mysqltest.test)
940
 
        mtr_options_from_test_file($tinfo, $sourced_file);
941
 
      }
942
 
    }
943
 
  }
944
 
}
945
 
 
946
 
 
947
 
sub print_testcases {
948
 
  my (@cases)= @_;
949
 
 
950
 
  print "=" x 60, "\n";
951
 
  foreach my $test (@cases){
952
 
    print "[", $test->{name}, "]", "\n";
953
 
    while ((my ($key, $value)) = each(%$test)) {
954
 
      print " ", $key, "=";
955
 
      if (ref $value eq "ARRAY") {
956
 
        print join(", ", @$value);
957
 
      } else {
958
 
        print $value;
959
 
      }
960
 
      print "\n";
961
 
    }
962
 
    print "\n";
963
 
  }
964
 
  print "=" x 60, "\n";
965
 
}
966
 
 
967
 
 
968
 
1;