2012-07-24 Teresa Johnson <tejohnson@google.com>
authorCary Coutant <ccoutant@google.com>
Tue, 24 Jul 2012 21:06:58 +0000 (21:06 +0000)
committerCary Coutant <ccoutant@google.com>
Tue, 24 Jul 2012 21:06:58 +0000 (21:06 +0000)
bfd/
* bfd.c (bfd_find_nearest_line_discriminator): New macro.
* coff-rs6000.c: Init _bfd_find_nearest_line_discriminator.
* coff64-rs6000.c: Likewise.
* dwarf2.c (struct line_info): Add discriminator field.
(add_line_info): Fill in new discriminator field.
(decode_line_info): Record discriminator information instead
        of ignoring it.
(lookup_address_in_line_info_table): Return discriminator field if
        requested.
(comp_unit_find_nearest_line): Add discriminator argument.
(find_line): Likewise.
(_bfd_dwarf2_find_nearest_line): Likewise.
(_bfd_dwarf2_find_line): Likewise.
* elf-bfd.h (_bfd_elf_find_nearest_line_discriminator): New.
        (_bfd_elf_find_line_discriminator): Likewise.
        (_bfd_generic_find_nearest_line_discriminator): Likewise. Defined.
* elf.c (_bfd_elf_find_nearest_line): Change to a wrapper
        that invokes _bfd_elf_find_nearest_line_discriminator with correct
        arguments.
(_bfd_elf_find_nearest_line_discriminator): New.
(_bfd_elf_find_line): Change to a wrapper
        that invokes _bfd_elf_find_line_discriminator with correct
        arguments.
(_bfd_elf_find_line_discriminator): New.
* coffgen.c (coff_find_nearest_line_with_names): Handle
        new discriminator argument.
* elf32-arm.c (elf32_arm_find_nearest_line): Likewise.
* elf64-alpha.c (elf64_alpha_find_nearest_line): Likewise.
* elfxx-mips.c (_bfd_mips_elf_find_nearest_line): Likewise.
* mach-o.c (bfd_mach_o_find_nearest_line): Likewise.
* libbfd-in.h (_bfd_dwarf2_find_nearest_line): Add discriminator
        argument.
        (_bfd_dwarf2_find_line): Likewise.
        (_bfd_generic_find_nearest_line_discriminator): New.
* libbfd.c (_bfd_generic_find_nearest_line_discriminator): New.
* bfd-in2.h: Regenerated.
* libbfd.h: Likewise.
* targets.c (BFD_JUMP_TABLE_SYMBOLS): Initialize
        _bfd_find_nearest_line_discriminator with
        _bfd_generic_find_nearest_line_discriminator.
        (bfd_target): Add _bfd_find_nearest_line_discriminator.

binutils/
* addr2line.c (find_address_in_section): Invoke
        bfd_find_nearest_line_discriminator to get the discriminator.
(find_offset_in_section): Likewise.
(translate_addresses): Print discriminator if it is non-zero.
* objdump.c (show_line): Invoke
        bfd_find_nearest_line_discriminator to get the discriminator,
        and keep track of prev_discriminator. Print discriminator
        if it is non-zero.
(disassemble_data): Initialize prev_discriminator.
(dump_reloc_set): Invoke bfd_find_nearest_line_discriminator
        to get the discriminator, and keep track of last_discriminator.
        Print discriminator if it is non-zero.

20 files changed:
bfd/ChangeLog
bfd/bfd-in2.h
bfd/bfd.c
bfd/coff-rs6000.c
bfd/coff64-rs6000.c
bfd/coffgen.c
bfd/dwarf2.c
bfd/elf-bfd.h
bfd/elf.c
bfd/elf32-arm.c
bfd/elf64-alpha.c
bfd/elfxx-mips.c
bfd/libbfd-in.h
bfd/libbfd.c
bfd/libbfd.h
bfd/mach-o.c
bfd/targets.c
binutils/ChangeLog
binutils/addr2line.c
binutils/objdump.c

