[Home]

Summary:ASTERISK-22455: Asterisk 12 on Ubuntu Lucid deadlocks with DEBUG_THREADS+OPTIONAL_API enabled
Reporter:David M. Lee (dlee)Labels:
Date Opened:2013-09-04 09:22:05Date Closed:2013-09-09 15:00:01
Priority:BlockerRegression?
Status:Closed/CompleteComponents:
Versions:12.0.0-alpha1 Frequency of
Occurrence
Related
Issues:
Environment:Attachments:
Description:@mmichelson discovered that Asterisk 12 will deadlock when DEBUG_THREADS+OPTIONAL_API is enabled, on Ubuntu Lucid.

It deadlocks consistently on startup with the sample config installed.

I've tried various permutations trying to narrow down the problem.
* Ubuntu Raring - no deadlock
* CentOS 5 - no deadlock
* Disable DEBUG_THREADS - no deadlock
* Disable OPTIONAL_API - no deadlock
* Update to r397988 (before the optional_api changes) - no deadlock
Comments:By: David M. Lee (dlee) 2013-09-04 12:46:23.738-0500

Figured it out.

When debug threads are enabled, {{ast_pthread_mutex_lock}} invokes {{backtrace()}}. In Lucid's libc (glibc-2.11.1), {{backtrace()}} ends up calling {{dl_iterate_phdr()}}, which "allows an application to inquire at run time to find out which shared objects it has loaded".

When log functions are called from {{__constructor__}} functions, they execute during a {{dlopen()}}. If glibc holds a lock while this happens, then it's a classic lock ordering problem. dlopen() locks the module list, then (buried in some calls) it locks the {{logmsgs}} reentrancy lock (for debug threads). The logger thread locks the {{logmsgs}} reentrancy lock, then (buried in {{backtrace()}}) locks the module list.

{code}
Main thread                       | Logger thread
-----------------------------------+-----------------------------
- dlopen()                        | - AST_LIST_LOCK(&logmsgs)
  - lock(dl)                      |   - ast_reentrancy_lock(lt)
  - __constructor__               |   - backtrace()
    - ast_verb()                  |     - lock(dl)
      - AST_LIST_LOCK(&logmsgs)   |       *** DEADLOCK ***
        - ast_reentrancy_lock(lt) |
          *** DEADLOCK ***        |
{code}