]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
Change pop_context to return a block
authorTom Tromey <tromey@adacore.com>
Wed, 15 Apr 2026 17:46:21 +0000 (11:46 -0600)
committerTom Tromey <tromey@adacore.com>
Mon, 20 Apr 2026 14:23:16 +0000 (08:23 -0600)
This changes buildsym_compunit::pop_context to create and return the
block, if needed.  It also arranges to reset some fields in the
buildsym_compunit object to their saved values.

This also enables the removal of the set_local_using_directives
method.

Approved-By: Simon Marchi <simon.marchi@efficios.com>
gdb/buildsym.c
gdb/buildsym.h
gdb/dwarf2/read.c

index 0746717b014aaec09d88cc682b5a7dce2c9186b1..733d6c7f0dd1ade7dfa055238879468a9d0e5a6d 100644 (file)
@@ -940,14 +940,25 @@ buildsym_compunit::push_context (CORE_ADDR valu)
   return ctx;
 }
 
-/* Pop a context block.  Returns the address of the context block just
-   popped.  */
+/* See buildsym.h.  */
 
-context_stack
-buildsym_compunit::pop_context ()
+block *
+buildsym_compunit::pop_context (CORE_ADDR end_addr,
+                               const struct dynamic_prop *static_link,
+                               bool required)
 {
   gdb_assert (!m_context_stack.empty ());
-  context_stack result = m_context_stack.back ();
+  context_stack cstk = std::move (m_context_stack.back ());
   m_context_stack.pop_back ();
+
+  block *result = nullptr;
+  if (required || !m_local_symbols.empty ()
+      || m_local_using_directives != nullptr)
+    result = finish_block (cstk.name, cstk.old_blocks, static_link,
+                          cstk.start_addr, end_addr);
+
+  m_local_symbols = std::move (cstk.locals);
+  m_local_using_directives = cstk.local_using_directives;
+
   return result;
 }
index 70d22229f5347fc210fbeeab5ed34c810e3ebc5f..d1199735abbe7c9bfa2195d0776dc082d35d5d37 100644 (file)
@@ -189,11 +189,6 @@ struct buildsym_compunit
     return &m_local_using_directives;
   }
 
-  void set_local_using_directives (struct using_direct *new_local)
-  {
-    m_local_using_directives = new_local;
-  }
-
   struct using_direct **get_global_using_directives ()
   {
     return &m_global_using_directives;
@@ -243,7 +238,15 @@ struct buildsym_compunit
 
   context_stack &push_context (CORE_ADDR valu);
 
-  context_stack pop_context ();
+  /* Pop a context and create the corresponding block.  Returns the
+     block.  END_ADDR is the final address of the block.  STATIC_LINK,
+     if provided, is the static link.  REQUIRED controls whether the
+     block is required.  When false, if the block does not contain any
+     variables or 'using' directives, this method will return
+     nullptr.  */
+  block *pop_context (CORE_ADDR end_addr,
+                     const struct dynamic_prop *static_link = nullptr,
+                     bool required = true);
 
   struct block *end_compunit_symtab_get_static_block
     (CORE_ADDR end_addr, bool expandable, bool required);
index c4601fee3917f64ca673df7feaaf1b6456592e5d..1c4173eb44d64833f865cb37174ccfeb00dcfd6c 100644 (file)
@@ -7717,7 +7717,6 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
   CORE_ADDR highpc;
   struct attribute *attr, *call_line, *call_file;
   const char *name;
-  struct block *block;
   int inlined_func = (die->tag == DW_TAG_inlined_subroutine);
   std::vector<struct symbol *> template_args;
   struct template_symbol *templ_func = NULL;
@@ -7804,17 +7803,18 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
 
   gdb_assert (cu->get_builder () != nullptr);
   context_stack &ctx = cu->get_builder ()->push_context (lowpc);
-  ctx.name = new_symbol (die, read_type_die (die, cu), cu, templ_func);
+  symbol *func_sym = new_symbol (die, read_type_die (die, cu), cu, templ_func);
+  ctx.name = func_sym;
 
   if (dwarf2_func_is_main_p (die, cu))
-    set_objfile_main_name (objfile, ctx.name->linkage_name (),
+    set_objfile_main_name (objfile, func_sym->linkage_name (),
                           cu->lang ());
 
   /* If there is a location expression for DW_AT_frame_base, record
      it.  */
   attr = dwarf2_attr (die, DW_AT_frame_base, cu);
   if (attr != nullptr)
-    dwarf2_symbol_mark_computed (attr, ctx.name, cu, 1);
+    dwarf2_symbol_mark_computed (attr, func_sym, cu, 1);
 
   /* If there is a location for the static link, record it.  */
   dynamic_prop *static_link = nullptr;
@@ -7866,11 +7866,7 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
        }
     }
 