index 76665c3cb7d5844187a286abc6fbce4d9732d6b5..b95888942163261f39d2d323eb68eee6159e59ca 100644 (file)
@@ -1,3 +1,47 @@
+2012-07-24  Teresa Johnson  <tejohnson@google.com>
+
+       * bfd.c (bfd_find_nearest_line_discriminator): New macro.
+       * coff-rs6000.c: Init _bfd_find_nearest_line_discriminator.
+       * coff64-rs6000.c: Likewise.
+       * dwarf2.c (struct line_info): Add discriminator field.
+       (add_line_info): Fill in new discriminator field.
+       (decode_line_info): Record discriminator information instead
+        of ignoring it.
+       (lookup_address_in_line_info_table): Return discriminator field if
+        requested.
+       (comp_unit_find_nearest_line): Add discriminator argument.
+       (find_line): Likewise.
+       (_bfd_dwarf2_find_nearest_line): Likewise.
+       (_bfd_dwarf2_find_line): Likewise.
+       * elf-bfd.h (_bfd_elf_find_nearest_line_discriminator): New.
+        (_bfd_elf_find_line_discriminator): Likewise.
+        (_bfd_generic_find_nearest_line_discriminator): Likewise. Defined.
+       * elf.c (_bfd_elf_find_nearest_line): Change to a wrapper
+        that invokes _bfd_elf_find_nearest_line_discriminator with correct
+        arguments.
+       (_bfd_elf_find_nearest_line_discriminator): New.
+       (_bfd_elf_find_line): Change to a wrapper
+        that invokes _bfd_elf_find_line_discriminator with correct
+        arguments.
+       (_bfd_elf_find_line_discriminator): New.
+       * coffgen.c (coff_find_nearest_line_with_names): Handle
+        new discriminator argument.
+       * elf32-arm.c (elf32_arm_find_nearest_line): Likewise.
+       * elf64-alpha.c (elf64_alpha_find_nearest_line): Likewise.
+       * elfxx-mips.c (_bfd_mips_elf_find_nearest_line): Likewise.
+       * mach-o.c (bfd_mach_o_find_nearest_line): Likewise.
+       * libbfd-in.h (_bfd_dwarf2_find_nearest_line): Add discriminator
+        argument.
+        (_bfd_dwarf2_find_line): Likewise.
+        (_bfd_generic_find_nearest_line_discriminator): New.
+       * libbfd.c (_bfd_generic_find_nearest_line_discriminator): New.
+       * bfd-in2.h: Regenerated.
+       * libbfd.h: Likewise.
+       * targets.c (BFD_JUMP_TABLE_SYMBOLS): Initialize
+        _bfd_find_nearest_line_discriminator with
+        _bfd_generic_find_nearest_line_discriminator.
+        (bfd_target): Add _bfd_find_nearest_line_discriminator.
+
 2012-07-24  Sean Keys  <skeys@ipdatasys.com>
 
         * elf32-m68hc1x.c (elf32_m68hc11_relocate_section): Added code
index 7a90a44390842be6aea033f23d590cf548e2e17e..c7ce4cc67a654544ed6f1022f68fdeecee2c35d8 100644 (file)
@@ -5810,6 +5810,11 @@ bfd_boolean bfd_set_private_flags (bfd *abfd, flagword flags);
        BFD_SEND (abfd, _bfd_find_nearest_line, \
                  (abfd, sec, syms, off, file, func, line))
 
+#define bfd_find_nearest_line_discriminator(abfd, sec, syms, off, file, func, \
+                                            line, disc) \
+       BFD_SEND (abfd, _bfd_find_nearest_line_discriminator, \
+                 (abfd, sec, syms, off, file, func, line, disc))
+
 #define bfd_find_line(abfd, syms, sym, file, line) \
        BFD_SEND (abfd, _bfd_find_line, \
                  (abfd, syms, sym, file, line))
@@ -6191,6 +6196,7 @@ typedef struct bfd_target
   NAME##_bfd_is_target_special_symbol, \
   NAME##_get_lineno, \
   NAME##_find_nearest_line, \
+  _bfd_generic_find_nearest_line_discriminator, \
   _bfd_generic_find_line, \
   NAME##_find_inliner_info, \
   NAME##_bfd_make_debug_symbol, \
@@ -6214,6 +6220,9 @@ typedef struct bfd_target
   bfd_boolean (*_bfd_find_nearest_line)
     (bfd *, struct bfd_section *, struct bfd_symbol **, bfd_vma,
      const char **, const char **, unsigned int *);
+  bfd_boolean (*_bfd_find_nearest_line_discriminator)
+    (bfd *, struct bfd_section *, struct bfd_symbol **, bfd_vma,
+     const char **, const char **, unsigned int *, unsigned int *);
   bfd_boolean (*_bfd_find_line)
     (bfd *, struct bfd_symbol **, struct bfd_symbol *,
      const char **, unsigned int *);
index 640b4205d162afc1c3776da33098792e7cb0d64b..eed18960855bdc51be8b57ddba27975afb6b02ef 100644 (file)
--- a/bfd/bfd.c
+++ b/bfd/bfd.c
@@ -1424,6 +1424,11 @@ DESCRIPTION
 .       BFD_SEND (abfd, _bfd_find_nearest_line, \
 .                 (abfd, sec, syms, off, file, func, line))
 .
+.#define bfd_find_nearest_line_discriminator(abfd, sec, syms, off, file, func, \
+.                                            line, disc) \
+.       BFD_SEND (abfd, _bfd_find_nearest_line_discriminator, \
+.                 (abfd, sec, syms, off, file, func, line, disc))
+.
 .#define bfd_find_line(abfd, syms, sym, file, line) \
 .       BFD_SEND (abfd, _bfd_find_line, \
 .                 (abfd, syms, sym, file, line))
