Date: prev next · Thread: first prev next last
2011 Archives by date, by thread · List index



have just found a great python command for GDB by Tom Tromey called "info mutex":

http://www.cygwin.com/ml/archer/2010-q3/msg00024.html

looks very helpful for debugging a deadlock:

(gdb) info mutex
Mutex 0x264fbb0:
*  Owned by thread 25481
   Thread 27391

Mutex 0xbd4370:
   Owned by thread 27391
*  Thread 25481

Threads not waiting for a lock:
   Thread 25499
   Thread 25504
   Thread 25505
   Thread 25535
   Thread 25536
   Thread 27620

the original script didn't run for me, but with a trivial tweak it does (attached).

regards,
 michael
import gdb

#----------------------------------------------------------------------
# http://www.cygwin.com/ml/archer/2010-q3/msg00024.html

class ThreadHolder:
    """A class that can be used with the 'with' statement to save and
restore the current thread while operating on some other thread."""
    def __init__(self, thread):
        self.thread = thread

    def __enter__(self):
        self.save = gdb.selected_thread()
        self.thread.switch()

    def __exit__ (self, exc_type, exc_value, traceback):
        try:
            self.save.switch()
        except:
            pass
        return None

def print_thread (selected_thread, thr, owner):
    "A helper function to nicely print a gdb.Thread."
    if thr == selected_thread:
        print "* ",
    else:
        print "  ",
    if owner:
        print "Owned by thread",
    else:
        print "Thread",
    (pid, lwp, tid) = thr.ptid
    print "%d  " % lwp
    # FIXME - function, file name, etc

class InfoMutex(gdb.Command):
    def __init__ (self):
        gdb.Command.__init__ (self, "info mutex", gdb.COMMAND_NONE)

    def invoke (self, arg, from_tty):
        # Map a mutex ID to the LWP owning the mutex.
        owner = {}
        # Map an LWP id to a thread object.
        threads = {}
        # Map a mutex ID to a list of thread objects that are waiting
        # for the lock.
        mutexes = {}

        for inf in gdb.inferiors():
            for thr in inf.threads():
                id = thr.ptid[1]
                threads[id] = thr
                with ThreadHolder (thr):
                    frame = gdb.selected_frame()
                    lock_name = None
                    for n in range(5):
                        if frame is None:
                            break
                        fn_sym = frame.function()
                        if fn_sym is not None and (fn_sym.name == '__pthread_mutex_lock' or 
fn_sym.name == '__pthread_mutex_lock_full' or fn_sym.name == 'pthread_mutex_timedlock'):
                            m = frame.read_var ('mutex')
                            lock_name = long (m)
                            if lock_name not in owner:
                                owner[lock_name] = long (m['__data']['__owner'])
                                break
                        frame = frame.older()
                    if lock_name not in mutexes:
                        mutexes[lock_name] = []
                    mutexes[lock_name] += [thr]

        selected_thread = gdb.selected_thread()

        for id in mutexes.keys():
            if id is None:
                print "Threads not waiting for a lock:"
            else:
                print "Mutex 0x%x:" % id
                print_thread (selected_thread, threads[owner[id]], True)
            for thr in mutexes[id]:
                print_thread (selected_thread, thr, False)
            print

InfoMutex()


Context


Privacy Policy | Impressum (Legal Info) | Copyright information: Unless otherwise specified, all text and images on this website are licensed under the Creative Commons Attribution-Share Alike 3.0 License. This does not include the source code of LibreOffice, which is licensed under the Mozilla Public License (MPLv2). "LibreOffice" and "The Document Foundation" are registered trademarks of their corresponding registered owners or are in actual use as trademarks in one or more countries. Their respective logos and icons are also subject to international copyright laws. Use thereof is explained in our trademark policy.