Update year range in copyright notice of all files.
[external/binutils.git] / binutils / testsuite / lib / utils-lib.exp
1 # Copyright (C) 1993-2017 Free Software Foundation, Inc.
2
3 # This program is free software; you can redistribute it and/or modify
4 # it under the terms of the GNU General Public License as published by
5 # the Free Software Foundation; either version 3 of the License, or
6 # (at your option) any later version.
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 Street - Fifth Floor, Boston, MA 02110-1301, USA.
16
17 # Please email any bugs, comments, and/or additions to this file to:
18 # bug-dejagnu@prep.ai.mit.edu
19
20 # This file was written by Rob Savoye <rob@cygnus.com>
21 # and extended by Ian Lance Taylor <ian@cygnus.com>
22
23 proc load_common_lib { name } {
24     load_lib $name
25 }
26
27 load_common_lib binutils-common.exp
28
29 proc binutil_version { prog } {
30     if ![is_remote host] {
31         set path [which $prog]
32         if {$path == 0} then {
33             perror "$prog can't be run, file not found."
34             return ""
35         }
36     } else {
37         set path $prog
38     }
39     set state [remote_exec host $prog --version]
40     set tmp "[lindex $state 1]\n"
41     # Should find a way to discard constant parts, keep whatever's
42     # left, so the version string could be almost anything at all...
43     regexp "\[^\n\]* (cygnus-|)(\[-0-9.a-zA-Z-\]+)\[\r\n\].*" "$tmp" version cyg number
44     if ![info exists number] then {
45         return "$path (no version number)\n"
46     }
47     return "$path $number\n"
48 }
49
50 #
51 # default_binutils_run
52 #       run a program, returning the output
53 #       sets binutils_run_failed if the program does not exist
54 #
55 proc default_binutils_run { prog progargs } {
56     global binutils_run_failed
57     global host_triplet
58
59     set binutils_run_failed 0
60
61     if ![is_remote host] {
62         if {[which $prog] == 0} then {
63             perror "$prog does not exist"
64             set binutils_run_failed 1
65             return ""
66         }
67     }
68
69     # For objdump, automatically translate standard section
70     # names to the targets one, if they are different.
71     set sect_names [get_standard_section_names]
72     if { $sect_names != "" && [string match "*objdump" $prog] } {
73         regsub -- "-j \\.text" $progargs "-j [lindex $sect_names 0]" progargs
74         regsub -- "-j \\.data" $progargs "-j [lindex $sect_names 1]" progargs
75         regsub -- "-j \\.bss"  $progargs "-j [lindex $sect_names 2]" progargs
76     }
77
78     send_log "$prog $progargs\n"
79     verbose "$prog $progargs"
80
81     # Gotta quote dollar-signs because they get mangled by the
82     # shell otherwise.
83     regsub -all "\\$" "$progargs" "\\$" progargs
84
85     set state [remote_exec host $prog $progargs]
86     set exec_output [prune_warnings [lindex $state 1]]
87     if {![string match "" $exec_output]} then {
88         send_log "$exec_output\n"
89         verbose "$exec_output"
90     } else {
91         if { [lindex $state 0] != 0 } {
92             set exec_output "$prog exited with status [lindex $state 0]"
93             send_log "$exec_output\n"
94             verbose "$exec_output"
95         }
96     }
97     return $exec_output
98 }
99
100 #
101 # default_binutils_assemble_flags
102 #       assemble a file
103 #
104 proc default_binutils_assemble_flags { source object asflags } {
105     global srcdir
106     global host_triplet
107
108     # The HPPA assembler syntax is a little different than most, to make
109     # the test source file assemble we need to run it through sed.
110     #
111     # This is a hack in that it won't scale well if other targets need
112     # similar transformations to assemble.  We'll generalize the hack
113     # if/when other targets need similar handling.
114     if { [istarget "hppa*-*-*"] && ![istarget "*-*-linux*" ] } then {
115         set sed_file $srcdir/config/hppa.sed
116         send_log "sed -f $sed_file < $source > asm.s\n"
117         verbose "sed -f $sed_file < $source > asm.s"
118         catch "exec sed -f $sed_file < $source > asm.s"
119         set source asm.s
120     }
121
122     set exec_output [target_assemble $source $object $asflags]
123     set exec_output [prune_warnings $exec_output]
124
125     if [string match "" $exec_output] {
126         return 1
127     } else {
128         send_log "$exec_output\n"
129         verbose "$exec_output"
130         perror "$source: assembly failed"
131         return 0
132     }
133 }
134
135 #
136 # exe_ext
137 #       Returns target executable extension, if any.
138 #
139 proc exe_ext {} {
140     if { [istarget *-*-mingw*] || [istarget *-*-cygwin*] } {
141         return ".exe"
142     } else {
143         return ""
144     }
145 }
146
147 # Copied and modified from gas.
148
149 # run_dump_test FILE (optional:) EXTRA_OPTIONS
150 #
151 # Assemble a .s file, then run some utility on it and check the output.
152 #
153 # There should be an assembly language file named FILE.s in the test
154 # suite directory, and a pattern file called FILE.d.  `run_dump_test'
155 # will assemble FILE.s, run some tool like `objdump', `objcopy', or
156 # `nm' on the .o file to produce textual output, and then analyze that
157 # with regexps.  The FILE.d file specifies what program to run, and
158 # what to expect in its output.
159 #
160 # The FILE.d file begins with zero or more option lines, which specify
161 # flags to pass to the assembler, the program to run to dump the
162 # assembler's output, and the options it wants.  The option lines have
163 # the syntax:
164 #
165 #         # OPTION: VALUE
166 #
167 # OPTION is the name of some option, like "name" or "objdump", and
168 # VALUE is OPTION's value.  The valid options are described below.
169 # Whitespace is ignored everywhere, except within VALUE.  The option
170 # list ends with the first line that doesn't match the above syntax.
171 # However, a line within the options that begins with a #, but doesn't
172 # have a recognizable option name followed by a colon, is considered a
173 # comment and entirely ignored.
174 #
175 # The optional EXTRA_OPTIONS argument to `run_dump_test' is a list of
176 # two-element lists.  The first element of each is an option name, and
177 # the second additional arguments to be added on to the end of the
178 # option list as given in FILE.d.  (If omitted, no additional options
179 # are added.)
180 #
181 # The interesting options are:
182 #
183 #   name: TEST-NAME
184 #       The name of this test, passed to DejaGNU's `pass' and `fail'
185 #       commands.  If omitted, this defaults to FILE, the root of the
186 #       .s and .d files' names.
187 #
188 #   as: FLAGS
189 #       When assembling FILE.s, pass FLAGS to the assembler.
190 #
191 #   PROG: PROGRAM-NAME
192 #       The name of the program to run to modify or analyze the .o file
193 #       produced by the assembler.  This option is required.  Recognised
194 #       names are: ar, elfedit, nm, objcopy, ranlib, strings, and strip.
195 #
196 #   DUMPPROG: PROGRAM-NAME
197 #       The name of the program to run to analyze the .o file after it has
198 #       has been modified by PROG.  This can be omitted; run_dump_test will
199 #       guess which program to run by seeing if any of the flags options
200 #       for the recognised dump programs are set.  Recognised names are:
201 #       addr2line, nm, objdump, readelf and size.
202 #
203 #   nm: FLAGS
204 #   objcopy: FLAGS
205 #   objdump: FLAGS
206 #   readelf: FLAGS
207 #   size: FLAGS
208 #       Use the specified program to analyze the .o file, and pass it
209 #       FLAGS, in addition to the .o file name.  Note that they are run
210 #       with LC_ALL=C in the environment to give consistent sorting
211 #       of symbols.
212 #
213 #   source: SOURCE
214 #       Assemble the file SOURCE.s.  If omitted, this defaults to FILE.s.
215 #       This is useful if several .d files want to share a .s file.
216 #
217 #   target: GLOBS...
218 #       Run this test only on a specified list of targets.  More precisely,
219 #       each glob in the space-separated list is passed to "istarget"; if
220 #       it evaluates true for any of them, the test will be run, otherwise
221 #       it will be marked unsupported.
222 #
223 #   not-target: GLOBS...
224 #       Do not run this test on a specified list of targets.  Again,
225 #       the each glob in the space-separated list is passed to
226 #       "istarget", and the test is run if it evaluates *false* for
227 #       *all* of them.  Otherwise it will be marked unsupported.
228 #
229 #   skip: GLOBS...
230 #   not-skip: GLOBS...
231 #       These are exactly the same as "not-target" and "target",
232 #       respectively, except that they do nothing at all if the check
233 #       fails.  They should only be used in groups, to construct a single
234 #       test which is run on all targets but with variant options or
235 #       expected output on some targets.  (For example, see
236 #       gas/arm/inst.d and gas/arm/wince_inst.d.)
237 #
238 #   error: REGEX
239 #       An error with message matching REGEX must be emitted for the test
240 #       to pass.  The PROG, objdump, nm and objcopy options have no
241 #       meaning and need not supplied if this is present.
242 #
243 #   warning: REGEX
244 #       Expect a gas warning matching REGEX.  It is an error to issue
245 #       both "error" and "warning".
246 #
247 #   stderr: FILE
248 #       FILE contains regexp lines to be matched against the diagnostic
249 #       output of the assembler.  This does not preclude the use of
250 #       PROG, nm, objdump, or objcopy.
251 #
252 #   error-output: FILE
253 #       Means the same as 'stderr', but also indicates that the assembler
254 #       is expected to exit unsuccessfully (therefore PROG, objdump, nm,
255 #       and objcopy have no meaning and should not be supplied).
256 #
257 # Each option may occur at most once.
258 #
259 # After the option lines come regexp lines.  `run_dump_test' calls
260 # `regexp_diff' to compare the output of the dumping tool against the
261 # regexps in FILE.d.  `regexp_diff' is defined in binutils-common.exp;
262 # see further comments there.
263
264 proc run_dump_test { name {extra_options {}} } {
265     global subdir srcdir
266     global OBJDUMP NM OBJCOPY READELF STRIP
267     global OBJDUMPFLAGS NMFLAGS OBJCOPYFLAGS READELFFLAGS STRIPFLAGS
268     global ELFEDIT ELFEDITFLAGS
269     global host_triplet
270     global env
271     global copyfile
272     global tempfile
273
274     if [string match "*/*" $name] {
275         set file $name
276         set name [file tail $name]
277     } else {
278         set file "$srcdir/$subdir/$name"
279     }
280     set opt_array [slurp_options "${file}.d"]
281     if { $opt_array == -1 } {
282         perror "error reading options from $file.d"
283         unresolved $subdir/$name
284         return
285     }
286     set opts(addr2line) {}
287     set opts(ar) {}
288     set opts(as) {}
289     set opts(elfedit) {}
290     set opts(name) {}
291     set opts(nm) {}
292     set opts(objcopy) {}
293     set opts(objdump) {}
294     set opts(ranlib) {}
295     set opts(readelf) {}
296     set opts(size) {}
297     set opts(strings) {}
298     set opts(strip) {}
299     set opts(PROG) {}
300     set opts(DUMPPROG) {}
301     set opts(source) {}
302     set opts(target) {}
303     set opts(not-target) {}
304     set opts(skip) {}
305     set opts(not-skip) {}
306
307     foreach i $opt_array {
308         set opt_name [lindex $i 0]
309         set opt_val [lindex $i 1]
310         if ![info exists opts($opt_name)] {
311             perror "unknown option $opt_name in file $file.d"
312             unresolved $subdir/$name
313             return
314         }
315
316         # Permit the option to use $srcdir to refer to the source
317         # directory.
318         regsub -all "\\\$srcdir" "$opt_val" "$srcdir/$subdir" opt_val
319
320         if [string length $opts($opt_name)] {
321             perror "option $opt_name multiply set in $file.d"
322             unresolved $subdir/$name
323             return
324         }
325         set opts($opt_name) $opt_val
326     }
327
328     foreach i $extra_options {
329         set opt_name [lindex $i 0]
330         set opt_val [lindex $i 1]
331         if ![info exists opts($opt_name)] {
332             perror "unknown option $opt_name given in extra_opts"
333             unresolved $subdir/$name
334             return
335         }
336
337         # Permit the option to use $srcdir to refer to the source
338         # directory.
339         regsub -all "\\\$srcdir" "$opt_val" "$srcdir/$subdir" opt_val
340
341         # add extra option to end of existing option, adding space
342         # if necessary.
343         if [string length $opts($opt_name)] {
344             append opts($opt_name) " "
345         }
346         append opts($opt_name) $opt_val
347     }
348
349     if { $opts(name) == "" } {
350         set testname "$subdir/$name"
351     } else {
352         set testname $opts(name)
353     }
354     verbose "Testing $testname"
355
356     if {$opts(PROG) == ""} {
357         perror "PROG isn't set in $file.d"
358         unresolved $testname
359         return
360     }
361
362     set destopt ""
363     switch -- $opts(PROG) {
364         ar      { set program ar }
365         elfedit { set program elfedit }
366         nm      { set program nm }
367         objcopy { set program objcopy }
368         ranlib  { set program ranlib }
369         strings { set program strings }
370         strip   {
371             set program strip
372             set destopt "-o"
373         }
374         default {
375             perror "unrecognized program option $opts(PROG) in $file.d"
376             unresolved $testname
377             return }
378     }
379
380     set dumpprogram ""
381     if { $opts(DUMPPROG) != "" } {
382         switch -- $opts(DUMPPROG) {
383             addr2line   { set dumpprogram addr2line }
384             nm          { set dumpprogram nm }
385             objdump     { set dumpprogram objdump }
386             readelf     { set dumpprogram readelf }
387             size        { set dumpprogram size }
388             default     {
389                 perror "unrecognized dump program option $opts(DUMPPROG) in $file.d"
390                 unresolved $testname
391                 return }
392         }
393     } else {
394         # Guess which program to run, by seeing which option was specified.
395         foreach p {addr2line nm objdump readelf size} {
396             if {$opts($p) != ""} {
397                 if {$dumpprogram != ""} {
398                     perror "more than one possible dump program specified in $file.d"
399                     unresolved $testname
400                     return
401                 } else {
402                     set dumpprogram $p
403                 }
404             }
405         }
406     }
407
408     # Handle skipping the test on specified targets.
409     # You can have both skip/not-skip and target/not-target, but you can't
410     # have both skip and not-skip, or target and not-target, in the same file.
411     if { $opts(skip) != "" } then {
412         if { $opts(not-skip) != "" } then {
413             perror "$testname: mixing skip and not-skip directives is invalid"
414             unresolved $testname
415             return
416         }
417         foreach glob $opts(skip) {
418             if {[istarget $glob]} { return }
419         }
420     }
421     if { $opts(not-skip) != "" } then {
422         set skip 1
423         foreach glob $opts(not-skip) {
424             if {[istarget $glob]} {
425                 set skip 0
426                 break
427             }
428         }
429         if {$skip} { return }
430     }
431     if { $opts(target) != "" } then {
432         set skip 1
433         foreach glob $opts(target) {
434             if {[istarget $glob]} {
435                 set skip 0
436                 break
437             }
438         }
439         if {$skip} {
440             unsupported $testname
441             return
442         }
443     }
444     if { $opts(not-target) != "" } then {
445         foreach glob $opts(not-target) {
446             if {[istarget $glob]} {
447                 unsupported $testname
448                 return
449             }
450         }
451     }
452
453     if { $opts(source) == "" } {
454         set srcfile ${file}.s
455     } else {
456         set srcfile $srcdir/$subdir/$opts(source)
457     }
458
459     if { $opts(as) == "binary" } {
460         while {[file type $srcfile] eq "link"} {
461             set newfile [file readlink $srcfile]
462             if {[string index $newfile 0] ne "/"} {
463                 set newfile [file dirname $srcfile]/$newfile
464             }
465             set srcfile $newfile
466         }
467         # Make sure we copy the file if we are doing remote host testing.
468         remote_download host ${srcfile} $tempfile
469     } else {
470         set exec_output [binutils_assemble_flags ${srcfile} $tempfile $opts(as)]
471         if [string match "" $exec_output] then {
472             send_log "$exec_output\n"
473             verbose "$exec_output"
474             fail $testname
475            return
476         }
477     }
478
479     set progopts1 $opts($program)
480     eval set progopts \$[string toupper $program]FLAGS
481     eval set binary \$[string toupper $program]
482
483     set exec_output [binutils_run $binary "$progopts $progopts1 $tempfile $destopt ${copyfile}.o"]
484     if ![string match "" $exec_output] {
485         send_log "$exec_output\n"
486         verbose "$exec_output"
487         fail $testname
488         return
489     }
490
491     set progopts1 $opts($dumpprogram)
492     eval set progopts \$[string toupper $dumpprogram]FLAGS
493     eval set binary \$[string toupper $dumpprogram]
494
495     if { ![is_remote host] && [which $binary] == 0 } {
496         untested $testname
497         return
498     }
499
500     # For objdump, automatically translate standard section names to the targets one,
501     # if they are different.
502     set sect_names [get_standard_section_names]
503     if { $sect_names != "" && $dumpprogram == "objdump"} {
504         regsub -- "-j \\.text" $progopts1 "-j [lindex $sect_names 0]" progopts1
505         regsub -- "-j \\.data" $progopts1 "-j [lindex $sect_names 1]" progopts1
506         regsub -- "-j \\.bss"  $progopts1 "-j [lindex $sect_names 2]" progopts1
507     }
508
509     verbose "running $binary $progopts $progopts1" 3
510
511     set cmd "$binary $progopts $progopts1 ${copyfile}.o"
512
513     # Ensure consistent sorting of symbols
514     if {[info exists env(LC_ALL)]} {
515         set old_lc_all $env(LC_ALL)
516     }
517     set env(LC_ALL) "C"
518     send_log "$cmd\n"
519     set comp_output [remote_exec host $cmd "" "/dev/null" "tmpdir/dump.out"]
520     if {[info exists old_lc_all]} {
521         set env(LC_ALL) $old_lc_all
522     } else {
523         unset env(LC_ALL)
524     }
525     if { [lindex $comp_output 0] != 0 } then {
526         send_log "$comp_output\n"
527         fail $testname
528         return
529     }
530     set comp_output [prune_warnings [lindex $comp_output 1]]
531     if ![string match "" $comp_output] then {
532         send_log "$comp_output\n"
533         fail $testname
534         return
535     }
536
537     verbose_eval {[file_contents "tmpdir/dump.out"]} 3
538     if { [regexp_diff "tmpdir/dump.out" "${file}.d"] } then {
539         fail $testname
540         verbose "output is [file_contents "tmpdir/dump.out"]" 2
541         return
542     }
543
544     pass $testname
545 }
546
547 proc slurp_options { file } {
548     if [catch { set f [open $file r] } x] {
549         #perror "couldn't open `$file': $x"
550         perror "$x"
551         return -1
552     }
553     set opt_array {}
554     # whitespace expression
555     set ws  {[  ]*}
556     set nws {[^         ]*}
557     # whitespace is ignored anywhere except within the options list;
558     # option names are alphabetic plus dash
559     set pat "^#${ws}(\[a-zA-Z-\]*)$ws:${ws}(.*)$ws\$"
560     while { [gets $f line] != -1 } {
561         set line [string trim $line]
562         # Whitespace here is space-tab.
563         if [regexp $pat $line xxx opt_name opt_val] {
564             # match!
565             lappend opt_array [list $opt_name $opt_val]
566         } elseif {![regexp "^#" $line ]} {
567             break
568         }
569     }
570     close $f
571     return $opt_array
572 }
573
574 proc file_contents { filename } {
575     set file [open $filename r]
576     set contents [read $file]
577     close $file
578     return $contents
579 }
580
581 proc verbose_eval { expr { level 1 } } {
582     global verbose
583     if $verbose>$level then { eval verbose "$expr" $level }
584 }
585
586 # Internal procedure: return the names of the standard sections
587 #
588 proc get_standard_section_names {} {
589     if [istarget "rx-*-*"] {
590         return { "P" "D_1" "B_1" }
591     }
592     if [istarget "alpha*-*-*vms*"] {
593         # Double quote: for TCL and for sh.
594         return { "\\\$CODE\\\$" "\\\$DATA\\\$" "\\\$BSS\\\$" }
595     }
596     return
597 }