index 2a968bfc03f170565a8ba2b1e3f46f67926a0406..9326b32bd1bc8320dbf9f42f1feb0d26d7dfb537 100644 (file)
@@ -4118,6 +4118,7 @@ const bfd_target rs6000coff_vec =
     coff_bfd_is_target_special_symbol,
     coff_get_lineno,
     xcoff_find_nearest_line,
+    _bfd_generic_find_nearest_line_discriminator,
     _bfd_generic_find_line,
     coff_find_inliner_info,
     coff_bfd_make_debug_symbol,
@@ -4373,6 +4374,7 @@ const bfd_target pmac_xcoff_vec =
     coff_bfd_is_target_special_symbol,
     coff_get_lineno,
     xcoff_find_nearest_line,
+    _bfd_generic_find_nearest_line_discriminator,
     _bfd_generic_find_line,
     coff_find_inliner_info,
     coff_bfd_make_debug_symbol,
index 031385deeedd26eeab8504ced446842cad2ac7f8..0821b6ff1774e334bc74633078a662c0fa12e681 100644 (file)
@@ -2710,6 +2710,7 @@ const bfd_target rs6000coff64_vec =
     coff_bfd_is_target_special_symbol,
     coff_get_lineno,
     coff_find_nearest_line,
+    _bfd_generic_find_nearest_line_discriminator,
     _bfd_generic_find_line,
     coff_find_inliner_info,
     coff_bfd_make_debug_symbol,
@@ -2967,6 +2968,7 @@ const bfd_target aix5coff64_vec =
     coff_bfd_is_target_special_symbol,
     coff_get_lineno,
     coff_find_nearest_line,
+    _bfd_generic_find_nearest_line_discriminator,
     _bfd_generic_find_line,
     coff_find_inliner_info,
     coff_bfd_make_debug_symbol,
index c0505c6c02b810adbea251c5db1d550c454d914a..509119b075d9d2ec2d3a6ce4310e7e8f72c96e2b 100644 (file)
@@ -2153,7 +2153,7 @@ coff_find_nearest_line_with_names (bfd *abfd,
   if (_bfd_dwarf2_find_nearest_line (abfd, debug_sections,
                                      section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, 0,
+                                    line_ptr, NULL, 0,
                                     &coff_data(abfd)->dwarf2_find_line_info))
     return TRUE;
 
index d31b84939ad47b29643b3d39627bd8d2e28470d9..069d6141a7717f608f42cd7897f22d6d4ea70979 100644 (file)
@@ -980,6 +980,7 @@ struct line_info
   char *filename;
   unsigned int line;
   unsigned int column;
+  unsigned int discriminator;
   unsigned char op_index;
   unsigned char end_sequence;          /* End of (sequential) code sequence.  */
 };
@@ -1080,6 +1081,7 @@ add_line_info (struct line_info_table *table,
               char *filename,
               unsigned int line,
               unsigned int column,
+              unsigned int discriminator,
               int end_sequence)
 {
   bfd_size_type amt = sizeof (struct line_info);
@@ -1095,6 +1097,7 @@ add_line_info (struct line_info_table *table,
   info->op_index = op_index;
   info->line = line;
   info->column = column;
+  info->discriminator = discriminator;
   info->end_sequence = end_sequence;
 
   if (filename && filename[0])
@@ -1573,6 +1576,7 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
       char * filename = table->num_files ? concat_filename (table, 1) : NULL;
       unsigned int line = 1;
       unsigned int column = 0;
+      unsigned int discriminator = 0;
       int is_stmt = lh.default_is_stmt;
       int end_sequence = 0;
       /* eraxxon@alumni.rice.edu: Against the DWARF2 specs, some
@@ -1607,8 +1611,9 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
              line += lh.line_base + (adj_opcode % lh.line_range);
              /* Append row to matrix using current values.  */
              if (!add_line_info (table, address, op_index, filename,
-                                 line, column, 0))
+                                 line, column, discriminator, 0))
                goto line_fail;
+              discriminator = 0;
              if (address < low_pc)
                low_pc = address;
              if (address > high_pc)
@@ -1626,9 +1631,10 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
                {
                case DW_LNE_end_sequence:
                  end_sequence = 1;
-                 if (!add_line_info (table, address, op_index, filename,
-                                     line, column, end_sequence))
+                 if (!add_line_info (table, address, op_index, filename, line,
+                                     column, discriminator, end_sequence))
                    goto line_fail;
+                  discriminator = 0;
                  if (address < low_pc)
                    low_pc = address;
                  if (address > high_pc)
@@ -1668,7 +1674,8 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
                  table->num_files++;
                  break;
                case DW_LNE_set_discriminator:
-                 (void) read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
+                 discriminator =
+                      read_unsigned_leb128 (abfd, line_ptr, &bytes_read);
                  line_ptr += bytes_read;
                  break;
                case DW_LNE_HP_source_file_correlation:
@@ -1686,8 +1693,9 @@ decode_line_info (struct comp_unit *unit, struct dwarf2_debug *stash)
              break;
            case DW_LNS_copy:
              if (!add_line_info (table, address, op_index,
-                                 filename, line, column, 0))
+                                 filename, line, column, discriminator, 0))
                goto line_fail;
