Fix: sessiond: memory leak of lttng_pipe structure
authorJérémie Galarneau <jeremie.galarneau@efficios.com>
Mon, 24 Jul 2023 19:25:39 +0000 (15:25 -0400)
committerJérémie Galarneau <jeremie.galarneau@efficios.com>
Mon, 24 Jul 2023 19:25:39 +0000 (15:25 -0400)
Issue observed
--------------

When running the session daemon under ASAN, the following report is
produced:

  Direct leak of 104 byte(s) in 1 object(s) allocated from:
      #0 0x7f93866e0cd1 in __interceptor_calloc /usr/src/debug/gcc/gcc/libsanitizer/asan/asan_malloc_linux.cpp:77
      #1 0x55c55a7c4963 in zmalloc_internal /home/simark/src/lttng-tools/src/common/macros.hpp:60
      #2 0x55c55a7c4973 in lttng_pipe* zmalloc<lttng_pipe>() /home/simark/src/lttng-tools/src/common/macros.hpp:88
      #3 0x55c55a7c26eb in _pipe_create /home/simark/src/lttng-tools/src/common/pipe.cpp:111
      #4 0x55c55a7c351d in lttng_pipe_open(int) /home/simark/src/lttng-tools/src/common/pipe.cpp:185
      #5 0x55c55a586dd6 in operator() /home/simark/src/lttng-tools/src/bin/lttng-sessiond/rotation-thread.cpp:403
      #6 0x55c55a58744a in lttng::sessiond::rotation_thread::rotation_thread(lttng::sessiond::rotation_thread_timer_queue&, notification_thread_handle&) /home/simark/src/lttng-tools/src/bin/lttng-sessiond/rotation-thread.cpp:402
      #7 0x55c55a46377f in std::unique_ptr<lttng::sessiond::rotation_thread, std::default_delete<lttng::sessiond::rotation_thread> > lttng::make_unique<lttng::sessiond::rotation_thread, lttng::sessiond::rotation_thread_timer_queue&, notification_thread_handle&>(lttng::sessiond::rotation_thread_timer_queue&, notification_thread_handle&) /home/simark/src/lttng-tools/src/common/make-unique.hpp:18
      #8 0x55c55a455024 in _main /home/simark/src/lttng-tools/src/bin/lttng-sessiond/main.cpp:1773
      #9 0x55c55a455c2e in main /home/simark/src/lttng-tools/src/bin/lttng-sessiond/main.cpp:1982
      #10 0x7f9385c1484f  (/usr/lib/libc.so.6+0x2384f) (BuildId: 2f005a79cd1a8e385972f5a102f16adba414d75e)

Cause
-----

On destruction, the std::unique_ptr wrapper of
lttng_pipe (lttng_pipe::uptr) invokes `lttng_pipe_close` (which only
closes the file descriptors of the underlying pipe) rather than
`lttng_pipe_destroy` which closes the file descriptors _and_ frees the
memory allocated by lttng_open.

Currently, the rotation thread is the only user of this wrapper (through
its quit_pipe).

Solution
--------

The deleter of lttng_pipe::uptr is replaced to invoke lttng_pipe_destroy.

Fixes #1380
Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
Change-Id: I5715ac6131c5aa134cfd18d8b677f31aabed36f0

src/common/pipe.hpp

index 9798a8cf8c794ea191db2fa0445695dc3a4feca0..5249061f865ba12a66b842f614abf6316d2b5a3a 100644 (file)
@@ -21,16 +21,12 @@ enum lttng_pipe_state {
 
 /* Close both side of pipe. */
 int lttng_pipe_close(struct lttng_pipe *pipe);
+void lttng_pipe_destroy(struct lttng_pipe *pipe);
 
 struct lttng_pipe {
-       static void _lttng_pipe_close_wrapper(lttng_pipe *pipe)
-       {
-               lttng_pipe_close(pipe);
-       }
-
        using uptr = std::unique_ptr<
                lttng_pipe,
-               lttng::memory::create_deleter_class<lttng_pipe, _lttng_pipe_close_wrapper>::deleter>;
+               lttng::memory::create_deleter_class<lttng_pipe, lttng_pipe_destroy>::deleter>;
 
        /* Read: 0, Write: 1. */
        int fd[2];
@@ -82,7 +78,6 @@ struct lttng_pipe *lttng_pipe_open(int flags);
 struct lttng_pipe *lttng_pipe_named_open(const char *path, mode_t mode, int flags);
 int lttng_pipe_write_close(struct lttng_pipe *pipe);
 int lttng_pipe_read_close(struct lttng_pipe *pipe);
-void lttng_pipe_destroy(struct lttng_pipe *pipe);
 
 ssize_t lttng_pipe_read(struct lttng_pipe *pipe, void *buf, size_t count);
 ssize_t lttng_pipe_write(struct lttng_pipe *pipe, const void *buf, size_t count);
This page took 0.025543 seconds and 4 git commands to generate.