[binutils-gdb] Always fetch Ada "main" name from the executable

Tom Tromey via Gdb-cvs <[email protected]> Mon, 3 Aug 2026 13:27:04 +0000 (GMT)
Newsgroups gmane.comp.gdb.cvs
Message-ID <[email protected]>
https://sourceware.org/git/gitweb.cgi?p=3Dbinutils-gdb.git;h=3D8eafbbc74748=
e499ec785f78858687bd7ea79005

commit 8eafbbc74748e499ec785f78858687bd7ea79005
Author: Tom Tromey <[email protected]>
Date:   Wed Jul 29 12:40:03 2026 -0600

    Always fetch Ada "main" name from the executable
   =20
    The gdb.ada/file-then-restart.exp test was failing with gnat-llvm.  I
    tracked this down to the "main" name not being stored in a readonly
    section, meaning that the code in ada_main_name using trust_readonly
    did not work.
   =20
    However, it seems to me that gdb should always prefer the data from
    the executable in this particular case.  So, rather than relying on
    trust_readonly, this patch changes gdb to do this directly.
   =20
    Approved-By: Pedro Alves <[email protected]>

Diff:
---
 gdb/ada-lang.c | 32 ++++++++++++++++++++------------
 1 file changed, 20 insertions(+), 12 deletions(-)

diff --git a/gdb/ada-lang.c b/gdb/ada-lang.c
index 3c6c9af488f..906c5cd3465 100644
--- a/gdb/ada-lang.c
+++ b/gdb/ada-lang.c
@@ -775,8 +775,6 @@ ada_get_decoded_type (struct type *type)
 const char *
 ada_main_name ()
 {
-  static gdb::unique_xmalloc_ptr<char> main_program_name;
-
   /* For Ada, the name of the main procedure is stored in a specific
      string constant, generated by the binder.  Look for that symbol,
      extract its address, and then read that string.  If we didn't find
@@ -786,21 +784,31 @@ ada_main_name ()
     =3D lookup_minimal_symbol (current_program_space,
 			     ADA_MAIN_PROGRAM_SYMBOL_NAME);
=20
-  if (msym.minsym !=3D NULL)
+  if (msym.minsym !=3D nullptr)
     {
+      static gdb_byte main_program_name[1024];
+
       CORE_ADDR main_program_name_addr =3D msym.value_address ();
       if (main_program_name_addr =3D=3D 0)
 	error (_("Invalid address for Ada main program name."));
=20
-      /* Force trust_readonly, because we always want to fetch this
-	 string from the executable, not from inferior memory.  If the
-	 user changes the exec-file and invokes "start", we want to
-	 pick the "main" from the new executable, not one that may
-	 come from the still-live inferior.  */
-      scoped_restore save_trust_readonly
-	=3D make_scoped_restore (&trust_readonly, true);
-      main_program_name =3D target_read_string (main_program_name_addr, 10=
24);
-      return main_program_name.get ();
+      /* We always want to fetch this string from the executable, not
+	 from inferior memory.  If the user changes the exec-file and
+	 invokes "start", we want to pick the "main" from the new
+	 executable, not one that may come from the still-live
+	 inferior.  */
+      ULONGEST xferred =3D 0;
+      const auto &sections =3D current_program_space->target_sections ();
+      if ((section_table_xfer_memory_partial (main_program_name, nullptr,
+					      main_program_name_addr,
+					      sizeof (main_program_name),
+					      &xferred,
+					      sections)
+	   =3D=3D TARGET_XFER_OK)
+	  && xferred > 0
+	  && (strnlen ((char *) main_program_name, sizeof (main_program_name))
+	      < sizeof (main_program_name)))
+	return (char *) main_program_name;
     }
=20
   /* The main procedure doesn't seem to be in Ada.  */