+              discriminator = 0;
              if (address < low_pc)
                low_pc = address;
              if (address > high_pc)
@@ -1788,7 +1796,8 @@ static bfd_boolean
 lookup_address_in_line_info_table (struct line_info_table *table,
                                   bfd_vma addr,
                                   const char **filename_ptr,
-                                  unsigned int *linenumber_ptr)
+                                  unsigned int *linenumber_ptr,
+                                  unsigned int *discriminator_ptr)
 {
   struct line_sequence *seq = NULL;
   struct line_info *each_line;
@@ -1823,6 +1832,8 @@ lookup_address_in_line_info_table (struct line_info_table *table,
         {
           *filename_ptr = each_line->filename;
           *linenumber_ptr = each_line->line;
+          if (discriminator_ptr)
+            *discriminator_ptr = each_line->discriminator;
           return TRUE;
         }
     }
@@ -2552,6 +2563,7 @@ comp_unit_find_nearest_line (struct comp_unit *unit,
                             const char **filename_ptr,
                             const char **functionname_ptr,
                             unsigned int *linenumber_ptr,
+                            unsigned int *discriminator_ptr,
                             struct dwarf2_debug *stash)
 {
   bfd_boolean line_p;
@@ -2592,7 +2604,8 @@ comp_unit_find_nearest_line (struct comp_unit *unit,
     stash->inliner_chain = function;
   line_p = lookup_address_in_line_info_table (unit->line_table, addr,
                                              filename_ptr,
-                                             linenumber_ptr);
+                                             linenumber_ptr,
+                                             discriminator_ptr);
   return line_p || func_p;
 }
 
@@ -3308,6 +3321,7 @@ find_line (bfd *abfd,
           const char **filename_ptr,
           const char **functionname_ptr,
           unsigned int *linenumber_ptr,
+          unsigned int *discriminator_ptr,
           unsigned int addr_size,
           void **pinfo)
 {
@@ -3419,6 +3433,7 @@ find_line (bfd *abfd,
                                                   filename_ptr,
                                                   functionname_ptr,
                                                   linenumber_ptr,
+                                                  discriminator_ptr,
                                                   stash));
          if (found)
            goto done;
@@ -3512,6 +3527,7 @@ find_line (bfd *abfd,
                                                     filename_ptr,
                                                     functionname_ptr,
                                                     linenumber_ptr,
+                                                    discriminator_ptr,
                                                     stash));
 
          if ((bfd_vma) (stash->info_ptr - stash->sec_info_ptr)
@@ -3546,12 +3562,13 @@ _bfd_dwarf2_find_nearest_line (bfd *abfd,
                               const char **filename_ptr,
                               const char **functionname_ptr,
                               unsigned int *linenumber_ptr,
+                               unsigned int *discriminator_ptr,
                               unsigned int addr_size,
                               void **pinfo)
 {
   return find_line (abfd, debug_sections, section, offset, NULL, symbols,
-                    filename_ptr, functionname_ptr, linenumber_ptr, addr_size,
-                   pinfo);
+                    filename_ptr, functionname_ptr, linenumber_ptr,
+                    discriminator_ptr, addr_size, pinfo);
 }
 
 /* The DWARF2 version of find_line.
@@ -3563,11 +3580,13 @@ _bfd_dwarf2_find_line (bfd *abfd,
                       asymbol *symbol,
                       const char **filename_ptr,
                       unsigned int *linenumber_ptr,
+                       unsigned int *discriminator_ptr,
                       unsigned int addr_size,
                       void **pinfo)
 {
   return find_line (abfd, dwarf_debug_sections, NULL, 0, symbol, symbols,
-                    filename_ptr, NULL, linenumber_ptr, addr_size, pinfo);
+                    filename_ptr, NULL, linenumber_ptr, discriminator_ptr,
+                    addr_size, pinfo);
 }
 
 bfd_boolean
index 889ce128b4b526ad731af03bee0688b7a3774d4c..ff0e615cfdc1e1370cdf1cc0e571037cf2321a79 100644 (file)
@@ -1876,9 +1876,16 @@ extern bfd_boolean _bfd_elf_set_arch_mach
 extern bfd_boolean _bfd_elf_find_nearest_line
   (bfd *, asection *, asymbol **, bfd_vma, const char **, const char **,
    unsigned int *);
+extern bfd_boolean _bfd_elf_find_nearest_line_discriminator
+  (bfd *, asection *, asymbol **, bfd_vma, const char **, const char **,
+   unsigned int *, unsigned int *);
 extern bfd_boolean _bfd_elf_find_line
   (bfd *, asymbol **, asymbol *, const char **, unsigned int *);
+extern bfd_boolean _bfd_elf_find_line_discriminator
+  (bfd *, asymbol **, asymbol *, const char **, unsigned int *, unsigned int *);
 #define _bfd_generic_find_line _bfd_elf_find_line
+#define _bfd_generic_find_nearest_line_discriminator \
+        _bfd_elf_find_nearest_line_discriminator
 extern bfd_boolean _bfd_elf_find_inliner_info
   (bfd *, const char **, const char **, unsigned int *);
 #define _bfd_elf_read_minisymbols _bfd_generic_read_minisymbols
index 48e5d68341354e0d6915c8d9659e5cc6885d71d8..0ac4032b699cb0a703a41b896ec403ac8b04b178 100644 (file)
--- a/bfd/elf.c
+++ b/bfd/elf.c
@@ -7566,6 +7566,23 @@ _bfd_elf_find_nearest_line (bfd *abfd,
                            const char **filename_ptr,
                            const char **functionname_ptr,
                            unsigned int *line_ptr)
+{
+  return _bfd_elf_find_nearest_line_discriminator (abfd, section, symbols,
+                                                   offset, filename_ptr,
+                                                   functionname_ptr,
+                                                   line_ptr,
+                                                   NULL);
+}
+
+bfd_boolean
+_bfd_elf_find_nearest_line_discriminator (bfd *abfd,
+                                          asection *section,
+                                          asymbol **symbols,
+                                          bfd_vma offset,
+                                          const char **filename_ptr,
+                                          const char **functionname_ptr,
+                                          unsigned int *line_ptr,
+                                          unsigned int *discriminator_ptr)
 {
   bfd_boolean found;
 
@@ -7584,7 +7601,7 @@ _bfd_elf_find_nearest_line (bfd *abfd,
   if (_bfd_dwarf2_find_nearest_line (abfd, dwarf_debug_sections,
                                      section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, 0,
+                                    line_ptr, discriminator_ptr, 0,
                                     &elf_tdata (abfd)->dwarf2_find_line_info))
     {
       if (!*functionname_ptr)
@@ -7619,9 +7636,20 @@ _bfd_elf_find_nearest_line (bfd *abfd,
 bfd_boolean
 _bfd_elf_find_line (bfd *abfd, asymbol **symbols, asymbol *symbol,
                    const char **filename_ptr, unsigned int *line_ptr)
+{
+  return _bfd_elf_find_line_discriminator (abfd, symbols, symbol,
+                                          filename_ptr, line_ptr,
+                                           NULL);
+}
+
+bfd_boolean
+_bfd_elf_find_line_discriminator (bfd *abfd, asymbol **symbols, asymbol *symbol,
+                                  const char **filename_ptr,
+                                  unsigned int *line_ptr,
+                                  unsigned int *discriminator_ptr)
 {
   return _bfd_dwarf2_find_line (abfd, symbols, symbol,
-                               filename_ptr, line_ptr, 0,
+                               filename_ptr, line_ptr, discriminator_ptr, 0,
                                &elf_tdata (abfd)->dwarf2_find_line_info);
 }
 
index bc1f19532cde4d5a48f7c88430ccdf8a7931cd3a..1bbd96ce9ef2105ccc406084eec3e48b9f2421ca 100644 (file)
@@ -12886,7 +12886,7 @@ elf32_arm_find_nearest_line (bfd *          abfd,
   if (_bfd_dwarf2_find_nearest_line (abfd, dwarf_debug_sections,
                                      section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, 0,
+                                    line_ptr, NULL, 0,
                                     & elf_tdata (abfd)->dwarf2_find_line_info))
     {
       if (!*functionname_ptr)
index 40e4bfb318c5abc31fb19f5b9786cc0a98bd7cf5..deb03c183c0c6294c85263f528010c0e07f18449 100644 (file)
@@ -1452,7 +1452,7 @@ elf64_alpha_find_nearest_line (bfd *abfd, asection *section, asymbol **symbols,
   if (_bfd_dwarf2_find_nearest_line (abfd, dwarf_debug_sections,
                                      section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, 0,
+                                    line_ptr, NULL, 0,
                                     &elf_tdata (abfd)->dwarf2_find_line_info))
     return TRUE;
 
index 9478f16380e89d0e451fda9d652177b712483fa6..9fef8efe464c7a92eacd64589ebd4a0ae6ee33d0 100644 (file)
@@ -11709,7 +11709,7 @@ _bfd_mips_elf_find_nearest_line (bfd *abfd, asection *section,
   if (_bfd_dwarf2_find_nearest_line (abfd, dwarf_debug_sections,
                                      section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, ABI_64_P (abfd) ? 8 : 0,
+                                    line_ptr, NULL, ABI_64_P (abfd) ? 8 : 0,
                                     &elf_tdata (abfd)->dwarf2_find_line_info))
     return TRUE;
 
index baffaea1bafbeee5906a8af0b7bfaa3de90fd409..c424fe2510e297803dc64cba09bd4c3a7a1cdf08 100644 (file)
@@ -540,16 +540,21 @@ extern const struct dwarf_debug_section dwarf_debug_sections[];
 /* Find the nearest line using DWARF 2 debugging information.  */
 extern bfd_boolean _bfd_dwarf2_find_nearest_line
   (bfd *, const struct dwarf_debug_section *, asection *, asymbol **, bfd_vma,
-   const char **, const char **, unsigned int *, unsigned int, void **);
+   const char **, const char **, unsigned int *, unsigned int *, unsigned int,
+   void **);
 
 /* Find the line using DWARF 2 debugging information.  */
 extern bfd_boolean _bfd_dwarf2_find_line
   (bfd *, asymbol **, asymbol *, const char **,
-   unsigned int *, unsigned int, void **);
+   unsigned int *, unsigned int *, unsigned int, void **);
 
 bfd_boolean _bfd_generic_find_line
   (bfd *, asymbol **, asymbol *, const char **, unsigned int *);
 
