mirror of
https://github.com/VDR4Arch/vdr.git
synced 2023-10-10 13:36:52 +02:00
Changed cPatPmtGenerator to make sure the PMT pid doesn't collide with any of the actual pids of the channel
This commit is contained in:
parent
1ca753003b
commit
2b174b07bd
2
HISTORY
2
HISTORY
@ -5952,3 +5952,5 @@ Video Disk Recorder Revision History
|
|||||||
Schmirler).
|
Schmirler).
|
||||||
- Checking the pointer field in cPatPmtParser::ParsePmt() only in 'payload start'
|
- Checking the pointer field in cPatPmtParser::ParsePmt() only in 'payload start'
|
||||||
packets (suggested by Frank Schmirler).
|
packets (suggested by Frank Schmirler).
|
||||||
|
- Changed cPatPmtGenerator to make sure the PMT pid doesn't collide with any of
|
||||||
|
the actual pids of the channel.
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: recorder.c 2.1 2009/01/06 12:38:01 kls Exp $
|
* $Id: recorder.c 2.2 2009/01/23 16:44:29 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "recorder.h"
|
#include "recorder.h"
|
||||||
@ -44,7 +44,7 @@ cRecorder::cRecorder(const char *FileName, tChannelID ChannelID, int Priority, i
|
|||||||
Type = 0x06;
|
Type = 0x06;
|
||||||
}
|
}
|
||||||
frameDetector = new cFrameDetector(Pid, Type);
|
frameDetector = new cFrameDetector(Pid, Type);
|
||||||
patPmtGenerator.GeneratePmt(ChannelID);
|
patPmtGenerator.SetChannel(Channel);
|
||||||
fileName = NULL;
|
fileName = NULL;
|
||||||
index = NULL;
|
index = NULL;
|
||||||
fileSize = 0;
|
fileSize = 0;
|
||||||
|
54
remux.c
54
remux.c
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: remux.c 2.10 2009/01/23 16:43:23 kls Exp $
|
* $Id: remux.c 2.11 2009/01/23 16:44:29 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "remux.h"
|
#include "remux.h"
|
||||||
@ -111,13 +111,14 @@ void cRemux::SetBrokenLink(uchar *Data, int Length)
|
|||||||
|
|
||||||
// --- cPatPmtGenerator ------------------------------------------------------
|
// --- cPatPmtGenerator ------------------------------------------------------
|
||||||
|
|
||||||
cPatPmtGenerator::cPatPmtGenerator(void)
|
cPatPmtGenerator::cPatPmtGenerator(cChannel *Channel)
|
||||||
{
|
{
|
||||||
numPmtPackets = 0;
|
numPmtPackets = 0;
|
||||||
patCounter = pmtCounter = 0;
|
patCounter = pmtCounter = 0;
|
||||||
patVersion = pmtVersion = 0;
|
patVersion = pmtVersion = 0;
|
||||||
|
pmtPid = 0;
|
||||||
esInfoLength = NULL;
|
esInfoLength = NULL;
|
||||||
GeneratePat();
|
SetChannel(Channel);
|
||||||
}
|
}
|
||||||
|
|
||||||
void cPatPmtGenerator::IncCounter(int &Counter, uchar *TsPacket)
|
void cPatPmtGenerator::IncCounter(int &Counter, uchar *TsPacket)
|
||||||
@ -206,8 +207,23 @@ int cPatPmtGenerator::MakeCRC(uchar *Target, const uchar *Data, int Length)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#define P_TSID 0x8008 // pseudo TS ID
|
#define P_TSID 0x8008 // pseudo TS ID
|
||||||
#define P_PNR 0x0084 // pseudo Program Number
|
|
||||||
#define P_PMT_PID 0x0084 // pseudo PMT pid
|
#define P_PMT_PID 0x0084 // pseudo PMT pid
|
||||||
|
#define MAXPID 0x2000 // the maximum possible number of pids
|
||||||
|
|
||||||
|
void cPatPmtGenerator::GeneratePmtPid(cChannel *Channel)
|
||||||
|
{
|
||||||
|
bool Used[MAXPID] = { false };
|
||||||
|
#define SETPID(p) { if ((p) >= 0 && (p) < MAXPID) Used[p] = true; }
|
||||||
|
#define SETPIDS(l) { const int *p = l; while (*p) { SETPID(*p); p++; } }
|
||||||
|
SETPID(Channel->Vpid());
|
||||||
|
SETPID(Channel->Ppid());
|
||||||
|
SETPID(Channel->Tpid());
|
||||||
|
SETPIDS(Channel->Apids());
|
||||||
|
SETPIDS(Channel->Dpids());
|
||||||
|
SETPIDS(Channel->Spids());
|
||||||
|
for (pmtPid = P_PMT_PID; Used[pmtPid]; pmtPid++)
|
||||||
|
;
|
||||||
|
}
|
||||||
|
|
||||||
void cPatPmtGenerator::GeneratePat(void)
|
void cPatPmtGenerator::GeneratePat(void)
|
||||||
{
|
{
|
||||||
@ -229,22 +245,21 @@ void cPatPmtGenerator::GeneratePat(void)
|
|||||||
p[i++] = 0xC1 | (patVersion << 1); // dummy (2), version number (5), current/next indicator (1)
|
p[i++] = 0xC1 | (patVersion << 1); // dummy (2), version number (5), current/next indicator (1)
|
||||||
p[i++] = 0x00; // section number
|
p[i++] = 0x00; // section number
|
||||||
p[i++] = 0x00; // last section number
|
p[i++] = 0x00; // last section number
|
||||||
p[i++] = P_PNR >> 8; // program number hi
|
p[i++] = pmtPid >> 8; // program number hi
|
||||||
p[i++] = P_PNR & 0xFF; // program number lo
|
p[i++] = pmtPid & 0xFF; // program number lo
|
||||||
p[i++] = 0xE0 | (P_PMT_PID >> 8); // dummy (3), PMT pid hi (5)
|
p[i++] = 0xE0 | (pmtPid >> 8); // dummy (3), PMT pid hi (5)
|
||||||
p[i++] = P_PMT_PID & 0xFF; // PMT pid lo
|
p[i++] = pmtPid & 0xFF; // PMT pid lo
|
||||||
pat[SectionLength] = i - SectionLength - 1 + 4; // -2 = SectionLength storage, +4 = length of CRC
|
pat[SectionLength] = i - SectionLength - 1 + 4; // -2 = SectionLength storage, +4 = length of CRC
|
||||||
MakeCRC(pat + i, pat + PayloadStart, i - PayloadStart);
|
MakeCRC(pat + i, pat + PayloadStart, i - PayloadStart);
|
||||||
IncVersion(patVersion);
|
IncVersion(patVersion);
|
||||||
}
|
}
|
||||||
|
|
||||||
void cPatPmtGenerator::GeneratePmt(tChannelID ChannelID)
|
void cPatPmtGenerator::GeneratePmt(cChannel *Channel)
|
||||||
{
|
{
|
||||||
// generate the complete PMT section:
|
// generate the complete PMT section:
|
||||||
uchar buf[MAX_SECTION_SIZE];
|
uchar buf[MAX_SECTION_SIZE];
|
||||||
memset(buf, 0xFF, sizeof(buf));
|
memset(buf, 0xFF, sizeof(buf));
|
||||||
numPmtPackets = 0;
|
numPmtPackets = 0;
|
||||||
cChannel *Channel = Channels.GetByChannelID(ChannelID);
|
|
||||||
if (Channel) {
|
if (Channel) {
|
||||||
int Vpid = Channel->Vpid();
|
int Vpid = Channel->Vpid();
|
||||||
uchar *p = buf;
|
uchar *p = buf;
|
||||||
@ -253,8 +268,8 @@ void cPatPmtGenerator::GeneratePmt(tChannelID ChannelID)
|
|||||||
int SectionLength = i;
|
int SectionLength = i;
|
||||||
p[i++] = 0xB0; // section syntax indicator (1), dummy (3), section length hi (4)
|
p[i++] = 0xB0; // section syntax indicator (1), dummy (3), section length hi (4)
|
||||||
p[i++] = 0x00; // section length lo (filled in later)
|
p[i++] = 0x00; // section length lo (filled in later)
|
||||||
p[i++] = P_PNR >> 8; // program number hi
|
p[i++] = pmtPid >> 8; // program number hi
|
||||||
p[i++] = P_PNR & 0xFF; // program number lo
|
p[i++] = pmtPid & 0xFF; // program number lo
|
||||||
p[i++] = 0xC1 | (pmtVersion << 1); // dummy (2), version number (5), current/next indicator (1)
|
p[i++] = 0xC1 | (pmtVersion << 1); // dummy (2), version number (5), current/next indicator (1)
|
||||||
p[i++] = 0x00; // section number
|
p[i++] = 0x00; // section number
|
||||||
p[i++] = 0x00; // last section number
|
p[i++] = 0x00; // last section number
|
||||||
@ -293,8 +308,8 @@ void cPatPmtGenerator::GeneratePmt(tChannelID ChannelID)
|
|||||||
uchar *p = pmt[numPmtPackets++];
|
uchar *p = pmt[numPmtPackets++];
|
||||||
int j = 0;
|
int j = 0;
|
||||||
p[j++] = TS_SYNC_BYTE; // TS indicator
|
p[j++] = TS_SYNC_BYTE; // TS indicator
|
||||||
p[j++] = (pusi ? TS_PAYLOAD_START : 0x00) | (P_PNR >> 8); // flags (3), pid hi (5)
|
p[j++] = (pusi ? TS_PAYLOAD_START : 0x00) | (pmtPid >> 8); // flags (3), pid hi (5)
|
||||||
p[j++] = P_PNR & 0xFF; // pid lo
|
p[j++] = pmtPid & 0xFF; // pid lo
|
||||||
p[j++] = 0x10; // flags (4), continuity counter (4)
|
p[j++] = 0x10; // flags (4), continuity counter (4)
|
||||||
if (pusi) {
|
if (pusi) {
|
||||||
p[j++] = 0x00; // pointer field (payload unit start indicator is set)
|
p[j++] = 0x00; // pointer field (payload unit start indicator is set)
|
||||||
@ -307,8 +322,15 @@ void cPatPmtGenerator::GeneratePmt(tChannelID ChannelID)
|
|||||||
}
|
}
|
||||||
IncVersion(pmtVersion);
|
IncVersion(pmtVersion);
|
||||||
}
|
}
|
||||||
else
|
}
|
||||||
esyslog("ERROR: can't find channel %s", *ChannelID.ToString());
|
|
||||||
|
void cPatPmtGenerator::SetChannel(cChannel *Channel)
|
||||||
|
{
|
||||||
|
if (Channel) {
|
||||||
|
GeneratePmtPid(Channel);
|
||||||
|
GeneratePat();
|
||||||
|
GeneratePmt(Channel);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
uchar *cPatPmtGenerator::GetPat(void)
|
uchar *cPatPmtGenerator::GetPat(void)
|
||||||
|
17
remux.h
17
remux.h
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: remux.h 2.5 2009/01/23 16:40:27 kls Exp $
|
* $Id: remux.h 2.6 2009/01/23 16:44:46 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef __REMUX_H
|
#ifndef __REMUX_H
|
||||||
@ -153,6 +153,7 @@ private:
|
|||||||
int pmtCounter;
|
int pmtCounter;
|
||||||
int patVersion;
|
int patVersion;
|
||||||
int pmtVersion;
|
int pmtVersion;
|
||||||
|
int pmtPid;
|
||||||
uchar *esInfoLength;
|
uchar *esInfoLength;
|
||||||
void IncCounter(int &Counter, uchar *TsPacket);
|
void IncCounter(int &Counter, uchar *TsPacket);
|
||||||
void IncVersion(int &Version);
|
void IncVersion(int &Version);
|
||||||
@ -163,14 +164,18 @@ protected:
|
|||||||
int MakeSubtitlingDescriptor(uchar *Target, const char *Language);
|
int MakeSubtitlingDescriptor(uchar *Target, const char *Language);
|
||||||
int MakeLanguageDescriptor(uchar *Target, const char *Language);
|
int MakeLanguageDescriptor(uchar *Target, const char *Language);
|
||||||
int MakeCRC(uchar *Target, const uchar *Data, int Length);
|
int MakeCRC(uchar *Target, const uchar *Data, int Length);
|
||||||
public:
|
void GeneratePmtPid(cChannel *Channel);
|
||||||
cPatPmtGenerator(void);
|
///< Generates a PMT pid that doesn't collide with any of the actual
|
||||||
|
///< pids of the Channel.
|
||||||
void GeneratePat(void);
|
void GeneratePat(void);
|
||||||
///< Generates a PAT section for later use with GetPat().
|
///< Generates a PAT section for later use with GetPat().
|
||||||
///< This function is called by default from the constructor.
|
void GeneratePmt(cChannel *Channel);
|
||||||
void GeneratePmt(tChannelID ChannelID);
|
///< Generates a PMT section for the given Channel, for later use
|
||||||
///< Generates a PMT section for the given ChannelId, for later use
|
|
||||||
///< with GetPmt().
|
///< with GetPmt().
|
||||||
|
public:
|
||||||
|
cPatPmtGenerator(cChannel *Channel = NULL);
|
||||||
|
void SetChannel(cChannel *Channel);
|
||||||
|
///< Sets the Channel for which the PAT/PMT shall be generated.
|
||||||
uchar *GetPat(void);
|
uchar *GetPat(void);
|
||||||
///< Returns a pointer to the PAT section, which consists of exactly
|
///< Returns a pointer to the PAT section, which consists of exactly
|
||||||
///< one TS packet.
|
///< one TS packet.
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
* See the main source file 'vdr.c' for copyright information and
|
* See the main source file 'vdr.c' for copyright information and
|
||||||
* how to reach the author.
|
* how to reach the author.
|
||||||
*
|
*
|
||||||
* $Id: transfer.c 2.2 2009/01/16 15:16:08 kls Exp $
|
* $Id: transfer.c 2.3 2009/01/23 16:44:29 kls Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "transfer.h"
|
#include "transfer.h"
|
||||||
@ -14,7 +14,7 @@
|
|||||||
cTransfer::cTransfer(tChannelID ChannelID, int VPid, const int *APids, const int *DPids, const int *SPids)
|
cTransfer::cTransfer(tChannelID ChannelID, int VPid, const int *APids, const int *DPids, const int *SPids)
|
||||||
:cReceiver(ChannelID, -1, VPid, APids, Setup.UseDolbyDigital ? DPids : NULL, SPids)
|
:cReceiver(ChannelID, -1, VPid, APids, Setup.UseDolbyDigital ? DPids : NULL, SPids)
|
||||||
{
|
{
|
||||||
patPmtGenerator.GeneratePmt(ChannelID);
|
patPmtGenerator.SetChannel(Channels.GetByChannelID(ChannelID));
|
||||||
}
|
}
|
||||||
|
|
||||||
cTransfer::~cTransfer()
|
cTransfer::~cTransfer()
|
||||||
|
Loading…
Reference in New Issue
Block a user