OSDN Git Service

* gcc.c-torture/execute/builtins/memops-asm.c: Set inside_main.
[pf3gnuchains/gcc-fork.git] / gcc / testsuite / lib / gcc-dg.exp
1 #   Copyright (C) 1997, 1999, 2000, 2003, 2004, 2005, 2006, 2007
2 #   Free Software Foundation, Inc.
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; either version 3 of the License, or
7 # (at your option) any later version.
8 #
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 # GNU General Public License for more details.
13 #
14 # You should have received a copy of the GNU General Public License
15 # along with GCC; see the file COPYING3.  If not see
16 # <http://www.gnu.org/licenses/>.
17
18 load_lib dg.exp
19 load_lib file-format.exp
20 load_lib target-supports.exp
21 load_lib target-supports-dg.exp
22 load_lib scanasm.exp
23 load_lib scanrtl.exp
24 load_lib scantree.exp
25 load_lib scanipa.exp
26 load_lib prune.exp
27 load_lib libgloss.exp
28 load_lib target-libpath.exp
29 load_lib torture-options.exp
30
31 # We set LC_ALL and LANG to C so that we get the same error messages as expected.
32 setenv LC_ALL C
33 setenv LANG C
34
35 if [info exists TORTURE_OPTIONS] {
36     set DG_TORTURE_OPTIONS $TORTURE_OPTIONS
37 } else {
38     # It is theoretically beneficial to group all of the O2/O3 options together,
39     # as in many cases the compiler will generate identical executables for
40     # all of them--and the c-torture testsuite will skip testing identical
41     # executables multiple times.
42     # Also note that -finline-functions is explicitly included in one of the
43     # items below, even though -O3 is also specified, because some ports may
44     # choose to disable inlining functions by default, even when optimizing.
45     set DG_TORTURE_OPTIONS [list \
46         { -O0 } \
47         { -O1 } \
48         { -O2 } \
49         { -O3 -fomit-frame-pointer } \
50         { -O3 -fomit-frame-pointer -funroll-loops } \
51         { -O3 -fomit-frame-pointer -funroll-all-loops -finline-functions } \
52         { -O3 -g } \
53         { -Os } ]
54 }
55
56 global GCC_UNDER_TEST
57 if ![info exists GCC_UNDER_TEST] {
58     set GCC_UNDER_TEST "[find_gcc]"
59 }
60
61 global orig_environment_saved
62
63 # This file may be sourced, so don't override environment settings
64 # that have been previously setup.
65 if { $orig_environment_saved == 0 } {
66     append ld_library_path [gcc-set-multilib-library-path $GCC_UNDER_TEST]
67     set_ld_library_path_env_vars
68 }
69
70 # Define gcc callbacks for dg.exp.
71
72 proc gcc-dg-test-1 { target_compile prog do_what extra_tool_flags } {
73     # Set up the compiler flags, based on what we're going to do.
74
75     set options [list]
76
77     # Tests should be able to use "dg-do repo".  However, the dg test
78     # driver checks the argument to dg-do against a list of acceptable
79     # options, and "repo" is not among them.  Therefore, we resort to
80     # this ugly approach.
81     if [string match "*-frepo*" $extra_tool_flags] then {
82         set do_what "repo"
83     }
84
85     switch $do_what {
86         "preprocess" {
87             set compile_type "preprocess"
88             set output_file "[file rootname [file tail $prog]].i"
89         }
90         "compile" {
91             set compile_type "assembly"
92             set output_file "[file rootname [file tail $prog]].s"
93         }
94         "assemble" {
95             set compile_type "object"
96             set output_file "[file rootname [file tail $prog]].o"
97         }
98         "precompile" {
99             set compile_type "precompiled_header"
100             set output_file "[file tail $prog].gch"
101         }
102         "link" {
103             set compile_type "executable"
104             set output_file "[file rootname [file tail $prog]].exe"
105             # The following line is needed for targets like the i960 where
106             # the default output file is b.out.  Sigh.
107         }
108         "repo" {
109             set compile_type "object"
110             set output_file "[file rootname [file tail $prog]].o"
111         }
112         "run" {
113             set compile_type "executable"
114             # FIXME: "./" is to cope with "." not being in $PATH.
115             # Should this be handled elsewhere?
116             # YES.
117             set output_file "./[file rootname [file tail $prog]].exe"
118             # This is the only place where we care if an executable was
119             # created or not.  If it was, dg.exp will try to run it.
120             catch { remote_file build delete $output_file }
121         }
122         default {
123             perror "$do_what: not a valid dg-do keyword"
124             return ""
125         }
126     }
127
128     if { $extra_tool_flags != "" } {
129         lappend options "additional_flags=$extra_tool_flags"
130     }
131
132     set comp_output [$target_compile "$prog" "$output_file" "$compile_type" $options]
133
134     # Look for an internal compiler error, which sometimes masks the fact
135     # that we didn't get an expected error message.  XFAIL an ICE via
136     # dg-xfail-if and use { dg-prune-output ".*internal compiler error.*" }
137     # to avoid a second failure for excess errors.
138     if [string match "*internal compiler error*" $comp_output] {
139         upvar 2 name name
140         fail "$name (internal compiler error)"
141     }
142
143     if { $do_what == "repo" } {
144         set object_file "$output_file"
145         set output_file "[file rootname [file tail $prog]].exe"
146         set comp_output \
147             [ concat $comp_output \
148                   [$target_compile "$object_file" "$output_file" \
149                        "executable" $options] ]
150     }
151
152     return [list $comp_output $output_file]
153 }
154
155 proc gcc-dg-test { prog do_what extra_tool_flags } {
156     return [gcc-dg-test-1 gcc_target_compile $prog $do_what $extra_tool_flags]
157 }
158
159 proc gcc-dg-prune { system text } {
160     global additional_prunes
161
162     set text [prune_gcc_output $text]
163
164     foreach p $additional_prunes {
165         if { [string length $p] > 0 } {
166             # Following regexp matches a complete line containing $p.
167             regsub -all "(^|\n)\[^\n\]*$p\[^\n\]*" $text "" text
168         }
169     }
170
171     # If we see "region xxx is full" then the testcase is too big for ram.
172     # This is tricky to deal with in a large testsuite like c-torture so
173     # deal with it here.  Just mark the testcase as unsupported.
174     if [regexp "(^|\n)\[^\n\]*: region \[^\n\]* is full" $text] {
175         # The format here is important.  See dg.exp.
176         return "::unsupported::memory full"
177     }
178
179     # Likewise, if we see ".text exceeds local store range" or
180     # similar.
181     if {[string match "spu-*" $system] && \
182             [string match "*exceeds local store range*" $text]} {
183         # The format here is important.  See dg.exp.
184         return "::unsupported::memory full"
185     }
186
187     return $text
188 }
189
190 # Replace ${tool}_load with a wrapper to provide for an expected nonzero
191 # exit status.  Multiple languages include this file so this handles them
192 # all, not just gcc.
193 if { [info procs ${tool}_load] != [list] \
194       && [info procs saved_${tool}_load] == [list] } {
195     rename ${tool}_load saved_${tool}_load
196
197     proc ${tool}_load { program args } {
198         global tool
199         global shouldfail
200         set result [eval [list saved_${tool}_load $program] $args]
201         if { $shouldfail != 0 } {
202             switch [lindex $result 0] {
203                 "pass" { set status "fail" }
204                 "fail" { set status "pass" }
205             }
206             set result [list $status [lindex $result 1]]
207         }
208         return $result
209     }
210 }
211
212 # Utility routines.
213
214 #
215 # search_for -- looks for a string match in a file
216 #
217 proc search_for { file pattern } {
218     set fd [open $file r]
219     while { [gets $fd cur_line]>=0 } {
220         if [string match "*$pattern*" $cur_line] then {
221             close $fd
222             return 1
223         }
224     }
225     close $fd
226     return 0
227 }
228
229 # Modified dg-runtest that can cycle through a list of optimization options
230 # as c-torture does.
231 proc gcc-dg-runtest { testcases default-extra-flags } {
232     global runtests
233
234     # Some callers set torture options themselves; don't override those.
235     set existing_torture_options [torture-options-exist]
236     if { $existing_torture_options == 0 } {
237         global DG_TORTURE_OPTIONS
238         torture-init
239         set-torture-options $DG_TORTURE_OPTIONS
240     }
241     dump-torture-options
242
243     foreach test $testcases {
244         global torture_with_loops torture_without_loops
245         # If we're only testing specific files and this isn't one of
246         # them, skip it.
247         if ![runtest_file_p $runtests $test] {
248             continue
249         }
250
251         # Look for a loop within the source code - if we don't find one,
252         # don't pass -funroll[-all]-loops.
253         if [expr [search_for $test "for*("]+[search_for $test "while*("]] {
254             set option_list $torture_with_loops
255         } else {
256             set option_list $torture_without_loops
257         }
258
259         set nshort [file tail [file dirname $test]]/[file tail $test]
260
261         foreach flags $option_list {
262             verbose "Testing $nshort, $flags" 1
263             dg-test $test $flags ${default-extra-flags}
264         }
265     }
266
267     if { $existing_torture_options == 0 } {
268         torture-finish
269     }
270 }
271
272 proc gcc-dg-debug-runtest { target_compile trivial opt_opts testcases } {
273     global srcdir subdir
274
275     if ![info exists DEBUG_TORTURE_OPTIONS] {
276         set DEBUG_TORTURE_OPTIONS ""
277         foreach type {-gdwarf-2 -gstabs -gstabs+ -gxcoff -gxcoff+ -gcoff} {
278             set comp_output [$target_compile \
279                     "$srcdir/$subdir/$trivial" "trivial.S" assembly \
280                     "additional_flags=$type"]
281             if { ! [string match "*: target system does not support the * debug format*" \
282                     $comp_output] } {
283                 remove-build-file "trivial.S"
284                 foreach level {1 "" 3} {
285                     lappend DEBUG_TORTURE_OPTIONS [list "${type}${level}"]
286                     foreach opt $opt_opts {
287                         lappend DEBUG_TORTURE_OPTIONS \
288                                 [list "${type}${level}" "$opt" ]
289                     }
290                 }
291             }
292         }
293     }
294
295     verbose -log "Using options $DEBUG_TORTURE_OPTIONS"
296
297     global runtests
298
299     foreach test $testcases {
300         # If we're only testing specific files and this isn't one of
301         # them, skip it.
302         if ![runtest_file_p $runtests $test] {
303             continue
304         }
305
306         set nshort [file tail [file dirname $test]]/[file tail $test]
307
308         foreach flags $DEBUG_TORTURE_OPTIONS {
309             set doit 1
310
311             # These tests check for information which may be deliberately
312             # suppressed at -g1.
313             if { ([string match {*/debug-[126].c} "$nshort"] \
314                    || [string match {*/enum-1.c} "$nshort"] \
315                    || [string match {*/enum-[12].C} "$nshort"]) \
316                     && [string match "*1" [lindex "$flags" 0] ] } {
317                 set doit 0
318             }
319
320     # High optimization can remove the variable whose existence is tested.
321     # Dwarf debugging with commentary (-dA) preserves the symbol name in the
322     # assembler output, but stabs debugging does not.
323     # http://gcc.gnu.org/ml/gcc-regression/2003-04/msg00095.html
324             if { [string match {*/debug-[12].c} "$nshort"] \
325                     && [string match "*O*" "$flags"] \
326                     && ( [string match "*coff*" "$flags"] \
327                          || [string match "*stabs*" "$flags"] ) } {
328                 set doit 0
329             }
330
331             if { $doit } {
332                 verbose -log "Testing $nshort, $flags" 1
333                 dg-test $test $flags ""
334             }
335         }
336     }
337 }
338
339 # Prune any messages matching ARGS[1] (a regexp) from test output.
340 proc dg-prune-output { args } {
341     global additional_prunes
342
343     if { [llength $args] != 2 } {
344         error "[lindex $args 1]: need one argument"
345         return
346     }
347
348     lappend additional_prunes [lindex $args 1]
349 }
350
351 # Remove files matching the pattern from the build machine.
352 proc remove-build-file { pat } {
353     verbose "remove-build-file `$pat'" 2
354     set file_list "[glob -nocomplain $pat]"
355     verbose "remove-build-file `$file_list'" 2
356     foreach output_file $file_list {
357         remote_file build delete $output_file
358     }
359 }
360
361 # Remove runtime-generated profile file for the current test.
362 proc cleanup-profile-file { } {
363     remove-build-file "mon.out"
364     remove-build-file "gmon.out"
365 }
366
367 # Remove compiler-generated coverage files for the current test.
368 proc cleanup-coverage-files { } {
369     # This assumes that we are two frames down from dg-test or some other proc
370     # that stores the filename of the testcase in a local variable "name".
371     # A cleaner solution would require a new DejaGnu release.
372     upvar 2 name testcase
373     remove-build-file "[file rootname [file tail $testcase]].gc??"
374
375     # Clean up coverage files for additional source files.
376     if [info exists additional_sources] {
377         foreach srcfile $additional_sources {
378             remove-build-file "[file rootname [file tail $srcfile]].gc??"
379         }
380     }
381 }
382
383 # Remove compiler-generated files from -repo for the current test.
384 proc cleanup-repo-files { } {
385     # This assumes that we are two frames down from dg-test or some other proc
386     # that stores the filename of the testcase in a local variable "name".
387     # A cleaner solution would require a new DejaGnu release.
388     upvar 2 name testcase
389     remove-build-file "[file rootname [file tail $testcase]].o"
390     remove-build-file "[file rootname [file tail $testcase]].rpo"
391
392     # Clean up files for additional source files.
393     if [info exists additional_sources] {
394         foreach srcfile $additional_sources {
395             remove-build-file "[file rootname [file tail $srcfile]].o"
396             remove-build-file "[file rootname [file tail $srcfile]].rpo"
397         }
398     }
399 }
400
401 # Remove compiler-generated RTL dump files for the current test.
402 #
403 # SUFFIX is the filename suffix pattern.
404 proc cleanup-rtl-dump { suffix } {
405   cleanup-dump "\[0-9\]\[0-9\]\[0-9\]r.$suffix"
406 }
407
408 # Remove a specific tree dump file for the current test.
409 #
410 # SUFFIX is the tree dump file suffix pattern.
411 proc cleanup-tree-dump { suffix } {
412   cleanup-dump "\[0-9\]\[0-9\]\[0-9\]t.$suffix"
413 }
414
415 # Remove a specific ipa dump file for the current test.
416 #
417 # SUFFIX is the ipa dump file suffix pattern.
418 proc cleanup-ipa-dump { suffix } {
419   cleanup-dump "\[0-9\]\[0-9\]\[0-9\]i.$suffix"
420 }
421
422 # Remove all dump files with the provided suffix.
423 proc cleanup-dump { suffix } {
424     # This assumes that we are three frames down from dg-test or some other
425     # proc that stores the filename of the testcase in a local variable
426     # "name".  A cleaner solution would require a new DejaGnu release.
427     upvar 3 name testcase
428     # The name might include a list of options; extract the file name.
429     set src [file tail [lindex $testcase 0]]
430     remove-build-file "[file tail $src].$suffix"
431
432     # Clean up dump files for additional source files.
433     if [info exists additional_sources] {
434         foreach srcfile $additional_sources {
435             remove-build-file "[file tail $srcfile].$suffix"
436         }
437     }
438 }
439
440 # Remove files kept by --save-temps for the current test.
441 #
442 # Currently this is only .i, .ii and .s files, but more can be added
443 # if there are tests generating them.
444 # ARGS is a list of suffixes to NOT delete.
445 proc cleanup-saved-temps { args } {
446     global additional_sources
447     set suffixes {}
448
449     # add the to-be-kept suffixes
450     foreach suffix {".ii" ".i" ".s"} {
451         if {[lsearch $args $suffix] < 0} {
452             lappend suffixes $suffix
453         }
454     }
455
456     # This assumes that we are two frames down from dg-test or some other proc
457     # that stores the filename of the testcase in a local variable "name".
458     # A cleaner solution would require a new DejaGnu release.
459     upvar 2 name testcase
460     foreach suffix $suffixes {
461         remove-build-file "[file rootname [file tail $testcase]]$suffix"
462     }
463
464     # Clean up saved temp files for additional source files.
465     if [info exists additional_sources] {
466         foreach srcfile $additional_sources {
467             foreach suffix $suffixes {
468                 remove-build-file "[file rootname [file tail $srcfile]]$suffix"
469             }
470         }
471     }
472 }
473
474 # Remove files for specified Fortran modules.
475 proc cleanup-modules { modlist } {
476     foreach modname $modlist {
477         remove-build-file [string tolower $modname].mod
478     }
479 }
480
481 # Scan Fortran modules for a given regexp.
482 #
483 # Argument 0 is the module name
484 # Argument 1 is the regexp to match
485 proc scan-module { args } {
486     set modfilename [string tolower [lindex $args 0]].mod
487     set fd [open $modfilename r]
488     set text [read $fd]
489     close $fd
490
491     upvar 2 name testcase
492     if [regexp -- [lindex $args 1] $text] {
493       pass "$testcase scan-module [lindex $args 1]"
494     } else {
495       fail "$testcase scan-module [lindex $args 1]"
496     }
497 }
498
499 # Verify that the compiler output file exists, invoked via dg-final.
500 proc output-exists { args } {
501     # Process an optional target or xfail list.
502     if { [llength $args] >= 1 } {
503         switch [dg-process-target [lindex $args 0]] {
504             "S" { }
505             "N" { return }
506             "F" { setup_xfail "*-*-*" }
507             "P" { }
508         }
509     }
510
511     # Access variables from gcc-dg-test-1.
512     upvar 2 name testcase
513     upvar 2 output_file output_file
514
515     if [file exists $output_file] {
516         pass "$testcase output-exists $output_file"
517     } else {
518         fail "$testcase output-exists $output_file"
519     }
520 }
521
522 # Verify that the compiler output file does not exist, invoked via dg-final.
523 proc output-exists-not { args } {
524     # Process an optional target or xfail list.
525     if { [llength $args] >= 1 } {
526         switch [dg-process-target [lindex $args 0]] {
527             "S" { }
528             "N" { return }
529             "F" { setup_xfail "*-*-*" }
530             "P" { }
531         }
532     }
533
534     # Access variables from gcc-dg-test-1.
535     upvar 2 name testcase
536     upvar 2 output_file output_file
537
538     if [file exists $output_file] {
539         fail "$testcase output-exists-not $output_file"
540     } else {
541         pass "$testcase output-exists-not $output_file"
542     }
543 }
544
545 # We need to make sure that additional_* are cleared out after every
546 # test.  It is not enough to clear them out *before* the next test run
547 # because gcc-target-compile gets run directly from some .exp files
548 # (outside of any test).  (Those uses should eventually be eliminated.)
549
550 # Because the DG framework doesn't provide a hook that is run at the
551 # end of a test, we must replace dg-test with a wrapper.
552
553 if { [info procs saved-dg-test] == [list] } {
554     rename dg-test saved-dg-test
555
556     proc dg-test { args } {
557         global additional_files
558         global additional_sources
559         global additional_prunes
560         global errorInfo
561         global compiler_conditional_xfail_data
562         global shouldfail
563
564         if { [ catch { eval saved-dg-test $args } errmsg ] } {
565             set saved_info $errorInfo
566             set additional_files ""
567             set additional_sources ""
568             set additional_prunes ""
569             set shouldfail 0
570             if [info exists compiler_conditional_xfail_data] {
571                 unset compiler_conditional_xfail_data
572             }
573             error $errmsg $saved_info
574         }
575         set additional_files ""
576         set additional_sources ""
577         set additional_prunes ""
578         set shouldfail 0
579         if [info exists compiler_conditional_xfail_data] {
580             unset compiler_conditional_xfail_data
581         }
582     }
583 }
584
585 if { [info procs saved-dg-warning] == [list] \
586      && [info exists gcc_warning_prefix] } {
587     rename dg-warning saved-dg-warning
588
589     proc dg-warning { args } {
590         # Make this variable available here and to the saved proc.
591         upvar dg-messages dg-messages
592         global gcc_warning_prefix
593
594         process-message saved-dg-warning "$gcc_warning_prefix" "$args"
595     }
596 }
597
598 if { [info procs saved-dg-error] == [list] \
599      && [info exists gcc_error_prefix] } {
600     rename dg-error saved-dg-error
601
602     proc dg-error { args } {
603         # Make this variable available here and to the saved proc.
604         upvar dg-messages dg-messages
605         global gcc_error_prefix
606
607         process-message saved-dg-error "$gcc_error_prefix" "$args"
608     }
609 }
610
611 # Modify the regular expression saved by a DejaGnu message directive to
612 # include a prefix and to force the expression to match a single line.
613 # MSGPROC is the procedure to call.
614 # MSGPREFIX is the prefix to prepend.
615 # DGARGS is the original argument list.
616
617 proc process-message { msgproc msgprefix dgargs } {
618     upvar dg-messages dg-messages
619
620     # Process the dg- directive, including adding the regular expression
621     # to the new message entry in dg-messages.
622     set msgcnt [llength ${dg-messages}]
623     catch { eval $msgproc $dgargs }
624
625     # If the target expression wasn't satisfied there is no new message.
626     if { [llength ${dg-messages}] == $msgcnt } {
627         return;
628     }
629
630     # Prepend the message prefix to the regular expression and make
631     # it match a single line.
632     set newentry [lindex ${dg-messages} end]
633     set expmsg [lindex $newentry 2]
634     set expmsg "$msgprefix\[^\n]*$expmsg"
635     set newentry [lreplace $newentry 2 2 $expmsg]
636     set dg-messages [lreplace ${dg-messages} end end $newentry]
637     verbose "process-message:\n${dg-messages}" 2
638 }
639
640 # Look for messages that don't have standard prefixes.
641
642 proc dg-message { args } {
643     upvar dg-messages dg-messages
644     process-message saved-dg-warning "" $args
645 }
646
647 set additional_prunes ""