mirror of
https://github.com/VDR4Arch/vdr.git
synced 2023-10-10 13:36:52 +02:00
Fixed a possible deadlock when quickly zapping through encrypted channels
This commit is contained in:
parent
5443fd4219
commit
0055eeeeb8
@ -2627,6 +2627,7 @@ J
|
||||
for making cEpgHandlers::BeginSegmentTransfer() boolean
|
||||
for suggesting to change tEventID back to u_int32_t
|
||||
for adding the 'aux' member to cEvent
|
||||
for reporting a possible deadlock when quickly zapping through encrypted channels
|
||||
|
||||
Peter Pinnau <vdr@unterbrecher.de>
|
||||
for reporting that 'uint32_t' requires including stdint.h in font.h on some systems
|
||||
|
4
HISTORY
4
HISTORY
@ -9162,7 +9162,7 @@ Video Disk Recorder Revision History
|
||||
a subdirectory.
|
||||
- SVDRP peering can now be limited to the default SVDRP host (see MANUAL for details).
|
||||
|
||||
2018-01-17: Version 2.3.9
|
||||
2018-01-28: Version 2.3.9
|
||||
|
||||
- Updated the Italian OSD texts (thanks to Diego Pierotto).
|
||||
- Updated the Finnish OSD texts (thanks to Rolf Ahrenberg).
|
||||
@ -9245,3 +9245,5 @@ Video Disk Recorder Revision History
|
||||
- Now using the 'example' macro in vdr.5 (thanks to Chris Mayo).
|
||||
- Now unlocking the Recordings list before displaying an error message in
|
||||
cMenuPathEdit::ApplyChanges() and cReplayControl::Stop() (reported by Matthias Senzel).
|
||||
- Fixed a possible deadlock when quickly zapping through encrypted channels (reported
|
||||
by Jörg Wendel).
|
||||
|
31
ci.c
31
ci.c
@ -4,7 +4,7 @@
|
||||
* See the main source file 'vdr.c' for copyright information and
|
||||
* how to reach the author.
|
||||
*
|
||||
* $Id: ci.c 4.18 2017/06/19 12:13:38 kls Exp $
|
||||
* $Id: ci.c 4.19 2018/01/28 11:14:40 kls Exp $
|
||||
*/
|
||||
|
||||
#include "ci.h"
|
||||
@ -122,6 +122,8 @@ private:
|
||||
uchar *bufp;
|
||||
uchar mtdCatBuffer[TS_SIZE]; // TODO: handle multi packet CATs!
|
||||
int length;
|
||||
cMutex mutex;
|
||||
bool handlingPid;
|
||||
void AddEmmPid(int Pid);
|
||||
void DelEmmPids(void);
|
||||
public:
|
||||
@ -130,6 +132,15 @@ public:
|
||||
virtual void Receive(const uchar *Data, int Length);
|
||||
bool HasCaPids(void) const { return NumPids() - emmPids.Size() - 1 > 0; }
|
||||
void Reset(void) { DelEmmPids(); catVersion = -1; }
|
||||
bool HandlingPid(void);
|
||||
///< The cCaPidReceiver adds/deletes PIDs to/from the base class cReceiver,
|
||||
///< which in turn does the same on the cDevice it is attached to. The cDevice
|
||||
///< then sets the PIDs on the assigned cCamSlot, which can cause a deadlock on the
|
||||
///< cCamSlot's mutex if a cReceiver is detached from the device at the same time.
|
||||
///< Since these PIDs, however, are none that have to be decrypted,
|
||||
///< it is not necessary to set them in the CAM. Therefore this function is
|
||||
///< used in cCamSlot::SetPid() to detect this situation, and thus avoid the
|
||||
///< deadlock.
|
||||
};
|
||||
|
||||
cCaPidReceiver::cCaPidReceiver(void)
|
||||
@ -137,7 +148,11 @@ cCaPidReceiver::cCaPidReceiver(void)
|
||||
catVersion = -1;
|
||||
bufp = NULL;
|
||||
length = 0;
|
||||
handlingPid = false;
|
||||
cMutexLock MutexLock(&mutex);
|
||||
handlingPid = true;
|
||||
AddPid(CATPID);
|
||||
handlingPid = false;
|
||||
}
|
||||
|
||||
void cCaPidReceiver::AddEmmPid(int Pid)
|
||||
@ -147,14 +162,20 @@ void cCaPidReceiver::AddEmmPid(int Pid)
|
||||
return;
|
||||
}
|
||||
emmPids.Append(Pid);
|
||||
cMutexLock MutexLock(&mutex);
|
||||
handlingPid = true;
|
||||
AddPid(Pid);
|
||||
handlingPid = false;
|
||||
}
|
||||
|
||||
void cCaPidReceiver::DelEmmPids(void)
|
||||
{
|
||||
cMutexLock MutexLock(&mutex);
|
||||
handlingPid = true;
|
||||
for (int i = 0; i < emmPids.Size(); i++)
|
||||
DelPid(emmPids[i]);
|
||||
emmPids.Clear();
|
||||
handlingPid = false;
|
||||
}
|
||||
|
||||
void cCaPidReceiver::Receive(const uchar *Data, int Length)
|
||||
@ -239,6 +260,12 @@ void cCaPidReceiver::Receive(const uchar *Data, int Length)
|
||||
}
|
||||
}
|
||||
|
||||
bool cCaPidReceiver::HandlingPid(void)
|
||||
{
|
||||
cMutexLock MutexLock(&mutex);
|
||||
return handlingPid;
|
||||
}
|
||||
|
||||
// --- cCaActivationReceiver -------------------------------------------------
|
||||
|
||||
// A receiver that is used to make the device stay on a given channel and
|
||||
@ -2588,6 +2615,8 @@ void cCamSlot::AddPid(int ProgramNumber, int Pid, int StreamType)
|
||||
|
||||
void cCamSlot::SetPid(int Pid, bool Active)
|
||||
{
|
||||
if (caPidReceiver && caPidReceiver->HandlingPid())
|
||||
return;
|
||||
cMutexLock MutexLock(&mutex);
|
||||
for (cCiCaProgramData *p = caProgramList.First(); p; p = caProgramList.Next(p)) {
|
||||
for (cCiCaPidData *q = p->pidList.First(); q; q = p->pidList.Next(q)) {
|
||||
|
Loading…
Reference in New Issue
Block a user