-  struct context_stack cstk = cu->get_builder ()->pop_context ();
-
-  /* Make a block for the local symbols within.  */
-  block = cu->get_builder ()->finish_block (cstk.name, cstk.old_blocks,
-                                           static_link, lowpc, highpc);
+  block *block = cu->get_builder ()->pop_context (highpc, static_link);
 
   /* For C++, set the block's scope.  */
   if ((cu->lang () == language_cplus
@@ -7884,7 +7880,7 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
   /* If we have address ranges, record them.  */
   dwarf2_record_block_ranges (die, block, cu);
 
-  gdbarch_make_symbol_special (gdbarch, cstk.name, objfile);
+  gdbarch_make_symbol_special (gdbarch, func_sym, objfile);
 
   /* Attach template arguments to function.  */
   if (!template_args.empty ())
@@ -7906,13 +7902,6 @@ read_func_scope (struct die_info *die, struct dwarf2_cu *cu)
       for (symbol *sym : template_args)
        sym->set_symtab (templ_func->symtab ());
     }
-
-  /* In C++, we can have functions nested inside functions (e.g., when
-     a function declares a class that has methods).  This means that
-     when we finish processing a function scope, we may need to go
-     back to building a containing block's symbol lists.  */
-  cu->get_builder ()->get_local_symbols () = std::move (cstk.locals);
-  cu->get_builder ()->set_local_using_directives (cstk.local_using_directives);
 }
 
 /* Process all the DIES contained within a lexical block scope.  Start
@@ -7960,29 +7949,21 @@ read_lexical_block_scope (struct die_info *die, struct dwarf2_cu *cu)
     process_die (child_die, cu);
 
   inherit_abstract_dies (die, cu);
-  struct context_stack cstk = cu->get_builder ()->pop_context ();
 
-  if (!cu->get_builder ()->get_local_symbols ().empty ()
-      || (*cu->get_builder ()->get_local_using_directives ()) != NULL)
-    {
-      struct block *block
-       = cu->get_builder ()->finish_block (0, cstk.old_blocks, NULL,
-                                    cstk.start_addr, highpc);
+  block *block = cu->get_builder ()->pop_context (highpc, nullptr, false);
 
-      /* Note that recording ranges after traversing children, as we
-        do here, means that recording a parent's ranges entails
-        walking across all its children's ranges as they appear in
-        the address map, which is quadratic behavior.
+  /* Note that recording ranges after traversing children, as we
+     do here, means that recording a parent's ranges entails
+     walking across all its children's ranges as they appear in
+     the address map, which is quadratic behavior.
 
-        It would be nicer to record the parent's ranges before
-        traversing its children, simply overriding whatever you find
-        there.  But since we don't even decide whether to create a
-        block until after we've traversed its children, that's hard
-        to do.  */
-      dwarf2_record_block_ranges (die, block, cu);
-    }
-  cu->get_builder ()->get_local_symbols () = std::move (cstk.locals);
-  cu->get_builder ()->set_local_using_directives (cstk.local_using_directives);
+     It would be nicer to record the parent's ranges before
+     traversing its children, simply overriding whatever you find
+     there.  But since we don't even decide whether to create a
+     block until after we've traversed its children, that's hard
+     to do.  */
+  if (block != nullptr)
+    dwarf2_record_block_ranges (die, block, cu);
 }
 
 static void dwarf2_ranges_read_low_addrs