XCOFF C_STSYM test failure on 32-bit host
authorAlan Modra <amodra@gmail.com>
Tue, 14 Dec 2021 10:43:21 +0000 (21:13 +1030)
committerAlan Modra <amodra@gmail.com>
Tue, 14 Dec 2021 21:53:10 +0000 (08:23 +1030)
This test was failing here and on another similar symbol:
[  4](sec  1)(fl 0x00)(ty   0)(scl 143) (nx 0) 0x05d1745d11745d21 .bs
where correct output is
[  4](sec  1)(fl 0x00)(ty   0)(scl 143) (nx 0) 0x000000000000000a .bs

The problem is caused by a 32-bit host pointer being sign-extended
when stored into a 64-bit bfd_vma, and then that value not being
trimmed back to 32 bits when used.  The following belt-and-braces
patch fixes both the store and subsequent reads.

* coffcode.h (coff_slurp_symbol_table): Do not sign extend
when storing a host pointer to syment.n_value.
* coffgen.c (coff_get_symbol_info): Cast syment.n_value to a
bfd_hostptr_t before using in arithmetic.
(coff_print_symbol): Likewise.

bfd/coffcode.h
bfd/coffgen.c

index e2b256648ad78bb1db0dceb28721a2092c120da9..4405c9fe5ead17eded6c58f6223e673115a895f6 100644 (file)
@@ -4826,8 +4826,8 @@ coff_slurp_symbol_table (bfd * abfd)
              /* The value is actually a symbol index.  Save a pointer
                 to the symbol instead of the index.  FIXME: This
                 should use a union.  */
-             src->u.syment.n_value =
-               (long) (intptr_t) (native_symbols + src->u.syment.n_value);
+             src->u.syment.n_value
+               = (bfd_hostptr_t) (native_symbols + src->u.syment.n_value);
              dst->symbol.value = src->u.syment.n_value;
              src->fix_value = 1;
              break;
index 5474f6c24d8d35d513ebb0fe36912aae236d649a..5681af1b6217a9f351a96379a82e77037b857da8 100644 (file)
@@ -2130,10 +2130,10 @@ coff_get_symbol_info (bfd *abfd, asymbol *symbol, symbol_info *ret)
   if (coffsymbol (symbol)->native != NULL
       && coffsymbol (symbol)->native->fix_value
       && coffsymbol (symbol)->native->is_sym)
-    ret->value =
-      ((coffsymbol (symbol)->native->u.syment.n_value -
-       (bfd_hostptr_t) obj_raw_syments (abfd))
-       / sizeof (combined_entry_type));
+    ret->value
+      = (((bfd_hostptr_t) coffsymbol (symbol)->native->u.syment.n_value
+         - (bfd_hostptr_t) obj_raw_syments (abfd))
+        / sizeof (combined_entry_type));
 }
 
 /* Print out information about COFF symbol.  */
@@ -2181,7 +2181,8 @@ coff_print_symbol (bfd *abfd,
          if (! combined->fix_value)
            val = (bfd_vma) combined->u.syment.n_value;
          else
-           val = ((combined->u.syment.n_value - (bfd_hostptr_t) root)
+           val = (((bfd_hostptr_t) combined->u.syment.n_value
+                   - (bfd_hostptr_t) root)
                   / sizeof (combined_entry_type));
 
          fprintf (file, "(sec %2d)(fl 0x%02x)(ty %3x)(scl %3d) (nx %d) 0x",