[RFA] Fix leaks in ada catch command
Commit Message
Valgrind reports leaks such as the below in various gdb.ada tests:
==14141== 114 bytes in 4 blocks are definitely lost in loss record 1,054 of 3,424
==14141== at 0x4C2BE6D: malloc (vg_replace_malloc.c:309)
==14141== by 0x405107: xmalloc (common-utils.c:44)
==14141== by 0x7563F9: xstrdup (xstrdup.c:34)
==14141== by 0x381B21: ada_exception_sal (ada-lang.c:13217)
==14141== by 0x381B21: create_ada_exception_catchpoint(gdbarch*, ada_exception_catchpoint_kind, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, int, int, int) (ada-lang.c:13251)
==14141== by 0x3820A8: catch_ada_exception_command(char const*, int, cmd_list_element*) (ada-lang.c:13285)
==14141== by 0x3F4828: cmd_func(cmd_list_element*, char const*, int) (cli-decode.c:1892)
...
==14141== 114 bytes in 4 blocks are definitely lost in loss record 1,055 of 3,424
==14141== at 0x4C2BE6D: malloc (vg_replace_malloc.c:309)
==14141== by 0x405107: xmalloc (common-utils.c:44)
==14141== by 0x7563F9: xstrdup (xstrdup.c:34)
==14141== by 0x3B82B3: set_breakpoint_location_function(bp_location*, int) (breakpoint.c:7156)
==14141== by 0x3C112B: add_location_to_breakpoint(breakpoint*, symtab_and_line const*) (breakpoint.c:8609)
==14141== by 0x3C127A: init_raw_breakpoint(breakpoint*, gdbarch*, symtab_and_line, bptype, breakpoint_ops const*) (breakpoint.c:7187)
==14141== by 0x3C1B52: init_ada_exception_breakpoint(breakpoint*, gdbarch*, symtab_and_line, char const*, breakpoint_ops const*, int, int, int) (breakpoint.c:11262)
==14141== by 0x381C2E: create_ada_exception_catchpoint(gdbarch*, ada_exception_catchpoint_kind, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, int, int, int) (ada-lang.c:13255)
...
Fix the first leak by xfree-ing the addr_string allocated by ada_exception_sal.
Fix the second leak by calling the base bp_location dtor.
Tested on debian/amd64, natively and under valgrind.
gdb/ChangeLog
2019-02-10 Philippe Waroquiers <philippe.waroquiers@skynet.be>
* breakpoint.c (bp_location_dtor): Rename to base_bp_location_dtor,
make non static, and update users.
* breakpoint.h (base_bp_location_dtor): Declare.
* ada-lang.c (ada_catchpoint_location_dtor): Call
base_bp_location_ops.dtor.
(create_ada_exception_catchpoint): Free addr_string.
---
gdb/ada-lang.c | 9 +++++++--
gdb/breakpoint.c | 8 ++++----
gdb/breakpoint.h | 4 ++++
3 files changed, 15 insertions(+), 6 deletions(-)
@@ -12415,6 +12415,8 @@ ada_catchpoint_location_dtor (struct bp_location *bl)
struct ada_catchpoint_location *al = (struct ada_catchpoint_location *) bl;
al->excep_cond_expr.reset ();
+
+ base_bp_location_ops.dtor (bl);
}
/* The vtable to be used in Ada catchpoint locations. */
@@ -13246,13 +13248,16 @@ create_ada_exception_catchpoint (struct gdbarch *gdbarch,
int disabled,
int from_tty)
{
- const char *addr_string = NULL;
+ char *addr_string = NULL;
const struct breakpoint_ops *ops = NULL;
- struct symtab_and_line sal = ada_exception_sal (ex_kind, &addr_string, &ops);
+ struct symtab_and_line sal = ada_exception_sal (ex_kind,
+ (const char **) &addr_string,
+ &ops);
std::unique_ptr<ada_catchpoint> c (new ada_catchpoint ());
init_ada_exception_breakpoint (c.get (), gdbarch, sal, addr_string,
ops, tempflag, disabled, from_tty);
+ xfree (addr_string);
c->excep_string = excep_string;
create_excep_cond_exprs (c.get (), ex_kind);
if (!cond_string.empty ())
@@ -12168,14 +12168,14 @@ say_where (struct breakpoint *b)
/* Default bp_location_ops methods. */
static void
-bp_location_dtor (struct bp_location *self)
+base_bp_location_dtor (struct bp_location *self)
{
xfree (self->function_name);
}
-static const struct bp_location_ops bp_location_ops =
+const struct bp_location_ops base_bp_location_ops =
{
- bp_location_dtor
+ base_bp_location_dtor
};
/* Destructor for the breakpoint base class. */
@@ -12190,7 +12190,7 @@ breakpoint::~breakpoint ()
static struct bp_location *
base_breakpoint_allocate_location (struct breakpoint *self)
{
- return new bp_location (&bp_location_ops, self);
+ return new bp_location (&base_bp_location_ops, self);
}
static void
@@ -312,6 +312,10 @@ struct bp_location_ops
void (*dtor) (struct bp_location *self);
};
+/* Default bp_location_ops methods. */
+
+extern const struct bp_location_ops base_bp_location_ops;
+
class bp_location
{
public: