salhelper/source/timer.cxx |   10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

New commits:
commit 6fd26404015305a1450e6a055d6c0aa735dd7e71
Author:     Caolán McNamara <caolan.mcnam...@collabora.com>
AuthorDate: Mon May 26 20:17:38 2025 +0100
Commit:     Miklos Vajna <vmik...@collabora.com>
CommitDate: Tue May 27 14:27:30 2025 +0200

    don't return impl by shared_ptr
    
    Thread 1 exits, and TimerManagerImpl dtor reduces its m_pImpl shared_ptr of
    TimerManager to use_count 0 triggering dtor of its contents. That dtor
    waits for Thread 2 to join.
    
    Thread 2 calls checkForTimeout which calls 
TimerManagerImpl::unregisterTimer.
    whose m_pImpl is still set, but with a use_count is 0. Return by value
    results in a temp std::shared_ptr of use_count 0 which on going out of scope
    triggers a second dtor of m_pImpl.
    
    Work around this by not returning a shared_ptr.
    
    Thread 1 (Thread 0x7ffff7ab5100 (LWP 3274153) "cppunittester"):
     #0  0x00007ffff71509a4 in salhelper::TimerManager::~TimerManager 
(this=0x508000000da0) at salhelper/source/timer.cxx:269
     #1  0x00007ffff71548c0 in std::_Sp_counted_ptr<salhelper::TimerManager*, 