+bfd_boolean _bfd_generic_find_nearest_line_discriminator
+  (bfd *, asection *, asymbol **, bfd_vma, const char **, const char **,
+   unsigned int *, unsigned int *);
+
 /* Find inliner info after calling bfd_find_nearest_line. */
 extern bfd_boolean _bfd_dwarf2_find_inliner_info
   (bfd *, const char **, const char **, unsigned int *, void **);
index 44651cf9c3e17122633b3c16b3c0ff565c8b9c15..553c729562acaa497dff6eb67dc3c2b995538ae7 100644 (file)
@@ -1117,6 +1117,19 @@ _bfd_generic_find_line (bfd *abfd ATTRIBUTE_UNUSED,
   return FALSE;
 }
 
+bfd_boolean
+_bfd_generic_find_nearest_line_discriminator (bfd *abfd ATTRIBUTE_UNUSED,
+                                              asection *section ATTRIBUTE_UNUSED,
+                                              asymbol **symbols ATTRIBUTE_UNUSED,
+                                              bfd_vma offset ATTRIBUTE_UNUSED,
+                                              const char **filename_ptr ATTRIBUTE_UNUSED,
+                                              const char **functionname_ptr ATTRIBUTE_UNUSED,
+                                              unsigned int *line_ptr ATTRIBUTE_UNUSED,
+                                              unsigned int *discriminator_ptr ATTRIBUTE_UNUSED)
+{
+  return FALSE;
+}
+
 bfd_boolean
 _bfd_generic_init_private_section_data (bfd *ibfd ATTRIBUTE_UNUSED,
                                        asection *isec ATTRIBUTE_UNUSED,
index 1d95fd8352f8e8a272bb5e458236af8341f905c7..e74ce34ad40821cc66f9e7bdbecc87127d3a309c 100644 (file)
@@ -545,16 +545,21 @@ extern const struct dwarf_debug_section dwarf_debug_sections[];
 /* Find the nearest line using DWARF 2 debugging information.  */
 extern bfd_boolean _bfd_dwarf2_find_nearest_line
   (bfd *, const struct dwarf_debug_section *, asection *, asymbol **, bfd_vma,
-   const char **, const char **, unsigned int *, unsigned int, void **);
+   const char **, const char **, unsigned int *, unsigned int *, unsigned int,
+   void **);
 
 /* Find the line using DWARF 2 debugging information.  */
 extern bfd_boolean _bfd_dwarf2_find_line
   (bfd *, asymbol **, asymbol *, const char **,
-   unsigned int *, unsigned int, void **);
+   unsigned int *, unsigned int *, unsigned int, void **);
 
 bfd_boolean _bfd_generic_find_line
   (bfd *, asymbol **, asymbol *, const char **, unsigned int *);
 
