Added check for already known audio pid.

This commit is contained in:
Rolf Ahrenberg 2008-02-02 20:51:47 +00:00
parent 55440bf047
commit 4188a5d4e2
3 changed files with 39 additions and 35 deletions

2
README
View File

@ -170,4 +170,6 @@ Acknowledgements:
- The IPTV section filtering code is derived from Linux kernel. - The IPTV section filtering code is derived from Linux kernel.
- The pid scanning code is derived from Udo Richter's streamplayer plugin.
- Udo Richter's po2i18n package is used to support VDR's old i18n system. - Udo Richter's po2i18n package is used to support VDR's old i18n system.

View File

@ -3,7 +3,7 @@
* *
* See the README file for copyright information and how to reach the author. * See the README file for copyright information and how to reach the author.
* *
* $Id: pidscanner.c,v 1.4 2008/02/02 20:23:44 ajhseppa Exp $ * $Id: pidscanner.c,v 1.5 2008/02/02 20:51:47 rahrenbe Exp $
*/ */
#include "common.h" #include "common.h"
@ -31,6 +31,24 @@ cPidScanner::~cPidScanner()
debug("cPidScanner::~cPidScanner()\n"); debug("cPidScanner::~cPidScanner()\n");
} }
void cPidScanner::SetChannel(const cChannel *Channel)
{
if (Channel) {
debug("cPidScanner::SetChannel(): %s\n", Channel->PluginParam());
channel = *Channel;
}
else {
debug("cPidScanner::SetChannel()\n");
channel = cChannel();
}
Vpid = 0xFFFF;
numVpids = 0;
Apid = 0xFFFF;
numApids = 0;
process = true;
timeout.Set(PIDSCANNER_TIMEOUT_IN_MS);
}
void cPidScanner::Process(const uint8_t* buf) void cPidScanner::Process(const uint8_t* buf)
{ {
//debug("cPidScanner::Process()\n"); //debug("cPidScanner::Process()\n");
@ -43,6 +61,7 @@ void cPidScanner::Process(const uint8_t* buf)
process = false; process = false;
} }
// Verify TS packet
if (buf[0] != 0x47) { if (buf[0] != 0x47) {
error("Not TS packet: 0x%X\n", buf[0]); error("Not TS packet: 0x%X\n", buf[0]);
return; return;
@ -52,7 +71,7 @@ void cPidScanner::Process(const uint8_t* buf)
int pid = ts_pid(buf); int pid = ts_pid(buf);
int xpid = (buf[1] << 8 | buf[2]); int xpid = (buf[1] << 8 | buf[2]);
// count == 0 if no payload or out of range // Check if payload available
uint8_t count = payload(buf); uint8_t count = payload(buf);
if (count == 0) if (count == 0)
return; return;
@ -96,13 +115,11 @@ void cPidScanner::Process(const uint8_t* buf)
} }
if ((numVpids > NR_VPIDS && numApids > NR_APIDS) || if ((numVpids > NR_VPIDS && numApids > NR_APIDS) ||
abs(numApids - numVpids) > NR_PID_DELTA) { abs(numApids - numVpids) > NR_PID_DELTA) {
// Lock channels for pid updates
if (!Channels.Lock(true, 10)) { if (!Channels.Lock(true, 10)) {
timeout.Set(PIDSCANNER_TIMEOUT_IN_MS); timeout.Set(PIDSCANNER_TIMEOUT_IN_MS);
return; return;
} }
debug("cPidScanner::Process(): Vpid=0x%04X, Apid=0x%04X\n", Vpid,
Apid);
cChannel *IptvChannel = Channels.GetByChannelID(channel.GetChannelID()); cChannel *IptvChannel = Channels.GetByChannelID(channel.GetChannelID());
int Apids[MAXAPIDS + 1] = { 0 }; // these lists are zero-terminated int Apids[MAXAPIDS + 1] = { 0 }; // these lists are zero-terminated
int Dpids[MAXDPIDS + 1] = { 0 }; int Dpids[MAXDPIDS + 1] = { 0 };
@ -112,21 +129,23 @@ void cPidScanner::Process(const uint8_t* buf)
char SLangs[MAXSPIDS][MAXLANGCODE2] = { "" }; char SLangs[MAXSPIDS][MAXLANGCODE2] = { "" };
int Ppid = IptvChannel->Ppid(); int Ppid = IptvChannel->Ppid();
int Tpid = IptvChannel->Tpid(); int Tpid = IptvChannel->Tpid();
Apids[0] = Apid; bool foundApid = false;
for (unsigned int i = 1; i < MAXAPIDS; ++i) if (numVpids <= NR_VPIDS)
Vpid = 0; // No detected video pid
else if (numApids <= NR_APIDS)
Apid = 0; // No detected audio pid
for (unsigned int i = 1; i < MAXAPIDS; ++i) {
Apids[i] = IptvChannel->Apid(i); Apids[i] = IptvChannel->Apid(i);
if (Apids[i] && (Apids[i] == Apid))
foundApid = true;
}
if (!foundApid)
Apids[0] = Apid;
for (unsigned int i = 0; i < MAXDPIDS; ++i) for (unsigned int i = 0; i < MAXDPIDS; ++i)
Dpids[i] = IptvChannel->Dpid(i); Dpids[i] = IptvChannel->Dpid(i);
for (unsigned int i = 0; i < MAXSPIDS; ++i) for (unsigned int i = 0; i < MAXSPIDS; ++i)
Spids[i] = IptvChannel->Spid(i); Spids[i] = IptvChannel->Spid(i);
if (numVpids <= NR_VPIDS) { debug("cPidScanner::Process(): Vpid=0x%04X, Apid=0x%04X\n", Vpid, Apid);
// No detected video pid, set zero.
Vpid = 0;
}
else if (numApids <= NR_APIDS) {
// Channel with no detected audio pid. Set zero.
Apids[0] = 0;
}
IptvChannel->SetPids(Vpid, Ppid, Apids, ALangs, Dpids, DLangs, Spids, SLangs, Tpid); IptvChannel->SetPids(Vpid, Ppid, Apids, ALangs, Dpids, DLangs, Spids, SLangs, Tpid);
Channels.Unlock(); Channels.Unlock();
process = false; process = false;
@ -134,21 +153,3 @@ void cPidScanner::Process(const uint8_t* buf)
} }
} }
} }
void cPidScanner::SetChannel(const cChannel *Channel)
{
if (Channel) {
debug("cPidScanner::SetChannel(): %s\n", Channel->PluginParam());
channel = *Channel;
}
else {
debug("cPidScanner::SetChannel()\n");
channel = cChannel();
}
Vpid = 0xFFFF;
numVpids = 0;
Apid = 0xFFFF;
numApids = 0;
process = true;
timeout.Set(PIDSCANNER_TIMEOUT_IN_MS);
}

View File

@ -3,12 +3,13 @@
* *
* See the README file for copyright information and how to reach the author. * See the README file for copyright information and how to reach the author.
* *
* $Id: pidscanner.h,v 1.2 2008/02/01 21:54:24 rahrenbe Exp $ * $Id: pidscanner.h,v 1.3 2008/02/02 20:51:47 rahrenbe Exp $
*/ */
#ifndef __PIDSCANNER_H #ifndef __PIDSCANNER_H
#define __PIDSCANNER_H #define __PIDSCANNER_H
#include <vdr/tools.h>
#include <vdr/channels.h> #include <vdr/channels.h>
class cPidScanner { class cPidScanner {
@ -24,8 +25,8 @@ private:
public: public:
cPidScanner(void); cPidScanner(void);
~cPidScanner(); ~cPidScanner();
void Process(const uint8_t* buf);
void SetChannel(const cChannel *Channel); void SetChannel(const cChannel *Channel);
void Process(const uint8_t* buf);
}; };
#endif // __PIDSCANNER_H #endif // __PIDSCANNER_H