# default_ld_nm
# run nm on a file, putting the result in the array nm_output
#
-proc default_ld_nm { nm object } {
+proc default_ld_nm { nm nmflags object } {
global NMFLAGS
global nm_output
global host_triplet
if ![info exists NMFLAGS] { set NMFLAGS "" }
- verbose -log "$nm $NMFLAGS $object >tmpdir/nm.out"
+ verbose -log "$nm $NMFLAGS $nmflags $object >tmpdir/nm.out"
- catch "exec $nm $NMFLAGS $object >tmpdir/nm.out" exec_output
+ catch "exec $nm $NMFLAGS $nmflags $object >tmpdir/nm.out" exec_output
set exec_output [prune_warnings $exec_output]
if [string match "" $exec_output] then {
set file [open tmpdir/nm.out r]
while { [gets $file line] != -1 } {
verbose "$line" 2
- if [regexp "^(\[0-9a-fA-F\]+) \[a-zA-Z0-9\] (.+)$" $line whole value name] {
+ if [regexp "^(\[0-9a-fA-F\]+) \[a-zA-Z0-9\] \\.*(.+)$" $line whole value name] {
set name [string trimleft $name "_"]
verbose "Setting nm_output($name) to 0x$value" 2
set nm_output($name) 0x$value
}
}
+#
+# is_elf_format
+# true if the object format is known to be ELF
+#
+proc is_elf_format {} {
+ if { ![istarget *-*-sysv4*] \
+ && ![istarget *-*-unixware*] \
+ && ![istarget *-*-elf*] \
+ && ![istarget *-*-eabi*] \
+ && ![istarget *-*-linux*] \
+ && ![istarget *-*-irix5*] \
+ && ![istarget *-*-irix6*] \
+ && ![istarget *-*-solaris2*] } {
+ return 0
+ }
+
+ if { [istarget *-*-linux*aout*] \
+ || [istarget *-*-linux*oldld*] } {
+ return 0
+ }
+ return 1
+}
+
#
# simple_diff
# compares two files line-by-line
# Link assembled files using FLAGS, in the order of the "source"
# directives, when using multiple files.
#
+# objcopy_linked_file: FLAGS
+# Run objcopy on the linked file with the specified flags.
+# This lets you transform the linked file using objcopy, before the
+# result is analyzed by an analyzer program specified below (which
+# may in turn *also* be objcopy).
+#
# PROG: PROGRAM-NAME
# The name of the program to run to analyze the .o file produced
# by the assembler or the linker output. This can be omitted;
}
set dumpfile tmpdir/dump.out
set run_ld 0
+ set run_objcopy 0
set opts(as) {}
set opts(ld) {}
set opts(xfail) {}
set opts(PROG) {}
set opts(source) {}
set opts(error) {}
- set asflags{${file}.s} {}
+ set opts(objcopy_linked_file) {}
+ set asflags(${file}.s) {}
foreach i $opt_array {
set opt_name [lindex $i 0]
if { $opt_name == "ld" } {
set run_ld 1
}
+ # Likewise objcopy_linked_file.
+ if { $opt_name == "objcopy_linked_file" } {
+ set run_objcopy 1
+ }
}
}
set opts($opt_name) [concat $opts($opt_name) $opt_val]
# Perhaps link the file(s).
if { $run_ld } {
set objfile "tmpdir/dump"
- set cmd "$LD $LDFLAGS $opts(ld) -o $objfile $objfiles"
+
+ # Add -L$srcdir/$subdir so that the linker command can use
+ # linker scripts in the source directory.
+ set cmd "$LD $LDFLAGS -L$srcdir/$subdir \
+ $opts(ld) -o $objfile $objfiles"
send_log "$cmd\n"
set cmdret [catch "exec $cmd" comp_output]
verbose -log "failed with: <$comp_output>, expected: <$opts(error)>"
send_log "$comp_output\n"
verbose "$comp_output" 3
- if { $opts(error) != "" } {
+ if { $opts(error) != "" && $run_objcopy == 0 } {
if [regexp $opts(error) $comp_output] {
pass $testname
return
fail $testname
return
}
+
+ if { $run_objcopy } {
+ set infile $objfile
+ set objfile "tmpdir/dump1"
+
+ # Note that we don't use OBJCOPYFLAGS here; any flags must be
+ # explicitly specified.
+ set cmd "$OBJCOPY $opts(objcopy_linked_file) $infile $objfile"
+
+ send_log "$cmd\n"
+ set cmdret [catch "exec $cmd" comp_output]
+ set comp_output [prune_warnings $comp_output]
+
+ if { $cmdret != 0 || ![string match "" $comp_output] } then {
+ verbose -log "failed with: <$comp_output>, expected: <$opts(error)>"
+ send_log "$comp_output\n"
+ verbose "$comp_output" 3
+ if { $opts(error) != "" } {
+ if [regexp $opts(error) $comp_output] {
+ pass $testname
+ return
+ }
+ }
+ fail $testname
+ return
+ }
+ }
} else {
set objfile "tmpdir/dump0.o"
}
# We must not have expected failure if we get here.
if { $opts(error) != "" } {
fail $testname
+ return
}
if { [which $binary] == 0 } {
set ws {[ ]*}
set nws {[^ ]*}
# whitespace is ignored anywhere except within the options list;
- # option names are alphabetic only
- set pat "^#${ws}(\[a-zA-Z\]*)$ws:${ws}(.*)$ws\$"
+ # option names are alphabetic plus underscore only.
+ set pat "^#${ws}(\[a-zA-Z_\]*)$ws:${ws}(.*)$ws\$"
while { [gets $f line] != -1 } {
set line [string trim $line]
# Whitespace here is space-tab.