+bfd_boolean _bfd_generic_find_nearest_line_discriminator
+  (bfd *, asection *, asymbol **, bfd_vma, const char **, const char **,
+   unsigned int *, unsigned int *);
+
 /* Find inliner info after calling bfd_find_nearest_line. */
 extern bfd_boolean _bfd_dwarf2_find_inliner_info
   (bfd *, const char **, const char **, unsigned int *, void **);
index 1f9fc17608539692303a4c1c4c181d047355b730..84d5a72960f0a009d1504590df596821e1e604a8 100644 (file)
@@ -4836,7 +4836,7 @@ bfd_mach_o_find_nearest_line (bfd *abfd,
   if (_bfd_dwarf2_find_nearest_line (abfd, dwarf_debug_sections,
                                     section, symbols, offset,
                                     filename_ptr, functionname_ptr,
-                                    line_ptr, 0,
+                                    line_ptr, NULL, 0,
                                     &mdata->dwarf2_find_line_info))
     return TRUE;
   return FALSE;
index cfa91a8fb824b0a5a62562306438975068d23cbe..ce1cf350f4849a52d28e6855c24fed39da49cad9 100644 (file)
@@ -369,6 +369,7 @@ BFD_JUMP_TABLE macros.
 .  NAME##_bfd_is_target_special_symbol, \
 .  NAME##_get_lineno, \
 .  NAME##_find_nearest_line, \
+.  _bfd_generic_find_nearest_line_discriminator, \
 .  _bfd_generic_find_line, \
 .  NAME##_find_inliner_info, \
 .  NAME##_bfd_make_debug_symbol, \
@@ -392,6 +393,9 @@ BFD_JUMP_TABLE macros.
 .  bfd_boolean (*_bfd_find_nearest_line)
 .    (bfd *, struct bfd_section *, struct bfd_symbol **, bfd_vma,
 .     const char **, const char **, unsigned int *);
+.  bfd_boolean (*_bfd_find_nearest_line_discriminator)
+.    (bfd *, struct bfd_section *, struct bfd_symbol **, bfd_vma,
+.     const char **, const char **, unsigned int *, unsigned int *);
 .  bfd_boolean (*_bfd_find_line)
 .    (bfd *, struct bfd_symbol **, struct bfd_symbol *,
 .     const char **, unsigned int *);
index 306893761681efbda18c3cb6c0a34c79cdfa412c..0edd5197c09b8fa94b7b1ab3af6fd82984af50f6 100644 (file)
@@ -1,3 +1,18 @@
+2012-07-24  Teresa Johnson  <tejohnson@google.com>
+
+       * addr2line.c (find_address_in_section): Invoke
+        bfd_find_nearest_line_discriminator to get the discriminator.
+       (find_offset_in_section): Likewise.
+       (translate_addresses): Print discriminator if it is non-zero.
+       * objdump.c (show_line): Invoke
+        bfd_find_nearest_line_discriminator to get the discriminator,
+        and keep track of prev_discriminator. Print discriminator
+        if it is non-zero.
+       (disassemble_data): Initialize prev_discriminator.
+       (dump_reloc_set): Invoke bfd_find_nearest_line_discriminator
+        to get the discriminator, and keep track of last_discriminator.
+        Print discriminator if it is non-zero.
+
 2012-07-17  Nick Clifton  <nickc@redhat.com>
 
        * elfcomm.c (setup_archive): Extract index table and symbol table
index 663da4570e5887866456415d40dd8d477936020a..5febaeae629230d9069f9b2c9f05f3dc3b1e5744 100644 (file)
@@ -139,6 +139,7 @@ static bfd_vma pc;
 static const char *filename;
 static const char *functionname;
 static unsigned int line;
+static unsigned int discriminator;
 static bfd_boolean found;
 
 /* Look for an address in a section.  This is called via
@@ -165,8 +166,9 @@ find_address_in_section (bfd *abfd, asection *section,
   if (pc >= vma + size)
     return;
 
-  found = bfd_find_nearest_line (abfd, section, syms, pc - vma,
-                                &filename, &functionname, &line);
+  found = bfd_find_nearest_line_discriminator (abfd, section, syms, pc - vma,
+                                               &filename, &functionname,
+                                               &line, &discriminator);
 }
 
 /* Look for an offset in a section.  This is directly called.  */
@@ -186,8 +188,9 @@ find_offset_in_section (bfd *abfd, asection *section)
   if (pc >= size)
     return;
 
-  found = bfd_find_nearest_line (abfd, section, syms, pc,
-                                &filename, &functionname, &line);
+  found = bfd_find_nearest_line_discriminator (abfd, section, syms, pc,
+                                               &filename, &functionname,
+                                               &line, &discriminator);
 }
 
 /* Read hexadecimal addresses from stdin, translate into
@@ -294,7 +297,12 @@ translate_addresses (bfd *abfd, asection *section)
 
               printf ("%s:", filename ? filename : "??");
              if (line != 0)
-               printf ("%u\n", line);
+                {
+                  if (discriminator != 0)
+                    printf ("%u (discriminator %u)\n", line, discriminator);
+                  else
+                    printf ("%u\n", line);
+                }
              else
                printf ("?\n");
               if (!unwind_inlines)
index b22bf8bde62c977a622e9e892677bcbe1996d4ff..49a2457be73c155aaca29420e5e77635a32a2116 100644 (file)
@@ -1086,6 +1086,7 @@ objdump_symbol_at_address (bfd_vma vma, struct disassemble_info * inf)
 
 static char *prev_functionname;
 static unsigned int prev_line;
+static unsigned int prev_discriminator;
 
 /* We keep a list of all files that we have seen when doing a
    disassembly with source, so that we know how much of the file to
@@ -1312,13 +1313,15 @@ show_line (bfd *abfd, asection *section, bfd_vma addr_offset)
   const char *filename;
   const char *functionname;
   unsigned int linenumber;
+  unsigned int discriminator;
   bfd_boolean reloc;
 
   if (! with_line_numbers && ! with_source_code)
     return;
 
-  if (! bfd_find_nearest_line (abfd, section, syms, addr_offset, &filename,
-                              &functionname, &linenumber))
+  if (! bfd_find_nearest_line_discriminator (abfd, section, syms, addr_offset,
+                                             &filename, &functionname,
+                                             &linenumber, &discriminator))
     return;
 
   if (filename != NULL && *filename == '\0')
@@ -1370,8 +1373,15 @@ show_line (bfd *abfd, asection *section, bfd_vma addr_offset)
          && (prev_functionname == NULL
              || strcmp (functionname, prev_functionname) != 0))
        printf ("%s():\n", functionname);
-      if (linenumber > 0 && linenumber != prev_line)
-       printf ("%s:%u\n", filename == NULL ? "???" : filename, linenumber);
+      if (linenumber > 0 && (linenumber != prev_line || 
+                             (discriminator != prev_discriminator)))
+        { 
+          if (discriminator > 0)
+            printf ("%s:%u (discriminator %u)\n", filename == NULL ? "???" : filename,
+                    linenumber, discriminator);
+          else
+            printf ("%s:%u\n", filename == NULL ? "???" : filename, linenumber);
+        }
     }
 
   if (with_source_code
@@ -1423,6 +1433,9 @@ show_line (bfd *abfd, asection *section, bfd_vma addr_offset)
 
   if (linenumber > 0 && linenumber != prev_line)
     prev_line = linenumber;
+
+  if (discriminator != prev_discriminator)
+    prev_discriminator = discriminator;
 }
 
 /* Pseudo FILE object for strings.  */
