diff --git a/packages/3rdparty/multimedia/vdr/build b/packages/3rdparty/multimedia/vdr/build index 8e6627f485..ff78a42264 100755 --- a/packages/3rdparty/multimedia/vdr/build +++ b/packages/3rdparty/multimedia/vdr/build @@ -44,5 +44,5 @@ LIBS += -liconv EOF fi -make +make vdr make include-dir diff --git a/packages/3rdparty/multimedia/vdr/meta b/packages/3rdparty/multimedia/vdr/meta index 42c1904bf6..ca4a90f071 100644 --- a/packages/3rdparty/multimedia/vdr/meta +++ b/packages/3rdparty/multimedia/vdr/meta @@ -20,7 +20,7 @@ ################################################################################ PKG_NAME="vdr" -PKG_VERSION="1.7.27" +PKG_VERSION="1.7.33" PKG_REV="1" PKG_ARCH="any" PKG_LICENSE="GPL" diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-10_fontconfig_fontsort.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-10_fontconfig_fontsort.patch deleted file mode 100644 index 88f214d848..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-10_fontconfig_fontsort.patch +++ /dev/null @@ -1,14 +0,0 @@ -diff --git a/font.c b/font.c -index 706a017..72c5ec3 100644 ---- a/font.c -+++ b/font.c -@@ -482,7 +482,8 @@ cString cFont::GetFontFileName(const char *FontName) - FcPatternAddBool(pat, FC_SCALABLE, FcTrue); - FcConfigSubstitute(NULL, pat, FcMatchPattern); - FcDefaultSubstitute(pat); -- FcFontSet *fontset = FcFontSort(NULL, pat, FcFalse, NULL, NULL); -+ FcResult fresult; -+ FcFontSet *fontset = FcFontSort(NULL, pat, FcFalse, NULL, &fresult); - if (fontset) { - for (int i = 0; i < fontset->nfont; i++) { - FcBool scalable; diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-11_recording_h_deprecated.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-11_recording_h_deprecated.patch deleted file mode 100644 index b5eb918628..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-11_recording_h_deprecated.patch +++ /dev/null @@ -1,13 +0,0 @@ -diff --git a/recording.h b/recording.h -index 5f94ee2..0b44fe8 100644 ---- a/recording.h -+++ b/recording.h -@@ -22,7 +22,7 @@ - #define TIMERMACRO_TITLE "TITLE" - #define TIMERMACRO_EPISODE "EPISODE" - --//#define __RECORDING_H_DEPRECATED_DIRECT_MEMBER_ACCESS // Code enclosed with this macro is deprecated and may be removed in a future version -+#define __RECORDING_H_DEPRECATED_DIRECT_MEMBER_ACCESS // Code enclosed with this macro is deprecated and may be removed in a future version - - extern bool VfatFileSystem; - extern int InstanceId; diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-21_internal-cam-devices.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-21_internal-cam-devices.patch deleted file mode 100644 index 8785718468..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-21_internal-cam-devices.patch +++ /dev/null @@ -1,84 +0,0 @@ -Description: This patch allows tuning to encrypted channels which are - provided by a stremdev client device and therefore already are - decrypted on the streamdev server side. - See also: http://www.vdr-developer.org/mantisbt/view.php?id=429 -Author: Tobias Grimm - -Index: vdr-1.7.27/device.c -=================================================================== ---- vdr-1.7.27.orig/device.c 2012-03-13 10:48:14.000000000 +0100 -+++ vdr-1.7.27/device.c 2012-03-25 14:18:05.434975038 +0200 -@@ -236,6 +236,7 @@ - int NumCamSlots = CamSlots.Count(); - int SlotPriority[NumCamSlots]; - int NumUsableSlots = 0; -+ bool InternalCamNeeded = false; - if (Channel->Ca() >= CA_ENCRYPTED_MIN) { - for (cCamSlot *CamSlot = CamSlots.First(); CamSlot; CamSlot = CamSlots.Next(CamSlot)) { - SlotPriority[CamSlot->Index()] = MAXPRIORITY + 1; // assumes it can't be used -@@ -249,7 +250,7 @@ - } - } - if (!NumUsableSlots) -- return NULL; // no CAM is able to decrypt this channel -+ InternalCamNeeded = true; // no CAM is able to decrypt this channel - } - - bool NeedsDetachReceivers = false; -@@ -263,11 +264,13 @@ - for (int i = 0; i < numDevices; i++) { - if (Channel->Ca() && Channel->Ca() <= CA_DVB_MAX && Channel->Ca() != device[i]->CardIndex() + 1) - continue; // a specific card was requested, but not this one -- if (NumUsableSlots && !CamSlots.Get(j)->Assign(device[i], true)) -+ if (InternalCamNeeded && !device[i]->HasInternalCam()) -+ continue; // no CAM is able to decrypt this channel and the device uses vdr handled CAMs -+ if (NumUsableSlots && !device[i]->HasInternalCam() && !CamSlots.Get(j)->Assign(device[i], true)) - continue; // CAM slot can't be used with this device - bool ndr; - if (device[i]->ProvidesChannel(Channel, Priority, &ndr)) { // this device is basicly able to do the job -- if (NumUsableSlots && device[i]->CamSlot() && device[i]->CamSlot() != CamSlots.Get(j)) -+ if (NumUsableSlots && !device[i]->HasInternalCam() && device[i]->CamSlot() && device[i]->CamSlot() != CamSlots.Get(j)) - ndr = true; // using a different CAM slot requires detaching receivers - // Put together an integer number that reflects the "impact" using - // this device would have on the overall system. Each condition is represented -@@ -282,18 +285,18 @@ - imp <<= 4; imp |= GetClippedNumProvidedSystems(4, device[i]) - 1; // avoid cards which support multiple delivery systems - imp <<= 1; imp |= device[i] == cTransferControl::ReceiverDevice(); // avoid the Transfer Mode receiver device - imp <<= 8; imp |= device[i]->Priority() - IDLEPRIORITY; // use the device with the lowest priority (- IDLEPRIORITY to assure that values -100..99 can be used) -- imp <<= 8; imp |= (NumUsableSlots ? SlotPriority[j] : IDLEPRIORITY) - IDLEPRIORITY; // use the CAM slot with the lowest priority (- IDLEPRIORITY to assure that values -100..99 can be used) -+ imp <<= 8; imp |= ((NumUsableSlots && !device[i]->HasInternalCam()) ? SlotPriority[j] : IDLEPRIORITY) - IDLEPRIORITY; // use the CAM slot with the lowest priority (- IDLEPRIORITY to assure that values -100..99 can be used) - imp <<= 1; imp |= ndr; // avoid devices if we need to detach existing receivers -- imp <<= 1; imp |= NumUsableSlots ? 0 : device[i]->HasCi(); // avoid cards with Common Interface for FTA channels -+ imp <<= 1; imp |= (NumUsableSlots || InternalCamNeeded) ? 0 : device[i]->HasCi(); // avoid cards with Common Interface for FTA channels - imp <<= 1; imp |= device[i]->AvoidRecording(); // avoid SD full featured cards -- imp <<= 1; imp |= NumUsableSlots ? !ChannelCamRelations.CamDecrypt(Channel->GetChannelID(), j + 1) : 0; // prefer CAMs that are known to decrypt this channel -+ imp <<= 1; imp |= (NumUsableSlots && !device[i]->HasInternalCam()) ? !ChannelCamRelations.CamDecrypt(Channel->GetChannelID(), j + 1) : 0; // prefer CAMs that are known to decrypt this channel - imp <<= 1; imp |= device[i]->IsPrimaryDevice(); // avoid the primary device - if (imp < Impact) { - // This device has less impact than any previous one, so we take it. - Impact = imp; - d = device[i]; - NeedsDetachReceivers = ndr; -- if (NumUsableSlots) -+ if (NumUsableSlots && !device[i]->HasInternalCam()) - s = CamSlots.Get(j); - } - } -Index: vdr-1.7.27/device.h -=================================================================== ---- vdr-1.7.27.orig/device.h 2012-03-13 11:17:16.000000000 +0100 -+++ vdr-1.7.27/device.h 2012-03-25 14:18:05.434975038 +0200 -@@ -405,6 +405,13 @@ - public: - virtual bool HasCi(void); - ///< Returns true if this device has a Common Interface. -+#define INTERNAL_CAM_DEVICES_PATCH 1 -+ virtual bool HasInternalCam(void) { return false; } -+ ///< Returns true if this device handles encrypted channels itself -+ ///< without VDR assistance. This can be e.g. when the device is a -+ ///< client that gets the stream from another VDR instance that has -+ ///< already decrypted the stream. In this case ProvidesChannel() -+ ///< shall check whether the channel can be decrypted. - void SetCamSlot(cCamSlot *CamSlot); - ///< Sets the given CamSlot to be used with this device. - cCamSlot *CamSlot(void) const { return camSlot; } diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-44_rotor.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-44_rotor.patch deleted file mode 100644 index bed6014c98..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-44_rotor.patch +++ /dev/null @@ -1,114 +0,0 @@ -diff --git a/device.h b/device.h -index e61edd0..dc2ea5f 100644 ---- a/device.h -+++ b/device.h -@@ -24,6 +24,8 @@ - #include "spu.h" - #include "thread.h" - #include "tools.h" -+#include -+#include - - #define MAXDEVICES 16 // the maximum number of devices in the system - #define MAXPIDHANDLES 64 // the maximum number of different PIDs per device -@@ -331,7 +333,7 @@ public: - virtual bool HasProgramme(void); - ///< Returns true if the device is currently showing any programme to - ///< the user, either through replaying or live. -- -+ virtual bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd) {return false;} - // PID handle facilities - - private: -diff --git a/dvbdevice.c b/dvbdevice.c -index 65e9a4b..53a4a22 100644 ---- a/dvbdevice.c -+++ b/dvbdevice.c -@@ -285,6 +285,7 @@ class cDvbTuner : public cThread { - private: - static cMutex bondMutex; - enum eTunerStatus { tsIdle, tsSet, tsTuned, tsLocked }; -+ bool SendDiseqc; - const cDvbDevice *device; - int fd_frontend; - int adapter, frontend; -@@ -300,6 +301,7 @@ private: - cMutex mutex; - cCondVar locked; - cCondVar newSet; -+ dvb_diseqc_master_cmd diseqc_cmd; - cDvbTuner *bondedTuner; - bool bondedMaster; - bool bondedMasterFailed; -@@ -322,6 +324,7 @@ public: - uint32_t SubsystemId(void) const { return subsystemId; } - bool IsTunedTo(const cChannel *Channel) const; - void SetChannel(const cChannel *Channel); -+ bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd); - bool Locked(int TimeoutMs = 0); - int GetSignalStrength(void) const; - int GetSignalQuality(void) const; -@@ -333,6 +336,7 @@ cDvbTuner::cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int - { - device = Device; - fd_frontend = Fd_Frontend; -+ SendDiseqc=false; - adapter = Adapter; - frontend = Frontend; - subsystemId = cDvbDeviceProbe::GetSubsystemId(adapter, frontend); -@@ -860,6 +864,10 @@ void cDvbTuner::Action(void) - Status = NewStatus; - cMutexLock MutexLock(&mutex); - int WaitTime = 1000; -+ if (SendDiseqc) { -+ CHECK(ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &diseqc_cmd)); -+ SendDiseqc=false; -+ } - switch (tunerStatus) { - case tsIdle: - break; -@@ -913,6 +921,20 @@ void cDvbTuner::Action(void) - } - } - -+bool cDvbTuner::SendDiseqcCmd(dvb_diseqc_master_cmd cmd) -+{ -+ cMutexLock MutexLock(&mutex); -+ cDvbTransponderParameters dtp(channel.Parameters()); -+ // Determine the required frontend type: -+ int frontendType = GetRequiredDeliverySystem(&channel, &dtp); -+ if ((frontendType!=SYS_DVBS2 && frontendType!=SYS_DVBS) || SendDiseqc) -+ return false; -+ diseqc_cmd=cmd; -+ SendDiseqc=true; -+ newSet.Broadcast(); -+ return true; -+} -+ - // --- cDvbSourceParam ------------------------------------------------------- - - class cDvbSourceParam : public cSourceParam { -@@ -1534,6 +1556,11 @@ bool cDvbDevice::HasLock(int TimeoutMs) - return dvbTuner ? dvbTuner->Locked(TimeoutMs) : false; - } - -+bool cDvbDevice::SendDiseqcCmd(dvb_diseqc_master_cmd cmd) -+{ -+ return dvbTuner->SendDiseqcCmd(cmd); -+} -+ - void cDvbDevice::SetTransferModeForDolbyDigital(int Mode) - { - setTransferModeForDolbyDigital = Mode; -diff --git a/dvbdevice.h b/dvbdevice.h -index c53a208..4ffcb91 100644 ---- a/dvbdevice.h -+++ b/dvbdevice.h -@@ -192,6 +192,7 @@ protected: - virtual bool SetChannelDevice(const cChannel *Channel, bool LiveView); - public: - virtual bool HasLock(int TimeoutMs = 0); -+ virtual bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd); - - // PID handle facilities - diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_externalci.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_externalci.patch deleted file mode 100644 index 50dae570cb..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_externalci.patch +++ /dev/null @@ -1,258 +0,0 @@ -Description: Patch for VDR to support external CI devices -Origin: https://github.com/flensrocker/vdr-plugin-dynamite -Forwarded: no -Author: Lars Hanisch -Index: vdr-1.7.27/ci.h -=================================================================== ---- vdr-1.7.27.orig/ci.h 2012-03-25 14:47:30.464975099 +0200 -+++ vdr-1.7.27/ci.h 2012-03-25 14:51:11.824975107 +0200 -@@ -72,6 +72,7 @@ - }; - - class cDevice; -+class cTSBufferBase; - class cCamSlot; - - enum eModuleStatus { msNone, msReset, msPresent, msReady }; -@@ -115,6 +116,11 @@ - ///< The derived class must call Cancel(3) in its destructor. - virtual bool Ready(void); - ///< Returns 'true' if all present CAMs in this adapter are ready. -+#define EXTERNALCI_PATCH -+ virtual cTSBufferBase *GetTSBuffer(int FdDvr) { return NULL; } -+ ///< Derived classes can return a special TS buffer with features -+ ///< like rerouting the stream through an external ci. -+ ///< The caller must delete the buffer. - virtual bool SetIdle(bool Idle, bool TestOnly) { return false; } - virtual bool IsIdle(void) const { return false; } - }; -Index: vdr-1.7.27/device.h -=================================================================== ---- vdr-1.7.27.orig/device.h 2012-03-25 14:47:30.474975099 +0200 -+++ vdr-1.7.27/device.h 2012-03-25 14:51:11.824975107 +0200 -@@ -795,7 +795,14 @@ - /// sure the returned data points to a TS packet and automatically - /// re-synchronizes after broken packets. - --class cTSBuffer : public cThread { -+class cTSBufferBase { -+public: -+ cTSBufferBase() {} -+ virtual ~cTSBufferBase() {} -+ virtual uchar *Get(void) = 0; -+ }; -+ -+class cTSBuffer : public cTSBufferBase, public cThread { - private: - int f; - int cardIndex; -@@ -804,8 +811,8 @@ - virtual void Action(void); - public: - cTSBuffer(int File, int Size, int CardIndex); -- ~cTSBuffer(); -- uchar *Get(void); -+ virtual ~cTSBuffer(); -+ virtual uchar *Get(void); - }; - - /// A plugin that want to create devices handled by the dynamite-plugin needs to create -Index: vdr-1.7.27/dvbci.c -=================================================================== ---- vdr-1.7.27.orig/dvbci.c 2012-03-25 14:47:30.474975099 +0200 -+++ vdr-1.7.27/dvbci.c 2012-03-25 14:51:11.824975107 +0200 -@@ -22,23 +22,8 @@ - adapter = Adapter; - frontend = Frontend; - idle = false; -- ca_caps_t Caps; -- if (ioctl(fd, CA_GET_CAP, &Caps) == 0) { -- if ((Caps.slot_type & CA_CI_LINK) != 0) { -- int NumSlots = Caps.slot_num; -- if (NumSlots > 0) { -- for (int i = 0; i < NumSlots; i++) -- new cCamSlot(this); -- Start(); -- } -- else -- esyslog("ERROR: no CAM slots found on device %d", device->DeviceNumber()); -- } -- else -- isyslog("device %d doesn't support CI link layer interface", device->DeviceNumber()); -- } -- else -- esyslog("ERROR: can't get CA capabilities on device %d", device->DeviceNumber()); -+ GetNumCamSlots(Device, Fd, this); -+ Start(); - } - - cDvbCiAdapter::~cDvbCiAdapter() -@@ -48,6 +33,13 @@ - CloseCa(); - } - -+cTSBufferBase *cDvbCiAdapter::GetTSBuffer(int FdDvr) -+{ -+ if (device) -+ return new cTSBuffer(FdDvr, MEGABYTE(2), device->CardIndex() + 1); -+ return NULL; -+} -+ - bool cDvbCiAdapter::OpenCa(void) - { - if (fd >= 0) -@@ -142,10 +134,60 @@ - return true; - } - -+int cDvbCiAdapter::GetNumCamSlots(cDevice *Device, int Fd, cCiAdapter *CiAdapter) -+{ -+ int NumSlots = -1; -+ if (Fd >= 0) { -+ ca_caps_t Caps; -+ if (ioctl(Fd, CA_GET_CAP, &Caps) == 0) { -+ if ((Caps.slot_type & CA_CI_LINK) != 0) { -+ NumSlots = Caps.slot_num; -+ if (NumSlots == 0) -+ esyslog("ERROR: no CAM slots found on device %d", Device->DeviceNumber()); -+ else if (CiAdapter != NULL) { -+ for (int i = 0; i < NumSlots; i++) -+ new cCamSlot(CiAdapter); -+ } -+ else -+ return NumSlots; -+ } -+ else -+ isyslog("device %d doesn't support CI link layer interface", Device->DeviceNumber()); -+ } -+ else -+ esyslog("ERROR: can't get CA capabilities on device %d", Device->DeviceNumber()); -+ } -+ return -1; -+} -+ - cDvbCiAdapter *cDvbCiAdapter::CreateCiAdapter(cDevice *Device, int Fd, int Adapter, int Frontend) - { -- // TODO check whether a CI is actually present? -- if (Device) -+ // don't create a ci-adapter if it's not useable -+ if (Device && (Fd >= 0) && (GetNumCamSlots(Device, Fd, NULL) > 0)) - return new cDvbCiAdapter(Device, Fd, Adapter, Frontend); -- return NULL; -+ -+ if (Fd >= 0) -+ close(Fd); -+ -+ // try to find an external ci-adapter -+ for (cDvbCiAdapterProbe *cp = DvbCiAdapterProbes.First(); cp; cp = DvbCiAdapterProbes.Next(cp)) { -+ cDvbCiAdapter *ca = cp->Probe(Device); -+ if (ca) -+ return ca; -+ } -+ return NULL; -+} -+ -+// --- cDvbCiAdapterProbe ------------------------------------------------------- -+ -+cList DvbCiAdapterProbes; -+ -+cDvbCiAdapterProbe::cDvbCiAdapterProbe(void) -+{ -+ DvbCiAdapterProbes.Add(this); -+} -+ -+cDvbCiAdapterProbe::~cDvbCiAdapterProbe() -+{ -+ DvbCiAdapterProbes.Del(this, false); - } -Index: vdr-1.7.27/dvbci.h -=================================================================== ---- vdr-1.7.27.orig/dvbci.h 2012-03-25 14:47:30.474975099 +0200 -+++ vdr-1.7.27/dvbci.h 2012-03-25 14:51:11.824975107 +0200 -@@ -31,9 +31,33 @@ - cDvbCiAdapter(cDevice *Device, int Fd, int Adapter = -1, int Frontend = -1); - public: - virtual ~cDvbCiAdapter(); -+ virtual cTSBufferBase *GetTSBuffer(int FdDvr); -+ static int GetNumCamSlots(cDevice *Device, int Fd, cCiAdapter *CiAdapter); -+ ///< Tests if the CA device is usable for vdr. -+ ///< If CiAdapter is not NULL it will create the CamSlots for the given ci-adapter. - virtual bool SetIdle(bool Idle, bool TestOnly); - virtual bool IsIdle(void) const { return idle; } - static cDvbCiAdapter *CreateCiAdapter(cDevice *Device, int Fd, int Adapter = -1, int Frontend = -1); - }; - -+// A plugin that implements an external DVB ci-adapter derived from cDvbCiAdapter needs to create -+// a cDvbCiAdapterProbe derived object on the heap in order to have its Probe() -+// function called, where it can actually create the appropriate ci-adapter. -+// The cDvbCiAdapterProbe object must be created in the plugin's constructor, -+// and deleted in its destructor. -+// Every plugin has to track its own list of already used device nodes. -+// The Probes are always called if the base cDvbCiAdapter can't create a ci-adapter on its own. -+ -+class cDvbCiAdapterProbe : public cListObject { -+public: -+ cDvbCiAdapterProbe(void); -+ virtual ~cDvbCiAdapterProbe(); -+ virtual cDvbCiAdapter *Probe(cDevice *Device) = 0; -+ ///< Probes for a DVB ci-adapter for the given Device and creates the appropriate -+ ///< object derived from cDvbCiAdapter if applicable. -+ ///< Returns NULL if no adapter has been created. -+ }; -+ -+extern cList DvbCiAdapterProbes; -+ - #endif //__DVBCI_H -Index: vdr-1.7.27/dvbdevice.c -=================================================================== ---- vdr-1.7.27.orig/dvbdevice.c 2012-03-25 14:47:30.474975099 +0200 -+++ vdr-1.7.27/dvbdevice.c 2012-03-25 14:51:11.824975107 +0200 -@@ -1106,9 +1106,8 @@ - - // Common Interface: - -- fd_ca = DvbOpen(DEV_DVB_CA, adapter, frontend, O_RDWR); -- if (fd_ca >= 0) -- ciAdapter = cDvbCiAdapter::CreateCiAdapter(parentDevice ? parentDevice : this, fd_ca, adapter, frontend); -+ int fd_ca = DvbOpen(DEV_DVB_CA, adapter, frontend, O_RDWR); -+ ciAdapter = cDvbCiAdapter::CreateCiAdapter(parentDevice ? parentDevice : this, fd_ca, adapter, frontend); - - // The DVR device (will be opened and closed as needed): - -@@ -1665,8 +1664,12 @@ - { - CloseDvr(); - fd_dvr = DvbOpen(DEV_DVB_DVR, adapter, frontend, O_RDONLY | O_NONBLOCK, true); -- if (fd_dvr >= 0) -- tsBuffer = new cTSBuffer(fd_dvr, MEGABYTE(2), CardIndex() + 1); -+ if (fd_dvr >= 0) { -+ if (ciAdapter) -+ tsBuffer = ciAdapter->GetTSBuffer(fd_dvr); -+ if (tsBuffer == NULL) -+ tsBuffer = new cTSBuffer(fd_dvr, MEGABYTE(2), CardIndex() + 1); -+ } - return fd_dvr >= 0; - } - -Index: vdr-1.7.27/dvbdevice.h -=================================================================== ---- vdr-1.7.27.orig/dvbdevice.h 2012-03-25 14:50:28.174975106 +0200 -+++ vdr-1.7.27/dvbdevice.h 2012-03-25 14:51:11.824975107 +0200 -@@ -127,7 +127,7 @@ - int deliverySystems[MAXDELIVERYSYSTEMS]; - int numDeliverySystems; - int numModulations; -- int fd_dvr, fd_ca; -+ int fd_dvr; - static cMutex bondMutex; - cDvbDevice *bondedDevice; - mutable bool needsDetachBondedReceivers; -@@ -227,7 +227,7 @@ - // Receiver facilities - - private: -- cTSBuffer *tsBuffer; -+ cTSBufferBase *tsBuffer; - protected: - virtual bool OpenDvr(void); - virtual void CloseDvr(void); diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_linux-3.7.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_linux-3.7.patch deleted file mode 100644 index 5cf092b3c6..0000000000 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-90_linux-3.7.patch +++ /dev/null @@ -1,16 +0,0 @@ -diff --git a/dvbdevice.c b/dvbdevice.c -index 42ec5b1..9c397d7 100644 ---- a/dvbdevice.c -+++ b/dvbdevice.c -@@ -839,7 +839,11 @@ bool cDvbTuner::SetFrontend(void) - SETCMD(DTV_HIERARCHY, dtp.Hierarchy()); - if (frontendType == SYS_DVBT2) { - // DVB-T2 -+#ifdef DTV_DVBT2_PLP_ID - SETCMD(DTV_DVBT2_PLP_ID, dtp.PlpId()); -+#else -+ SETCMD(DTV_DVBT2_PLP_ID_LEGACY, dtp.PlpId()); -+#endif - } - - tuneTimeout = DVBT_TUNE_TIMEOUT; diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-01_disable_ca_updates.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-01_disable_ca_updates.patch similarity index 100% rename from packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-01_disable_ca_updates.patch rename to packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-01_disable_ca_updates.patch diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-02_disable_eitscan.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-02_disable_eitscan.patch similarity index 100% rename from packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-02_disable_eitscan.patch rename to packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-02_disable_eitscan.patch diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-10_hannels.conf.terr-fix.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-10_hannels.conf.terr-fix.patch similarity index 100% rename from packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-10_hannels.conf.terr-fix.patch rename to packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-10_hannels.conf.terr-fix.patch diff --git a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-61_dynamite-subdevice.patch b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-20_dynamite+externalci+rotorng.patch similarity index 67% rename from packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-61_dynamite-subdevice.patch rename to packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-20_dynamite+externalci+rotorng.patch index 50aabae7d1..079e38dfca 100644 --- a/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.27-61_dynamite-subdevice.patch +++ b/packages/3rdparty/multimedia/vdr/patches/vdr-1.7.33-20_dynamite+externalci+rotorng.patch @@ -1,21 +1,5 @@ -From a13c75ec46f2783b2d258af48d7de28d44666715 Mon Sep 17 00:00:00 2001 -From: Stefan Saraev -Date: Sat, 5 May 2012 21:50:48 +0300 -Subject: [PATCH 2/2] dynamite - ---- - ci.c | 2 + - ci.h | 2 + - device.c | 121 +++++++++++++++++++++++++++++++++++++++++++++++++++++++---- - device.h | 85 ++++++++++++++++++++++++++++++++++++----- - dvbci.c | 51 +++++++++++++++++++++++-- - dvbci.h | 12 +++++- - dvbdevice.c | 95 ++++++++++++++++++++++++++++++++++++++++++---- - dvbdevice.h | 6 ++- - 8 files changed, 339 insertions(+), 35 deletions(-) - diff --git a/ci.c b/ci.c -index 0135d07..cf21952 100644 +index 904697e..1e95313 100644 --- a/ci.c +++ b/ci.c @@ -1571,6 +1571,8 @@ cCamSlot::cCamSlot(cCiAdapter *CiAdapter) @@ -28,29 +12,43 @@ index 0135d07..cf21952 100644 DeleteAllConnections(); } diff --git a/ci.h b/ci.h -index 74e0270..d38e2dd 100644 +index 74e0270..818ea29 100644 --- a/ci.h +++ b/ci.h -@@ -115,6 +115,8 @@ public: +@@ -72,6 +72,7 @@ public: + }; + + class cDevice; ++class cTSBufferBase; + class cCamSlot; + + enum eModuleStatus { msNone, msReset, msPresent, msReady }; +@@ -115,6 +116,13 @@ public: ///< The derived class must call Cancel(3) in its destructor. virtual bool Ready(void); ///< Returns 'true' if all present CAMs in this adapter are ready. ++#define EXTERNALCI_PATCH ++ virtual cTSBufferBase *GetTSBuffer(int FdDvr) { return NULL; } ++ ///< Derived classes can return a special TS buffer with features ++ ///< like rerouting the stream through an external ci. ++ ///< The caller must delete the buffer. + virtual bool SetIdle(bool Idle, bool TestOnly) { return false; } + virtual bool IsIdle(void) const { return false; } }; class cTPDU; diff --git a/device.c b/device.c -index 273757e..f83e789 100644 +index 2678d68..56c2b9c 100644 --- a/device.c +++ b/device.c @@ -69,12 +69,22 @@ int cDevice::currentChannel = 1; cDevice *cDevice::device[MAXDEVICES] = { NULL }; cDevice *cDevice::primaryDevice = NULL; cList cDevice::deviceHooks; -+cDevice *cDevice::nextParentDevice = NULL; - +- -cDevice::cDevice(void) ++cDevice *cDevice::nextParentDevice = NULL; ++ +cDevice::cDevice(cDevice *ParentDevice) :patPmtParser(true) -{ @@ -128,7 +126,7 @@ index 273757e..f83e789 100644 for (int i = 0; i < numDevices; i++) { if (device[i] == this) return i; -@@ -349,6 +388,8 @@ bool cDevice::HasCi(void) +@@ -355,6 +394,8 @@ bool cDevice::HasCi(void) void cDevice::SetCamSlot(cCamSlot *CamSlot) { @@ -137,7 +135,7 @@ index 273757e..f83e789 100644 camSlot = CamSlot; } -@@ -561,6 +602,10 @@ void cDevice::DelLivePids(void) +@@ -567,6 +608,10 @@ void cDevice::DelLivePids(void) void cDevice::StartSectionHandler(void) { @@ -148,7 +146,7 @@ index 273757e..f83e789 100644 if (!sectionHandler) { sectionHandler = new cSectionHandler(this); AttachFilter(eitFilter = new cEitFilter); -@@ -572,6 +617,10 @@ void cDevice::StartSectionHandler(void) +@@ -578,6 +623,10 @@ void cDevice::StartSectionHandler(void) void cDevice::StopSectionHandler(void) { @@ -159,7 +157,7 @@ index 273757e..f83e789 100644 if (sectionHandler) { delete nitFilter; delete sdtFilter; -@@ -598,12 +647,17 @@ void cDevice::CloseFilter(int Handle) +@@ -609,12 +658,17 @@ void cDevice::CloseFilter(int Handle) void cDevice::AttachFilter(cFilter *Filter) { @@ -177,7 +175,7 @@ index 273757e..f83e789 100644 if (sectionHandler) sectionHandler->Detach(Filter); } -@@ -765,6 +819,7 @@ eSetChannelResult cDevice::SetChannel(const cChannel *Channel, bool LiveView) +@@ -776,6 +830,7 @@ eSetChannelResult cDevice::SetChannel(const cChannel *Channel, bool LiveView) sectionHandler->SetStatus(false); sectionHandler->SetChannel(NULL); } @@ -185,7 +183,7 @@ index 273757e..f83e789 100644 // Tell the camSlot about the channel switch and add all PIDs of this // channel to it, for possible later decryption: if (camSlot) -@@ -811,19 +866,27 @@ void cDevice::ForceTransferMode(void) +@@ -822,19 +877,27 @@ void cDevice::ForceTransferMode(void) { if (!cTransferControl::ReceiverDevice()) { cChannel *Channel = Channels.GetByNumber(CurrentChannel()); @@ -214,7 +212,7 @@ index 273757e..f83e789 100644 if (Seconds >= 0) occupiedTimeout = time(NULL) + min(Seconds, MAXOCCUPIEDTIMEOUT); } -@@ -1196,7 +1259,10 @@ bool cDevice::Transferring(void) const +@@ -1209,7 +1272,10 @@ bool cDevice::Transferring(void) const bool cDevice::AttachPlayer(cPlayer *Player) { @@ -225,7 +223,7 @@ index 273757e..f83e789 100644 if (player) Detach(player); DELETENULL(liveSubtitle); -@@ -1215,6 +1281,8 @@ bool cDevice::AttachPlayer(cPlayer *Player) +@@ -1228,6 +1294,8 @@ bool cDevice::AttachPlayer(cPlayer *Player) void cDevice::Detach(cPlayer *Player) { @@ -234,7 +232,7 @@ index 273757e..f83e789 100644 if (Player && player == Player) { cPlayer *p = player; player = NULL; // avoids recursive calls to Detach() -@@ -1234,6 +1302,8 @@ void cDevice::Detach(cPlayer *Player) +@@ -1247,6 +1315,8 @@ void cDevice::Detach(cPlayer *Player) void cDevice::StopReplay(void) { @@ -243,7 +241,7 @@ index 273757e..f83e789 100644 if (player) { Detach(player); if (IsPrimaryDevice()) -@@ -1516,6 +1586,8 @@ int cDevice::PlayTs(const uchar *Data, int Length, bool VideoOnly) +@@ -1529,6 +1599,8 @@ int cDevice::PlayTs(const uchar *Data, int Length, bool VideoOnly) int cDevice::Priority(void) const { @@ -252,7 +250,7 @@ index 273757e..f83e789 100644 int priority = IDLEPRIORITY; if (IsPrimaryDevice() && !Replaying() && ActualDevice() == PrimaryDevice()) priority = TRANSFERPRIORITY; // we use the same value here, no matter whether it's actual Transfer Mode or real live viewing -@@ -1534,6 +1606,8 @@ bool cDevice::Ready(void) +@@ -1547,6 +1619,8 @@ bool cDevice::Ready(void) bool cDevice::Receiving(bool Dummy) const { @@ -261,7 +259,7 @@ index 273757e..f83e789 100644 cMutexLock MutexLock(&mutexReceiver); for (int i = 0; i < MAXRECEIVERS; i++) { if (receiver[i]) -@@ -1614,10 +1688,13 @@ bool cDevice::GetTSPacket(uchar *&Data) +@@ -1627,10 +1701,13 @@ bool cDevice::GetTSPacket(uchar *&Data) bool cDevice::AttachReceiver(cReceiver *Receiver) { @@ -275,7 +273,7 @@ index 273757e..f83e789 100644 // activate the following line if you need it - actually the driver should be fixed! //#define WAIT_FOR_TUNER_LOCK #ifdef WAIT_FOR_TUNER_LOCK -@@ -1656,6 +1733,8 @@ bool cDevice::AttachReceiver(cReceiver *Receiver) +@@ -1669,6 +1746,8 @@ bool cDevice::AttachReceiver(cReceiver *Receiver) void cDevice::Detach(cReceiver *Receiver) { @@ -284,7 +282,7 @@ index 273757e..f83e789 100644 if (!Receiver || Receiver->device != this) return; bool receiversLeft = false; -@@ -1681,6 +1760,8 @@ void cDevice::Detach(cReceiver *Receiver) +@@ -1694,6 +1773,8 @@ void cDevice::Detach(cReceiver *Receiver) void cDevice::DetachAll(int Pid) { @@ -293,7 +291,7 @@ index 273757e..f83e789 100644 if (Pid) { cMutexLock MutexLock(&mutexReceiver); for (int i = 0; i < MAXRECEIVERS; i++) { -@@ -1693,6 +1774,8 @@ void cDevice::DetachAll(int Pid) +@@ -1706,6 +1787,8 @@ void cDevice::DetachAll(int Pid) void cDevice::DetachAllReceivers(void) { @@ -302,7 +300,7 @@ index 273757e..f83e789 100644 cMutexLock MutexLock(&mutexReceiver); for (int i = 0; i < MAXRECEIVERS; i++) Detach(receiver[i]); -@@ -1764,3 +1847,25 @@ uchar *cTSBuffer::Get(void) +@@ -1778,3 +1861,25 @@ uchar *cTSBuffer::Get(void) } return NULL; } @@ -329,10 +327,18 @@ index 273757e..f83e789 100644 + DynamicDeviceProbes.Del(this, false); +} diff --git a/device.h b/device.h -index dc2ea5f..e5e92a3 100644 +index e2847d8..3a8aa01 100644 --- a/device.h +++ b/device.h -@@ -171,7 +171,6 @@ private: +@@ -24,6 +24,7 @@ + #include "spu.h" + #include "thread.h" + #include "tools.h" ++#include + + #define MAXDEVICES 16 // the maximum number of devices in the system + #define MAXPIDHANDLES 64 // the maximum number of different PIDs per device +@@ -169,7 +170,6 @@ private: static int nextCardIndex; int cardIndex; protected: @@ -340,7 +346,7 @@ index dc2ea5f..e5e92a3 100644 virtual ~cDevice(); virtual bool Ready(void); ///< Returns true if this device is ready. Devices with conditional -@@ -198,9 +197,6 @@ protected: +@@ -196,9 +196,6 @@ protected: ///< A derived class must call the MakePrimaryDevice() function of its ///< base class. public: @@ -349,8 +355,16 @@ index dc2ea5f..e5e92a3 100644 - ///< Returns the card index of this device (0 ... MAXDEVICES - 1). int DeviceNumber(void) const; ///< Returns the number of this device (0 ... numDevices). - virtual cString DeviceName(void) const; -@@ -416,9 +412,6 @@ public: + virtual cString DeviceType(void) const; +@@ -338,6 +335,7 @@ public: + ///< Returns true if the device is currently showing any programme to + ///< the user, either through replaying or live. + ++ virtual bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd) {return false;} + // PID handle facilities + + private: +@@ -423,9 +421,6 @@ public: ///< shall check whether the channel can be decrypted. void SetCamSlot(cCamSlot *CamSlot); ///< Sets the given CamSlot to be used with this device. @@ -360,7 +374,7 @@ index dc2ea5f..e5e92a3 100644 // Image Grab facilities -@@ -574,9 +567,6 @@ private: +@@ -581,9 +576,6 @@ private: cTsToPes tsToPesSubtitle; bool isPlayingVideo; protected: @@ -370,11 +384,11 @@ index dc2ea5f..e5e92a3 100644 virtual bool CanReplay(void) const; ///< Returns true if this device can currently start a replay session. virtual bool SetPlayMode(ePlayMode PlayMode); -@@ -761,6 +751,38 @@ public: +@@ -795,6 +787,38 @@ public: ///< Detaches all receivers from this device for this pid. virtual void DetachAllReceivers(void); ///< Detaches all receivers from this device. -+ ++ +// --- dynamite subdevice patch start --- + friend class cDynamicDevice; +private: @@ -409,10 +423,32 @@ index dc2ea5f..e5e92a3 100644 }; /// Derived cDevice classes that can receive channels will have to provide -@@ -784,4 +806,47 @@ public: - uchar *Get(void); - }; +@@ -805,7 +829,14 @@ public: + /// sure the returned data points to a TS packet and automatically + /// re-synchronizes after broken packets. +-class cTSBuffer : public cThread { ++class cTSBufferBase { ++public: ++ cTSBufferBase() {} ++ virtual ~cTSBufferBase() {} ++ virtual uchar *Get(void) = 0; ++ }; ++ ++class cTSBuffer : public cTSBufferBase, public cThread { + private: + int f; + int cardIndex; +@@ -814,8 +845,51 @@ private: + virtual void Action(void); + public: + cTSBuffer(int File, int Size, int CardIndex); +- ~cTSBuffer(); +- uchar *Get(void); ++ virtual ~cTSBuffer(); ++ virtual uchar *Get(void); ++ }; ++ +/// A plugin that want to create devices handled by the dynamite-plugin needs to create +/// a cDynamicDeviceProbe derived object on the heap in order to have its Probe() +/// function called, where it can actually create the appropriate device. @@ -452,16 +488,16 @@ index dc2ea5f..e5e92a3 100644 + ///< object derived from cDevice if applicable. + ///< Returns the device that has been created or NULL if not. + ///< The dynamite-plugin will delete the device if it is detached. -+ }; -+ + }; + +extern cList DynamicDeviceProbes; -+ ++ #endif //__DEVICE_H diff --git a/dvbci.c b/dvbci.c -index 5289bbd..fea3a83 100644 +index 5289bbd..baa70bc 100644 --- a/dvbci.c +++ b/dvbci.c -@@ -10,15 +10,18 @@ +@@ -10,41 +10,70 @@ #include "dvbci.h" #include #include @@ -476,13 +512,30 @@ index 5289bbd..fea3a83 100644 device = Device; SetDescription("CI adapter on device %d", device->DeviceNumber()); fd = Fd; +- ca_caps_t Caps; +- if (ioctl(fd, CA_GET_CAP, &Caps) == 0) { +- if ((Caps.slot_type & CA_CI_LINK) != 0) { +- int NumSlots = Caps.slot_num; +- if (NumSlots > 0) { +- for (int i = 0; i < NumSlots; i++) +- new cCamSlot(this); +- Start(); +- } +- else +- esyslog("ERROR: no CAM slots found on device %d", device->DeviceNumber()); +- } +- else +- isyslog("device %d doesn't support CI link layer interface", device->DeviceNumber()); +- } +- else +- esyslog("ERROR: can't get CA capabilities on device %d", device->DeviceNumber()); + adapter = Adapter; + frontend = Frontend; + idle = false; - ca_caps_t Caps; - if (ioctl(fd, CA_GET_CAP, &Caps) == 0) { - if ((Caps.slot_type & CA_CI_LINK) != 0) { -@@ -41,10 +44,44 @@ cDvbCiAdapter::cDvbCiAdapter(cDevice *Device, int Fd) ++ GetNumCamSlots(Device, Fd, this); ++ Start(); + } + cDvbCiAdapter::~cDvbCiAdapter() { Cancel(3); @@ -518,6 +571,13 @@ index 5289bbd..fea3a83 100644 + OpenCa(); + idle = Idle; + return true; ++} ++ ++cTSBufferBase *cDvbCiAdapter::GetTSBuffer(int FdDvr) ++{ ++ if (device) ++ return new cTSBuffer(FdDvr, MEGABYTE(5), device->CardIndex() + 1); ++ return NULL; } int cDvbCiAdapter::Read(uint8_t *Buffer, int MaxLength) @@ -527,7 +587,7 @@ index 5289bbd..fea3a83 100644 if (Buffer && MaxLength > 0) { struct pollfd pfd[1]; pfd[0].fd = fd; -@@ -61,6 +98,8 @@ int cDvbCiAdapter::Read(uint8_t *Buffer, int MaxLength) +@@ -61,6 +90,8 @@ int cDvbCiAdapter::Read(uint8_t *Buffer, int MaxLength) void cDvbCiAdapter::Write(const uint8_t *Buffer, int Length) { @@ -536,7 +596,7 @@ index 5289bbd..fea3a83 100644 if (Buffer && Length > 0) { if (safe_write(fd, Buffer, Length) != Length) esyslog("ERROR: can't write to CI adapter on device %d: %m", device->DeviceNumber()); -@@ -69,6 +108,8 @@ void cDvbCiAdapter::Write(const uint8_t *Buffer, int Length) +@@ -69,6 +100,8 @@ void cDvbCiAdapter::Write(const uint8_t *Buffer, int Length) bool cDvbCiAdapter::Reset(int Slot) { @@ -545,7 +605,7 @@ index 5289bbd..fea3a83 100644 if (ioctl(fd, CA_RESET, 1 << Slot) != -1) return true; else -@@ -78,6 +119,8 @@ bool cDvbCiAdapter::Reset(int Slot) +@@ -78,6 +111,8 @@ bool cDvbCiAdapter::Reset(int Slot) eModuleStatus cDvbCiAdapter::ModuleStatus(int Slot) { @@ -554,24 +614,77 @@ index 5289bbd..fea3a83 100644 ca_slot_info_t sinfo; sinfo.num = Slot; if (ioctl(fd, CA_GET_SLOT_INFO, &sinfo) != -1) { -@@ -99,10 +142,10 @@ bool cDvbCiAdapter::Assign(cDevice *Device, bool Query) +@@ -99,10 +134,60 @@ bool cDvbCiAdapter::Assign(cDevice *Device, bool Query) return true; } -cDvbCiAdapter *cDvbCiAdapter::CreateCiAdapter(cDevice *Device, int Fd) -+cDvbCiAdapter *cDvbCiAdapter::CreateCiAdapter(cDevice *Device, int Fd, int Adapter, int Frontend) ++int cDvbCiAdapter::GetNumCamSlots(cDevice *Device, int Fd, cCiAdapter *CiAdapter) { - // TODO check whether a CI is actually present? - if (Device) +- // TODO check whether a CI is actually present? +- if (Device) - return new cDvbCiAdapter(Device, Fd); +- return NULL; ++ int NumSlots = -1; ++ if (Fd >= 0) { ++ ca_caps_t Caps; ++ if (ioctl(Fd, CA_GET_CAP, &Caps) == 0) { ++ if ((Caps.slot_type & CA_CI_LINK) != 0) { ++ NumSlots = Caps.slot_num; ++ if (NumSlots == 0) ++ esyslog("ERROR: no CAM slots found on device %d", Device->DeviceNumber()); ++ else if (CiAdapter != NULL) { ++ for (int i = 0; i < NumSlots; i++) ++ new cCamSlot(CiAdapter); ++ } ++ else ++ return NumSlots; ++ } ++ else ++ isyslog("device %d doesn't support CI link layer interface", Device->DeviceNumber()); ++ } ++ else ++ esyslog("ERROR: can't get CA capabilities on device %d", Device->DeviceNumber()); ++ } ++ return -1; ++} ++ ++cDvbCiAdapter *cDvbCiAdapter::CreateCiAdapter(cDevice *Device, int Fd, int Adapter, int Frontend) ++{ ++ // don't create a ci-adapter if it's not useable ++ if (Device && (Fd >= 0) && (GetNumCamSlots(Device, Fd, NULL) > 0)) + return new cDvbCiAdapter(Device, Fd, Adapter, Frontend); - return NULL; ++ ++ if (Fd >= 0) ++ close(Fd); ++ ++ // try to find an external ci-adapter ++ for (cDvbCiAdapterProbe *cp = DvbCiAdapterProbes.First(); cp; cp = DvbCiAdapterProbes.Next(cp)) { ++ cDvbCiAdapter *ca = cp->Probe(Device); ++ if (ca) ++ return ca; ++ } ++ return NULL; ++} ++ ++// --- cDvbCiAdapterProbe ------------------------------------------------------- ++ ++cList DvbCiAdapterProbes; ++ ++cDvbCiAdapterProbe::cDvbCiAdapterProbe(void) ++{ ++ DvbCiAdapterProbes.Add(this); ++} ++ ++cDvbCiAdapterProbe::~cDvbCiAdapterProbe() ++{ ++ DvbCiAdapterProbes.Del(this, false); } diff --git a/dvbci.h b/dvbci.h -index adbe40d..6d117b2 100644 +index adbe40d..d908b2f 100644 --- a/dvbci.h +++ b/dvbci.h -@@ -16,16 +16,24 @@ class cDvbCiAdapter : public cCiAdapter { +@@ -16,16 +16,48 @@ class cDvbCiAdapter : public cCiAdapter { private: cDevice *device; int fd; @@ -592,26 +705,53 @@ index adbe40d..6d117b2 100644 public: virtual ~cDvbCiAdapter(); - static cDvbCiAdapter *CreateCiAdapter(cDevice *Device, int Fd); ++ virtual cTSBufferBase *GetTSBuffer(int FdDvr); ++ static int GetNumCamSlots(cDevice *Device, int Fd, cCiAdapter *CiAdapter); ++ ///< Tests if the CA device is usable for vdr. ++ ///< If CiAdapter is not NULL it will create the CamSlots for the given ci-adapter. + virtual bool SetIdle(bool Idle, bool TestOnly); + virtual bool IsIdle(void) const { return idle; } + static cDvbCiAdapter *CreateCiAdapter(cDevice *Device, int Fd, int Adapter = -1, int Frontend = -1); ++ }; ++ ++// A plugin that implements an external DVB ci-adapter derived from cDvbCiAdapter needs to create ++// a cDvbCiAdapterProbe derived object on the heap in order to have its Probe() ++// function called, where it can actually create the appropriate ci-adapter. ++// The cDvbCiAdapterProbe object must be created in the plugin's constructor, ++// and deleted in its destructor. ++// Every plugin has to track its own list of already used device nodes. ++// The Probes are always called if the base cDvbCiAdapter can't create a ci-adapter on its own. ++ ++class cDvbCiAdapterProbe : public cListObject { ++public: ++ cDvbCiAdapterProbe(void); ++ virtual ~cDvbCiAdapterProbe(); ++ virtual cDvbCiAdapter *Probe(cDevice *Device) = 0; ++ ///< Probes for a DVB ci-adapter for the given Device and creates the appropriate ++ ///< object derived from cDvbCiAdapter if applicable. ++ ///< Returns NULL if no adapter has been created. }; ++extern cList DvbCiAdapterProbes; ++ #endif //__DVBCI_H diff --git a/dvbdevice.c b/dvbdevice.c -index 53a4a22..7fc12a4 100644 +index 43e8544..49b5f61 100644 --- a/dvbdevice.c +++ b/dvbdevice.c -@@ -287,7 +287,7 @@ private: +@@ -287,9 +287,10 @@ class cDvbTuner : public cThread { + private: + static cMutex bondMutex; enum eTunerStatus { tsIdle, tsSet, tsTuned, tsLocked }; - bool SendDiseqc; ++ bool SendDiseqc; + int frontendType; const cDvbDevice *device; - int fd_frontend; + mutable int fd_frontend; int adapter, frontend; uint32_t subsystemId; int tuneTimeout; -@@ -298,7 +298,7 @@ private: +@@ -300,7 +301,7 @@ private: const cScr *scr; bool lnbPowerTurnedOn; eTunerStatus tunerStatus; @@ -619,8 +759,14 @@ index 53a4a22..7fc12a4 100644 + mutable cMutex mutex; cCondVar locked; cCondVar newSet; - dvb_diseqc_master_cmd diseqc_cmd; -@@ -313,6 +313,10 @@ private: + cDvbTuner *bondedTuner; +@@ -308,11 +309,16 @@ private: + bool SetFrontendType(const cChannel *Channel); + cString GetBondingParams(const cChannel *Channel = NULL) const; + void ClearEventQueue(void) const; ++ dvb_diseqc_master_cmd diseqc_cmd; + bool GetFrontendStatus(fe_status_t &Status) const; + void ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency); void ResetToneAndVoltage(void); bool SetFrontend(void); virtual void Action(void); @@ -631,24 +777,37 @@ index 53a4a22..7fc12a4 100644 public: cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int Frontend); virtual ~cDvbTuner(); -@@ -324,6 +328,8 @@ public: +@@ -325,9 +331,13 @@ public: uint32_t SubsystemId(void) const { return subsystemId; } bool IsTunedTo(const cChannel *Channel) const; void SetChannel(const cChannel *Channel); -+ bool SetIdle(bool Idle); -+ bool IsIdle(void) const { return isIdle; } - bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd); ++ bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd); bool Locked(int TimeoutMs = 0); int GetSignalStrength(void) const; -@@ -350,6 +356,7 @@ cDvbTuner::cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int + int GetSignalQuality(void) const; ++ ++ bool SetIdle(bool Idle); ++ bool IsIdle(void) const { return isIdle; } + }; + + cMutex cDvbTuner::bondMutex; +@@ -337,6 +347,7 @@ cDvbTuner::cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int + frontendType = SYS_UNDEFINED; + device = Device; + fd_frontend = Fd_Frontend; ++ SendDiseqc=false; + adapter = Adapter; + frontend = Frontend; + subsystemId = cDvbDeviceProbe::GetSubsystemId(adapter, frontend); +@@ -349,6 +360,7 @@ cDvbTuner::cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int + tunerStatus = tsIdle; bondedTuner = NULL; bondedMaster = false; - bondedMasterFailed = false; + isIdle = false; SetDescription("tuner on frontend %d/%d", adapter, frontend); Start(); } -@@ -367,6 +374,8 @@ cDvbTuner::~cDvbTuner() +@@ -366,6 +378,8 @@ cDvbTuner::~cDvbTuner() ExecuteDiseqc(lastDiseqc, &Frequency); } */ @@ -657,7 +816,7 @@ index 53a4a22..7fc12a4 100644 } bool cDvbTuner::Bond(cDvbTuner *Tuner) -@@ -524,6 +533,8 @@ bool cDvbTuner::Locked(int TimeoutMs) +@@ -510,6 +524,8 @@ bool cDvbTuner::Locked(int TimeoutMs) void cDvbTuner::ClearEventQueue(void) const { @@ -666,8 +825,28 @@ index 53a4a22..7fc12a4 100644 cPoller Poller(fd_frontend); if (Poller.Poll(TUNER_POLL_TIMEOUT)) { dvb_frontend_event Event; -@@ -714,6 +725,8 @@ static int GetRequiredDeliverySystem(const cChannel *Channel, const cDvbTranspon +@@ -710,8 +726,28 @@ static int GetRequiredDeliverySystem(const cChannel *Channel, const cDvbTranspon + return ds; + } ++bool cDvbTuner::SendDiseqcCmd(dvb_diseqc_master_cmd cmd) ++{ ++ cMutexLock MutexLock(&mutex); ++ cDvbTransponderParameters dtp(channel.Parameters()); ++ ++ // Determine the required frontend type: ++ int frontendType = GetRequiredDeliverySystem(&channel, &dtp); ++ ++ if ((frontendType!=SYS_DVBS2 && frontendType!=SYS_DVBS) || SendDiseqc) ++ return false; ++ if (!OpenFrontend()) ++ return false; ++ diseqc_cmd=cmd; ++ SendDiseqc=true; ++ newSet.Broadcast(); ++ return true; ++} ++ bool cDvbTuner::SetFrontend(void) { + if (!OpenFrontend()) @@ -675,7 +854,7 @@ index 53a4a22..7fc12a4 100644 #define MAXFRONTENDCMDS 16 #define SETCMD(c, d) { Frontend[CmdSeq.num].cmd = (c);\ Frontend[CmdSeq.num].u.data = (d);\ -@@ -859,9 +872,11 @@ void cDvbTuner::Action(void) +@@ -857,10 +893,16 @@ void cDvbTuner::Action(void) bool LostLock = false; fe_status_t Status = (fe_status_t)0; while (Running()) { @@ -688,10 +867,15 @@ index 53a4a22..7fc12a4 100644 + Status = NewStatus; + } cMutexLock MutexLock(&mutex); ++ if (SendDiseqc) { ++ CHECK(ioctl(fd_frontend, FE_DISEQC_SEND_MASTER_CMD, &diseqc_cmd)); ++ SendDiseqc=false; ++ } int WaitTime = 1000; - if (SendDiseqc) { -@@ -935,6 +950,40 @@ bool cDvbTuner::SendDiseqcCmd(dvb_diseqc_master_cmd cmd) - return true; + switch (tunerStatus) { + case tsIdle: +@@ -912,6 +954,40 @@ void cDvbTuner::Action(void) + } } +bool cDvbTuner::SetIdle(bool Idle) @@ -731,7 +915,7 @@ index 53a4a22..7fc12a4 100644 // --- cDvbSourceParam ------------------------------------------------------- class cDvbSourceParam : public cSourceParam { -@@ -1020,7 +1069,8 @@ const char *DeliverySystemNames[] = { +@@ -997,7 +1073,8 @@ const char *DeliverySystemNames[] = { NULL }; @@ -741,16 +925,19 @@ index 53a4a22..7fc12a4 100644 { adapter = Adapter; frontend = Frontend; -@@ -1040,7 +1090,7 @@ cDvbDevice::cDvbDevice(int Adapter, int Frontend) +@@ -1015,9 +1092,8 @@ cDvbDevice::cDvbDevice(int Adapter, int Frontend) - fd_ca = DvbOpen(DEV_DVB_CA, adapter, frontend, O_RDWR); - if (fd_ca >= 0) + // Common Interface: + +- fd_ca = DvbOpen(DEV_DVB_CA, adapter, frontend, O_RDWR); +- if (fd_ca >= 0) - ciAdapter = cDvbCiAdapter::CreateCiAdapter(this, fd_ca); -+ ciAdapter = cDvbCiAdapter::CreateCiAdapter(parentDevice ? parentDevice : this, fd_ca, adapter, frontend); ++ int fd_ca = DvbOpen(DEV_DVB_CA, adapter, frontend, O_RDWR); ++ ciAdapter = cDvbCiAdapter::CreateCiAdapter(parentDevice ? parentDevice : this, fd_ca, adapter, frontend); // The DVR device (will be opened and closed as needed): -@@ -1257,7 +1307,11 @@ bool cDvbDevice::BondDevices(const char *Bondings) +@@ -1245,7 +1321,11 @@ bool cDvbDevice::BondDevices(const char *Bondings) if (d >= 0) { int ErrorDevice = 0; if (cDevice *Device1 = cDevice::GetDevice(i)) { @@ -762,7 +949,7 @@ index 53a4a22..7fc12a4 100644 if (cDvbDevice *DvbDevice1 = dynamic_cast(Device1)) { if (cDvbDevice *DvbDevice2 = dynamic_cast(Device2)) { if (!DvbDevice1->Bond(DvbDevice2)) -@@ -1291,7 +1345,10 @@ bool cDvbDevice::BondDevices(const char *Bondings) +@@ -1279,7 +1359,10 @@ bool cDvbDevice::BondDevices(const char *Bondings) void cDvbDevice::UnBondDevices(void) { for (int i = 0; i < cDevice::NumDevices(); i++) { @@ -774,7 +961,7 @@ index 53a4a22..7fc12a4 100644 d->UnBond(); } } -@@ -1345,6 +1402,26 @@ bool cDvbDevice::BondingOk(const cChannel *Channel, bool ConsiderOccupied) const +@@ -1333,6 +1416,26 @@ bool cDvbDevice::BondingOk(const cChannel *Channel, bool ConsiderOccupied) const return true; } @@ -801,7 +988,7 @@ index 53a4a22..7fc12a4 100644 bool cDvbDevice::HasCi(void) { return ciAdapter; -@@ -1511,7 +1588,7 @@ bool cDvbDevice::ProvidesChannel(const cChannel *Channel, int Priority, bool *Ne +@@ -1499,7 +1602,7 @@ bool cDvbDevice::ProvidesChannel(const cChannel *Channel, int Priority, bool *Ne bool cDvbDevice::ProvidesEIT(void) const { @@ -810,8 +997,35 @@ index 53a4a22..7fc12a4 100644 } int cDvbDevice::NumProvidedSystems(void) const +@@ -1544,6 +1647,11 @@ bool cDvbDevice::HasLock(int TimeoutMs) + return dvbTuner ? dvbTuner->Locked(TimeoutMs) : false; + } + ++bool cDvbDevice::SendDiseqcCmd(dvb_diseqc_master_cmd cmd) ++{ ++ return dvbTuner->SendDiseqcCmd(cmd); ++} ++ + void cDvbDevice::SetTransferModeForDolbyDigital(int Mode) + { + setTransferModeForDolbyDigital = Mode; +@@ -1553,8 +1661,12 @@ bool cDvbDevice::OpenDvr(void) + { + CloseDvr(); + fd_dvr = DvbOpen(DEV_DVB_DVR, adapter, frontend, O_RDONLY | O_NONBLOCK, true); +- if (fd_dvr >= 0) +- tsBuffer = new cTSBuffer(fd_dvr, MEGABYTE(5), CardIndex() + 1); ++ if (fd_dvr >= 0) { ++ if (ciAdapter) ++ tsBuffer = ciAdapter->GetTSBuffer(fd_dvr); ++ if (tsBuffer == NULL) ++ tsBuffer = new cTSBuffer(fd_dvr, MEGABYTE(5), CardIndex() + 1); ++ } + return fd_dvr >= 0; + } + diff --git a/dvbdevice.h b/dvbdevice.h -index 4ffcb91..e9b7cd6 100644 +index 7da9c56..6cd4abf 100644 --- a/dvbdevice.h +++ b/dvbdevice.h @@ -107,7 +107,7 @@ class cDvbTuner; @@ -823,7 +1037,14 @@ index 4ffcb91..e9b7cd6 100644 static cString DvbName(const char *Name, int Adapter, int Frontend); static int DvbOpen(const char *Name, int Adapter, int Frontend, int Mode, bool ReportError = false); private: -@@ -133,12 +133,14 @@ private: +@@ -127,19 +127,20 @@ private: + int deliverySystems[MAXDELIVERYSYSTEMS]; + int numDeliverySystems; + int numModulations; +- int fd_dvr, fd_ca; ++ int fd_dvr; + static cMutex bondMutex; + cDvbDevice *bondedDevice; mutable bool needsDetachBondedReceivers; bool QueryDeliverySystems(int fd_frontend); public: @@ -833,12 +1054,26 @@ index 4ffcb91..e9b7cd6 100644 int Adapter(void) const { return adapter; } int Frontend(void) const { return frontend; } virtual bool Ready(void); + virtual cString DeviceType(void) const; virtual cString DeviceName(void) const; + virtual bool SetIdleDevice(bool Idle, bool TestOnly); -+ static bool BondDevices(const char *Bondings); ///< Bonds the devices as defined in the given Bondings string. ///< A bonding is a sequence of device numbers (starting at 1), --- -1.7.2.5 - +@@ -193,6 +194,7 @@ protected: + virtual bool SetChannelDevice(const cChannel *Channel, bool LiveView); + public: + virtual bool HasLock(int TimeoutMs = 0); ++ virtual bool SendDiseqcCmd(dvb_diseqc_master_cmd cmd); + + // PID handle facilities + +@@ -225,7 +227,7 @@ public: + // Receiver facilities + + private: +- cTSBuffer *tsBuffer; ++ cTSBufferBase *tsBuffer; + protected: + virtual bool OpenDvr(void); + virtual void CloseDvr(void);