From 9c04942eaac18f9a494c5ace7f3e73e62a820c47 Mon Sep 17 00:00:00 2001 From: Klaus Schmidinger Date: Sun, 16 Feb 2003 11:20:55 +0100 Subject: [PATCH] Broken CAM connections are now restored automatically --- ci.c | 10 ++++++--- ci.h | 4 ++-- dvbdevice.c | 65 +++++++++++++++++++++++++++++------------------------ 3 files changed, 45 insertions(+), 34 deletions(-) diff --git a/ci.c b/ci.c index 06a08c43..d345a3ef 100644 --- a/ci.c +++ b/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 1.6 2003/02/15 14:14:57 kls Exp $ + * $Id: ci.c 1.7 2003/02/16 11:20:55 kls Exp $ */ /* XXX TODO @@ -1423,8 +1423,9 @@ int cCiHandler::CloseAllSessions(int Slot) return result; } -void cCiHandler::Process(void) +bool cCiHandler::Process(void) { + bool result = true; cMutexLock MutexLock(&mutex); for (int Slot = 0; Slot < numSlots; Slot++) { tc = tpl->Process(Slot); @@ -1453,8 +1454,10 @@ void cCiHandler::Process(void) } } } - else if (CloseAllSessions(Slot)) + else if (CloseAllSessions(Slot)) { tpl->ResetSlot(Slot); + result = false; + } else if (tpl->ModuleReady(Slot)) { dbgprotocol("Module ready in slot %d\n", Slot); tpl->NewConnection(Slot); @@ -1464,6 +1467,7 @@ void cCiHandler::Process(void) if (sessions[i]) sessions[i]->Process(); } + return result; } bool cCiHandler::EnterMenu(int Slot) diff --git a/ci.h b/ci.h index 5d33b611..255292a2 100644 --- a/ci.h +++ b/ci.h @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: ci.h 1.2 2003/02/09 11:44:00 kls Exp $ + * $Id: ci.h 1.3 2003/02/16 10:55:21 kls Exp $ */ #ifndef __CI_H @@ -95,7 +95,7 @@ private: public: ~cCiHandler(); static cCiHandler *CreateCiHandler(const char *FileName); - void Process(void); + bool Process(void); bool EnterMenu(int Slot); cCiMenu *GetMenu(void); cCiEnquiry *GetEnquiry(void); diff --git a/dvbdevice.c b/dvbdevice.c index e587f69b..92356ada 100644 --- a/dvbdevice.c +++ b/dvbdevice.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: dvbdevice.c 1.44 2003/02/09 12:41:14 kls Exp $ + * $Id: dvbdevice.c 1.45 2003/02/16 10:58:59 kls Exp $ */ #include "dvbdevice.h" @@ -65,7 +65,7 @@ static int DvbOpen(const char *Name, int n, int Mode, bool ReportError = false) class cDvbTuner : public cThread { private: - enum eTunerStatus { tsIdle, tsSet, tsTuned, tsLocked }; + enum eTunerStatus { tsIdle, tsSet, tsTuned, tsLocked, tsCam }; int fd_frontend; int cardIndex; fe_type_t frontendType; @@ -74,7 +74,6 @@ private: const char *diseqcCommands; bool active; eTunerStatus tunerStatus; - bool caSet; cMutex mutex; cCondVar newSet; bool SetFrontend(void); @@ -96,7 +95,6 @@ cDvbTuner::cDvbTuner(int Fd_Frontend, int CardIndex, fe_type_t FrontendType, cCi diseqcCommands = NULL; active = false; tunerStatus = tsIdle; - caSet = false; Start(); } @@ -119,7 +117,8 @@ void cDvbTuner::Set(const cChannel *Channel, bool Tune) channel = *Channel; if (Tune) tunerStatus = tsSet; - caSet = false; + else if (tunerStatus == tsCam) + tunerStatus = tsLocked; newSet.Broadcast(); } @@ -251,31 +250,39 @@ void cDvbTuner::Action(void) if (status & FE_HAS_LOCK) tunerStatus = tsLocked; } - dvb_frontend_event event; - if (ioctl(fd_frontend, FE_GET_EVENT, &event) == 0) { - if (tunerStatus != tsIdle && event.status & FE_REINIT) { - tunerStatus = tsSet; - esyslog("ERROR: frontend %d was reinitialized - re-tuning", cardIndex); - continue; + if (tunerStatus != tsIdle) { + dvb_frontend_event event; + if (ioctl(fd_frontend, FE_GET_EVENT, &event) == 0) { + if (event.status & FE_REINIT) { + tunerStatus = tsSet; + esyslog("ERROR: frontend %d was reinitialized - re-tuning", cardIndex); + continue; + } } - } - if (ciHandler) { - ciHandler->Process(); - if (!caSet) {//XXX TODO update in case the CA descriptors have changed - uchar buffer[2048]; - int length = cSIProcessor::GetCaDescriptors(channel.Source(), channel.Frequency(), channel.Sid(), sizeof(buffer), buffer); - if (length > 0) { - cCiCaPmt CaPmt(channel.Sid()); - CaPmt.AddCaDescriptor(length, buffer); - if (channel.Vpid()) - CaPmt.AddPid(channel.Vpid()); - if (channel.Apid1()) - CaPmt.AddPid(channel.Apid1()); - if (channel.Apid2()) - CaPmt.AddPid(channel.Apid2()); - if (channel.Dpid1()) - CaPmt.AddPid(channel.Dpid1()); - caSet = ciHandler->SetCaPmt(CaPmt); + if (tunerStatus >= tsLocked) { + if (ciHandler) { + if (ciHandler->Process()) { + if (tunerStatus != tsCam) {//XXX TODO update in case the CA descriptors have changed + uchar buffer[2048]; + int length = cSIProcessor::GetCaDescriptors(channel.Source(), channel.Frequency(), channel.Sid(), sizeof(buffer), buffer); + if (length > 0) { + cCiCaPmt CaPmt(channel.Sid()); + CaPmt.AddCaDescriptor(length, buffer); + if (channel.Vpid()) + CaPmt.AddPid(channel.Vpid()); + if (channel.Apid1()) + CaPmt.AddPid(channel.Apid1()); + if (channel.Apid2()) + CaPmt.AddPid(channel.Apid2()); + if (channel.Dpid1()) + CaPmt.AddPid(channel.Dpid1()); + if (ciHandler->SetCaPmt(CaPmt)) + tunerStatus = tsCam; + } + } + } + else + tunerStatus = tsLocked; } } }