@@ -2115,6 +2128,7 @@ disassemble_data (bfd *abfd)
   print_files = NULL;
   prev_functionname = NULL;
   prev_line = -1;
+  prev_discriminator = 0;
 
   /* We make a copy of syms to sort.  We don't want to sort syms
      because that will screw up the relocs.  */
@@ -2895,6 +2909,7 @@ dump_reloc_set (bfd *abfd, asection *sec, arelent **relpp, long relcount)
   arelent **p;
   char *last_filename, *last_functionname;
   unsigned int last_line;
+  unsigned int last_discriminator;
 
   /* Get column headers lined up reasonably.  */
   {
@@ -2913,12 +2928,14 @@ dump_reloc_set (bfd *abfd, asection *sec, arelent **relpp, long relcount)
   last_filename = NULL;
   last_functionname = NULL;
   last_line = 0;
+  last_discriminator = 0;
 
   for (p = relpp; relcount && *p != NULL; p++, relcount--)
     {
       arelent *q = *p;
       const char *filename, *functionname;
       unsigned int linenumber;
+      unsigned int discriminator;
       const char *sym_name;
       const char *section_name;
       bfd_vma addend2 = 0;
@@ -2932,8 +2949,9 @@ dump_reloc_set (bfd *abfd, asection *sec, arelent **relpp, long relcount)
 
       if (with_line_numbers
          && sec != NULL
-         && bfd_find_nearest_line (abfd, sec, syms, q->address,
-                                   &filename, &functionname, &linenumber))
+         && bfd_find_nearest_line_discriminator (abfd, sec, syms, q->address,
+                                                  &filename, &functionname,
+                                                  &linenumber, &discriminator))
        {
          if (functionname != NULL
              && (last_functionname == NULL
@@ -2949,10 +2967,16 @@ dump_reloc_set (bfd *abfd, asection *sec, arelent **relpp, long relcount)
              && (linenumber != last_line
                  || (filename != NULL
                      && last_filename != NULL
-                     && filename_cmp (filename, last_filename) != 0)))
+                     && filename_cmp (filename, last_filename) != 0)
+                  || (discriminator != last_discriminator)))
            {
-             printf ("%s:%u\n", filename == NULL ? "???" : filename, linenumber);
+              if (discriminator > 0)
+                printf ("%s:%u\n", filename == NULL ? "???" : filename, linenumber);
+              else
+                printf ("%s:%u (discriminator %u)\n", filename == NULL ? "???" : filename,
+                        linenumber, discriminator);
              last_line = linenumber;
+             last_discriminator = discriminator;
              if (last_filename != NULL)
                free (last_filename);
              if (filename == NULL)