Callback in pjnath holds internal lock [resend]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



I'm seeing an occasional deadlock in a test program that uses pjnath.  The
code uses a callback to receive data from an ICE session, the "on_rx_data"
callback sent to pj_ice_strans_create.  I have noticed that the callback
runs with an internal lock held, which is contributing to the deadlock.
(The deadlock also involves a mutex in the client code, so it's not a
deadlock in the library.)

My actual question is: is that lock *supposed* to be held while the
callback runs?  (And if this is documented somewhere, my apologies for
missing it.)

Some gory details based on a debugger stack trace and some looking at the
source code:

  client_thread()

     |
    \|/
  pj_ioqueue_poll [ ioqueue_select.c ]
     |
    \|/
     .
     .
     .
     .
     |
    \|/
  on_data_recvfrom  [ stun_sock.c ]

        pj_grp_lock_acquire(stun_sock->grp_lock);

     -- (*stun_sock->cb.on_rx_data)(stun_sock,...), which calls
     |    stun_on_rx_data
     |
     |  pj_grp_lock_release(stun_sock->grp_lock),
     |     where stun_sock->grp_lock == 0x145c0d8
    \|/
  stun_on_rx_data  [ ice_strans.c ]

        No locking or unlocking, but manipulates reference count.
        Based on address, it's the same lock.

        pj_grp_lock_add_ref(ice_st->grp_lock);
          where ice_st->grp_lock == 0x145c0d8

     -- pj_ice_sess_on_rx_pkt(comp->ice_st->ice,...)
     |
     |  pj_grp_lock_dec_ref(ice_st->grp_lock)
    \|/
  pj_ice_sess_on_rx_pkt(ice,...)   [ ice_session.c ]

        pj_grp_lock_acquire(ice->grp_lock);

        pj_grp_lock_release(ice->grp_lock);
          where again ice->grp_lock == 0x145c0d8

        There is a comment in the code here that it's important to
        release the lock before making the callback.  But the lock
        acquired in on_data_recvfrom appears to still be held.

     -- (*ice->cb.on_rx_data)(ice,...)
     |    which invokes the client call-back.
    \|/
  client_function(ice,...)

     |  The client function runs with the group lock held.
    \|/

I'm thinking that this may not be intended, particularly from the comment
in  pj_ice_sess_on_rx_pkt, which suggests that the lock should not be
held.  Also, the lock in that function seems redundant.  Am I reading this
correctly, or am I just confused?

Version 2.4.

Appreciate any info here.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.pjsip.org/pipermail/pjsip_lists.pjsip.org/attachments/20150619/911c9a41/attachment.html>


[Index of Archives]     [Asterisk Users]     [Asterisk App Development]     [Linux ARM Kernel]     [Linux ARM]     [Linux Omap]     [Fedora ARM]     [IETF Annouce]     [Security]     [Bugtraq]     [Linux]     [Linux OMAP]     [Linux MIPS]     [Linux API]
  Powered by Linux