]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - libctf/testsuite/lib/ctf-lib.exp
libctf, ld: fix symtypetab and var section population under ld -r
[thirdparty/binutils-gdb.git] / libctf / testsuite / lib / ctf-lib.exp
CommitLineData
c59e30ed
NA
1# Support routines for libctf testsuite.
2# Copyright (C) 1994-2021 Free Software Foundation, Inc.
3#
4# This file is part of the GNU Binutils.
5#
6# This file is free software; you can redistribute it and/or modify
7# it under the terms of the GNU General Public License as published by
8# the Free Software Foundation; either version 3 of the License, or
9# (at your option) any later version.
10#
11# This program is distributed in the hope that it will be useful,
12# but WITHOUT ANY WARRANTY; without even the implied warranty of
13# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14# GNU General Public License for more details.
15#
16# You should have received a copy of the GNU General Public License
17# along with this program; if not, write to the Free Software
18# Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19# MA 02110-1301, USA.
20
21proc load_common_lib { name } {
22 global srcdir
23 load_file $srcdir/../../binutils/testsuite/lib/$name
24}
25
26load_common_lib binutils-common.exp
27
28proc run_native_host_cmd { command } {
29 global link_output
30 global ld
31
32 verbose -log "$command"
33 set run_output ""
34 try {
35 set run_output [exec "sh" "-c" "$command" "2>@1"]
36 set status 0
37 } trap CHILDSTATUS {results options} {
38 set status [lindex [dict get $options -errorcode] 2]
39 set run_output $results
40 }
41 regsub "\n$" $run_output "" run_output
42 if { [lindex $status 0] != 0 && [string match "" $run_output] } then {
43 append run_output "child process exited abnormally"
44 }
45
46 if [string match "" $run_output] then {
47 return ""
48 }
49
50 verbose -log "$run_output"
51 return "$run_output"
52}
53
54proc run_host_cmd { prog command } {
55 global link_output
56 global gcc_B_opt
57 global gcc_ld_B_opt_tested
58 global ld
59
60 if { ![is_remote host] && [which "$prog"] == 0 } then {
61 perror "$prog does not exist"
62 return 0
63 }
64
65 # If we are compiling with gcc, we want to add gcc_B_opt to flags. However,
66 # if $prog already has -B options, which might be the case when running gcc
67 # out of a build directory, we want our -B options to come first.
68 set gccexe $prog
69 set gccparm [string first " " $gccexe]
70 set gccflags ""
71 if { $gccparm > 0 } then {
72 set gccflags [string range $gccexe $gccparm end]
73 set gccexe [string range $gccexe 0 $gccparm]
74 set prog $gccexe
75 }
76 set gccexe [string replace $gccexe 0 [string last "/" $gccexe] ""]
77 if {[string match "*cc*" $gccexe] || [string match "*++*" $gccexe]} then {
78 set gccflags "$gcc_B_opt $gccflags"
79 if {![info exists gcc_ld_B_opt_tested]} {
80 set gcc_ld_B_opt_tested 1
81 set ld_version_message [run_host_cmd "$ld" "--version"]
82 set gcc_ld_version_message [run_host_cmd "$prog" "$gccflags -Wl,--version"]
83 if {[string first $ld_version_message $gcc_ld_version_message] < 0} {
84 perror "************************************************************************"
85 perror "Your compiler driver ignores -B when choosing ld."
86 perror "You will not be testing the new ld in many of the following tests."
87 set gcc_ld_version [run_host_cmd "$prog" "$gccflags --print-prog-name=ld"]
88 if {![string match "" $gcc_ld_version] && ![string match "ld" $gcc_ld_version]} {
89 perror "It seems you will be testing $gcc_ld_version instead."
90 }
91 perror "************************************************************************"
92 }
93 }
94 }
95
96 verbose -log "$prog $gccflags $command"
97 set status [remote_exec host [concat sh -c [list "$prog $gccflags $command 2>&1"]] "" "/dev/null" "libctf.tmp"]
98 remote_upload host "libctf.tmp"
99 set run_output [file_contents "libctf.tmp"]
100 regsub "\n$" $run_output "" run_output
101 if { [lindex $status 0] != 0 && [string match "" $run_output] } then {
102 append run_output "child process exited abnormally"
103 }
104 remote_file build delete libctf.tmp
105 remote_file host delete libctf.tmp
106
107 if [string match "" $run_output] then {
108 return ""
109 }
110
111 verbose -log "$run_output"
112 return "$run_output"
113}
114
115proc run_host_cmd_yesno { prog command } {
116 global exec_output
117 global errcnt warncnt
118
119 set exec_output [prune_warnings [run_host_cmd "$prog" "$command"]]
120 # Ignore error and warning.
121 set errcnt 0
122 set warncnt 0
123 if [string match "" $exec_output] then {
124 return 1;
125 }
126 return 0;
127}
128
129# Return true if we can build a program with the compiler.
130# On some targets, CC might be defined, but libraries and startup
131# code might be missing or require special options that the ld test
132# harness doesn't know about.
133
134proc check_compiler_available { } {
135 global compiler_available_saved
136 global CC
137
138 if {![info exists compiler_available_saved]} {
139 if { [which $CC] == 0 } {
140 set compiler_available_saved 0
141 return 0
142 }
143
144 set flags ""
145 if [board_info [target_info name] exists cflags] {
146 append flags " [board_info [target_info name] cflags]"
147 }
148 if [board_info [target_info name] exists ldflags] {
149 append flags " [board_info [target_info name] ldflags]"
150 }
151
152 set basename "tmpdir/compiler[pid]"
153 set src ${basename}.c
154 set output ${basename}.out
155 set f [open $src "w"]
156 puts $f "int main (void)"
157 puts $f "{"
158 puts $f " return 0; "
159 puts $f "}"
160 close $f
161 if [is_remote host] {
162 set src [remote_download host $src]
163 }
164 set compiler_available_saved [run_host_cmd_yesno "$CC" "$flags $src -o $output"]
165 remote_file host delete $src
166 remote_file host delete $output
167 file delete $src
168 }
169 return $compiler_available_saved
170}
171
172# Compile and link a C source file for execution on the host.
173proc compile_link_one_host_cc { src output additional_args } {
174 global CC_FOR_HOST
175 global CFLAGS
176
177 return [run_native_host_cmd "./libtool --quiet --tag=CC --mode=link $CC_FOR_HOST $CFLAGS $src -o $output $additional_args" ]
178}
179
180# Compile a C source file, with the specified additional_flags.
181proc compile_one_cc { src output additional_flags } {
182 global CC
183 global CFLAGS
184
185 set flags ""
186 if [board_info [target_info name] exists cflags] {
187 append flags " [board_info [target_info name] cflags]"
188 }
189 if [board_info [target_info name] exists ldflags] {
190 append flags " [board_info [target_info name] ldflags]"
191 }
192
193 if [is_remote host] {
194 set src [remote_download host $src]
195 }
196 return [run_host_cmd "$CC" "$flags $CFLAGS $additional_flags $src -o $output"]
197}
198
199# run_lookup_test FILE
200#
201# Compile with the host compiler and link a .c file into a "lookup" binary, then
202# compile and optionally link together a bunch of .s or .c files with CTF info
203# and pass the name of the resulting binary to the "lookup" binary and check the
204# output. (If none is specified, the binary is expected to generate its own CTF
205# for testing purposes.)
206#
207# As with run_dump_test, this is all driven by a file (in this case, a .lk file)
208# beginning with zero or more option lines, which specify the names of the
209# lookup binary's source file, the source file(s) with CTF info to compile
210# together, and whether to link them. The optional lines have the syntax:
211#
212# # OPTION: VALUE
213#
214# OPTION is the name of some option, like "name" or "lookup", and
215# VALUE is OPTION's value. The valid options are described below.
216# Whitespace is ignored everywhere, except within VALUE. The option
217# list ends with the first line that doesn't match the above syntax.
218# However, a line within the options that begins with a #, but doesn't
219# have a recognizable option name followed by a colon, is considered a
220# comment and entirely ignored.
221#
222# The interesting options are:
223#
224# name: TEST-NAME
225# The name of this test, passed to DejaGNU's `pass' and `fail'
226# commands. If omitted, this defaults to FILE, the root of the
227# lookup .c file's name.
228#
229# lookup: SOURCE
230# Compile the file SOURCE.c. If omitted, the lookup source defaults
231# to FILE.c.
232#
233# source: SOURCE
234# Assemble the file SOURCE.c and pass it to the LOOKUP program.
235#
35a01a04
NA
236# nonshared:
237# If set, do not link with -shared.
238#
c59e30ed
NA
239# link:
240# If set, link the SOURCE together even if only one file is specified.
241#
242# link_flags:
243# If set, extra flags to pass to the linker.
244#
245# xfail: GLOB|PROC ...
246# This test is expected to fail on a specified list of targets.
247#
248# Each option may occur at most once unless otherwise mentioned.
249#
250# After the option lines come regexp lines. run_lookup_test calls
251# regexp_diff to compare the output of the lookup program against the
252# regexps in FILE.d.
253#
254proc run_lookup_test { name } {
255 global CC CFLAGS LIBS
256 global copyfile env runtests srcdir subdir verbose
257
258 if ![runtest_file_p $runtests $name] then {
259 return
260 }
261
262 if [string match "*/*" $name] {
263 set file $name
264 set name [file tail $name]
265 } else {
266 set file "$srcdir/$subdir/$name"
267 }
268
269 set opt_array [slurp_options "${file}.lk"]
270 if { $opt_array == -1 } {
271 perror "error reading options from $file.lk"
272 unresolved $subdir/$name
273 return
274 }
275 set run_ld 0
35a01a04 276 set shared "-shared"
c59e30ed
NA
277 set opts(link) {}
278 set opts(link_flags) {}
35a01a04 279 set opts(nonshared) {}
c59e30ed
NA
280 set opts(lookup) {}
281 set opts(name) {}
282 set opts(source) {}
283 set opts(xfail) {}
284
285 foreach i $opt_array {
286 set opt_name [lindex $i 0]
287 set opt_val [lindex $i 1]
288 if { $opt_name == "" } {
289 set in_extra 1
290 continue
291 }
292 if ![info exists opts($opt_name)] {
293 perror "unknown option $opt_name in file $file.lk"
294 unresolved $subdir/$name
295 return
296 }
297
298 set opts($opt_name) [concat $opts($opt_name) $opt_val]
299 }
300
301 if { [llength $opts(lookup)] == 0 } {
302 set opts(lookup) "$file.c"
303 } else {
304 set opts(lookup) "[file dirname $file]/$opts(lookup)"
305 }
306
307 if { [llength $opts(name)] == 0 } {
308 set opts(name) $opts(lookup)
309 }
310
311 if { [llength $opts(link)] != 0
312 || [llength $opts(source)] > 1 } {
313 set run_ld 1
314 }
315
35a01a04
NA
316 if { [llength $opts(nonshared)] != 0 } {
317 set shared ""
318 }
319
c59e30ed
NA
320 set testname $opts(name)
321 if { $opts(name) == "" } {
322 set testname "$subdir/$name"
323 }
324
325 # Compile and link the lookup program.
326 set comp_output [compile_link_one_host_cc $opts(lookup) "tmpdir/lookup" "libctf.la"]
327
328 if { $comp_output != ""} {
329 send_log "compilation of lookup program $opts(lookup) failed with <$comp_output>"
330 perror "compilation of lookup program $opts(lookup) failed"
331 fail $testname
332 return 0
333 }
334
335 # Compile the inputs and posibly link them together.
336
337 set lookup_output ""
338 if { [llength $opts(source)] > 0 } {
339 set lookup_flags ""
340 if { $run_ld } {
341 set lookup_output "tmpdir/out.so"
35a01a04 342 set lookup_flags "-gt -fPIC $shared $opts(link_flags)"
c59e30ed
NA
343 } else {
344 set lookup_output "tmpdir/out.o"
345 set lookup_flags "-gt -fPIC -c"
346 }
347 if [board_info [target_info name] exists cflags] {
348 append lookup_flags " [board_info [target_info name] cflags]"
349 }
350 if [board_info [target_info name] exists ldflags] {
351 append lookup_flags " [board_info [target_info name] ldflags]"
352 }
353 set src {}
354 foreach sfile $opts(source) {
355 if [is_remote host] {
356 lappend src [remote_download host [file join [file dirname $file] $sfile]]
357 } else {
358 lappend src [file join [file dirname $file] $sfile]
359 }
360 }
361
362 set comp_output [run_host_cmd "$CC" "$CFLAGS $lookup_flags [concat $src] -o $lookup_output"]
363
364 if { $comp_output != ""} {
365 send_log "compilation of CTF program [concat $src] failed with <$comp_output>"
366 fail $testname
367 return 0
368 }
369 }
370
371 # Time to setup xfailures.
372 foreach targ $opts(xfail) {
373 if [match_target $targ] {
374 setup_xfail "*-*-*"
375 break
376 }
377 }
378
379 # Invoke the lookup program on the outputs.
380
381 set results [run_host_cmd tmpdir/lookup $lookup_output]
382
383 set f [open "tmpdir/lookup.out" "w"]
384 puts $f $results
385 close $f
386
387 if { [regexp_diff "tmpdir/lookup.out" "${file}.lk"] } then {
388 fail $testname
389 if { $verbose == 2 } then { verbose "output is [file_contents tmpdir/lookup.out]" 2 }
390 return 0
391 }
392
393 pass $testname
394 return 0
395}
396
397# Returns true if the target compiler supports -gt
398proc check_ctf_available { } {
399 global ctf_available_saved
400
401 if {![info exists ctf_available_saved]} {
402 if { ![check_compiler_available] } {
403 set ctf_available_saved 0
404 } else {
405 set basename "tmpdir/ctf_available[pid]"
406 set src ${basename}.c
407 set output ${basename}.o
408 set f [open $src "w"]
409 puts $f "int main() { return 0; }"
410 close $f
70d3120f
NA
411 set comp_output [compile_one_cc $src $output "-gt -c"]
412 if { $comp_output == ""} {
413 set ctf_available_saved 1
414 } else {
415 set ctf_available_saved 0
416 }
c59e30ed
NA
417 remote_file host delete $src
418 remote_file host delete $output
419 file delete $src
420 }
421 }
422 return $ctf_available_saved
423}