From a49ce434f6152a4431b0dd717f4070dc0da401ef Mon Sep 17 00:00:00 2001 From: Klaus Schmidinger Date: Sun, 4 Dec 2011 12:45:26 +0100 Subject: [PATCH] Implemented "Device Bonding" --- HISTORY | 6 +- INSTALL | 11 ++ MANUAL | 8 +- config.c | 69 +++++++++- config.h | 22 +++- device.c | 8 +- device.h | 16 ++- dvbdevice.c | 364 ++++++++++++++++++++++++++++++++++++++++++++++------ dvbdevice.h | 36 +++++- eitscan.c | 4 +- menu.c | 25 +++- po/ar.po | 9 +- po/ca_ES.po | 9 +- po/cs_CZ.po | 9 +- po/da_DK.po | 9 +- po/de_DE.po | 9 +- po/el_GR.po | 9 +- po/es_ES.po | 9 +- po/et_EE.po | 9 +- po/fi_FI.po | 9 +- po/fr_FR.po | 9 +- po/hr_HR.po | 9 +- po/hu_HU.po | 9 +- po/it_IT.po | 9 +- po/lt_LT.po | 9 +- po/mk_MK.po | 9 +- po/nl_NL.po | 9 +- po/nn_NO.po | 9 +- po/pl_PL.po | 9 +- po/pt_PT.po | 9 +- po/ro_RO.po | 9 +- po/ru_RU.po | 9 +- po/sk_SK.po | 9 +- po/sl_SI.po | 9 +- po/sr_SR.po | 9 +- po/sv_SE.po | 9 +- po/tr_TR.po | 9 +- po/uk_UA.po | 9 +- po/zh_CN.po | 9 +- vdr.c | 5 +- 40 files changed, 740 insertions(+), 86 deletions(-) diff --git a/HISTORY b/HISTORY index 85af028f..aaed9427 100644 --- a/HISTORY +++ b/HISTORY @@ -6743,7 +6743,7 @@ Video Disk Recorder Revision History extends over TS packet boundaries is now done by locally skipping TS packets in cFrameDetector. -2011-10-16: Version 1.7.22 +2011-12-04: Version 1.7.22 - Fixed scaling subtitles in case the primary device's GetVideoSize() function doesn't return actual values (thanks to Luca Olivetti). @@ -6765,3 +6765,7 @@ Video Disk Recorder Revision History - Temporarily switching free devices to transponders in order to have their running status updated is now done by marking the devices as "occupied" for a certain amount of time. +- The new setup options "LNB/Device n connected to sat cable" can be used to define + which DVB-S devices are connected to the same sat cable and are therefore "bonded". + This obsoletes the LNBSHARE patch. Users of the LNBSHARE patch will need to newly + set up their sat devices with the above options. diff --git a/INSTALL b/INSTALL index ea04f1c9..96ebebb7 100644 --- a/INSTALL +++ b/INSTALL @@ -392,6 +392,17 @@ according to EN50494 (aka "Unicable(TM)", "OLT(TM)", "SatCR", "Single Cable Distribution", "Channel Stacking System" or "Single Cable Interface") uses the file "scr.conf" to specify which SCR channels use which user band frequency. +If DVB-S devices need to be connected to the same satellite cable, but no +"Satellite Channel Routing" is available, they can be set to be "bonded" in +the Setup/LNB menu. Bonded devices can only be tuned to the same polarization +and frequency band, which reduces the number of potentially receivable channels. + +Note that it doesn't make sense to use "Satellite Channel Routing" and +"Device Bonding" at the same time with the same devices. If you use either +of these methods, it is necessary that your devices are always created in the +same sequence when the drivers are loaded. You may need to configure some +proper "udev" rules to make sure this happens. + Running VDR with DVB-C (cable) or DVB-T (terrestrial): ------------------------------------------------------ diff --git a/MANUAL b/MANUAL index 54e166e9..3e3adad3 100644 --- a/MANUAL +++ b/MANUAL @@ -732,12 +732,18 @@ Version 1.6 LNB: + Use DiSEqC = no Generally turns DiSEqC support on or off. + SLOF = 11700 The switching frequency (in MHz) between low and high LOF Low LNB frequency = 9750 The LNB's low and high local oscillator frequencies High LNB frequency = 10600 (in MHz, these have no meaning for DVB-C receivers) - Use DiSEqC = no Generally turns DiSEqC support on or off. + Device n connected to sat cable = own + Defines whether DVB-S device n has its own satellite cable, + or is "bonded" with another device. All DVB-S devices that + are connected to the same sat cable must be set to the same + number here. CAM: diff --git a/config.c b/config.c index 73bb00d6..94f68454 100644 --- a/config.c +++ b/config.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: config.c 2.15 2011/08/20 09:12:05 kls Exp $ + * $Id: config.c 2.16 2011/12/03 15:21:30 kls Exp $ */ #include "config.h" @@ -63,6 +63,69 @@ bool cSVDRPhost::Accepts(in_addr_t Address) return (Address & mask) == (addr.s_addr & mask); } +// --- cSatCableNumbers ------------------------------------------------------ + +cSatCableNumbers::cSatCableNumbers(int Size, const char *s) +{ + size = Size; + array = MALLOC(int, size); + memset(array, size * sizeof(int), 0); + FromString(s); +} + +cSatCableNumbers::~cSatCableNumbers() +{ + free(array); +} + +bool cSatCableNumbers::FromString(const char *s) +{ + char *t; + int i = 0; + const char *p = s; + while (p && *p) { + int n = strtol(p, &t, 10); + if (t != p) { + if (i < size) + array[i++] = n; + else { + esyslog("ERROR: too many sat cable numbers in '%s'", s); + return false; + } + } + else { + esyslog("ERROR: invalid sat cable number in '%s'", s); + return false; + } + p = skipspace(t); + } + for ( ; i < size; i++) + array[i] = 0; + return true; +} + +cString cSatCableNumbers::ToString(void) +{ + cString s(""); + for (int i = 0; i < size; i++) { + s = cString::sprintf("%s%d ", *s, array[i]); + } + return s; +} + +int cSatCableNumbers::FirstDeviceIndex(int DeviceIndex) const +{ + if (0 <= DeviceIndex && DeviceIndex < size) { + if (int CableNr = array[DeviceIndex]) { + for (int i = 0; i < size; i++) { + if (i < DeviceIndex && array[i] == CableNr) + return i; + } + } + } + return -1; +} + // --- cNestedItem ----------------------------------------------------------- cNestedItem::cNestedItem(const char *Text, bool WithSubItems) @@ -396,6 +459,7 @@ cSetup::cSetup(void) CurrentVolume = MAXVOLUME; CurrentDolby = 0; InitialChannel = ""; + DeviceBondings = ""; InitialVolume = -1; ChannelsWrap = 0; EmergencyExit = 1; @@ -405,6 +469,7 @@ cSetup& cSetup::operator= (const cSetup &s) { memcpy(&__BeginData__, &s.__BeginData__, (char *)&s.__EndData__ - (char *)&s.__BeginData__); InitialChannel = s.InitialChannel; + DeviceBondings = s.DeviceBondings; return *this; } @@ -589,6 +654,7 @@ bool cSetup::Parse(const char *Name, const char *Value) else if (!strcasecmp(Name, "CurrentDolby")) CurrentDolby = atoi(Value); else if (!strcasecmp(Name, "InitialChannel")) InitialChannel = Value; else if (!strcasecmp(Name, "InitialVolume")) InitialVolume = atoi(Value); + else if (!strcasecmp(Name, "DeviceBondings")) DeviceBondings = Value; else if (!strcasecmp(Name, "ChannelsWrap")) ChannelsWrap = atoi(Value); else if (!strcasecmp(Name, "EmergencyExit")) EmergencyExit = atoi(Value); else @@ -685,6 +751,7 @@ bool cSetup::Save(void) Store("CurrentDolby", CurrentDolby); Store("InitialChannel", InitialChannel); Store("InitialVolume", InitialVolume); + Store("DeviceBondings", DeviceBondings); Store("ChannelsWrap", ChannelsWrap); Store("EmergencyExit", EmergencyExit); diff --git a/config.h b/config.h index ea167c05..73db58f0 100644 --- a/config.h +++ b/config.h @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: config.h 2.35 2011/09/10 09:45:55 kls Exp $ + * $Id: config.h 2.36 2011/12/03 14:19:52 kls Exp $ */ #ifndef __CONFIG_H @@ -61,6 +61,25 @@ public: bool Accepts(in_addr_t Address); }; +class cSatCableNumbers { +private: + int size; + int *array; +public: + cSatCableNumbers(int Size, const char *s = NULL); + ~cSatCableNumbers(); + int Size(void) const { return size; } + int *Array(void) { return array; } + bool FromString(const char *s); + cString ToString(void); + int FirstDeviceIndex(int DeviceIndex) const; + ///< Returns the first device index (starting at 0) that uses the same + ///< sat cable number as the device with the given DeviceIndex. + ///< If the given device does not use the same sat cable as any other device, + ///< or if the resulting value would be the same as DeviceIndex, + ///< or if DeviceIndex is out of range, -1 is returned. + }; + template class cConfig : public cList { private: char *fileName; @@ -292,6 +311,7 @@ public: int EmergencyExit; int __EndData__; cString InitialChannel; + cString DeviceBondings; cSetup(void); cSetup& operator= (const cSetup &s); bool Load(const char *FileName); diff --git a/device.c b/device.c index 8664db9a..0bab66cd 100644 --- a/device.c +++ b/device.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: device.c 2.43 2011/10/16 14:01:30 kls Exp $ + * $Id: device.c 2.44 2011/10/16 14:36:43 kls Exp $ */ #include "device.h" @@ -640,12 +640,12 @@ const cChannel *cDevice::GetCurrentlyTunedTransponder(void) const return NULL; } -bool cDevice::IsTunedToTransponder(const cChannel *Channel) +bool cDevice::IsTunedToTransponder(const cChannel *Channel) const { return false; } -bool cDevice::MaySwitchTransponder(void) +bool cDevice::MaySwitchTransponder(const cChannel *Channel) const { return time(NULL) > occupiedTimeout && !Receiving(true) && !(pidHandles[ptAudio].pid || pidHandles[ptVideo].pid || pidHandles[ptDolby].pid); } @@ -1488,6 +1488,7 @@ int cDevice::PlayTs(const uchar *Data, int Length, bool VideoOnly) int cDevice::Priority(void) const { int priority = IsPrimaryDevice() ? Setup.PrimaryLimit - 1 : DEFAULTPRIORITY; + cMutexLock MutexLock(&mutexReceiver); for (int i = 0; i < MAXRECEIVERS; i++) { if (receiver[i]) priority = max(receiver[i]->priority, priority); @@ -1502,6 +1503,7 @@ bool cDevice::Ready(void) bool cDevice::Receiving(bool CheckAny) const { + cMutexLock MutexLock(&mutexReceiver); for (int i = 0; i < MAXRECEIVERS; i++) { if (receiver[i] && (CheckAny || receiver[i]->priority >= 0)) // cReceiver with priority < 0 doesn't count return true; diff --git a/device.h b/device.h index fc6214c0..2d4edeca 100644 --- a/device.h +++ b/device.h @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: device.h 2.28 2011/10/16 13:27:23 kls Exp $ + * $Id: device.h 2.29 2011/10/16 14:10:33 kls Exp $ */ #ifndef __DEVICE_H @@ -275,12 +275,14 @@ public: ///< This is not one of the channels in the global cChannels list, but rather ///< a local copy. The result may be NULL if the device is not tuned to any ///< transponder. - virtual bool IsTunedToTransponder(const cChannel *Channel); + virtual bool IsTunedToTransponder(const cChannel *Channel) const; ///< Returns true if this device is currently tuned to the given Channel's ///< transponder. - virtual bool MaySwitchTransponder(void); - ///< Returns true if it is ok to switch the transponder on this device, - ///< without disturbing any other activities. + virtual bool MaySwitchTransponder(const cChannel *Channel) const; + ///< Returns true if it is ok to switch to the Channel's transponder on this + ///< device, without disturbing any other activities. If an occupied timeout + ///< has been set for this device, and that timeout has not yet expired, + ///< this function returns false, bool SwitchChannel(const cChannel *Channel, bool LiveView); ///< Switches the device to the given Channel, initiating transfer mode ///< if necessary. @@ -710,7 +712,7 @@ public: // Receiver facilities private: - cMutex mutexReceiver; + mutable cMutex mutexReceiver; cReceiver *receiver[MAXRECEIVERS]; public: int Priority(void) const; @@ -739,7 +741,7 @@ public: ///< Detaches the given receiver from this device. void DetachAll(int Pid); ///< Detaches all receivers from this device for this pid. - void DetachAllReceivers(void); + virtual void DetachAllReceivers(void); ///< Detaches all receivers from this device. }; diff --git a/dvbdevice.c b/dvbdevice.c index 726159ff..163fce36 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 2.47 2011/09/17 12:53:46 kls Exp $ + * $Id: dvbdevice.c 2.48 2011/12/03 15:24:27 kls Exp $ */ #include "dvbdevice.h" @@ -259,8 +259,9 @@ bool cDvbTransponderParameters::Parse(const char *s) class cDvbTuner : public cThread { private: + static cMutex bondMutex; enum eTunerStatus { tsIdle, tsSet, tsTuned, tsLocked }; - int device; + const cDvbDevice *device; int fd_frontend; int adapter, frontend; uint32_t subsystemId; @@ -275,24 +276,35 @@ private: cMutex mutex; cCondVar locked; cCondVar newSet; + cDvbTuner *bondedTuner; + bool bondedMaster; + bool bondedMasterFailed; + cString GetBondingParams(const cChannel *Channel = NULL) const; void ClearEventQueue(void) const; bool GetFrontendStatus(fe_status_t &Status) const; - void ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency) const; + void ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency); + void ResetToneAndVoltage(void); bool SetFrontend(void); virtual void Action(void); public: - cDvbTuner(int Device, int Fd_Frontend, int Adapter, int Frontend, fe_delivery_system FrontendType); + cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int Frontend, fe_delivery_system FrontendType); virtual ~cDvbTuner(); + bool Bond(cDvbTuner *Tuner); + void UnBond(void); + bool BondingOk(const cChannel *Channel, bool ConsiderOccupied = false) const; + cDvbTuner *GetBondedMaster(void); const cChannel *GetTransponder(void) const { return &channel; } uint32_t SubsystemId(void) const { return subsystemId; } bool IsTunedTo(const cChannel *Channel) const; - void Set(const cChannel *Channel); + void SetChannel(const cChannel *Channel); bool Locked(int TimeoutMs = 0); int GetSignalStrength(void) const; int GetSignalQuality(void) const; }; -cDvbTuner::cDvbTuner(int Device, int Fd_Frontend, int Adapter, int Frontend, fe_delivery_system FrontendType) +cMutex cDvbTuner::bondMutex; + +cDvbTuner::cDvbTuner(const cDvbDevice *Device, int Fd_Frontend, int Adapter, int Frontend, fe_delivery_system FrontendType) { device = Device; fd_frontend = Fd_Frontend; @@ -306,8 +318,11 @@ cDvbTuner::cDvbTuner(int Device, int Fd_Frontend, int Adapter, int Frontend, fe_ lastDiseqc = NULL; scr = NULL; tunerStatus = tsIdle; + bondedTuner = NULL; + bondedMaster = false; + bondedMasterFailed = false; if (frontendType == SYS_DVBS || frontendType == SYS_DVBS2) - CHECK(ioctl(fd_frontend, FE_SET_VOLTAGE, SEC_VOLTAGE_13)); // must explicitly turn on LNB power + ResetToneAndVoltage(); // must explicitly turn on LNB power SetDescription("tuner on frontend %d/%d", adapter, frontend); Start(); } @@ -318,6 +333,7 @@ cDvbTuner::~cDvbTuner() newSet.Broadcast(); locked.Broadcast(); Cancel(3); + UnBond(); /* looks like this irritates the SCR switch, so let's leave it out for now if (lastDiseqc && lastDiseqc->IsScr()) { unsigned int Frequency = 0; @@ -326,6 +342,109 @@ cDvbTuner::~cDvbTuner() */ } +bool cDvbTuner::Bond(cDvbTuner *Tuner) +{ + cMutexLock MutexLock(&bondMutex); + if (!bondedTuner) { + if ((frontendType == SYS_DVBS || frontendType == SYS_DVBS2) && (Tuner->frontendType == SYS_DVBS || Tuner->frontendType == SYS_DVBS2)) { + ResetToneAndVoltage(); + bondedMaster = false; // makes sure we don't disturb an existing master + bondedTuner = Tuner->bondedTuner ? Tuner->bondedTuner : Tuner; + Tuner->bondedTuner = this; + dsyslog("tuner %d/%d bonded with tuner %d/%d", adapter, frontend, bondedTuner->adapter, bondedTuner->frontend); + return true; + } + else + esyslog("ERROR: can't bond tuner %d/%d with tuner %d/%d (only DVB-S(2) tuners can be bonded)", adapter, frontend, Tuner->adapter, Tuner->frontend); + } + else + esyslog("ERROR: tuner %d/%d already bonded with tuner %d/%d, can't bond with tuner %d/%d", adapter, frontend, bondedTuner->adapter, bondedTuner->frontend, Tuner->adapter, Tuner->frontend); + return false; +} + +void cDvbTuner::UnBond(void) +{ + cMutexLock MutexLock(&bondMutex); + if (cDvbTuner *t = bondedTuner) { + dsyslog("tuner %d/%d unbonded from tuner %d/%d", adapter, frontend, bondedTuner->adapter, bondedTuner->frontend); + while (t->bondedTuner != this) + t = t->bondedTuner; + if (t == bondedTuner) + t->bondedTuner = NULL; + else + t->bondedTuner = bondedTuner; + bondedMaster = false; // another one will automatically become master whenever necessary + bondedTuner = NULL; + } +} + +cString cDvbTuner::GetBondingParams(const cChannel *Channel) const +{ + if (!Channel) + Channel = &channel; + cDvbTransponderParameters dtp(Channel->Parameters()); + if (Setup.DiSEqC) { + if (const cDiseqc *diseqc = Diseqcs.Get(device->CardIndex() + 1, Channel->Source(), Channel->Frequency(), dtp.Polarization(), NULL)) + return diseqc->Commands(); + } + else { + bool ToneOff = Channel->Frequency() < (unsigned int)Setup.LnbSLOF; + bool VoltOff = dtp.Polarization() == 'V' || dtp.Polarization() == 'R'; + return cString::sprintf("%c %c", ToneOff ? 't' : 'T', VoltOff ? 'v' : 'V'); + } + return ""; +} + +bool cDvbTuner::BondingOk(const cChannel *Channel, bool ConsiderOccupied) const +{ + cMutexLock MutexLock(&bondMutex); + if (cDvbTuner *t = bondedTuner) { + cString BondingParams = GetBondingParams(Channel); + do { + if (t->device->Receiving() || t->tunerStatus != tsIdle && (t->device == cDevice::ActualDevice() || ConsiderOccupied && t->device->Occupied())) { + if (strcmp(BondingParams, t->GetBondingParams()) != 0) + return false; + } + t = t->bondedTuner; + } while (t != bondedTuner); + } + return true; +} + +cDvbTuner *cDvbTuner::GetBondedMaster(void) +{ + if (!bondedTuner) + return this; // an unbonded tuner is always "master" + cMutexLock MutexLock(&bondMutex); + if (bondedMaster) { + if (!bondedMasterFailed) + return this; + else + bondedMaster = false; + } + // This tuner is bonded, but it's not the master, so let's see if there is a master at all: + if (cDvbTuner *t = bondedTuner) { + while (t != this) { + if (t->bondedMaster) + return t; + t = t->bondedTuner; + } + } + // None of the other bonded tuners is master, so make this one the master: + cDvbTuner *t = this; + if (bondedMasterFailed) { + // This one has failed, so switch to the next one: + t = bondedTuner; + t->bondedMasterFailed = false; + cMutexLock MutexLock(&t->mutex); + t->channel = channel; + t->tunerStatus = tsSet; + } + t->bondedMaster = true; + dsyslog("tuner %d/%d is now bonded master", t->adapter, t->frontend); + return t; +} + bool cDvbTuner::IsTunedTo(const cChannel *Channel) const { if (tunerStatus == tsIdle) @@ -336,14 +455,34 @@ bool cDvbTuner::IsTunedTo(const cChannel *Channel) const return strcmp(channel.Parameters(), Channel->Parameters()) == 0; } -void cDvbTuner::Set(const cChannel *Channel) +void cDvbTuner::SetChannel(const cChannel *Channel) { - cMutexLock MutexLock(&mutex); - if (!IsTunedTo(Channel)) - tunerStatus = tsSet; - channel = *Channel; - lastTimeoutReport = 0; - newSet.Broadcast(); + if (Channel) { + if (bondedTuner) { + cMutexLock MutexLock(&bondMutex); + cDvbTuner *BondedMaster = GetBondedMaster(); + if (BondedMaster == this) { + if (strcmp(GetBondingParams(Channel), GetBondingParams()) != 0) { + // switching to a completely different band, so set all others to idle: + for (cDvbTuner *t = bondedTuner; t && t != this; t = t->bondedTuner) + t->SetChannel(NULL); + } + } + else if (!BondedMaster->device->Receiving()) + BondedMaster->SetChannel(Channel); + } + cMutexLock MutexLock(&mutex); + if (!IsTunedTo(Channel)) + tunerStatus = tsSet; + channel = *Channel; + lastTimeoutReport = 0; + newSet.Broadcast(); + } + else { + cMutexLock MutexLock(&mutex); + tunerStatus = tsIdle; + ResetToneAndVoltage(); + } } bool cDvbTuner::Locked(int TimeoutMs) @@ -493,7 +632,7 @@ static unsigned int FrequencyToHz(unsigned int f) return f; } -void cDvbTuner::ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency) const +void cDvbTuner::ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency) { struct dvb_diseqc_master_cmd cmd; const char *CurrentAction = NULL; @@ -514,7 +653,13 @@ void cDvbTuner::ExecuteDiseqc(const cDiseqc *Diseqc, unsigned int *Frequency) co } } if (scr) - CHECK(ioctl(fd_frontend, FE_SET_VOLTAGE, SEC_VOLTAGE_13)); // makes sure we don't block the bus! + ResetToneAndVoltage(); // makes sure we don't block the bus! +} + +void cDvbTuner::ResetToneAndVoltage(void) +{ + CHECK(ioctl(fd_frontend, FE_SET_VOLTAGE, SEC_VOLTAGE_13)); + CHECK(ioctl(fd_frontend, FE_SET_TONE, SEC_TONE_OFF)); } bool cDvbTuner::SetFrontend(void) @@ -544,12 +689,16 @@ bool cDvbTuner::SetFrontend(void) if (frontendType == SYS_DVBS || frontendType == SYS_DVBS2) { unsigned int frequency = channel.Frequency(); if (Setup.DiSEqC) { - if (const cDiseqc *diseqc = Diseqcs.Get(device, channel.Source(), frequency, dtp.Polarization(), &scr)) { + if (const cDiseqc *diseqc = Diseqcs.Get(device->CardIndex() + 1, channel.Source(), frequency, dtp.Polarization(), &scr)) { frequency -= diseqc->Lof(); if (diseqc != lastDiseqc || diseqc->IsScr()) { - ExecuteDiseqc(diseqc, &frequency); - if (frequency == 0) - return false; + if (GetBondedMaster() == this) { + ExecuteDiseqc(diseqc, &frequency); + if (frequency == 0) + return false; + } + else + ResetToneAndVoltage(); lastDiseqc = diseqc; } } @@ -568,7 +717,11 @@ bool cDvbTuner::SetFrontend(void) frequency -= Setup.LnbFrequHi; tone = SEC_TONE_ON; } - int volt = (dtp.Polarization() == 'v' || dtp.Polarization() == 'V' || dtp.Polarization() == 'r' || dtp.Polarization() == 'R') ? SEC_VOLTAGE_13 : SEC_VOLTAGE_18; + int volt = (dtp.Polarization() == 'V' || dtp.Polarization() == 'R') ? SEC_VOLTAGE_13 : SEC_VOLTAGE_18; + if (GetBondedMaster() != this) { + tone = SEC_TONE_OFF; + volt = SEC_VOLTAGE_13; + } CHECK(ioctl(fd_frontend, FE_SET_VOLTAGE, volt)); CHECK(ioctl(fd_frontend, FE_SET_TONE, tone)); } @@ -675,6 +828,9 @@ void cDvbTuner::Action(void) isyslog("frontend %d/%d timed out while tuning to channel %d, tp %d", adapter, frontend, channel.Number(), channel.Transponder()); lastTimeoutReport = time(NULL); } + cMutexLock MutexLock(&bondMutex); + if (bondedTuner && bondedMaster) + bondedMasterFailed = true; // give an other tuner a chance in case the sat cable was disconnected continue; } case tsLocked: @@ -770,6 +926,7 @@ cOsdItem *cDvbSourceParam::GetOsdItem(void) // --- cDvbDevice ------------------------------------------------------------ int cDvbDevice::setTransferModeForDolbyDigital = 1; +cMutex cDvbDevice::bondMutex; const char *DeliverySystems[] = { "UNDEFINED", @@ -799,6 +956,8 @@ cDvbDevice::cDvbDevice(int Adapter, int Frontend) dvbTuner = NULL; frontendType = SYS_UNDEFINED; numProvidedSystems = 0; + bondedDevice = NULL; + needsDetachBondedReceivers = false; // Devices that are present on all card types: @@ -848,7 +1007,7 @@ cDvbDevice::cDvbDevice(int Adapter, int Frontend) else p = (char *)"unknown modulations"; isyslog("frontend %d/%d provides %s with %s (\"%s\")", adapter, frontend, DeliverySystems[frontendType], p, frontendInfo.name); - dvbTuner = new cDvbTuner(CardIndex() + 1, fd_frontend, adapter, frontend, frontendType); + dvbTuner = new cDvbTuner(this, fd_frontend, adapter, frontend, frontendType); } } else @@ -862,6 +1021,7 @@ cDvbDevice::~cDvbDevice() StopSectionHandler(); delete dvbTuner; delete ciAdapter; + UnBond(); // We're not explicitly closing any device files here, since this sometimes // caused segfaults. Besides, the program is about to terminate anyway... } @@ -953,6 +1113,104 @@ bool cDvbDevice::Ready(void) return true; } +bool cDvbDevice::BondDevices(const char *Bondings) +{ + UnBondDevices(); + if (Bondings) { + cSatCableNumbers SatCableNumbers(MAXDEVICES, Bondings); + for (int i = 0; i < cDevice::NumDevices(); i++) { + int d = SatCableNumbers.FirstDeviceIndex(i); + if (d >= 0) { + int ErrorDevice = 0; + if (cDevice *Device1 = cDevice::GetDevice(i)) { + if (cDevice *Device2 = cDevice::GetDevice(d)) { + if (cDvbDevice *DvbDevice1 = dynamic_cast(Device1)) { + if (cDvbDevice *DvbDevice2 = dynamic_cast(Device2)) { + if (!DvbDevice2->Bond(DvbDevice1)) + return false; // Bond() has already logged the error + } + else + ErrorDevice = d + 1; + } + else + ErrorDevice = i + 1; + if (ErrorDevice) { + esyslog("ERROR: device '%d' in device bondings '%s' is not a cDvbDevice", ErrorDevice, Bondings); + return false; + } + } + else + ErrorDevice = d + 1; + } + else + ErrorDevice = i + 1; + if (ErrorDevice) { + esyslog("ERROR: unknown device '%d' in device bondings '%s'", ErrorDevice, Bondings); + return false; + } + } + } + } + return true; +} + +void cDvbDevice::UnBondDevices(void) +{ + for (int i = 0; i < cDevice::NumDevices(); i++) { + if (cDvbDevice *d = dynamic_cast(cDevice::GetDevice(i))) + d->UnBond(); + } +} + +bool cDvbDevice::Bond(cDvbDevice *Device) +{ + cMutexLock MutexLock(&bondMutex); + if (!bondedDevice) { + if (Device != this) { + if ((frontendType == SYS_DVBS || frontendType == SYS_DVBS2) && (Device->frontendType == SYS_DVBS || Device->frontendType == SYS_DVBS2)) { + if (dvbTuner && Device->dvbTuner && dvbTuner->Bond(Device->dvbTuner)) { + bondedDevice = Device->bondedDevice ? Device->bondedDevice : Device; + Device->bondedDevice = this; + dsyslog("device %d bonded with device %d", CardIndex() + 1, bondedDevice->CardIndex() + 1); + return true; + } + } + else + esyslog("ERROR: can't bond device %d with device %d (only DVB-S(2) devices can be bonded)", CardIndex() + 1, Device->CardIndex() + 1); + } + else + esyslog("ERROR: can't bond device %d with itself", CardIndex() + 1); + } + else + esyslog("ERROR: device %d already bonded with device %d, can't bond with device %d", CardIndex() + 1, bondedDevice->CardIndex() + 1, Device->CardIndex() + 1); + return false; +} + +void cDvbDevice::UnBond(void) +{ + cMutexLock MutexLock(&bondMutex); + if (cDvbDevice *d = bondedDevice) { + if (dvbTuner) + dvbTuner->UnBond(); + dsyslog("device %d unbonded from device %d", CardIndex() + 1, bondedDevice->CardIndex() + 1); + while (d->bondedDevice != this) + d = d->bondedDevice; + if (d == bondedDevice) + d->bondedDevice = NULL; + else + d->bondedDevice = bondedDevice; + bondedDevice = NULL; + } +} + +bool cDvbDevice::BondingOk(const cChannel *Channel, bool ConsiderOccupied) const +{ + cMutexLock MutexLock(&bondMutex); + if (bondedDevice) + return dvbTuner && dvbTuner->BondingOk(Channel, ConsiderOccupied); + return true; +} + bool cDvbDevice::HasCi(void) { return ciAdapter; @@ -1055,7 +1313,7 @@ bool cDvbDevice::ProvidesTransponder(const cChannel *Channel) const dtp.Modulation() == PSK_8 && !(frontendInfo.caps & FE_CAN_TURBO_FEC) && dtp.System() == SYS_DVBS) // "turbo fec" is a non standard FEC used by North American broadcasters - this is a best guess to determine this condition return false; // requires modulation system which frontend doesn't provide if (!cSource::IsSat(Channel->Source()) || - !Setup.DiSEqC || Diseqcs.Get(CardIndex() + 1, Channel->Source(), Channel->Frequency(), dtp.Polarization(), NULL)) + (!Setup.DiSEqC || Diseqcs.Get(CardIndex() + 1, Channel->Source(), Channel->Frequency(), dtp.Polarization(), NULL))) return DeviceHooksProvidesTransponder(Channel); return false; } @@ -1065,28 +1323,44 @@ bool cDvbDevice::ProvidesChannel(const cChannel *Channel, int Priority, bool *Ne bool result = false; bool hasPriority = Priority < 0 || Priority > this->Priority(); bool needsDetachReceivers = false; + needsDetachBondedReceivers = false; if (dvbTuner && ProvidesTransponder(Channel)) { result = hasPriority; - if (Priority >= 0 && Receiving(true)) { - if (dvbTuner->IsTunedTo(Channel)) { - if (Channel->Vpid() && !HasPid(Channel->Vpid()) || Channel->Apid(0) && !HasPid(Channel->Apid(0))) { - if (CamSlot() && Channel->Ca() >= CA_ENCRYPTED_MIN) { - if (CamSlot()->CanDecrypt(Channel)) + if (Priority >= 0) { + if (Receiving(true)) { + if (dvbTuner->IsTunedTo(Channel)) { + if (Channel->Vpid() && !HasPid(Channel->Vpid()) || Channel->Apid(0) && !HasPid(Channel->Apid(0))) { + if (CamSlot() && Channel->Ca() >= CA_ENCRYPTED_MIN) { + if (CamSlot()->CanDecrypt(Channel)) + result = true; + else + needsDetachReceivers = true; + } + else if (!IsPrimaryDevice()) result = true; else - needsDetachReceivers = true; + result = Priority >= Setup.PrimaryLimit; } - else if (!IsPrimaryDevice()) - result = true; else - result = Priority >= Setup.PrimaryLimit; + result = !IsPrimaryDevice() || Priority >= Setup.PrimaryLimit; } else - result = !IsPrimaryDevice() || Priority >= Setup.PrimaryLimit; + needsDetachReceivers = true; + } + if (result) { + if (!BondingOk(Channel)) { + // This device is bonded, so we need to check the priorities of the others: + for (cDvbDevice *d = bondedDevice; d && d != this; d = d->bondedDevice) { + if (d->Priority() >= Priority) { + result = false; + break; + } + } + needsDetachBondedReceivers = true; + needsDetachReceivers = true; + } } - else - needsDetachReceivers = true; } } if (NeedsDetachReceivers) @@ -1119,15 +1393,20 @@ const cChannel *cDvbDevice::GetCurrentlyTunedTransponder(void) const return dvbTuner ? dvbTuner->GetTransponder() : NULL; } -bool cDvbDevice::IsTunedToTransponder(const cChannel *Channel) +bool cDvbDevice::IsTunedToTransponder(const cChannel *Channel) const { return dvbTuner ? dvbTuner->IsTunedTo(Channel) : false; } +bool cDvbDevice::MaySwitchTransponder(const cChannel *Channel) const +{ + return BondingOk(Channel, true) && cDevice::MaySwitchTransponder(Channel); +} + bool cDvbDevice::SetChannelDevice(const cChannel *Channel, bool LiveView) { if (dvbTuner) - dvbTuner->Set(Channel); + dvbTuner->SetChannel(Channel); return true; } @@ -1169,6 +1448,17 @@ bool cDvbDevice::GetTSPacket(uchar *&Data) return false; } +void cDvbDevice::DetachAllReceivers(void) +{ + cMutexLock MutexLock(&bondMutex); + cDvbDevice *d = this; + do { + d->cDevice::DetachAllReceivers(); + d = d->bondedDevice; + } while (d && d != this && needsDetachBondedReceivers); + needsDetachBondedReceivers = false; +} + // --- cDvbDeviceProbe ------------------------------------------------------- cList DvbDeviceProbes; diff --git a/dvbdevice.h b/dvbdevice.h index e1842b7d..aee74592 100644 --- a/dvbdevice.h +++ b/dvbdevice.h @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: dvbdevice.h 2.16 2011/08/26 12:55:45 kls Exp $ + * $Id: dvbdevice.h 2.17 2011/11/27 11:56:57 kls Exp $ */ #ifndef __DVBDEVICE_H @@ -122,10 +122,40 @@ private: int numProvidedSystems; fe_delivery_system frontendType; int fd_dvr, fd_ca; + static cMutex bondMutex; + cDvbDevice *bondedDevice; + mutable bool needsDetachBondedReceivers; public: cDvbDevice(int Adapter, int Frontend); virtual ~cDvbDevice(); virtual bool Ready(void); + 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), + ///< separated by '+' characters. Several bondings are separated by + ///< commas, as in "1+2,3+4+5". + ///< Returns false if an error occurred. + static void UnBondDevices(void); + ///< Unbonds all devices. + bool Bond(cDvbDevice *Device); + ///< Bonds this device with the given Device, making both of them use + ///< the same satellite cable and LNB. Only DVB-S(2) devices can be + ///< bonded. When this function is called, the calling device must + ///< not be bonded to any other device. The given Device, however, + ///< may already be bonded to an other device. That way several devices + ///< can be bonded together. + ///< Returns true if the bonding was successful. + void UnBond(void); + ///< Removes this device from any bonding it might have with other + ///< devices. If this device is not bonded with any other device, + ///< nothing happens. + bool BondingOk(const cChannel *Channel, bool ConsiderOccupied = false) const; + ///< Returns true if this device is either not bonded to any other + ///< device, or the given Channel is on the same satellite, polarization + ///< and band as those the bonded devices are tuned to (if any). + ///< If ConsiderOccupied is true, any bonded devices that are currently + ///< occupied but not otherwise receiving will cause this function to + ///< return false. // Common Interface facilities: @@ -145,7 +175,8 @@ public: virtual int SignalStrength(void) const; virtual int SignalQuality(void) const; virtual const cChannel *GetCurrentlyTunedTransponder(void) const; - virtual bool IsTunedToTransponder(const cChannel *Channel); + virtual bool IsTunedToTransponder(const cChannel *Channel) const; + virtual bool MaySwitchTransponder(const cChannel *Channel) const; protected: virtual bool SetChannelDevice(const cChannel *Channel, bool LiveView); public: @@ -187,6 +218,7 @@ protected: virtual bool OpenDvr(void); virtual void CloseDvr(void); virtual bool GetTSPacket(uchar *&Data); + virtual void DetachAllReceivers(void); }; // A plugin that implements a DVB device derived from cDvbDevice needs to create diff --git a/eitscan.c b/eitscan.c index 8b435920..91d9a88c 100644 --- a/eitscan.c +++ b/eitscan.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: eitscan.c 2.4 2011/08/26 13:10:00 kls Exp $ + * $Id: eitscan.c 2.5 2011/10/16 14:10:00 kls Exp $ */ #include "eitscan.h" @@ -150,7 +150,7 @@ void cEITScanner::Process(void) if (!Channel->Ca() || Channel->Ca() == Device->DeviceNumber() + 1 || Channel->Ca() >= CA_ENCRYPTED_MIN) { if (Device->ProvidesTransponder(Channel)) { if (!Device->Receiving()) { - bool MaySwitchTransponder = Device->MaySwitchTransponder(); + bool MaySwitchTransponder = Device->MaySwitchTransponder(Channel); if (MaySwitchTransponder || Device->ProvidesTransponderExclusively(Channel) && now - lastActivity > Setup.EPGScanTimeout * 3600) { if (!MaySwitchTransponder) { if (Device == cDevice::ActualDevice() && !currentChannel) { diff --git a/menu.c b/menu.c index ef2bb468..b1f083df 100644 --- a/menu.c +++ b/menu.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: menu.c 2.32 2011/08/27 11:05:33 kls Exp $ + * $Id: menu.c 2.33 2011/12/03 15:11:42 kls Exp $ */ #include "menu.h" @@ -2885,6 +2885,7 @@ eOSState cMenuSetupDVB::ProcessKey(eKeys Key) class cMenuSetupLNB : public cMenuSetupBase { private: + cSatCableNumbers satCableNumbers; void Setup(void); public: cMenuSetupLNB(void); @@ -2892,7 +2893,9 @@ public: }; cMenuSetupLNB::cMenuSetupLNB(void) +:satCableNumbers(MAXDEVICES) { + satCableNumbers.FromString(data.DeviceBondings); SetSection(tr("LNB")); Setup(); } @@ -2910,6 +2913,18 @@ void cMenuSetupLNB::Setup(void) Add(new cMenuEditIntItem( tr("Setup.LNB$High LNB frequency (MHz)"), &data.LnbFrequHi)); } + int NumSatDevices = 0; + for (int i = 0; i < cDevice::NumDevices(); i++) { + if (cDevice::GetDevice(i)->ProvidesSource(cSource::stSat)) + NumSatDevices++; + } + if (NumSatDevices > 1) { + for (int i = 0; i < cDevice::NumDevices(); i++) { + if (cDevice::GetDevice(i)->ProvidesSource(cSource::stSat)) + Add(new cMenuEditIntItem(cString::sprintf(tr("Setup.LNB$Device %d connected to sat cable"), i + 1), &satCableNumbers.Array()[i], 0, NumSatDevices, tr("Setup.LNB$own"))); + } + } + SetCurrent(Get(current)); Display(); } @@ -2917,10 +2932,18 @@ void cMenuSetupLNB::Setup(void) eOSState cMenuSetupLNB::ProcessKey(eKeys Key) { int oldDiSEqC = data.DiSEqC; + bool DeviceBondingsChanged = false; + if (Key == kOk) { + cString NewDeviceBondings = satCableNumbers.ToString(); + DeviceBondingsChanged = strcmp(data.DeviceBondings, NewDeviceBondings) != 0; + data.DeviceBondings = NewDeviceBondings; + } eOSState state = cMenuSetupBase::ProcessKey(Key); if (Key != kNone && data.DiSEqC != oldDiSEqC) Setup(); + else if (DeviceBondingsChanged) + cDvbDevice::BondDevices(data.DeviceBondings); return state; } diff --git a/po/ar.po b/po/ar.po index d3dd29af..c936078d 100644 --- a/po/ar.po +++ b/po/ar.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-10-16 11:16-0400\n" "Last-Translator: Osama Alrawab \n" "Language-Team: Arabic \n" @@ -983,6 +983,13 @@ msgstr "التردد المنخفض للاقط م هرتز" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "التردد المرتفع للاقط م هرتز" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "اعادة تشغيل الكامة" diff --git a/po/ca_ES.po b/po/ca_ES.po index b104fea3..d609cda7 100644 --- a/po/ca_ES.po +++ b/po/ca_ES.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-03-02 19:02+0100\n" "Last-Translator: Luca Olivetti \n" "Language-Team: Catalan \n" @@ -965,6 +965,13 @@ msgstr "Freq msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Freqncia LNB alta (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reiniciar CAM" diff --git a/po/cs_CZ.po b/po/cs_CZ.po index bcafac7d..eef82571 100644 --- a/po/cs_CZ.po +++ b/po/cs_CZ.po @@ -9,7 +9,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.14\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-05-06 11:00+0200\n" "Last-Translator: Radek Šťastný \n" "Language-Team: Czech \n" @@ -964,6 +964,13 @@ msgstr "Dolní frekvence LNB (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Horní frekvence LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reset CAMu" diff --git a/po/da_DK.po b/po/da_DK.po index 81b11eb0..db6b3987 100644 --- a/po/da_DK.po +++ b/po/da_DK.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-08-12 14:17+0200\n" "Last-Translator: Mogens Elneff \n" "Language-Team: Danish \n" @@ -962,6 +962,13 @@ msgstr "Nedre LNB frekvens (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "vre LNB frekvens (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM nulstil" diff --git a/po/de_DE.po b/po/de_DE.po index 6d5b822f..4a475d7d 100644 --- a/po/de_DE.po +++ b/po/de_DE.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-01-16 16:46+0100\n" "Last-Translator: Klaus Schmidinger \n" "Language-Team: German \n" @@ -962,6 +962,13 @@ msgstr "Untere LNB-Frequenz (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Obere LNB-Frequenz (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "Device %d angeschlossen an Sat-Kabel" + +msgid "Setup.LNB$own" +msgstr "eigenes" + msgid "CAM reset" msgstr "CAM zurckgesetzt" diff --git a/po/el_GR.po b/po/el_GR.po index 9756ea78..64300f08 100644 --- a/po/el_GR.po +++ b/po/el_GR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-08-12 14:17+0200\n" "Last-Translator: Dimitrios Dimitrakos \n" "Language-Team: Greek \n" @@ -962,6 +962,13 @@ msgstr " msgid "Setup.LNB$High LNB frequency (MHz)" msgstr " LNB- (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "" diff --git a/po/es_ES.po b/po/es_ES.po index 193e75eb..288ad699 100644 --- a/po/es_ES.po +++ b/po/es_ES.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-03-02 19:02+0100\n" "Last-Translator: Luca Olivetti \n" "Language-Team: Spanish \n" @@ -963,6 +963,13 @@ msgstr "Frecuencia inferior del LNB (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Frecuencia superior del LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reset CAM" diff --git a/po/et_EE.po b/po/et_EE.po index 49794dd5..c12f31fe 100644 --- a/po/et_EE.po +++ b/po/et_EE.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-08-12 14:17+0200\n" "Last-Translator: Arthur Konovalov \n" "Language-Team: Estonian \n" @@ -962,6 +962,13 @@ msgstr "LO LNB sagedus (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "HI LNB sagedus (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM taaskivitamine" diff --git a/po/fi_FI.po b/po/fi_FI.po index b093e880..d0d1225f 100644 --- a/po/fi_FI.po +++ b/po/fi_FI.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-08-15 15:52+0200\n" "Last-Translator: Rolf Ahrenberg \n" "Language-Team: Finnish \n" @@ -965,6 +965,13 @@ msgstr "LNB-alataajuus (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "LNB-ylätaajuus (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM nollaus" diff --git a/po/fr_FR.po b/po/fr_FR.po index b5c51204..5f8b4113 100644 --- a/po/fr_FR.po +++ b/po/fr_FR.po @@ -13,7 +13,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-02-27 18:14+0100\n" "Last-Translator: Jean-Claude Repetto \n" "Language-Team: French \n" @@ -968,6 +968,13 @@ msgstr "Fr msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Frquence haute LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM remis zro" diff --git a/po/hr_HR.po b/po/hr_HR.po index ed519a2f..681cb791 100644 --- a/po/hr_HR.po +++ b/po/hr_HR.po @@ -9,7 +9,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-03-17 19:00+0100\n" "Last-Translator: Adrian Caval \n" "Language-Team: Croatian \n" @@ -964,6 +964,13 @@ msgstr "Donja LNB frekv. (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Gornja LNB frekv. (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Ponovno pokreni CAM" diff --git a/po/hu_HU.po b/po/hu_HU.po index 17b905f5..bebf6eff 100644 --- a/po/hu_HU.po +++ b/po/hu_HU.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-12-01 21:42+0200\n" "Last-Translator: Istvn Fley \n" "Language-Team: Hungarian \n" @@ -965,6 +965,13 @@ msgstr "Als msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Fels LNB-frekvencia (MHZ)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM jraindts" diff --git a/po/it_IT.po b/po/it_IT.po index 501300ed..6015881f 100644 --- a/po/it_IT.po +++ b/po/it_IT.po @@ -11,7 +11,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-06-13 00:30+0100\n" "Last-Translator: Diego Pierotto \n" "Language-Team: Italian \n" @@ -969,6 +969,13 @@ msgstr "Freq LO LNB (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Freq HI LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reimposta la CAM" diff --git a/po/lt_LT.po b/po/lt_LT.po index 6cb1faa0..53d24226 100644 --- a/po/lt_LT.po +++ b/po/lt_LT.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.16\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-10-30 11:55+0200\n" "Last-Translator: Valdemaras Pipiras \n" "Language-Team: Lithuanian \n" @@ -962,6 +962,13 @@ msgstr "Žemasis LNB dažnis (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Aukštasis LNB dažnis (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Dekodavimo modulis (CAM) perkrautas" diff --git a/po/mk_MK.po b/po/mk_MK.po index 0d22563f..5fa36345 100644 --- a/po/mk_MK.po +++ b/po/mk_MK.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR-1.7.14\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-03-11 00:54+0100\n" "Last-Translator: Dimitar Petrovski \n" "Language-Team: Macedonian \n" @@ -963,6 +963,13 @@ msgstr "Долна LNB фрекфенција (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Форна LNB фрекфенција (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Рестартирај CAM" diff --git a/po/nl_NL.po b/po/nl_NL.po index ae2b85e0..65aaba71 100644 --- a/po/nl_NL.po +++ b/po/nl_NL.po @@ -11,7 +11,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-02-26 17:20+0100\n" "Last-Translator: Johan Schuring \n" "Language-Team: Dutch \n" @@ -966,6 +966,13 @@ msgstr "Laagste LNB frequentie (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Hoogste LNB frequentie (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM herstarten" diff --git a/po/nn_NO.po b/po/nn_NO.po index 8ec8dfb4..a8ea942d 100644 --- a/po/nn_NO.po +++ b/po/nn_NO.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2007-08-12 14:17+0200\n" "Last-Translator: Truls Slevigen \n" "Language-Team: Norwegian Nynorsk \n" @@ -963,6 +963,13 @@ msgstr "LO-frekvens i lavb msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "LO-frekvens i hybndet (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "" diff --git a/po/pl_PL.po b/po/pl_PL.po index a5c1b472..94ba6921 100644 --- a/po/pl_PL.po +++ b/po/pl_PL.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-03-09 12:59+0100\n" "Last-Translator: Michael Rakowski \n" "Language-Team: Polish \n" @@ -963,6 +963,13 @@ msgstr "Dolna cz msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Grna czstotliwo LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM zresetowany" diff --git a/po/pt_PT.po b/po/pt_PT.po index c4433123..272ab75b 100644 --- a/po/pt_PT.po +++ b/po/pt_PT.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.15\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-03-28 22:49+0100\n" "Last-Translator: Cris Silva \n" "Language-Team: Portuguese \n" @@ -963,6 +963,13 @@ msgstr "Frequ msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Frequncia alta do LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reiniciar CAM" diff --git a/po/ro_RO.po b/po/ro_RO.po index f8c5a1e2..414ade19 100644 --- a/po/ro_RO.po +++ b/po/ro_RO.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.12\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2011-03-10 23:52+0100\n" "Last-Translator: Lucian Muresan \n" "Language-Team: Romanian \n" @@ -965,6 +965,13 @@ msgstr "Frecvn msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Frecvn LNB superioar (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Resetare CAM" diff --git a/po/ru_RU.po b/po/ru_RU.po index e683b8b1..a4eaca5b 100644 --- a/po/ru_RU.po +++ b/po/ru_RU.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-12-15 14:37+0100\n" "Last-Translator: Oleg Roitburd \n" "Language-Team: Russian \n" @@ -963,6 +963,13 @@ msgstr " msgid "Setup.LNB$High LNB frequency (MHz)" msgstr " ()" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM " diff --git a/po/sk_SK.po b/po/sk_SK.po index 46edef58..176673f2 100644 --- a/po/sk_SK.po +++ b/po/sk_SK.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.16\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2011-02-15 16:29+0100\n" "Last-Translator: Milan Hrala \n" "Language-Team: Slovak \n" @@ -962,6 +962,13 @@ msgstr "Doln msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Horn frekvencia LNB (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Resetnutie CAMu" diff --git a/po/sl_SI.po b/po/sl_SI.po index 89c69239..696e953e 100644 --- a/po/sl_SI.po +++ b/po/sl_SI.po @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-02-28 19:44+0100\n" "Last-Translator: Matjaz Thaler \n" "Language-Team: Slovenian \n" @@ -963,6 +963,13 @@ msgstr "Spodnja LNB-frek. (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Zgornja LNB-frek. (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Reset CAM-a" diff --git a/po/sr_SR.po b/po/sr_SR.po index 45d354bb..62c07d38 100644 --- a/po/sr_SR.po +++ b/po/sr_SR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.1\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2011-01-09 15:57+0100\n" "Last-Translator: Milan Cvijanovi \n" "Language-Team: Serbian \n" @@ -981,6 +981,13 @@ msgstr "Donja LNB frekv. (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Gornja LNB frekv. (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Ponovno pokreni CAM" diff --git a/po/sv_SE.po b/po/sv_SE.po index 150f95eb..ae6d72ff 100644 --- a/po/sv_SE.po +++ b/po/sv_SE.po @@ -10,7 +10,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-03-12 18:25+0100\n" "Last-Translator: Magnus Andersson \n" "Language-Team: Swedish \n" @@ -965,6 +965,13 @@ msgstr "Undre LNB frekvens (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "vre LNB frekvens (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM omstart" diff --git a/po/tr_TR.po b/po/tr_TR.po index 194943b8..946ab421 100644 --- a/po/tr_TR.po +++ b/po/tr_TR.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2008-02-28 00:33+0100\n" "Last-Translator: Oktay Yolgeen \n" "Language-Team: Turkish \n" @@ -962,6 +962,13 @@ msgstr "Alt LNB frekans msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "st LNB frekans (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM sfrland" diff --git a/po/uk_UA.po b/po/uk_UA.po index 433ec704..c383af8c 100644 --- a/po/uk_UA.po +++ b/po/uk_UA.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.7.7\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2010-04-25 16:35+0200\n" "Last-Translator: Yarema aka Knedlyk \n" "Language-Team: Ukrainian \n" @@ -962,6 +962,13 @@ msgstr "Нижня частота конвертера (МГц)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "Верхня частота конвертера (МГц)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "Перезавантаження CAM" diff --git a/po/zh_CN.po b/po/zh_CN.po index c28fe881..43a5ea56 100644 --- a/po/zh_CN.po +++ b/po/zh_CN.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: VDR 1.6.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2011-08-27 11:54+0200\n" +"POT-Creation-Date: 2011-12-03 16:25+0100\n" "PO-Revision-Date: 2009-09-23 23:50+0800\n" "Last-Translator: Nan Feng \n" "Language-Team: Chinese (simplified) \n" @@ -965,6 +965,13 @@ msgstr "低本振频率 (MHz)" msgid "Setup.LNB$High LNB frequency (MHz)" msgstr "高本振频率 (MHz)" +#, c-format +msgid "Setup.LNB$Device %d connected to sat cable" +msgstr "" + +msgid "Setup.LNB$own" +msgstr "" + msgid "CAM reset" msgstr "CAM重置" diff --git a/vdr.c b/vdr.c index 284230cb..3d79eef4 100644 --- a/vdr.c +++ b/vdr.c @@ -22,7 +22,7 @@ * * The project's page is at http://www.tvdr.de * - * $Id: vdr.c 2.26 2011/10/16 14:02:34 kls Exp $ + * $Id: vdr.c 2.27 2011/12/03 15:35:09 kls Exp $ */ #include @@ -639,6 +639,7 @@ int main(int argc, char *argv[]) // DVB interfaces: cDvbDevice::Initialize(); + cDvbDevice::BondDevices(Setup.DeviceBondings); // Initialize plugins: @@ -899,7 +900,7 @@ int main(int argc, char *argv[]) Device = d; break; } - if (d->MaySwitchTransponder()) { + if (d->MaySwitchTransponder(Timer->Channel())) { DeviceAvailable = true; // avoids using the actual device below Device = d; }