(__gnu_cxx::_Lock_policy)2>::_M_dispose (this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:428
     #2  0x00007ffff7153d11 in 
std::_Sp_counted_base<(__gnu_cxx::_Lock_policy)2>::_M_release 
(this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:346
     #3  0x00007ffff7153b56 in 
std::__shared_count<(__gnu_cxx::_Lock_policy)2>::~__shared_count 
(this=0x7ffff715edd8 <(anonymous namespace)::getTimerManager()::aManager+56>) 
at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:1069
     #4  0x00007ffff7154559 in std::__shared_ptr<salhelper::TimerManager, 
(__gnu_cxx::_Lock_policy)2>::~__shared_ptr (this=0x7ffff715edd0 <(anonymous 
namespace)::getTimerManager()::aManager+48>) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:1525
     #5  0x00007ffff7153ae5 in 
std::shared_ptr<salhelper::TimerManager>::~shared_ptr (this=0x7ffff715edd0 
<(anonymous namespace)::getTimerManager()::aManager+48>) at 
/usr/bin/../lib/gcc/x--Type <RET> for more, q to quit, c to continue without 
paging--
     86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr.h:175
     #6  0x00007ffff7152759 in (anonymous 
namespace)::TimerManagerImpl::~TimerManagerImpl (this=0x7ffff715eda0 
<(anonymous namespace)::getTimerManager()::aManager>) at 
salhelper/source/timer.cxx:62
     #7  0x00007ffff7651641 in __run_exit_handlers () from /lib64/libc.so.6
     #8  0x00007ffff765170e in exit () from /lib64/libc.so.6
     #9  0x00007ffff763808f in __libc_start_call_main () from /lib64/libc.so.6
     #10 0x00007ffff763814b in __libc_start_main_impl () from /lib64/libc.so.6
     #11 0x00000000004314e5 in _start ()
    
    Thread 2 (Thread 0x7fffe6fff6c0 (LWP 3274156) "salhelper::Time"):
     #0  salhelper::TimerManager::~TimerManager (this=0x508000000da0) at 
salhelper/source/timer.cxx:269
     #1  0x00007ffff71548c0 in std::_Sp_counted_ptr<salhelper::TimerManager*, 
(__gnu_cxx::_Lock_policy)2>::_M_dispose (this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:428
     #2  0x00007ffff7154024 in 
std::_Sp_counted_base<(__gnu_cxx::_Lock_policy)2>::_M_release_last_use 
(this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:175
     #3  0x00007ffff7153fb5 in 
std::_Sp_counted_base<(__gnu_cxx::_Lock_policy)2>::_M_release_last_use_cold 
(this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:199
     #4  0x00007ffff7153f6b in 
std::_Sp_counted_base<(__gnu_cxx::_Lock_policy)2>::_M_release 
(this=0x503000001060) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:353
     #5  0x00007ffff7153b56 in 
std::__shared_count<(__gnu_cxx::_Lock_policy)2>::~__shared_count 
(this=0x7fffe58ff268) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:1069
     #6  0x00007ffff7154559 in std::__shared_ptr<salhelper::TimerManager, 
(__gnu_cxx::_Lock_policy)2>::~__shared_ptr (this=0x7fffe58ff260) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr_base.h:1525
     #7  0x00007ffff7153ae5 in 
std::shared_ptr<salhelper::TimerManager>::~shared_ptr (this=0x7fffe58ff260) at 
/usr/bin/../lib/gcc/x86_64-redhat-linux/14/../../../../include/c++/14/bits/shared_ptr.h:175
     #8  0x00007ffff714fa2c in (anonymous 
namespace)::TimerManagerImpl::unregisterTimer (this=0x7ffff715eda0 <(anonymous 
namespace)::getTimerManager()::aManager>, pTimer=0x50d0000001e0) at 
salhelper/source/timer.cxx:100
     #9  0x00007ffff714f4b5 in salhelper::Timer::stop (this=0x50d0000001e0) at 
salhelper/source/timer.cxx:159
     #10 0x00007ffff714f465 in salhelper::Timer::~Timer (this=0x50d0000001e0) 
at salhelper/source/timer.cxx:143
     #11 0x00007ffff7172912 in (anonymous namespace)::TestTimer::~TestTimer() 
() from workdir/LinkTarget/CppunitTest/libtest_salhelper_testapi.so
     #12 0x00007ffff7172939 in (anonymous namespace)::TestTimer::~TestTimer() 
() from workdir/LinkTarget/CppunitTest/libtest_salhelper_testapi.so
     #13 0x00007ffff714ea88 in salhelper::SimpleReferenceObject::release() () 
from instdir/program/libuno_salhelpergcc3.so.3
     #14 0x00007ffff7151be0 in salhelper::TimerManager::checkForTimeout 
(this=0x508000000da0) at salhelper/source/timer.cxx:410
     #15 0x00007ffff7152189 in salhelper::TimerManager::run 
(this=0x508000000da0) at salhelper/source/timer.cxx:444
     #16 0x00007ffff714f109 in threadFunc () from 
instdir/program/libuno_salhelpergcc3.so.3
     #17 0x00007ffff7dbbc31 in osl_thread_start_Impl(void*) () from 
instdir/program/libuno_sal.so.3
     #18 0x00000000004c84ed in asan_thread_start(void*) ()
     #19 0x00007ffff76a6088 in start_thread () from /lib64/libc.so.6
     #20 0x00007ffff7729f8c in clone3 () from /lib64/libc.so.6
    
    Change-Id: I761ca9db12738415aa0eca386956c762b42b28d3
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/185868
    Tested-by: Jenkins
    Tested-by: Caolán McNamara <caolan.mcnam...@collabora.com>
    Reviewed-by: Caolán McNamara <caolan.mcnam...@collabora.com>
    (cherry picked from commit c6c8e1c325f22039bbd709085eaa4d95ffa22192)
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/185881
    Tested-by: Jenkins CollaboraOffice <jenkinscollaboraoff...@gmail.com>
    Reviewed-by: Miklos Vajna <vmik...@collabora.com>

diff --git a/salhelper/source/timer.cxx b/salhelper/source/timer.cxx
index 7a83149c867c..89cc5d6c5b2f 100644
--- a/salhelper/source/timer.cxx
+++ b/salhelper/source/timer.cxx
@@ -80,26 +80,26 @@ public:
             ensureThread();
     }
 
-    std::shared_ptr<TimerManager> ensureThread()
+    TimerManager& ensureThread()
     {
         if (!m_pImpl)
             m_pImpl.reset(new TimerManager(m_pHead, m_Lock));
-        return m_pImpl;
+        return *m_pImpl;
     }
 
     void registerTimer(salhelper::Timer* pTimer)
     {
-        ensureThread()->registerTimer(pTimer);
+        ensureThread().registerTimer(pTimer);
     }
 
     void unregisterTimer(salhelper::Timer * pTimer)
     {
-        ensureThread()->unregisterTimer(pTimer);
+        ensureThread().unregisterTimer(pTimer);
     }
 
     bool lookupTimer(const salhelper::Timer* pTimer)
     {
-        return ensureThread()->lookupTimer(pTimer);
+        return ensureThread().lookupTimer(pTimer);
     }
 };
 

Reply via email to