From: simon.marchi@polymtl.ca
To: gdb-patches@sourceware.org
Cc: Simon Marchi <simon.marchi@efficios.com>
Subject: [PATCH] gdb/solib-frv: remove manual memory management
Date: Tue, 17 Feb 2026 16:16:44 -0500 [thread overview]
Message-ID: <20260217211650.3999842-1-simon.marchi@polymtl.ca> (raw)
From: Simon Marchi <simon.marchi@efficios.com>
- Make fetch_loadmap return a unique pointer, adjust callers
- Make fetch_loadmap use a unique pointer for ext_ldmbuf
- Replace some fields of lm_info_frv to be unique pointers
- Make main_executable_lm_info a unique pointer
I can only build-test this.
Change-Id: I5782ea31b5e30fef2c7468f0bc24d10ffae92669
---
gdb/solib-frv.c | 105 +++++++++++++++++++++++-------------------------
1 file changed, 50 insertions(+), 55 deletions(-)
diff --git a/gdb/solib-frv.c b/gdb/solib-frv.c
index 95f97dc11333..dedf26ae64d8 100644
--- a/gdb/solib-frv.c
+++ b/gdb/solib-frv.c
@@ -80,6 +80,9 @@ struct ext_elf32_fdpic_loadmap {
struct ext_elf32_fdpic_loadseg segs[1 /* nsegs, actually */];
};
+using ext_elf32_fdpic_loadmap_up
+ = gdb::unique_xmalloc_ptr<ext_elf32_fdpic_loadmap>;
+
/* Internal versions; the types are GDB types and the data in each
of the fields is (or will be) decoded from the external struct
for ease of consumption. */
@@ -102,19 +105,20 @@ struct int_elf32_fdpic_loadmap {
struct int_elf32_fdpic_loadseg segs[1 /* nsegs, actually */];
};
+using int_elf32_fdpic_loadmap_up
+ = gdb::unique_xmalloc_ptr<int_elf32_fdpic_loadmap>;
+
/* Given address LDMADDR, fetch and decode the loadmap at that address.
Return NULL if there is a problem reading the target memory or if
there doesn't appear to be a loadmap at the given address. The
allocated space (representing the loadmap) returned by this
function may be freed via a single call to xfree(). */
-static struct int_elf32_fdpic_loadmap *
+static int_elf32_fdpic_loadmap_up
fetch_loadmap (CORE_ADDR ldmaddr)
{
bfd_endian byte_order = gdbarch_byte_order (current_inferior ()->arch ());
struct ext_elf32_fdpic_loadmap ext_ldmbuf_partial;
- struct ext_elf32_fdpic_loadmap *ext_ldmbuf;
- struct int_elf32_fdpic_loadmap *int_ldmbuf;
int ext_ldmbuf_size, int_ldmbuf_size;
int version, seg, nsegs;
@@ -147,18 +151,19 @@ fetch_loadmap (CORE_ADDR ldmaddr)
/* Allocate space for the complete (external) loadmap. */
ext_ldmbuf_size = sizeof (struct ext_elf32_fdpic_loadmap)
+ (nsegs - 1) * sizeof (struct ext_elf32_fdpic_loadseg);
- ext_ldmbuf = (struct ext_elf32_fdpic_loadmap *) xmalloc (ext_ldmbuf_size);
+ ext_elf32_fdpic_loadmap_up ext_ldmbuf
+ (XNEWVAR (ext_elf32_fdpic_loadmap, ext_ldmbuf_size));
/* Copy over the portion of the loadmap that's already been read. */
- memcpy (ext_ldmbuf, &ext_ldmbuf_partial, sizeof ext_ldmbuf_partial);
+ memcpy (ext_ldmbuf.get (), &ext_ldmbuf_partial, sizeof ext_ldmbuf_partial);
/* Read the rest of the loadmap from the target. */
if (target_read_memory (ldmaddr + sizeof ext_ldmbuf_partial,
- (gdb_byte *) ext_ldmbuf + sizeof ext_ldmbuf_partial,
+ ((gdb_byte *) ext_ldmbuf.get ()
+ + sizeof ext_ldmbuf_partial),
ext_ldmbuf_size - sizeof ext_ldmbuf_partial))
{
/* Couldn't read rest of the loadmap. */
- xfree (ext_ldmbuf);
return NULL;
}
@@ -166,7 +171,8 @@ fetch_loadmap (CORE_ADDR ldmaddr)
external loadsegs. I.e, allocate the internal loadsegs. */
int_ldmbuf_size = sizeof (struct int_elf32_fdpic_loadmap)
+ (nsegs - 1) * sizeof (struct int_elf32_fdpic_loadseg);
- int_ldmbuf = (struct int_elf32_fdpic_loadmap *) xmalloc (int_ldmbuf_size);
+ int_elf32_fdpic_loadmap_up int_ldmbuf
+ (XNEWVAR (int_elf32_fdpic_loadmap, int_ldmbuf_size));
/* Place extracted information in internal structs. */
int_ldmbuf->version = version;
@@ -187,7 +193,6 @@ fetch_loadmap (CORE_ADDR ldmaddr)
byte_order);
}
- xfree (ext_ldmbuf);
return int_ldmbuf;
}
@@ -219,22 +224,15 @@ struct ext_link_map
struct lm_info_frv final : public lm_info
{
- lm_info_frv (int_elf32_fdpic_loadmap *map, CORE_ADDR got_value,
+ lm_info_frv (int_elf32_fdpic_loadmap_up map, CORE_ADDR got_value,
CORE_ADDR lm_addr)
- : map (map), got_value (got_value), lm_addr (lm_addr)
+ : map (std::move (map)),
+ got_value (got_value),
+ lm_addr (lm_addr)
{}
- DISABLE_COPY_AND_ASSIGN (lm_info_frv);
-
- ~lm_info_frv ()
- {
- xfree (this->map);
- xfree (this->dyn_syms);
- xfree (this->dyn_relocs);
- }
-
/* The loadmap, digested into an easier to use form. */
- int_elf32_fdpic_loadmap *map;
+ int_elf32_fdpic_loadmap_up map;
/* The GOT address for this link map entry. */
CORE_ADDR got_value;
/* The link map address, needed for frv_fetch_objfile_link_map(). */
@@ -250,16 +248,18 @@ struct lm_info_frv final : public lm_info
supplied to the first call. Thus the caching of the dynamic
symbols (dyn_syms) is critical for correct operation. The
caching of the dynamic relocations could be dispensed with. */
- asymbol **dyn_syms = NULL;
- arelent **dyn_relocs = NULL;
+ gdb::unique_xmalloc_ptr<asymbol *> dyn_syms;
+ gdb::unique_xmalloc_ptr<arelent *> dyn_relocs;
int dyn_reloc_count = 0; /* Number of dynamic relocs. */
};
+using lm_info_frv_up = std::unique_ptr<lm_info_frv>;
+
/* The load map, got value, etc. are not available from the chain
of loaded shared objects. ``main_executable_lm_info'' provides
a way to get at this information so that it doesn't need to be
frequently recomputed. Initialized by frv_relocate_main_executable(). */
-static lm_info_frv *main_executable_lm_info;
+static lm_info_frv_up main_executable_lm_info;
static void frv_relocate_main_executable (void);
static CORE_ADDR main_got (void);
@@ -378,14 +378,13 @@ frv_solib_ops::current_sos () const
this in the list of shared objects. */
if (got_addr != mgot)
{
- struct int_elf32_fdpic_loadmap *loadmap;
CORE_ADDR addr;
/* Fetch the load map address. */
addr = extract_unsigned_integer (lm_buf.l_addr.map,
sizeof lm_buf.l_addr.map,
byte_order);
- loadmap = fetch_loadmap (addr);
+ int_elf32_fdpic_loadmap_up loadmap = fetch_loadmap (addr);
if (loadmap == NULL)
{
warning (_("frv_current_sos: Unable to fetch load map. "
@@ -405,11 +404,10 @@ frv_solib_ops::current_sos () const
if (name_buf == nullptr)
warning (_("Can't read pathname for link map entry."));
- sos.emplace_back (std::make_unique<lm_info_frv> (loadmap, got_addr,
- lm_addr),
- name_buf != nullptr ? name_buf.get () : "",
+ sos.emplace_back (std::make_unique<lm_info_frv> (std::move (loadmap),
+ got_addr, lm_addr),
name_buf != nullptr ? name_buf.get () : "",
- *this);
+ name_buf != nullptr ? name_buf.get () : "", *this);
}
else
{
@@ -521,7 +519,6 @@ enable_break2 (void)
int status;
CORE_ADDR addr, interp_loadmap_addr;
gdb_byte addr_buf[FRV_PTR_SIZE];
- struct int_elf32_fdpic_loadmap *ldm;
/* Read the contents of the .interp section into a local buffer;
the contents specify the dynamic linker this program uses. */
@@ -566,7 +563,7 @@ enable_break2 (void)
solib_debug_printf ("interp_loadmap_addr = %s",
hex_string_custom (interp_loadmap_addr, 8));
- ldm = fetch_loadmap (interp_loadmap_addr);
+ int_elf32_fdpic_loadmap_up ldm = fetch_loadmap (interp_loadmap_addr);
if (ldm == NULL)
{
warning (_("Unable to load dynamic linker loadmap at address %s."),
@@ -582,7 +579,7 @@ enable_break2 (void)
{
interp_text_sect_low = bfd_section_vma (interp_sect);
interp_text_sect_low
- += displacement_from_map (ldm, interp_text_sect_low);
+ += displacement_from_map (ldm.get (), interp_text_sect_low);
interp_text_sect_high
= interp_text_sect_low + bfd_section_size (interp_sect);
}
@@ -591,7 +588,7 @@ enable_break2 (void)
{
interp_plt_sect_low = bfd_section_vma (interp_sect);
interp_plt_sect_low
- += displacement_from_map (ldm, interp_plt_sect_low);
+ += displacement_from_map (ldm.get (), interp_plt_sect_low);
interp_plt_sect_high =
interp_plt_sect_low + bfd_section_size (interp_sect);
}
@@ -614,7 +611,7 @@ enable_break2 (void)
solib_debug_printf ("_dl_debug_addr (prior to relocation) = %s",
hex_string_custom (addr, 8));
- addr += displacement_from_map (ldm, addr);
+ addr += displacement_from_map (ldm.get (), addr);
solib_debug_printf ("_dl_debug_addr (after relocation) = %s",
hex_string_custom (addr, 8));
@@ -663,9 +660,6 @@ enable_break2 (void)
}
addr = extract_unsigned_integer (addr_buf, sizeof addr_buf, byte_order);
- /* We're done with the loadmap. */
- xfree (ldm);
-
/* Remove all the solib event breakpoints. Their addresses
may have changed since the last time we ran the program. */
remove_solib_event_breakpoints ();
@@ -728,7 +722,6 @@ frv_relocate_main_executable (void)
{
int status;
CORE_ADDR exec_addr, interp_addr;
- struct int_elf32_fdpic_loadmap *ldm;
int changed;
status = frv_fdpic_loadmap_addresses (current_inferior ()->arch (),
@@ -741,13 +734,14 @@ frv_relocate_main_executable (void)
}
/* Fetch the loadmap located at ``exec_addr''. */
- ldm = fetch_loadmap (exec_addr);
- if (ldm == NULL)
+ int_elf32_fdpic_loadmap_up ldm_up = fetch_loadmap (exec_addr);
+ if (ldm_up == nullptr)
error (_("Unable to load the executable's loadmap."));
- delete main_executable_lm_info;
- main_executable_lm_info = new lm_info_frv (ldm, 0, 0);
+ main_executable_lm_info
+ = std::make_unique<lm_info_frv> (std::move (ldm_up), 0, 0);
+ int_elf32_fdpic_loadmap *ldm = main_executable_lm_info->map.get ();
objfile *objf = current_program_space->symfile_object_file;
std::vector<CORE_ADDR> new_offsets (objf->section_offsets.size ());
changed = 0;
@@ -816,9 +810,7 @@ frv_solib_ops::clear_solib (program_space *pspace) const
lm_base_cache = 0;
enable_break2_done = 0;
main_lm_addr = 0;
-
- delete main_executable_lm_info;
- main_executable_lm_info = NULL;
+ main_executable_lm_info.reset ();
}
void
@@ -827,7 +819,7 @@ frv_solib_ops::relocate_section_addresses (solib &so,
{
int seg;
auto *li = gdb::checked_static_cast<lm_info_frv *> (so.lm_info.get ());
- int_elf32_fdpic_loadmap *map = li->map;
+ int_elf32_fdpic_loadmap *map = li->map.get ();
for (seg = 0; seg < map->nsegs; seg++)
{
@@ -868,7 +860,7 @@ frv_fdpic_find_global_pointer (CORE_ADDR addr)
{
int seg;
auto *li = gdb::checked_static_cast<lm_info_frv *> (so.lm_info.get ());
- int_elf32_fdpic_loadmap *map = li->map;
+ int_elf32_fdpic_loadmap *map = li->map.get ();
for (seg = 0; seg < map->nsegs; seg++)
{
@@ -915,7 +907,7 @@ frv_fdpic_find_canonical_descriptor (CORE_ADDR entry_point)
objfile *objf = current_program_space->symfile_object_file;
addr = find_canonical_descriptor_in_load_object
(entry_point, got_value, name, objf->obfd.get (),
- main_executable_lm_info);
+ main_executable_lm_info.get ());
/* If descriptor not found via main executable, check each load object
in list of shared objects. */
@@ -973,10 +965,11 @@ find_canonical_descriptor_in_load_object
return 0;
/* Allocate space for the dynamic symbol table. */
- lm->dyn_syms = (asymbol **) xmalloc (storage_needed);
+ lm->dyn_syms.reset (XNEWVAR (asymbol *, storage_needed));
/* Fetch the dynamic symbol table. */
- number_of_symbols = bfd_canonicalize_dynamic_symtab (abfd, lm->dyn_syms);
+ number_of_symbols
+ = bfd_canonicalize_dynamic_symtab (abfd, lm->dyn_syms.get ());
if (number_of_symbols == 0)
return 0;
@@ -995,17 +988,18 @@ find_canonical_descriptor_in_load_object
return 0;
/* Allocate space for the relocs. */
- lm->dyn_relocs = (arelent **) xmalloc (storage_needed);
+ lm->dyn_relocs.reset (XNEWVAR (arelent *, storage_needed));
/* Fetch the dynamic relocs. */
lm->dyn_reloc_count
- = bfd_canonicalize_dynamic_reloc (abfd, lm->dyn_relocs, lm->dyn_syms);
+ = bfd_canonicalize_dynamic_reloc (abfd, lm->dyn_relocs.get (),
+ lm->dyn_syms.get ());
}
/* Search the dynamic relocs. */
for (i = 0; i < lm->dyn_reloc_count; i++)
{
- rel = lm->dyn_relocs[i];
+ rel = lm->dyn_relocs.get ()[i];
/* Relocs of interest are those which meet the following
criteria:
@@ -1029,7 +1023,8 @@ find_canonical_descriptor_in_load_object
gdb_byte buf [FRV_PTR_SIZE];
/* Compute address of address of candidate descriptor. */
- addr = rel->address + displacement_from_map (lm->map, rel->address);
+ addr = (rel->address
+ + displacement_from_map (lm->map.get (), rel->address));
/* Fetch address of candidate descriptor. */
if (target_read_memory (addr, buf, sizeof buf) != 0)
base-commit: 625b835f63153677bf614de266c7bc8963163ffc
--
2.53.0
next reply other threads:[~2026-02-17 21:17 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-02-17 21:16 simon.marchi [this message]
2026-02-17 23:32 ` Kevin Buettner
2026-02-18 18:34 ` Tom Tromey
2026-02-19 7:14 ` Kevin Buettner
2026-02-20 18:05 ` Simon Marchi
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260217211650.3999842-1-simon.marchi@polymtl.ca \
--to=simon.marchi@polymtl.ca \
--cc=gdb-patches@sourceware.org \
--cc=simon.marchi@efficios.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox