12 #include <sys/ioctl.h>
64 #define MIN_PRE_1_3_19_PRIVATESTREAM 10
113 esyslog(
"ERROR: too many devices!");
126 for (time_t t0 = time(NULL); time(NULL) - t0 < Timeout; ) {
154 esyslog(
"ERROR: invalid value in nextCardIndex(%d)", n);
189 isyslog(
"setting primary device to %d", n + 1);
198 esyslog(
"ERROR: invalid primary device number: %d", n + 1);
227 int MaxNumProvidedSystems = (1 << AvailableBits) - 1;
229 if (NumProvidedSystems > MaxNumProvidedSystems) {
230 esyslog(
"ERROR: device %d supports %d modulation systems but cDevice::GetDevice() currently only supports %d delivery systems which should be fixed", Device->
CardIndex() + 1, NumProvidedSystems, MaxNumProvidedSystems);
231 NumProvidedSystems = MaxNumProvidedSystems;
233 else if (NumProvidedSystems <= 0) {
234 esyslog(
"ERROR: device %d reported an invalid number (%d) of supported delivery systems - assuming 1", Device->
CardIndex() + 1, NumProvidedSystems);
235 NumProvidedSystems = 1;
237 return NumProvidedSystems;
244 int SlotPriority[NumCamSlots];
245 int NumUsableSlots = 0;
246 bool InternalCamNeeded =
false;
260 InternalCamNeeded =
true;
263 bool NeedsDetachReceivers =
false;
267 uint32_t Impact = 0xFFFFFFFF;
268 for (
int j = 0; j < NumCamSlots || !NumUsableSlots; j++) {
269 if (NumUsableSlots && SlotPriority[j] >
MAXPRIORITY)
275 if (InternalCamNeeded && !HasInternalCam)
297 imp <<= 1; imp |= ndr;
298 imp <<= 1; imp |= (NumUsableSlots || InternalCamNeeded) ? 0 :
device[i]->
HasCi();
306 NeedsDetachReceivers = ndr;
307 if (NumUsableSlots && !HasInternalCam)
316 if (NeedsDetachReceivers)
338 if (d->IsTunedToTransponder(Channel))
340 if (d->ProvidesTransponder(Channel)) {
341 if (d->MaySwitchTransponder(Channel))
343 else if (!d->Occupied() && d->MaySwitchTransponder(Channel)) {
344 if (d->Priority() < Priority && (!Device || d->
Priority() < Device->
Priority()))
381 int fd = open(FileName, O_WRONLY | O_CREAT | O_NOFOLLOW | O_TRUNC, DEFFILEMODE);
386 if (
safe_write(fd, Image, ImageSize) == ImageSize)
387 isyslog(
"grabbed image to %s", FileName);
412 switch (VideoDisplayFormat) {
422 default:
esyslog(
"ERROR: invalid value for VideoDisplayFormat '%d'", VideoDisplayFormat);
465 if (Pid || PidType ==
ptPcr) {
468 if (PidType !=
ptPcr) {
505 esyslog(
"ERROR: no free slot for PID %d on device %d", Pid,
CardIndex() + 1);
529 if (Pid || PidType ==
ptPcr) {
531 if (PidType ==
ptPcr)
604 return safe_read(Handle, Buffer, Length);
700 for (
int i = 3; i--;) {
702 case scrOk:
return true;
708 default:
esyslog(
"ERROR: invalid return value from SetChannel");
718 Direction =
sgn(Direction);
728 n = channel->
Number() + Direction;
733 dsyslog(
"skipped channel %d", first);
735 dsyslog(
"skipped channels %d..%d", first, n -
sgn(d));
757 bool NeedsTransferMode = Device !=
this;
764 if (NeedsTransferMode) {
800 if (Result ==
scrOk) {
813 if (!NeedsTransferMode)
835 return Seconds > 0 ? Seconds : 0;
904 return (0 <= c && c <= 2) ? c : 0;
909 if (0 <= AudioChannel && AudioChannel <= 2)
930 if (DescriptionsOnly) {
974 esyslog(
"ERROR: SetAvailableTrack called with invalid Type/Index (%d/%d)", Type, Index);
986 for (
int i = FirstTrack; i <= LastTrack; i++) {
1039 if (TrackId && TrackId->
id) {
1055 int PreferredAudioChannel = 0;
1056 int LanguagePreference = -1;
1059 for (
int i = StartCheck; i <= EndCheck; i++) {
1064 PreferredAudioChannel = pos;
1075 dsyslog(
"setting audio track to %d (%d)", PreferredTrack, PreferredAudioChannel);
1088 int LanguagePreference = INT_MAX;
1151 if (Data[0] == 0x47) {
1157 int Pid =
TsPid(Data);
1167 int NewSize = Size + l;
1168 if (
uchar *NewBuffer = (
uchar *)realloc(buf, NewSize)) {
1171 memcpy(buf + Offset, p, l);
1189 int NewSize = Size + l;
1190 if (
uchar *NewBuffer = (
uchar *)realloc(buf, NewSize)) {
1193 memcpy(buf + Offset, p, l);
1196 esyslog(
"ERROR: out of memory");
1239 if (Player &&
player == Player) {
1294 bool FirstLoop =
true;
1297 const uchar *End = Start + Length;
1298 while (Start < End) {
1299 int d = End -
Start;
1318 if (Data[8] == 0x24 && Data[45] >= 0x10 && Data[45] < 0x20) {
1323 int PayloadOffset = Data[8] + 9;
1326 if ((Data[7] & 0x01) && (Data[PayloadOffset - 3] & 0x81) == 0x01 && Data[PayloadOffset - 2] == 0x81)
1329 uchar SubStreamId = Data[PayloadOffset];
1330 uchar SubStreamType = SubStreamId & 0xF0;
1331 uchar SubStreamIndex = SubStreamId & 0x1F;
1334 pre_1_3_19_PrivateStreamDetected:
1337 SubStreamType = 0x80;
1342 switch (SubStreamType) {
1373 dsyslog(
"switching to pre 1.3.19 Dolby Digital compatibility mode - substream id = %02X", SubStreamId);
1376 goto pre_1_3_19_PrivateStreamDetected;
1389 esyslog(
"ERROR: incomplete PES packet write!");
1390 return Start == Data ? w : Start - Data;
1405 while (i <= Length - 6) {
1406 if (Data[i] == 0x00 && Data[i + 1] == 0x00 && Data[i + 2] == 0x01) {
1408 if (i + l > Length) {
1409 esyslog(
"ERROR: incomplete PES packet!");
1416 return i == 0 ? w : i;
1422 esyslog(
"ERROR: leftover PES data!");
1485 esyslog(
"ERROR: skipped %d bytes of TS fragment", Length);
1494 esyslog(
"ERROR: skipped %d bytes to sync on start of TS packet", Skipped);
1495 return Played + Skipped;
1497 int Pid =
TsPid(Data);
1500 if (PayloadOffset <
TS_SIZE) {
1509 return Played ? Played : w;
1517 return Played ? Played : w;
1532 if ((l > 45) && (p[0] == 0x00) && (p[1] == 0x00) && (p[2] == 0x01) && (p[3] == 0xbd) && (p[8] == 0x24) && (p[45] >= 0x10) && (p[45] < 0x20))
1543 return Played ? Played : w;
1583 #define TS_SCRAMBLING_TIMEOUT 3 // seconds to wait until a TS becomes unscrambled
1584 #define TS_SCRAMBLING_TIME_OK 10 // seconds before a Channel/CAM combination is marked as known to decrypt
1596 bool DetachReceivers =
false;
1597 bool DescramblingOk =
false;
1598 int CamSlotNumber = 0;
1602 if (CamSlotNumber) {
1607 DetachReceivers =
true;
1610 DescramblingOk =
true;
1619 if (DetachReceivers) {
1657 if (Receiver->
device ==
this)
1661 #ifdef WAIT_FOR_TUNER_LOCK
1662 #define TUNER_LOCK_TIMEOUT 5000 // ms
1663 if (!
HasLock(TUNER_LOCK_TIMEOUT)) {
1664 esyslog(
"ERROR: device %d has no lock, can't attach receiver!",
CardIndex() + 1);
1671 for (
int n = 0; n < Receiver->
numPids; n++) {
1691 esyslog(
"ERROR: no free receiver slot!");
1697 if (!Receiver || Receiver->
device !=
this)
1699 bool receiversLeft =
false;
1708 for (
int n = 0; n < Receiver->
numPids; n++)
1712 receiversLeft =
true;
1726 if (Receiver && Receiver->
WantsPid(Pid))
1762 bool firstRead =
true;
1765 if (firstRead || Poller.
Poll(100)) {
1769 if (errno == EOVERFLOW)
1791 for (
int i = 1; i < Count; i++) {
1798 esyslog(
"ERROR: skipped %d bytes to sync on TS packet on device %d", Count,
cardIndex);