db6c8568811a42160e4f5f47c625d47e617fb433
[external/binutils.git] / binutils / testsuite / binutils-all / objcopy.exp
1 #   Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003,
2 #   2004
3 #   Free Software Foundation, Inc.
4
5 # This program is free software; you can redistribute it and/or modify
6 # it under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; either version 2 of the License, or
8 # (at your option) any later version.
9
10 # This program is distributed in the hope that it will be useful,
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 # GNU General Public License for more details.
14
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18
19 # Please email any bugs, comments, and/or additions to this file to:
20 # bug-dejagnu@prep.ai.mit.edu
21
22 # Written by Ian Lance Taylor <ian@cygnus.com>
23
24 if ![is_remote host] {
25     if {[which $OBJCOPY] == 0} then {
26         perror "$OBJCOPY does not exist"
27         return
28     }
29 }
30
31 send_user "Version [binutil_version $OBJCOPY]"
32
33 if {![binutils_assemble $srcdir/$subdir/bintest.s tmpdir/bintest.o]} then {
34     perror "unresolved 1"
35     unresolved "objcopy (simple copy)"
36     return
37 }
38
39 if ![is_remote host] {
40     set tempfile tmpdir/bintest.o
41     set copyfile tmpdir/copy
42 } else {
43     set tempfile [remote_download host tmpdir/bintest.o]
44     set copyfile copy
45 }
46
47 # Test that objcopy does not modify a file when copying it.
48
49 set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS $tempfile ${copyfile}.o"]
50
51 if ![string match "" $got] then {
52     fail "objcopy (simple copy)"
53 } else {
54     send_log "cmp $tempfile ${copyfile}.o\n"
55     verbose "cmp $tempfile ${copyfile}.o"
56     if [is_remote host] {
57         set src1 tmpdir/bintest.o
58         set src2 tmpdir/copy.o
59         remote_upload host $tempfile $src1
60         remote_upload host ${copyfile}.o $src2
61     } else {
62         set src1 ${tempfile}
63         set src2 ${copyfile}.o
64     }
65     set status [remote_exec build cmp "${src1} ${src2}"]
66     set exec_output [lindex $status 1]
67     set exec_output [prune_warnings $exec_output]
68
69     # On some systems the result of objcopy will not be identical.
70     # Usually this is just because gas isn't using bfd to write the files
71     # in the first place, and may order things a little differently.
72     # Those systems should use setup_xfail here.
73
74     setup_xfail "a29k-*"
75     setup_xfail "h8300-*-rtems*" "h8300-*-coff"
76     setup_xfail "h8500-*-rtems*" "h8500-*-coff"
77     setup_xfail "hppa*-*-*"
78     setup_xfail "i960-*"
79     setup_xfail "m68*-*-*coff" "m68*-*-hpux*" "m68*-*-lynxos*"
80     setup_xfail "m68*-*-sysv*" "m68*-apple-aux*"
81     setup_xfail "m8*-*"
82     setup_xfail "or32-*-rtems*" "or32-*-coff"
83     setup_xfail "sh-*-coff*" "sh-*-rtems*" 
84     setup_xfail "tic4x-*-*" "tic80-*-*" "w65-*" "z8*-*"
85
86     clear_xfail "hppa*64*-*-hpux*" "hppa*-*-linux*" "hppa*-*-lites*"
87     clear_xfail "hppa*-*-*n*bsd*" "hppa*-*-rtems*" "*-*-*elf*" "m68*-*-sysv4*"
88
89     if [string match "" $exec_output] then {
90         pass "objcopy (simple copy)"
91     } else {
92         send_log "$exec_output\n"
93         verbose "$exec_output" 1
94
95         # On OSF/1, this succeeds with gas and fails with /bin/as.
96         setup_xfail "alpha*-*-osf*"
97
98         # This fails for COFF i960-vxworks targets.
99         setup_xfail "i960-*-vxworks*"
100
101         fail "objcopy (simple copy)"
102     }
103 }
104
105 # Test generating S records.
106
107 # We make the srec filename 8.3 compatible. Note that the header string
108 # matched against depends on the name of the file. Ugh.
109
110 if [is_remote host] {
111     set srecfile copy.sre
112     set header_string S00B0000636F70792E737265C1
113 } else {
114     set srecfile ${copyfile}.srec
115     set header_string S0130000746D706469722F636F70792E7372656397
116 }
117
118 set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec $tempfile ${srecfile}"]
119
120 if ![string match "" $got] then {
121     fail "objcopy -O srec"
122 } else {
123     if [is_remote host] {
124         remote_upload host ${srecfile} tmpdir/copy.srec
125         set srecfile tmpdir/copy.srec
126     }
127     set file [open ${srecfile} r]
128
129     # The first S record is fixed by the file name we are using.
130     gets $file line
131     send_log "$line\n"
132     verbose $line
133     if ![regexp "$header_string.*" $line] {
134         send_log "bad header\n"
135         fail "objcopy -O srec"
136     } else {
137         while {[gets $file line] != -1 \
138                && [regexp "^S\[123\]\[0-9a-fA-F\]+\[\r\n\]*$" $line]} {
139             send_log "$line\n"
140             verbose $line
141             set line "**EOF**"
142         }
143         send_log "$line\n"
144         verbose $line
145         if ![regexp "^S\[789\]\[0-9a-fA-F\]+\[\r\n\]*$" $line] then {
146             send_log "bad trailer\n"
147             fail "objcopy -O srec"
148         } else {
149             if {[gets $file line] != -1} then {
150                 send_log "garbage at end\n"
151                 send_log "$line\n"
152                 verbose $line
153                 fail "objcopy -O srec"
154             } else {
155                 set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -f ${copyfile}.srec"]
156                 if ![regexp "file format srec" $got] then {
157                     send_log "objdump failed\n"
158                     fail "objcopy -O srec"
159                 } else {
160                     pass "objcopy -O srec"
161                 }
162             }
163         }
164     }
165
166     close $file
167 }
168
169 # Test setting and adjusting the start address.  We only test this
170 # while generating S records, because we may not be able to set the
171 # start address for other object file formats, and the S record case
172 # is the only useful one anyhow.
173
174 set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -f $tempfile"]
175 if ![regexp "start address (\[0-9a-fA-FxX\]+)" $got all origstart] then {
176     perror "objdump can not recognize bintest.o"
177     set origstart ""
178 } else {
179     set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec --set-start 0x7654 $tempfile ${copyfile}.srec"]
180     if ![string match "" $got] then {
181         fail "objcopy --set-start"
182     } else {
183         set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -f ${copyfile}.srec"]
184         if ![regexp "file format srec.*start address (\[0-9a-fA-FxX\]+)" $got all srecstart] then {
185             fail "objcopy --set-start"
186         } else {
187             if {$srecstart != 0x7654} then {
188                 send_log "$srecstart != 0x7654\n"
189                 fail "objcopy --set-start"
190             } else {
191                 pass "objcopy --set-start"
192             }
193         }
194     }
195
196     set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec --adjust-start 0x123 $tempfile ${copyfile}.srec"]
197     if ![string match "" $got] then {
198         fail "objcopy --adjust-start"
199     } else {
200         set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -f ${copyfile}.srec"]
201         if ![regexp "file format srec.*start address (\[0-9a-fA-FxX\]+)" $got all srecstart] then {
202             fail "objcopy --adjust-start"
203         } else {
204             if {$srecstart != $origstart + 0x123} then {
205                 send_log "$srecstart != $origstart + 0x123\n"
206                 fail "objcopy --adjust-start"
207             } else {
208                 pass "objcopy --adjust-start"
209             }
210         }
211     }
212 }
213
214 # Test adjusting the overall VMA, and adjusting the VMA of a
215 # particular section.  We again only test this when generating S
216 # records.
217
218 set low ""
219 set lowname ""
220
221 set headers [binutils_run $OBJDUMP "$OBJDUMPFLAGS -h $tempfile"]
222
223 set headers_regexp "\[  0-9\]+(\[^      \]+)\[  \]*(\[0-9a-fA-F\]+)\[   \]+\[0-9a-fA-F\]+\[     \]+(\[0-9a-fA-F\]+)\[   \]+\[0-9a-fA-F\]+\[     \]+2\[*\]\[*\]\[0-9\]+(.*)"
224
225 set got $headers
226 while {[regexp $headers_regexp $got all name size vma rest]} {
227     set vma 0x$vma
228     set size 0x$size
229     if {$size != 0} {
230         if {$low == "" || $vma < $low} {
231             set low $vma
232             set lowname $name
233         }
234     }
235     set got $rest
236 }
237
238 if {$low == "" || $origstart == ""} then {
239     perror "objdump can not recognize bintest.o"
240 } else {
241     set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec --adjust-vma 0x123 $tempfile ${copyfile}.srec"]
242     if ![string match "" $got] then {
243         fail "objcopy --adjust-vma"
244     } else {
245         set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -fh ${copyfile}.srec"]
246         set want "file format srec.*start address\[     \]*(\[0-9a-fA-FxX\]+).*sec1\[   \]+\[0-9a-fA-F\]+\[     \]+(\[0-9a-fA-F\]+)"
247         if ![regexp $want $got all start vma] then {
248             fail "objcopy --adjust-vma"
249         } else {
250             set vma 0x$vma
251             if {$vma != $low + 0x123} then {
252                 send_log "$vma != $low + 0x123\n"
253                 fail "objcopy --adjust-vma"
254             } else {
255                 if {$start != $origstart + 0x123} then {
256                     send_log "$start != $origstart + 0x123\n"
257                     fail "objcopy --adjust-vma"
258                 } else {
259                     pass "objcopy --adjust-vma"
260                 }
261             }
262         }
263     }
264
265     set arg ""
266     set got $headers
267     while {[regexp $headers_regexp $got all name size vma rest]} {
268         set vma 0x$vma
269         if {$vma == $low} then {
270             set arg "$arg --adjust-section-vma $name+4"
271         }
272         set got $rest
273     }
274
275     set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec $arg $tempfile ${copyfile}.srec"]
276     if ![string match "" $got] then {
277         fail "objcopy --adjust-section-vma +"
278     } else {
279         set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -h ${copyfile}.srec"]
280         set want "file format srec.*sec1\[      \]+\[0-9a-fA-F\]+\[     \]+(\[0-9a-fA-F\]+)"
281         if ![regexp $want $got all vma] then {
282             fail "objcopy --adjust-section-vma +"
283         } else {
284             set vma 0x$vma
285             if {$vma != $low + 4} then {
286                 send_log "$vma != $low + 4\n"
287                 fail "objcopy --adjust-section-vma +"
288             } else {
289                 pass "objcopy --adjust-section-vma +"
290             }
291         }
292     }
293
294     regsub -all "\\+4" $arg "=[expr $low + 4]" argeq
295     set got [binutils_run $OBJCOPY "$OBJCOPYFLAGS -O srec $argeq $tempfile ${copyfile}.srec"]
296     if ![string match "" $got] then {
297         fail "objcopy --adjust-section-vma ="
298     } else {
299         set got [binutils_run $OBJDUMP "$OBJDUMPFLAGS -h ${copyfile}.srec"]
300         set want "file format srec.*sec1\[      \]+\[0-9a-fA-F\]+\[     \]+(\[0-9a-fA-F\]+)"
301         if ![regexp $want $got all vma] then {
302             fail "objcopy --adjust-section-vma ="
303         } else {
304             set vma 0x$vma
305             if {$vma != $low + 4} then {
306                 send_log "$vma != $low + 4\n"
307                 fail "objcopy --adjust-section-vma ="
308             } else {
309                 pass "objcopy --adjust-section-vma ="
310             }
311         }
312     }
313 }
314
315 # Test stripping an object.
316
317 proc strip_test { } {
318     global AR
319     global CC
320     global STRIP
321     global STRIPFLAGS
322     global NM
323     global NMFLAGS
324     global srcdir
325     global subdir
326
327     set test "strip"
328
329     if { [target_compile $srcdir/$subdir/testprog.c tmpdir/testprog.o object debug] != "" } {
330         untested $test
331         return
332     }
333
334     if [is_remote host] {
335         set archive libstrip.a
336         set objfile [remote_download host tmpdir/testprog.o]
337         remote_file host delete $archive
338     } else {
339         set archive tmpdir/libstrip.a
340         set objfile tmpdir/testprog.o
341     }
342
343     remote_file build delete tmpdir/libstrip.a
344
345     set exec_output [binutils_run $AR "rc $archive ${objfile}"]
346     if ![string match "" $exec_output] {
347         fail $test
348         return
349     }
350
351     set exec_output [binutils_run $STRIP "$STRIPFLAGS $archive"]
352     if ![string match "" $exec_output] {
353         fail $test
354         return
355     }
356
357     if { [target_compile $srcdir/$subdir/testprog.c tmpdir/testprog.o object debug] != "" } {
358         untested $test
359         return
360     }
361
362     if [is_remote host] {
363         set objfile [remote_download host tmpdir/testprog.o]
364     } else {
365         set objfile tmpdir/testprog.o
366     }
367
368     set exec_output [binutils_run $STRIP "$STRIPFLAGS $objfile"]
369     if ![string match "" $exec_output] {
370         fail $test
371         return
372     }
373
374     set exec_output [binutils_run $NM "-a $NMFLAGS $objfile"]
375     if ![string match "*: no symbols*" $exec_output] {
376         fail $test
377         return
378     }
379
380     pass $test
381 }
382
383 strip_test
384
385 # Test stripping an object file with saving a symbol
386
387 proc strip_test_with_saving_a_symbol { } {
388     global CC
389     global STRIP
390     global STRIPFLAGS
391     global NM
392     global NMFLAGS
393     global srcdir
394     global subdir
395
396     set test "strip with saving a symbol"
397
398     if { [target_compile $srcdir/$subdir/testprog.c tmpdir/testprog.o object debug] != "" } {
399         untested $test
400         return
401     }
402
403     if [is_remote host] {
404         set objfile [remote_download host tmpdir/testprog.o]
405     } else {
406         set objfile tmpdir/testprog.o
407     }
408
409     set exec_output [binutils_run $STRIP "$STRIPFLAGS -K main -K _main $objfile"]
410     if ![string match "" $exec_output] {
411         fail $test
412         return
413     }
414
415     set exec_output [binutils_run $NM "$NMFLAGS $objfile"]
416     if {![regexp {^([0-9a-fA-F]+)?[ ]+[TD] main} $exec_output] \
417          && ![regexp {^([0-9a-fA-F]+)?[ ]+T _main} $exec_output]} {
418         fail $test
419         return
420     }
421
422     pass $test
423 }
424
425 strip_test_with_saving_a_symbol
426
427 # Build a final executable.
428
429 if { [istarget *-*-cygwin] || [istarget *-*-mingw32] } {
430     set test_prog "testprog.exe"
431 } else {
432     set test_prog "testprog"
433 }
434
435 proc copy_setup { } {
436     global srcdir
437     global subdir
438     global gcc_gas_flag
439     global test_prog
440     
441     set res [build_wrapper testglue.o]
442     set flags { debug }
443     
444     if { $res != "" } {
445         lappend flags "additional_flags=[lindex $res 1]"
446         set add_libs "testglue.o"
447     } else {
448         set add_libs ""
449     }
450
451     if { [istarget *-*-linux*] } {
452         foreach i $gcc_gas_flag {
453             set flags "additional_flags=$i $flags"
454         }
455     }
456     if { [target_compile "$srcdir/$subdir/testprog.c $add_libs" tmpdir/$test_prog executable $flags]  != "" } {
457         return 2
458     }
459
460     set result [remote_load target tmpdir/$test_prog]
461     set status [lindex $result 0]
462
463     if { $status != "pass"  } {
464         perror "unresolved setup, status = $status"
465         return 3
466     }
467
468     return 0
469 }
470
471 # Test copying an executable.
472
473 proc copy_executable { prog flags test1 test2 } {
474     global test_prog
475
476     if [is_remote host] {
477         set testfile [remote_download host tmpdir/$test_prog]
478         set testcopy copyprog
479     } else {
480         set testfile tmpdir/$test_prog
481         set testcopy tmpdir/copyprog
482     }
483     remote_file host delete $testcopy
484
485     set exec_output [binutils_run $prog "$flags $testfile $testcopy"]
486
487     if ![string match "" $exec_output] {
488         fail $test1
489         fail $test2
490         return
491     }
492
493     if [is_remote host] {
494         remote_upload host $testcopy tmpdir/copyprog
495     }
496
497     set status [remote_exec build "cmp" "tmpdir/$test_prog tmpdir/copyprog"]
498     set exec_output [lindex $status 1]
499
500     if [string match "" $exec_output] then {
501         pass $test1
502     } else {
503         send_log "$exec_output\n"
504         verbose "$exec_output"
505
506         # This will fail for many reasons.  For example, it will most
507         # likely fail if a non-GNU linker is used.  Therefore, we do
508         # not insist that it pass.  If you are using an assembler and
509         # linker based on the same BFD as objcopy, it is worth
510         # investigating to see why this failure occurs.  If we are
511         # cross compiling, we assume that a GNU linker is being used,
512         # and expect it to succeed.
513         if {[isnative]} then {
514             setup_xfail "*-*-*"
515         }
516
517         # This also fails for mips*-*-elf targets.  See elf32-mips.c
518         # mips_elf_sym_is_global.
519         setup_xfail "mips*-*-elf"
520
521         setup_xfail "*arm*-*-coff"
522         setup_xfail "xscale-*-coff"
523         setup_xfail "arm*-*-pe"
524         setup_xfail "thumb*-*-coff"
525         setup_xfail "thumb*-*-pe"
526     
527         fail $test1
528     }
529
530     set output [remote_load target tmpdir/copyprog]
531     set status [lindex $output 0]
532     if { $status != "pass" } {
533         fail $test2
534     } else {
535         pass $test2
536     }
537 }
538
539 # Test stripping an executable
540
541 proc strip_executable { prog flags test } {
542     global NM
543     global NMFLAGS
544
545     remote_download build tmpdir/copyprog tmpdir/striprog
546     if [is_remote host] {
547         set copyfile [remote_download host tmpdir/striprog]
548     } else {
549         set copyfile tmpdir/striprog
550     }
551
552     set exec_output [binutils_run $prog "$flags ${copyfile}"]
553     if ![string match "" $exec_output] {
554         fail $test
555         return
556     }
557
558     if [is_remote host] {
559         remote_upload host ${copyfile} tmpdir/striprog
560     }
561
562     set result [remote_load target tmpdir/striprog]
563     set status [lindex $result 0]
564     if { $status != "pass" } {
565         fail $test
566         return
567     }
568
569     set exec_output [binutils_run $NM "$NMFLAGS ${copyfile}"]
570     if ![string match "*: no symbols*" $exec_output] {
571         fail $test
572         return
573     }
574     pass $test
575 }
576
577 # Test stripping an executable with saving a symbol
578
579 proc strip_executable_with_saving_a_symbol { prog flags test } {
580     global NM
581     global NMFLAGS
582
583     remote_download build tmpdir/copyprog tmpdir/striprog
584     if [is_remote host] {
585         set copyfile [remote_download host tmpdir/striprog]
586     } else {
587         set copyfile tmpdir/striprog
588     }
589
590     set exec_output [binutils_run $prog "$flags ${copyfile}"]
591     if ![string match "" $exec_output] {
592         fail $test
593         return
594     }
595
596     if [is_remote host] {
597         remote_upload host ${copyfile} tmpdir/striprog
598     }
599
600     set result [remote_load target tmpdir/striprog]
601     set status [lindex $result 0]
602     if { $status != "pass" } {
603         fail $test
604         return
605     }
606
607     set exec_output [binutils_run $NM "$NMFLAGS ${copyfile}"]
608     if { [istarget mmix-knuth-mmixware] } {
609         # Whenever there's a symbol in the mmo format, there's the symbol
610         # Main, so remove it manually from the expected output for sake of
611         # this test.
612
613         # Using "" not {} to get the \n and \r translated.
614         regsub "^\[0-9a-fA-F\]+\[ \]+T Main\[\n\r\]+" $exec_output "" exec_output
615     }
616
617     if {![regexp {^([0-9a-fA-F]+)?[ ]+[TD] main} $exec_output] \
618          && ![regexp {^([0-9a-fA-F]+)?[ ]+[TD] _main} $exec_output]} {
619         fail $test
620         return
621     }
622     pass $test
623 }
624
625 set test1 "simple objcopy of executable"
626 set test2 "run objcopy of executable"
627 set test3 "run stripped executable"
628 set test4 "run stripped executable with saving a symbol"
629
630 switch [copy_setup] {
631     "1" {
632         # do nothing
633     }
634     "2" {
635         untested $test1
636         untested $test2
637         untested $test3
638         untested $test4
639     }
640     "3" {
641         unresolved $test1
642         unresolved $test2
643         unresolved $test3
644         unresolved $test4
645     }
646     "0" {
647         copy_executable "$OBJCOPY" "$OBJCOPYFLAGS" "$test1" "$test2"
648         strip_executable "$STRIP" "$STRIPFLAGS" "$test3"
649         strip_executable_with_saving_a_symbol "$STRIP" "-K main -K _main $STRIPFLAGS" "$test4"
650     }
651 }