]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
[gdb/symtab] Note errors in process_skeletonless_type_units
authorTom de Vries <tdevries@suse.de>
Wed, 28 May 2025 20:17:19 +0000 (22:17 +0200)
committerTom de Vries <tdevries@suse.de>
Wed, 28 May 2025 20:17:19 +0000 (22:17 +0200)
With a hello world a.out, and using the compiler flags from target board
dwarf5-fission-debug-types:
...
$ gcc -gdwarf-5 -fdebug-types-section -gsplit-dwarf ~/data/hello.c
...
I run into:
...
$ gdb -q -batch a.out
terminate called after throwing an instance of 'gdb_exception_error'
...

What happens is that an error is thrown due to invalid dwarf, but the error is
not caught, causing gdb to terminate.

In a way, this is a duplicate of PR32861, in the sense that we no longer run
into this after:
- applying the proposed patch (work around compiler bug), or
- using gcc 9 or newer (compiler bug fixed).

But in this case, the failure mode is worse than in PR32861.

Fix this by catching the error in
cooked_index_worker_debug_info::process_skeletonless_type_units.

With the patch, we get instead:
...
$ gdb -q -batch a.out
Offset from DW_FORM_GNU_str_index or DW_FORM_strx pointing outside of \
  .debug_str.dwo section in CU at offset 0x0 [in module a.out]
...

While we're at it, absorb the common use of
cooked_index_worker_result::note_error:
...
  try
    {
      ...
    }
  catch (gdb_exception &exc)
    {
      (...).note_error (std::move (exc));
    }
...
into the method and rename it to catch_error, resulting in more compact code
for the fix:
...
  (...).catch_error ([&] ()
    {
      ...
    });
...

While we're at it, also use it in
cooked_index_worker_debug_info::process_units which looks like it needs the
same fix.

Tested on x86_64-linux.

PR symtab/32979
Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=32979

gdb/dwarf2/cooked-index-worker.h
gdb/dwarf2/read-debug-names.c
gdb/dwarf2/read.c

index df5c31d572dfe89c067c1118d34e7d07e8a084aa..c68620578cc7b1fbfe6e665bf0666079093395b3 100644 (file)
@@ -107,11 +107,20 @@ public:
     return &m_parent_map;
   }
 
-  /* Add an exception to the list of exceptions caught while reading.
-     These are passed forward and printed by the main thread.  */
-  void note_error (gdb_exception &&except)
+  /* Catch exceptions from calling F (), and add them to the list of caught
+     exceptions.  These are passed forward and printed by the main thread.  */
+  template <typename F>
+  void
+  catch_error (F &&f)
   {
-    m_exceptions.push_back (std::move (except));
+    try
+      {
+       f ();
+      }
+    catch (gdb_exception &ex)
+      {
+       m_exceptions.push_back (std::move (ex));
+      }
   }
 
   /* Called when the thread using this object is done with its work.
index 11de9862882732138065e094bfd37a1610a51bc6..e5f604a8eb6c7de95b168b08e8058bad4d69d983 100644 (file)
@@ -416,15 +416,11 @@ cooked_index_worker_debug_names::do_reading ()
 {
   complaint_interceptor complaint_handler;
 
-  try
+  /* Arbitrarily put all exceptions into the first result.  */
+  m_map.indices[0].catch_error ([&] ()
     {
       m_map.scan_all_names ();
-    }
-  catch (gdb_exception &exc)
-    {
-      /* Arbitrarily put all exceptions into the first result.  */
-      m_map.indices[0].note_error (std::move (exc));
-    }
+    });
 
   bool first = true;
   for (auto &iter : m_map.indices)
index 273d594adfe24b5acf3fc31c872a1f60b3c6b5c3..b178dacbe3d18b28abca453edecf805ba0c22a71 100644 (file)
@@ -3425,7 +3425,10 @@ cooked_index_worker_debug_info::process_type_units
                          abbrev_table.get (), nullptr, false,
                          language_minimal);
       if (!reader.is_dummy ())
-       process_type_unit (&reader, storage);
+       storage->catch_error ([&] ()
+         {
+           process_type_unit (&reader, storage);
+         });
     }
 }
 
@@ -3467,7 +3470,10 @@ cooked_index_worker_debug_info::process_skeletonless_type_units
   if (per_objfile->per_bfd->dwp_file == nullptr)
     for (const dwo_file_up &file : per_objfile->per_bfd->dwo_files)
       for (const dwo_unit_up &unit : file->tus)
-       process_skeletonless_type_unit (unit.get (), per_objfile, storage);
+       storage->catch_error ([&] ()
+         {
+           process_skeletonless_type_unit (unit.get (), per_objfile, storage);
+         });
 }
 
 void
@@ -3486,14 +3492,10 @@ cooked_index_worker_debug_info::process_units (size_t task_number,
     {
       dwarf2_per_cu *per_cu = inner->get ();
 
-      try
+      thread_storage.catch_error ([&] ()
        {
          process_unit (per_cu, m_per_objfile, &thread_storage);
-       }
-      catch (gdb_exception &except)
-       {
-         thread_storage.note_error (std::move (except));
-       }
+       });
     }
 
   thread_storage.done_reading (complaint_handler.release ());