Skip to content

Commit

Permalink
[core] Fixed wrong usage of m_RecvDataLock.
Browse files Browse the repository at this point in the history
m_RecvDataCond must be used with m_RecvLock instead of m_RecvDataLock.
m_RecvDataLock is only used to sync releaseSynch() calls.
  • Loading branch information
maxsharabayko committed Oct 29, 2020
1 parent 7848fcd commit 7997515
Show file tree
Hide file tree
Showing 2 changed files with 9 additions and 8 deletions.
11 changes: 6 additions & 5 deletions srtcore/core.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7188,7 +7188,7 @@ int64_t CUDT::recvfile(fstream &ofs, int64_t &offset, int64_t size, int block)
throw CUDTException(MJ_NOTSUP, MN_INVALBUFFERAPI, 0);
}

ScopedLock recvguard(m_RecvLock);
UniqueLock recvguard(m_RecvLock);

// Well, actually as this works over a FILE (fstream), not just a stream,
// the size can be measured anyway and predicted if setting the offset might
Expand Down Expand Up @@ -7248,8 +7248,7 @@ int64_t CUDT::recvfile(fstream &ofs, int64_t &offset, int64_t size, int block)
}

{
UniqueLock gl (m_RecvDataLock);
CSync rcond (m_RecvDataCond, gl);
CSync rcond (m_RecvDataCond, recvguard);

THREAD_PAUSED();
while (stillConnected() && !m_pRcvBuffer->isRcvDataReady())
Expand Down Expand Up @@ -7634,7 +7633,8 @@ void CUDT::releaseSynch()
enterCS(m_SendLock);
leaveCS(m_SendLock);

CSync::lock_signal(m_RecvDataCond, m_RecvDataLock);
// Awake tsbpd() and srt_recv*(..) threads for them to check m_bClosing.
CSync::lock_signal(m_RecvDataCond, m_RecvLock);
CSync::lock_signal(m_RcvTsbPdCond, m_RecvLock);

enterCS(m_RecvDataLock);
Expand Down Expand Up @@ -7802,6 +7802,7 @@ void CUDT::sendCtrl(UDTMessageType pkttype, const int32_t* lparam, void* rparam,
/* Newly acknowledged data, signal TsbPD thread */
UniqueLock rcvlock (m_RecvLock);
CSync tscond (m_RcvTsbPdCond, rcvlock);
// m_bTsbPdAckWakeup is protected by m_RecvLock in the tsbpd() thread
if (m_bTsbPdAckWakeup)
tscond.signal_locked(rcvlock);
}
Expand All @@ -7810,7 +7811,7 @@ void CUDT::sendCtrl(UDTMessageType pkttype, const int32_t* lparam, void* rparam,
if (m_bSynRecving)
{
// signal a waiting "recv" call if there is any data available
CSync::lock_signal(m_RecvDataCond, m_RecvDataLock);
CSync::lock_signal(m_RecvDataCond, m_RecvLock);
}
// acknowledge any waiting epolls to read
s_UDTUnited.m_EPoll.update_events(m_SocketID, m_sPollID, SRT_EPOLL_IN, true);
Expand Down
6 changes: 3 additions & 3 deletions srtcore/core.h
Original file line number Diff line number Diff line change
Expand Up @@ -985,7 +985,7 @@ class CUDT
bool m_bGroupTsbPd; // TSBPD should be used for GROUP RECEIVER instead.

srt::sync::CThread m_RcvTsbPdThread; // Rcv TsbPD Thread handle
srt::sync::Condition m_RcvTsbPdCond; // TSBPD signals if reading is ready
srt::sync::Condition m_RcvTsbPdCond; // TSBPD signals if reading is ready. Use together with m_RecvLock.
bool m_bTsbPdAckWakeup; // Signal TsbPd thread on Ack sent

CallbackHolder<srt_listen_callback_fn> m_cbAcceptHook;
Expand Down Expand Up @@ -1017,11 +1017,11 @@ class CUDT
// Protects access to m_iSndCurrSeqNo, m_iSndLastAck
srt::sync::Mutex m_RecvAckLock; // Protects the state changes while processing incomming ACK (SRT_EPOLL_OUT)

srt::sync::Condition m_RecvDataCond; // used to block "recv" when there is no data
srt::sync::Condition m_RecvDataCond; // used to block "srt_recv*" when there is no data. Use together with m_RecvLock
srt::sync::Mutex m_RecvDataLock; // lock associated to m_RecvDataCond
srt::sync::Mutex m_RecvLock; // used to synchronize "srt_recv*" call, protects TSBPD drift updates (CRcvBuffer::isRcvDataReady())

srt::sync::Mutex m_SendLock; // used to synchronize "send" call
srt::sync::Mutex m_RecvLock; // used to synchronize "recv" call, protects TSBPD drift updates (CRcvBuffer::isRcvDataReady())
srt::sync::Mutex m_RcvLossLock; // Protects the receiver loss list (access: CRcvQueue::worker, CUDT::tsbpd)
srt::sync::Mutex m_StatsLock; // used to synchronize access to trace statistics

Expand Down

0 comments on commit 7997515

Please sign in to comment.