mirror of
https://github.com/VDR4Arch/vdr.git
synced 2023-10-10 13:36:52 +02:00
Now using 'libdtv' version 0.0.5
This commit is contained in:
parent
7c84508417
commit
f8a7e51d00
@ -166,6 +166,7 @@ Stefan Huelswitt <huels@iname.com>
|
||||
for reporting a problem with timers when channel IDs have a 'source' that is 0
|
||||
for reporting a new/delete malloc/free mismatch in ringbuffer.c
|
||||
for reporting a crash in case the index file can't be accessed any more during replay
|
||||
for adapting VDR to 'libdtv' version 0.0.5
|
||||
|
||||
Ulrich Röder <roeder@efr-net.de>
|
||||
for pointing out that there are channels that have a symbol rate higher than
|
||||
|
2
HISTORY
2
HISTORY
@ -2020,3 +2020,5 @@ Video Disk Recorder Revision History
|
||||
- Implemented a "resume ID" which allows several users to each have their own
|
||||
resume.vdr files (thanks to Martin Hammerschmid). This parameter can be set in
|
||||
the "Setup/Replay" menu (see MANUAL for details).
|
||||
- Now using 'libdtv' version 0.0.5 (thanks to Rolf Hakenes for the new version
|
||||
and Stefan Huelswitt for adapting VDR to it).
|
||||
|
51
eit.c
51
eit.c
@ -16,7 +16,7 @@
|
||||
* the Free Software Foundation; either version 2 of the License, or *
|
||||
* (at your option) any later version. *
|
||||
* *
|
||||
* $Id: eit.c 1.67 2003/03/16 11:20:05 kls Exp $
|
||||
* $Id: eit.c 1.68 2003/04/12 11:27:31 kls Exp $
|
||||
***************************************************************************/
|
||||
|
||||
#include "eit.h"
|
||||
@ -1011,29 +1011,37 @@ private:
|
||||
int length;
|
||||
uchar *data;
|
||||
public:
|
||||
cCaDescriptor(int Source, int Transponder, int ServiceId, int CaSystem, int Length, uchar *Data);
|
||||
cCaDescriptor(int Source, int Transponder, int ServiceId, int CaSystem, int CaPid, int Length, uchar *Data);
|
||||
virtual ~cCaDescriptor();
|
||||
int Length(void) const { return length; }
|
||||
const uchar *Data(void) const { return data; }
|
||||
};
|
||||
|
||||
cCaDescriptor::cCaDescriptor(int Source, int Transponder, int ServiceId, int CaSystem, int Length, uchar *Data)
|
||||
cCaDescriptor::cCaDescriptor(int Source, int Transponder, int ServiceId, int CaSystem, int CaPid, int Length, uchar *Data)
|
||||
{
|
||||
source = Source;
|
||||
transponder = Transponder;
|
||||
serviceId = ServiceId;
|
||||
caSystem = CaSystem;
|
||||
length = Length;
|
||||
length = Length + 6;
|
||||
data = MALLOC(uchar, length);
|
||||
memcpy(data, Data, length);
|
||||
/*//XXX just while debugging...
|
||||
data[0] = DESCR_CA;
|
||||
data[1] = length - 2;
|
||||
data[2] = (caSystem >> 8) & 0xFF;
|
||||
data[3] = caSystem & 0xFF;
|
||||
data[4] = ((CaPid >> 8) & 0xFF) | 0xE0;
|
||||
data[5] = CaPid & 0xFF;
|
||||
if (Length)
|
||||
memcpy(&data[6], Data, Length);
|
||||
//#define DEBUG_CA_DESCRIPTORS 1
|
||||
#ifdef DEBUG_CA_DESCRIPTORS
|
||||
char buffer[1024];
|
||||
char *q = buffer;
|
||||
q += sprintf(q, "CAM: %04X %5d %4d", source, transponder, serviceId);
|
||||
for (int i = 0; i < length; i++)
|
||||
q += sprintf(q, " %02X", data[i]);
|
||||
dsyslog(buffer);
|
||||
*///XXX
|
||||
#endif
|
||||
}
|
||||
|
||||
cCaDescriptor::~cCaDescriptor()
|
||||
@ -1312,16 +1320,13 @@ void cSIProcessor::Action()
|
||||
if (pid == pmtPid && buf[0] == 0x02 && currentSource && currentTransponder) {
|
||||
struct Pid *pi = siParsePMT(buf);
|
||||
if (pi) {
|
||||
for (struct LIST *d = (struct LIST *)pi->Descriptors; d; d = (struct LIST *)xSucc(d)) {
|
||||
if (DescriptorTag(d) == DESCR_CA) {
|
||||
uchar *Data = ((ConditionalAccessDescriptor *)d)->Data;
|
||||
int CaSystem = (Data[2] << 8) | Data[3];
|
||||
if (!caDescriptors->Get(currentSource, currentTransponder, pi->ProgramID, CaSystem)) {
|
||||
cMutexLock MutexLock(&caDescriptorsMutex);
|
||||
caDescriptors->Add(new cCaDescriptor(currentSource, currentTransponder, pi->ProgramID, CaSystem, ((ConditionalAccessDescriptor *)d)->Amount, Data));
|
||||
}
|
||||
//XXX update???
|
||||
}
|
||||
struct Descriptor *d;
|
||||
for (d = (struct Descriptor *)pi->Descriptors->Head; d; d = (struct Descriptor *)xSucc(d))
|
||||
NewCaDescriptor(d, pi->ProgramID);
|
||||
// Also scan the PidInfo list for descriptors - some broadcasts send them only here.
|
||||
for (struct PidInfo *p = (struct PidInfo *)pi->InfoList->Head; p; p = (struct PidInfo *)xSucc(p)) {
|
||||
for (d = (struct Descriptor *)p->Descriptors->Head; d; d = (struct Descriptor *)xSucc(d))
|
||||
NewCaDescriptor(d, pi->ProgramID);
|
||||
}
|
||||
}
|
||||
xMemFreeAll(NULL);
|
||||
@ -1438,6 +1443,18 @@ void cSIProcessor::TriggerDump(void)
|
||||
lastDump = 0;
|
||||
}
|
||||
|
||||
void cSIProcessor::NewCaDescriptor(struct Descriptor *d, int ProgramID)
|
||||
{
|
||||
if (DescriptorTag(d) == DESCR_CA) {
|
||||
struct CaDescriptor *cd = (struct CaDescriptor *)d;
|
||||
if (!caDescriptors->Get(currentSource, currentTransponder, ProgramID, cd->CA_type)) {
|
||||
cMutexLock MutexLock(&caDescriptorsMutex);
|
||||
caDescriptors->Add(new cCaDescriptor(currentSource, currentTransponder, ProgramID, cd->CA_type, cd->CA_PID, cd->DataLength, cd->Data));
|
||||
}
|
||||
//XXX update???
|
||||
}
|
||||
}
|
||||
|
||||
int cSIProcessor::GetCaDescriptors(int Source, int Transponder, int ServiceId, int BufSize, uchar *Data)
|
||||
{
|
||||
if (BufSize > 0 && Data) {
|
||||
|
3
eit.h
3
eit.h
@ -16,7 +16,7 @@
|
||||
* the Free Software Foundation; either version 2 of the License, or *
|
||||
* (at your option) any later version. *
|
||||
* *
|
||||
* $Id: eit.h 1.24 2003/02/02 14:07:39 kls Exp $
|
||||
* $Id: eit.h 1.25 2003/04/12 10:59:26 kls Exp $
|
||||
***************************************************************************/
|
||||
|
||||
#ifndef __EIT_H
|
||||
@ -158,6 +158,7 @@ private:
|
||||
bool AddFilter(unsigned short pid, u_char tid);
|
||||
bool DelFilter(unsigned short pid, u_char tid);
|
||||
bool ShutDownFilters(void);
|
||||
void NewCaDescriptor(struct Descriptor *d, int ProgramID);
|
||||
public:
|
||||
cSIProcessor(const char *FileName);
|
||||
~cSIProcessor();
|
||||
|
@ -4,11 +4,13 @@
|
||||
/// ///
|
||||
//////////////////////////////////////////////////////////////
|
||||
|
||||
// $Revision: 1.6 $
|
||||
// $Date: 2002/01/30 17:04:13 $
|
||||
// $Revision: 1.7 $
|
||||
// $Date: 2003/04/12 11:27:31 $
|
||||
// $Author: hakenes $
|
||||
//
|
||||
// (C) 2001 Rolf Hakenes <hakenes@hippomi.de>, under the GNU GPL.
|
||||
// (C) 2001-03 Rolf Hakenes <hakenes@hippomi.de>, under the
|
||||
// GNU GPL with contribution of Oleg Assovski,
|
||||
// www.satmania.com
|
||||
//
|
||||
// libsi is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
@ -38,9 +40,9 @@
|
||||
/* Program Identifier */
|
||||
|
||||
#define PID_PAT 0x00 /* Program Association Table */
|
||||
#define PID_BAT 0x01 /* Bouquet Association Table */
|
||||
#define PID_CAT 0x01 /* Conditional Access Table */
|
||||
#define PID_NIT 0x10 /* Network Information Table */
|
||||
#define PID_BAT 0x11 /* Bouquet Association Table */
|
||||
#define PID_SDT 0x11 /* Service Description Table */
|
||||
#define PID_EIT 0x12 /* Event Information Table */
|
||||
#define PID_RST 0x13 /* Running Status Table */
|
||||
@ -75,12 +77,13 @@
|
||||
#define TID_TOT 0x73 /* Time Offset Section */
|
||||
#define TID_CA_ECM_0 0x80
|
||||
#define TID_CA_ECM_1 0x81
|
||||
#define TID_CA_EMM 0x82
|
||||
|
||||
#define TID_BAT 0x01 /* Bouquet Association Section */
|
||||
#define TID_BAT 0x4A /* Bouquet Association Section */
|
||||
|
||||
#define TID_EIT 0x12 /* Event Information Section */
|
||||
#define TID_RST 0x13 /* Running Status Section */
|
||||
#define TID_ST 0x14 /* Stuffung Section */
|
||||
#define TID_RST 0x71 /* Running Status Section */
|
||||
#define TID_ST 0x72 /* Stuffing Section */
|
||||
/* 0xFF */ /* Reserved for future use */
|
||||
|
||||
/* Descriptor Identifier */
|
||||
@ -160,6 +163,40 @@
|
||||
#define MAX_SECTION_BUFFER 4096
|
||||
|
||||
|
||||
/* NetworkInfo structure (used to store NIT/BAT information) */
|
||||
|
||||
struct NetworkInfo {
|
||||
struct NODE Node;
|
||||
unsigned short ID; // NetworkID / BouquetID
|
||||
struct LIST *Descriptors;
|
||||
struct LIST *TransportStreams;
|
||||
};
|
||||
|
||||
#define CreateNetworkInfo(ni, id) \
|
||||
do { \
|
||||
xCreateNode (ni, NULL); \
|
||||
(ni)->ID = id; \
|
||||
(ni)->Descriptors = xNewList(NULL); \
|
||||
(ni)->TransportStreams = NULL; \
|
||||
} while(0)
|
||||
|
||||
/* TransportStream structure (NIT/BAT TS loop member) */
|
||||
|
||||
struct TransportStream {
|
||||
struct NODE Node;
|
||||
int TransportStreamID;
|
||||
unsigned short OriginalNetworkID;
|
||||
struct LIST *Descriptors;
|
||||
};
|
||||
|
||||
#define CreateTransportStream(ts, tsid, onid) \
|
||||
do { \
|
||||
xCreateNode (ts, NULL); \
|
||||
(ts)->TransportStreamID = tsid; \
|
||||
(ts)->OriginalNetworkID = onid; \
|
||||
(ts)->Descriptors = xNewList(NULL); \
|
||||
} while(0)
|
||||
|
||||
/* Strukturen zur Aufnahme der SDT und EIT Informationen */
|
||||
|
||||
struct Service {
|
||||
@ -305,6 +342,23 @@ struct PidInfo {
|
||||
#define STREAMTYPE_13818_D 13
|
||||
#define STREAMTYPE_13818_AUX 14
|
||||
|
||||
|
||||
struct Tot {
|
||||
time_t UTC;
|
||||
time_t Bias;
|
||||
struct LIST *Descriptors;
|
||||
};
|
||||
|
||||
#define CreateTot(tot, utc) \
|
||||
do \
|
||||
{ \
|
||||
xMemAlloc(sizeof(struct Tot), &tot); \
|
||||
tot->UTC = utc; \
|
||||
tot->Bias = ((utc - time(NULL) + 1800)/3600)*3600; \
|
||||
tot->Descriptors = xNewList(NULL); \
|
||||
} while (0)
|
||||
|
||||
|
||||
/* Descriptors */
|
||||
|
||||
#define DescriptorTag(x) ((struct Descriptor *)(x))->Tag
|
||||
@ -315,29 +369,6 @@ struct Descriptor {
|
||||
};
|
||||
|
||||
|
||||
/* ConditionalAccessDescriptor */
|
||||
|
||||
struct ConditionalAccessDescriptor {
|
||||
struct NODE Node;
|
||||
unsigned short Tag;
|
||||
unsigned short Amount; /* Data */
|
||||
unsigned char *Data;
|
||||
};
|
||||
|
||||
#define CreateConditionalAccessDescriptor(descr, amount, data) \
|
||||
do \
|
||||
{ \
|
||||
unsigned char *tmpptr; \
|
||||
\
|
||||
xMemAlloc (amount, &tmpptr); \
|
||||
memcpy (tmpptr, data, amount); \
|
||||
xCreateNode (((struct ConditionalAccessDescriptor *)descr), NULL); \
|
||||
((struct ConditionalAccessDescriptor *)descr)->Tag = DESCR_CA; \
|
||||
((struct ConditionalAccessDescriptor *)descr)->Amount = amount; \
|
||||
((struct ConditionalAccessDescriptor *)descr)->Data = tmpptr; \
|
||||
} while (0)
|
||||
|
||||
|
||||
/* Iso639LanguageDescriptor */
|
||||
|
||||
struct Iso639LanguageDescriptor {
|
||||
@ -434,19 +465,23 @@ struct AncillaryDataDescriptor {
|
||||
|
||||
|
||||
/* BouquetNameDescriptor */
|
||||
/*
|
||||
the same used instead of NetworkNameDescriptor because their structures
|
||||
are identical. We pass 'tag' parameter to distinguish between them later
|
||||
*/
|
||||
|
||||
struct BouquetNameDescriptor {
|
||||
struct NODE Node; /* Node enthält Namen */
|
||||
unsigned short Tag;
|
||||
};
|
||||
|
||||
#define CreateBouquetNameDescriptor(descr, text) \
|
||||
#define CreateBouquetNameDescriptor(descr, text, tag) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (((struct BouquetNameDescriptor *)descr), NULL); \
|
||||
((struct NODE *)descr)->Name = text; \
|
||||
((struct NODE *)descr)->HashKey = xHashKey (text); \
|
||||
((struct BouquetNameDescriptor *)descr)->Tag = DESCR_BOUQUET_NAME; \
|
||||
((struct BouquetNameDescriptor *)descr)->Tag = tag; \
|
||||
} while (0)
|
||||
|
||||
|
||||
@ -514,6 +549,33 @@ struct CaIdentifierDescriptor {
|
||||
((struct CaIdentifierDescriptor *)descr)->SystemID[num] = id
|
||||
#define GetCaIdentifierID(descr, num) (((struct CaIdentifierDescriptor *)descr)->SystemID[num])
|
||||
|
||||
/* CaDescriptor */
|
||||
|
||||
struct CaDescriptor {
|
||||
struct NODE Node;
|
||||
unsigned short Tag;
|
||||
unsigned short CA_type;
|
||||
unsigned short CA_PID;
|
||||
unsigned int ProviderID;
|
||||
unsigned short DataLength;
|
||||
unsigned char *Data;
|
||||
};
|
||||
|
||||
#define CreateCaDescriptor(descr, typ, capid, len) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (((struct CaDescriptor *)descr), NULL); \
|
||||
((struct CaDescriptor *)descr)->Tag = DESCR_CA; \
|
||||
((struct CaDescriptor *)descr)->CA_type = typ; \
|
||||
((struct CaDescriptor *)descr)->CA_PID = capid; \
|
||||
((struct CaDescriptor *)descr)->ProviderID = 0; \
|
||||
((struct CaDescriptor *)descr)->DataLength = len; \
|
||||
xMemAlloc (len+1, &((struct CaDescriptor *)descr)->Data); \
|
||||
} while (0)
|
||||
|
||||
#define SetCaData(descr, num, id) \
|
||||
((struct CaDescriptor *)descr)->Data[num] = id
|
||||
#define GetCaData(descr, num) (((struct CaDescriptor *)descr)->Data[num])
|
||||
|
||||
/* StreamIdentifierDescriptor */
|
||||
|
||||
@ -968,6 +1030,122 @@ struct SubtitlingItem {
|
||||
xAddTail (((struct SubtitlingDescriptor *)desc)->Items, item); \
|
||||
} while (0)
|
||||
|
||||
/* SatelliteDeliverySystemDescriptor */
|
||||
|
||||
struct SatelliteDeliverySystemDescriptor {
|
||||
struct NODE Node;
|
||||
unsigned short Tag;
|
||||
long Frequency;
|
||||
short OrbitalPosition;
|
||||
char Polarization;
|
||||
long SymbolRate;
|
||||
char FEC;
|
||||
};
|
||||
|
||||
#define CreateSatelliteDeliverySystemDescriptor(descr, freq, orb, polar, sr, fec) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (((struct SatelliteDeliverySystemDescriptor *)descr), NULL); \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->Tag = DESCR_SAT_DEL_SYS; \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->Frequency = freq; \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->OrbitalPosition = orb; \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->Polarization = polar; \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->SymbolRate = sr; \
|
||||
((struct SatelliteDeliverySystemDescriptor *)descr)->FEC = fec; \
|
||||
} while (0)
|
||||
|
||||
/* ServiceListDescriptor */
|
||||
|
||||
struct ServiceListDescriptor {
|
||||
struct NODE Node;
|
||||
unsigned short Tag;
|
||||
struct LIST *ServiceList;
|
||||
};
|
||||
|
||||
#define CreateServiceListDescriptor(descr) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (((struct ServiceListDescriptor *)descr), NULL); \
|
||||
((struct ServiceListDescriptor *)descr)->Tag = DESCR_SERVICE_LIST; \
|
||||
((struct ServiceListDescriptor *)descr)->ServiceList = xNewList(NULL); \
|
||||
} while (0)
|
||||
|
||||
struct ServiceListEntry {
|
||||
struct NODE Node;
|
||||
int ServiceID;
|
||||
unsigned short ServiceType;
|
||||
};
|
||||
|
||||
#define AddServiceListEntry(descr, id, typ) \
|
||||
do \
|
||||
{ \
|
||||
struct ServiceListEntry *newent; \
|
||||
\
|
||||
xCreateNode (newent, NULL); \
|
||||
newent->ServiceID = id; \
|
||||
newent->ServiceType = typ; \
|
||||
xAddTail (((struct ServiceListDescriptor *)descr)->ServiceList, newent); \
|
||||
} while (0)
|
||||
|
||||
/* LocalTimeOffsetDescriptor */
|
||||
|
||||
struct LocalTimeOffsetDescriptor {
|
||||
struct NODE Node;
|
||||
unsigned short Tag;
|
||||
struct LIST *LocalTimeOffsets;
|
||||
};
|
||||
|
||||
#define CreateLocalTimeOffsetDescriptor(descr) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (((struct LocalTimeOffsetDescriptor *)descr), NULL); \
|
||||
((struct LocalTimeOffsetDescriptor *)descr)->Tag = DESCR_LOCAL_TIME_OFF; \
|
||||
((struct LocalTimeOffsetDescriptor *)descr)->LocalTimeOffsets = xNewList(NULL); \
|
||||
} while (0)
|
||||
|
||||
struct LocalTimeOffsetEntry {
|
||||
struct NODE Node;
|
||||
char CountryCode[4];
|
||||
char RegionID;
|
||||
time_t CurrentOffset;
|
||||
time_t ChangeTime;
|
||||
time_t NextOffset;
|
||||
};
|
||||
|
||||
#define CreateLocalTimeOffsetEntry(newent, code1, code2, code3, reg, co, ct, no) \
|
||||
do \
|
||||
{ \
|
||||
xCreateNode (newent, NULL); \
|
||||
newent->CountryCode[0] = code1; \
|
||||
newent->CountryCode[1] = code2; \
|
||||
newent->CountryCode[2] = code3; \
|
||||
newent->CountryCode[3] = '\0'; \
|
||||
newent->RegionID = reg; \
|
||||
newent->CurrentOffset = co; \
|
||||
newent->ChangeTime = ct; \
|
||||
newent->NextOffset = no; \
|
||||
} while (0)
|
||||
|
||||
#define AddLocalTimeOffsetEntry(descr, code1, code2, code3, reg, co, ct, no) \
|
||||
do \
|
||||
{ \
|
||||
struct LocalTimeOffsetEntry *newent; \
|
||||
\
|
||||
xCreateNode (newent, NULL); \
|
||||
newent->CountryCode[0] = code1; \
|
||||
newent->CountryCode[1] = code2; \
|
||||
newent->CountryCode[2] = code3; \
|
||||
newent->CountryCode[3] = '\0'; \
|
||||
newent->RegionID = reg; \
|
||||
newent->CurrentOffset = co; \
|
||||
newent->ChangeTime = ct; \
|
||||
newent->NextOffset = no; \
|
||||
xAddTail (((struct LocalTimeOffsetDescriptor *)descr)->LocalTimeOffsets, newent); \
|
||||
} while (0)
|
||||
|
||||
#define timezonecmp(ptoe,cod,reg) \
|
||||
(strncmp(ptoe->CountryCode, cod, 3) || (ptoe->RegionID != reg))
|
||||
|
||||
|
||||
|
||||
/* Prototypes */
|
||||
@ -979,13 +1157,17 @@ extern "C" {
|
||||
/* si_parser.c */
|
||||
|
||||
struct LIST *siParsePAT (u_char *);
|
||||
struct LIST *siParseCAT (u_char *);
|
||||
struct Pid *siParsePMT (u_char *);
|
||||
struct LIST *siParseSDT (u_char *);
|
||||
struct LIST *siParseNIT (u_char *);
|
||||
struct LIST *siParseEIT (u_char *);
|
||||
time_t siParseTDT (u_char *);
|
||||
struct Tot *siParseTOT (u_char *);
|
||||
void siParseDescriptors (struct LIST *, u_char *, int, u_char);
|
||||
void siParseDescriptor (struct LIST *, u_char *);
|
||||
char *siGetDescriptorText (u_char *, int);
|
||||
char *siGetDescriptorName (u_char *, int);
|
||||
u_long crc32 (char *data, int len);
|
||||
|
||||
/* si_debug_services.c */
|
||||
@ -999,6 +1181,8 @@ void siDebugPids (char *, struct LIST *);
|
||||
void siDebugDescriptors (char *, struct LIST *);
|
||||
void siDebugEitServices (struct LIST *);
|
||||
void siDebugEitEvents (char *, struct LIST *);
|
||||
void siDumpDescriptor (void *);
|
||||
void siDumpSection (void *);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -5,11 +5,13 @@
|
||||
/// ///
|
||||
//////////////////////////////////////////////////////////////
|
||||
|
||||
// $Revision: 1.3 $
|
||||
// $Date: 2001/10/07 10:24:46 $
|
||||
// $Revision: 1.4 $
|
||||
// $Date: 2003/04/12 11:27:31 $
|
||||
// $Author: hakenes $
|
||||
//
|
||||
// (C) 2001 Rolf Hakenes <hakenes@hippomi.de>, under the GNU GPL.
|
||||
// (C) 2001-03 Rolf Hakenes <hakenes@hippomi.de>, under the
|
||||
// GNU GPL with contribution of Oleg Assovski,
|
||||
// www.satmania.com
|
||||
//
|
||||
// libsi is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
@ -32,12 +34,22 @@
|
||||
#define BcdTimeToSeconds(x) ((3600 * ((10*((x##_h & 0xF0)>>4)) + (x##_h & 0xF))) + \
|
||||
(60 * ((10*((x##_m & 0xF0)>>4)) + (x##_m & 0xF))) + \
|
||||
((10*((x##_s & 0xF0)>>4)) + (x##_s & 0xF)))
|
||||
#define BcdTimeToMinutes(x) ((60 * ((10*((x##_h & 0xF0)>>4)) + (x##_h & 0xF))) + \
|
||||
(((10*((x##_m & 0xF0)>>4)) + (x##_m & 0xF))))
|
||||
#define BcdCharToInt(x) (10*((x & 0xF0)>>4) + (x & 0xF))
|
||||
#define CheckBcdChar(x) ((((x & 0xF0)>>4) <= 9) && \
|
||||
((x & 0x0F) <= 9))
|
||||
#define CheckBcdSignedChar(x) ((((x & 0xF0)>>4) >= 0) && (((x & 0xF0)>>4) <= 9) && \
|
||||
((x & 0x0F) >= 0) && ((x & 0x0F) <= 9))
|
||||
|
||||
#define TableHasMoreSections(x) (((pat_t *)(x))->last_section_number > ((pat_t *)(x))->section_number)
|
||||
#define GetTableId(x) ((pat_t *)(x))->table_id
|
||||
#define GetSectionNumber(x) ((pat_t *)(x))->section_number
|
||||
#define GetLastSectionNumber(x) ((pat_t *)(x))->last_section_number
|
||||
#define GetServiceId(x) (((eit_t *)(x))->service_id_hi << 8) | ((eit_t *)(x))->service_id_lo
|
||||
#define GetSegmentLastSectionNumber(x) ((eit_t *)(x))->segment_last_section_number
|
||||
#define GetLastTableId(x) ((eit_t *)(x))->segment_last_table_id
|
||||
#define GetSectionLength(x) HILO(((pat_t *)(x))->section_length)
|
||||
|
||||
/*
|
||||
*
|
||||
@ -113,7 +125,37 @@ typedef struct {
|
||||
* applicable.
|
||||
*
|
||||
*/
|
||||
/* TO BE DONE */
|
||||
#define CAT_LEN 8
|
||||
|
||||
typedef struct {
|
||||
u_char table_id :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char section_syntax_indicator :1;
|
||||
u_char dummy :1; // has to be 0
|
||||
u_char :2;
|
||||
u_char section_length_hi :4;
|
||||
#else
|
||||
u_char section_length_hi :4;
|
||||
u_char :2;
|
||||
u_char dummy :1; // has to be 0
|
||||
u_char section_syntax_indicator :1;
|
||||
#endif
|
||||
u_char section_length_lo :8;
|
||||
u_char reserved_1 :8;
|
||||
u_char reserved_2 :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char :2;
|
||||
u_char version_number :5;
|
||||
u_char current_next_indicator :1;
|
||||
#else
|
||||
u_char current_next_indicator :1;
|
||||
u_char version_number :5;
|
||||
u_char :2;
|
||||
#endif
|
||||
u_char section_number :8;
|
||||
u_char last_section_number :8;
|
||||
} cat_t;
|
||||
|
||||
/*
|
||||
*
|
||||
* 3) Program Map Table (PMT):
|
||||
@ -297,7 +339,7 @@ typedef struct {
|
||||
* bouquet.
|
||||
*
|
||||
*/
|
||||
/* TO BE DONE */
|
||||
/* SEE NIT (It has the same structure but has different allowed descriptors) */
|
||||
/*
|
||||
*
|
||||
* 2) Service Description Table (SDT):
|
||||
@ -339,6 +381,9 @@ typedef struct {
|
||||
u_char :8;
|
||||
} sdt_t;
|
||||
|
||||
#define GetSDTTransportStreamId(x) (HILO(((sdt_t *) x)->transport_stream_id))
|
||||
#define GetSDTOriginalNetworkId(x) (HILO(((sdt_t *) x)->original_network_id))
|
||||
|
||||
#define SDT_DESCR_LEN 5
|
||||
|
||||
typedef struct {
|
||||
@ -483,7 +528,36 @@ typedef struct {
|
||||
* to the frequent updating of the time information.
|
||||
*
|
||||
*/
|
||||
/* TO BE DONE */
|
||||
#define TOT_LEN 10
|
||||
|
||||
typedef struct {
|
||||
u_char table_id :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char section_syntax_indicator :1;
|
||||
u_char :3;
|
||||
u_char section_length_hi :4;
|
||||
#else
|
||||
u_char section_length_hi :4;
|
||||
u_char :3;
|
||||
u_char section_syntax_indicator :1;
|
||||
#endif
|
||||
u_char section_length_lo :8;
|
||||
u_char utc_mjd_hi :8;
|
||||
u_char utc_mjd_lo :8;
|
||||
u_char utc_time_h :8;
|
||||
u_char utc_time_m :8;
|
||||
u_char utc_time_s :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char :4;
|
||||
u_char descriptors_loop_length_hi :4;
|
||||
#else
|
||||
u_char descriptors_loop_length_hi :4;
|
||||
u_char :4;
|
||||
#endif
|
||||
u_char descriptors_loop_length_lo :8;
|
||||
} tot_t;
|
||||
|
||||
|
||||
/*
|
||||
*
|
||||
* 7) Stuffing Table (ST):
|
||||
@ -545,6 +619,25 @@ typedef struct descr_gen_struct {
|
||||
#define GetDescriptorLength(x) (((descr_gen_t *) x)->descriptor_length+DESCR_GEN_LEN)
|
||||
|
||||
|
||||
/* 0x09 ca_descriptor */
|
||||
|
||||
#define DESCR_CA_LEN 6
|
||||
typedef struct descr_ca_struct {
|
||||
u_char descriptor_tag :8;
|
||||
u_char descriptor_length :8;
|
||||
u_char CA_type_hi :8;
|
||||
u_char CA_type_lo :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char reserved :3;
|
||||
u_char CA_PID_hi :5;
|
||||
#else
|
||||
u_char CA_PID_hi :5;
|
||||
u_char reserved :3;
|
||||
#endif
|
||||
u_char CA_PID_lo :8;
|
||||
} descr_ca_t;
|
||||
#define CastCaDescriptor(x) ((descr_ca_t *)(x))
|
||||
|
||||
/* 0x0A iso_639_language_descriptor */
|
||||
|
||||
#define DESCR_ISO_639_LANGUAGE_LEN 5
|
||||
@ -560,25 +653,31 @@ typedef struct descr_iso_639_language_struct {
|
||||
|
||||
/* 0x40 network_name_descriptor */
|
||||
|
||||
#define DESCR_NETWORK_NAME_LEN XX
|
||||
#define DESCR_NETWORK_NAME_LEN 2
|
||||
typedef struct descr_network_name_struct {
|
||||
u_char descriptor_tag :8;
|
||||
u_char descriptor_length :8;
|
||||
/* TBD */
|
||||
} descr_network_name_t;
|
||||
#define CastNetworkNameDescriptor(x) ((descr_network_name_t *)(x))
|
||||
|
||||
|
||||
/* 0x41 service_list_descriptor */
|
||||
|
||||
#define DESCR_SERVICE_LIST_LEN XX
|
||||
#define DESCR_SERVICE_LIST_LEN 2
|
||||
typedef struct descr_service_list_struct {
|
||||
u_char descriptor_tag :8;
|
||||
u_char descriptor_length :8;
|
||||
/* TBD */
|
||||
} descr_service_list_t;
|
||||
#define CastServiceListDescriptor(x) ((descr_service_list_t *)(x))
|
||||
|
||||
#define DESCR_SERVICE_LIST_LOOP_LEN 3
|
||||
typedef struct descr_service_list_loop_struct {
|
||||
u_char service_id_hi :8;
|
||||
u_char service_id_lo :8;
|
||||
u_char service_type :8;
|
||||
} descr_service_list_loop_t;
|
||||
#define CastServiceListDescriptorLoop(x) ((descr_service_list_loop_t *)(x))
|
||||
|
||||
|
||||
/* 0x42 stuffing_descriptor */
|
||||
|
||||
@ -604,13 +703,13 @@ typedef struct descr_satellite_delivery_system_struct {
|
||||
u_char orbital_position1 :8;
|
||||
u_char orbital_position2 :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char modulation :5;
|
||||
u_char polarization :2;
|
||||
u_char west_east_flag :1;
|
||||
u_char polarization :2;
|
||||
u_char modulation :5;
|
||||
#else
|
||||
u_char west_east_flag :1;
|
||||
u_char polarization :2;
|
||||
u_char modulation :5;
|
||||
u_char polarization :2;
|
||||
u_char west_east_flag :1;
|
||||
#endif
|
||||
u_char symbol_rate1 :8;
|
||||
u_char symbol_rate2 :8;
|
||||
@ -964,14 +1063,39 @@ typedef struct descr_telephone_struct {
|
||||
|
||||
/* 0x58 local_time_offset_descriptor */
|
||||
|
||||
#define DESCR_LOCAL_TIME_OFFSET_LEN XX
|
||||
#define DESCR_LOCAL_TIME_OFFSET_LEN 2
|
||||
typedef struct descr_local_time_offset_struct {
|
||||
u_char descriptor_tag :8;
|
||||
u_char descriptor_length :8;
|
||||
/* TBD */
|
||||
} descr_local_time_offset_t;
|
||||
#define CastLocalTimeOffsetDescriptor(x) ((descr_local_time_offset_t *)(x))
|
||||
|
||||
#define LOCAL_TIME_OFFSET_ENTRY_LEN 15
|
||||
typedef struct local_time_offset_entry_struct {
|
||||
u_char country_code1 :8;
|
||||
u_char country_code2 :8;
|
||||
u_char country_code3 :8;
|
||||
#if BYTE_ORDER == BIG_ENDIAN
|
||||
u_char country_region_id :6;
|
||||
u_char :1;
|
||||
u_char local_time_offset_polarity :1;
|
||||
#else
|
||||
u_char local_time_offset_polarity :1;
|
||||
u_char :1;
|
||||
u_char country_region_id :6;
|
||||
#endif
|
||||
u_char local_time_offset_h :8;
|
||||
u_char local_time_offset_m :8;
|
||||
u_char time_of_change_mjd_hi :8;
|
||||
u_char time_of_change_mjd_lo :8;
|
||||
u_char time_of_change_time_h :8;
|
||||
u_char time_of_change_time_m :8;
|
||||
u_char time_of_change_time_s :8;
|
||||
u_char next_time_offset_h :8;
|
||||
u_char next_time_offset_m :8;
|
||||
} local_time_offset_entry_t ;
|
||||
#define CastLocalTimeOffsetEntry(x) ((local_time_offset_entry_t *)(x))
|
||||
|
||||
|
||||
/* 0x59 subtitling_descriptor */
|
||||
|
||||
|
@ -4,11 +4,13 @@
|
||||
/// ///
|
||||
//////////////////////////////////////////////////////////////
|
||||
|
||||
// $Revision: 1.4 $
|
||||
// $Date: 2001/10/07 10:24:46 $
|
||||
// $Revision: 1.5 $
|
||||
// $Date: 2003/02/04 18:45:35 $
|
||||
// $Author: hakenes $
|
||||
//
|
||||
// (C) 2001 Rolf Hakenes <hakenes@hippomi.de>, under the GNU GPL.
|
||||
// (C) 2001-03 Rolf Hakenes <hakenes@hippomi.de>, under the
|
||||
// GNU GPL with contribution of Oleg Assovski,
|
||||
// www.satmania.com
|
||||
//
|
||||
// libsi is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
@ -26,11 +28,13 @@
|
||||
// Boston, MA 02111-1307, USA.
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "../liblx/liblx.h"
|
||||
#include "libsi.h"
|
||||
#include "si_tables.h"
|
||||
#include "si_debug_services.h"
|
||||
|
||||
|
||||
@ -208,6 +212,8 @@ void siDebugPids (char *Prepend, struct LIST *PidList)
|
||||
printf ("%s ProgramID: %d\n", Prepend, Pid->ProgramID);
|
||||
printf ("%s PcrPid: %d\n", Prepend, Pid->PcrPID);
|
||||
printf ("%s PmtVersion: %d\n", Prepend, Pid->PmtVersion);
|
||||
sprintf (NewPrepend, "%s ", Prepend);
|
||||
siDebugDescriptors (NewPrepend, Pid->Descriptors);
|
||||
|
||||
xForeach (Pid->InfoList, PidInfo)
|
||||
{
|
||||
@ -256,6 +262,11 @@ void siDebugDescriptors (char *Prepend, struct LIST *Descriptors)
|
||||
printf ("\n");
|
||||
break;
|
||||
|
||||
case DESCR_NW_NAME:
|
||||
printf ("%sDescriptor: Network Name\n", Prepend);
|
||||
printf ("%s Name: %s\n", Prepend, xName (Descriptor));
|
||||
break;
|
||||
|
||||
case DESCR_BOUQUET_NAME:
|
||||
printf ("%sDescriptor: Bouquet Name\n", Prepend);
|
||||
printf ("%s Name: %s\n", Prepend, xName (Descriptor));
|
||||
@ -336,9 +347,35 @@ void siDebugDescriptors (char *Prepend, struct LIST *Descriptors)
|
||||
case DESCR_CA_IDENT:
|
||||
printf ("%sDescriptor: Conditional Access Identity\n", Prepend);
|
||||
{
|
||||
int j;
|
||||
int j,k;
|
||||
for (j = 0; j < ((struct CaIdentifierDescriptor *)Descriptor)->Amount; j++)
|
||||
printf ("%s SystemID: 0x%04x\n", Prepend, GetCaIdentifierID (Descriptor, j));
|
||||
{
|
||||
printf ("%s SystemID: 0x%04x", Prepend, GetCaIdentifierID (Descriptor, j));
|
||||
k = GetCaIdentifierID (Descriptor, j) >> 8;
|
||||
if (k < 0 || k > MAX_CA_IDENT) printf (" (unknown)\n");
|
||||
else printf (" (%s)\n", CaIdents[k]);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_CA:
|
||||
{
|
||||
int j,k;
|
||||
|
||||
printf ("%sDescriptor: Conditional Access\n", Prepend);
|
||||
printf ("%s CA type: 0x%04x", Prepend, (((struct CaDescriptor *)Descriptor)->CA_type));
|
||||
k = (((struct CaDescriptor *)Descriptor)->CA_type) >> 8;
|
||||
if (k < 0 || k > MAX_CA_IDENT) printf (" (unknown)\n");
|
||||
else printf (" (%s)\n", CaIdents[k]);
|
||||
printf ("%s CA PID: %d\n", Prepend, (((struct CaDescriptor *)Descriptor)->CA_PID));
|
||||
printf ("%s ProviderID: 0x%04X\n", Prepend, (((struct CaDescriptor *)Descriptor)->ProviderID));
|
||||
if (((struct CaDescriptor *)Descriptor)->DataLength > 0)
|
||||
{
|
||||
printf ("%s CA data:", Prepend);
|
||||
for (j = 0; j < ((struct CaDescriptor *)Descriptor)->DataLength; j++)
|
||||
printf (" 0x%02x", GetCaData (Descriptor, j));
|
||||
printf ("\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
@ -489,16 +526,57 @@ void siDebugDescriptors (char *Prepend, struct LIST *Descriptors)
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_NW_NAME:
|
||||
case DESCR_SERVICE_LIST:
|
||||
case DESCR_STUFFING:
|
||||
case DESCR_SAT_DEL_SYS:
|
||||
{
|
||||
struct SatelliteDeliverySystemDescriptor *sds =
|
||||
(struct SatelliteDeliverySystemDescriptor *)Descriptor;
|
||||
|
||||
printf ("%sDescriptor: Satellite Delivery System\n", Prepend);
|
||||
printf ("%s Frequency: %ld\n", Prepend, sds->Frequency);
|
||||
printf ("%s OrbitalPosition: %d\n", Prepend, sds->OrbitalPosition);
|
||||
printf ("%s Polarization: %c\n", Prepend, sds->Polarization);
|
||||
printf ("%s SymbolRate: %ld\n", Prepend, sds->SymbolRate);
|
||||
printf ("%s FEC: %c\n", Prepend, sds->FEC);
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_SERVICE_LIST:
|
||||
{
|
||||
struct ServiceListEntry *Entry;
|
||||
|
||||
printf ("%sDescriptor: Service List\n", Prepend);
|
||||
xForeach (((struct ServiceListDescriptor *)Descriptor)->ServiceList, Entry)
|
||||
{
|
||||
printf ("%s Entry:\n");
|
||||
printf ("%s ServiceID: %d\n", Prepend, Entry->ServiceID);
|
||||
printf ("%s ServiceType: %04x\n", Prepend, Entry->ServiceType);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_LOCAL_TIME_OFF:
|
||||
{
|
||||
struct LocalTimeOffsetEntry *Offset;
|
||||
|
||||
printf ("%sDescriptor: Local Time Offset\n", Prepend);
|
||||
xForeach (((struct LocalTimeOffsetDescriptor *)Descriptor)->LocalTimeOffsets, Offset)
|
||||
{
|
||||
printf ("%s Offset:\n");
|
||||
printf ("%s CountryCode: %s\n", Offset->CountryCode);
|
||||
printf ("%s RegionID: %c\n", Offset->RegionID);
|
||||
printf ("%s CurrentOffset: %ld\n", Offset->CurrentOffset);
|
||||
printf ("%s ChangeTime: %ld\n", Offset->ChangeTime);
|
||||
printf ("%s NextOffset: %ld\n", Offset->NextOffset);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_STUFFING:
|
||||
case DESCR_CABLE_DEL_SYS:
|
||||
case DESCR_VBI_DATA:
|
||||
case DESCR_VBI_TELETEXT:
|
||||
case DESCR_MOSAIC:
|
||||
case DESCR_TELEPHONE:
|
||||
case DESCR_LOCAL_TIME_OFF:
|
||||
case DESCR_TERR_DEL_SYS:
|
||||
case DESCR_ML_NW_NAME:
|
||||
case DESCR_ML_BQ_NAME:
|
||||
@ -527,3 +605,39 @@ void siDebugDescriptors (char *Prepend, struct LIST *Descriptors)
|
||||
return;
|
||||
}
|
||||
|
||||
void siDumpDescriptor (void * Descriptor)
|
||||
{
|
||||
int Length, i;
|
||||
unsigned char *ptr;
|
||||
|
||||
Length = GetDescriptorLength (Descriptor);
|
||||
for (i = 0, ptr = (char*) Descriptor; i < Length; i++) {
|
||||
if ((i % 8) == 0)
|
||||
printf ("\n");
|
||||
printf ("0x%02X ", (unsigned int) ptr[i]);
|
||||
}
|
||||
printf ( "\n");
|
||||
}
|
||||
|
||||
void siDumpSection (void *Section)
|
||||
{
|
||||
int Length, i;
|
||||
unsigned char *ptr;
|
||||
char str[9];
|
||||
|
||||
Length = GetSectionLength (Section) + 3;
|
||||
for (i = 0, ptr = (unsigned char*) Section, memset (str, 0, 9); i < Length; i++) {
|
||||
if ((i % 8) == 0)
|
||||
{
|
||||
printf (" %s\n", str);
|
||||
memset (str, 0, 8);
|
||||
}
|
||||
printf ("0x%02X ", (unsigned int) ptr[i]);
|
||||
if (ptr[i] < 0x20 || (ptr[i] > 'z' && ptr[i] < ((unsigned char )'À')) )
|
||||
str[i % 8] = '.';
|
||||
else
|
||||
str[i % 8] = ptr[i];
|
||||
}
|
||||
printf (" %*s\n", (8 - ((abs(i - 1) % 8) ? (abs(i - 1) % 8) : 8)) * 5, str);
|
||||
}
|
||||
|
||||
|
@ -4,8 +4,8 @@
|
||||
/// ///
|
||||
//////////////////////////////////////////////////////////////
|
||||
|
||||
// $Revision: 1.1 $
|
||||
// $Date: 2001/08/15 10:00:00 $
|
||||
// $Revision: 1.2 $
|
||||
// $Date: 2003/04/12 11:27:31 $
|
||||
// $Author: hakenes $
|
||||
//
|
||||
// (C) 2001 Rolf Hakenes <hakenes@hippomi.de>, under the GNU GPL.
|
||||
@ -197,7 +197,7 @@ static struct content_type ContentTypes[] = {
|
||||
};
|
||||
#define CONTENT_TYPE_NUMBER 79
|
||||
|
||||
static char StreamTypes[][70] = {
|
||||
static char *StreamTypes[] = {
|
||||
"ITU-T|ISO/IEC Reserved",
|
||||
"ISO/IEC Video",
|
||||
"13818-2 Video or 11172-2 constrained parameter video stream",
|
||||
@ -215,3 +215,31 @@ static char StreamTypes[][70] = {
|
||||
"ITU-T Rec. H.222.0 | ISO 13818-1 Reserved",
|
||||
"User private"
|
||||
};
|
||||
|
||||
static char *CaIdents[] = {
|
||||
"Standardized systems",
|
||||
"Canal Plus",
|
||||
"CCETT",
|
||||
"Deutsche Telecom",
|
||||
"Eurodec",
|
||||
"France Telecom",
|
||||
"Irdeto",
|
||||
"Jerrold/GI",
|
||||
"Matra Communication",
|
||||
"News Datacom",
|
||||
"Nokia",
|
||||
"Norwegian Telekom",
|
||||
"NTL",
|
||||
"Philips",
|
||||
"Scientific Atlanta",
|
||||
"Sony",
|
||||
"Tandberg Television",
|
||||
"Thomson",
|
||||
"TV/Com",
|
||||
"HPT - Croatian Post and Telecommunications",
|
||||
"HRT - Croatian Radio and Television",
|
||||
"IBM",
|
||||
"Nera",
|
||||
"BetaTechnik"
|
||||
};
|
||||
#define MAX_CA_IDENT 24
|
||||
|
@ -4,11 +4,13 @@
|
||||
/// ///
|
||||
//////////////////////////////////////////////////////////////
|
||||
|
||||
// $Revision: 1.6 $
|
||||
// $Date: 2002/01/30 17:04:13 $
|
||||
// $Revision: 1.8 $
|
||||
// $Date: 2003/02/04 18:45:35 $
|
||||
// $Author: hakenes $
|
||||
//
|
||||
// (C) 2001 Rolf Hakenes <hakenes@hippomi.de>, under the GNU GPL.
|
||||
// (C) 2001-03 Rolf Hakenes <hakenes@hippomi.de>, under the
|
||||
// GNU GPL with contribution of Oleg Assovski,
|
||||
// www.satmania.com
|
||||
//
|
||||
// libsi is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
@ -83,6 +85,43 @@ struct LIST *siParsePAT (u_char *Buffer)
|
||||
}
|
||||
|
||||
|
||||
struct LIST *siParseCAT (u_char *Buffer)
|
||||
{
|
||||
cat_t *Cat;
|
||||
u_char *Ptr;
|
||||
int SectionLength;
|
||||
int TransportStreamID;
|
||||
int CatVersion;
|
||||
struct Descriptor *Descriptor;
|
||||
struct LIST *DescriptorList = NULL;
|
||||
|
||||
if (!Buffer) return NULL;
|
||||
|
||||
Cat = (cat_t *) Buffer; Ptr = Buffer;
|
||||
|
||||
if (Cat->table_id != TID_CAT) {
|
||||
// fprintf (stderr, "CAT: wrong TID %d\n", Cat->table_id);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
SectionLength = HILO (Cat->section_length) + 3 - CAT_LEN - 4;
|
||||
|
||||
if (crc32 (Ptr, HILO (Cat->section_length) + 3)) return (NULL);
|
||||
|
||||
CatVersion = Cat->version_number;
|
||||
|
||||
Ptr += CAT_LEN;
|
||||
|
||||
if (SectionLength >= 0)
|
||||
{
|
||||
DescriptorList = xNewList (NULL);
|
||||
siParseDescriptors (DescriptorList, Ptr, SectionLength, Cat->table_id);
|
||||
}
|
||||
|
||||
return (DescriptorList);
|
||||
}
|
||||
|
||||
|
||||
struct Pid *siParsePMT (u_char *Buffer)
|
||||
{
|
||||
pmt_t *Pmt;
|
||||
@ -147,6 +186,89 @@ struct Pid *siParsePMT (u_char *Buffer)
|
||||
}
|
||||
|
||||
|
||||
struct LIST *siParseNIT (u_char *Buffer)
|
||||
{
|
||||
nit_t *Nit;
|
||||
nit_mid_t *NitMid;
|
||||
nit_ts_t *TSDesc;
|
||||
u_char *Ptr;
|
||||
int SectionLength, LoopLength, Loop2Length;
|
||||
int TransportStreamID;
|
||||
int NitVersion;
|
||||
int NetworkID;
|
||||
struct TransportStream *TransportStream;
|
||||
struct LIST *TSList = NULL;
|
||||
struct LIST *Networks;
|
||||
struct NetworkInfo *Network;
|
||||
|
||||
if (!Buffer) return NULL;
|
||||
|
||||
Nit = (nit_t *) Buffer;
|
||||
Ptr = Buffer;
|
||||
|
||||
if (Nit->table_id != TID_NIT_ACT && Nit->table_id != TID_NIT_OTH && Nit->table_id != TID_BAT) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
SectionLength = HILO (Nit->section_length) + 3 - NIT_LEN - 4;
|
||||
|
||||
if (crc32 (Ptr, HILO (Nit->section_length) + 3)) return (NULL);
|
||||
|
||||
NitVersion = Nit->version_number;
|
||||
NetworkID = HILO (Nit->network_id);
|
||||
if (NetworkID == 65535)
|
||||
NetworkID = 0;
|
||||
CreateNetworkInfo (Network, NetworkID);
|
||||
Networks = xNewList (NULL);
|
||||
xAddTail (Networks, Network);
|
||||
|
||||
Ptr += NIT_LEN;
|
||||
|
||||
LoopLength = HILO (Nit->network_descriptor_length);
|
||||
// fprintf (stderr, "table 0x%X, SectionLen = %d, LoopLen = %d\n",
|
||||
// Nit->table_id, SectionLength, LoopLength);
|
||||
if (LoopLength > SectionLength - SDT_DESCR_LEN)
|
||||
return (Networks);
|
||||
|
||||
if (LoopLength <= SectionLength) {
|
||||
if (SectionLength >= 0) siParseDescriptors (Network->Descriptors, Ptr, LoopLength, Nit->table_id);
|
||||
SectionLength -= LoopLength;
|
||||
Ptr += LoopLength;
|
||||
NitMid = (nit_mid_t *) Ptr;
|
||||
LoopLength = HILO (NitMid->transport_stream_loop_length);
|
||||
// fprintf (stderr, "table 0x%X, TS LoopLen = %d\n",
|
||||
// Nit->table_id, LoopLength);
|
||||
if ((SectionLength > 0) && (LoopLength <= SectionLength)) {
|
||||
SectionLength -= SIZE_NIT_MID;
|
||||
Ptr += SIZE_NIT_MID;
|
||||
while (LoopLength > 0) {
|
||||
TSDesc = (nit_ts_t *) Ptr;
|
||||
CreateTransportStream (TransportStream, HILO(TSDesc->transport_stream_id), HILO(TSDesc->original_network_id));
|
||||
if (TransportStream->TransportStreamID == 65535)
|
||||
TransportStream->TransportStreamID = 0;
|
||||
if (TransportStream->OriginalNetworkID == 65535)
|
||||
TransportStream->OriginalNetworkID = 0;
|
||||
Loop2Length = HILO (TSDesc->transport_descriptors_length);
|
||||
// fprintf (stderr, "table 0x%X, TSdesc LoopLen = %d\n",
|
||||
// Nit->table_id, Loop2Length);
|
||||
Ptr += NIT_TS_LEN;
|
||||
if (Loop2Length <= LoopLength) {
|
||||
if (LoopLength >= 0) siParseDescriptors (TransportStream->Descriptors, Ptr, Loop2Length, Nit->table_id);
|
||||
}
|
||||
if (!Network->TransportStreams)
|
||||
Network->TransportStreams = xNewList (NULL);
|
||||
xAddTail (Network->TransportStreams, TransportStream);
|
||||
LoopLength -= Loop2Length + NIT_TS_LEN;
|
||||
SectionLength -= Loop2Length + NIT_TS_LEN;
|
||||
Ptr += Loop2Length;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return (Networks);
|
||||
}
|
||||
|
||||
|
||||
struct LIST *siParseSDT (u_char *Buffer)
|
||||
{
|
||||
sdt_t *Sdt;
|
||||
@ -344,6 +466,44 @@ time_t siParseTDT (u_char *Buffer)
|
||||
}
|
||||
|
||||
|
||||
struct Tot *siParseTOT (u_char *Buffer)
|
||||
{
|
||||
tot_t *Tot;
|
||||
u_char *Ptr;
|
||||
int SectionLength, LoopLength;
|
||||
struct Tot *table;
|
||||
time_t CurrentTime;
|
||||
|
||||
if (!Buffer) return NULL;
|
||||
|
||||
Tot = (tot_t *) Buffer;
|
||||
Ptr = Buffer;
|
||||
|
||||
if (Tot->table_id != TID_TOT) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (crc32 (Ptr, HILO (Tot->section_length) + 3)) return (NULL);
|
||||
// SectionLength = HILO (Tot->section_length) + 3 - TOT_LEN - 4;
|
||||
|
||||
CurrentTime = MjdToEpochTime (Tot->utc_mjd) +
|
||||
BcdTimeToSeconds (Tot->utc_time);
|
||||
LoopLength = HILO (Tot->descriptors_loop_length);
|
||||
if (!LoopLength)
|
||||
return NULL;
|
||||
|
||||
CreateTot (table, CurrentTime);
|
||||
|
||||
Ptr += TOT_LEN;
|
||||
|
||||
siParseDescriptors (table->Descriptors, Ptr, LoopLength, Tot->table_id);
|
||||
|
||||
// fprintf (stderr, "TOT Bias: %d\n", table->Bias);
|
||||
return (table);
|
||||
}
|
||||
|
||||
static u_char TempTableID = 0;
|
||||
|
||||
void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
int Length, u_char TableID)
|
||||
{
|
||||
@ -352,6 +512,7 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
|
||||
DescriptorLength = 0;
|
||||
Ptr = Buffer;
|
||||
TempTableID = TableID;
|
||||
|
||||
while (DescriptorLength < Length)
|
||||
{
|
||||
@ -362,15 +523,17 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
case TID_NIT_ACT: case TID_NIT_OTH:
|
||||
switch (GetDescriptorTag(Ptr))
|
||||
{
|
||||
case DESCR_NW_NAME:
|
||||
case DESCR_SERVICE_LIST:
|
||||
case DESCR_STUFFING:
|
||||
case DESCR_SAT_DEL_SYS:
|
||||
case DESCR_CABLE_DEL_SYS:
|
||||
case DESCR_SERVICE_LIST:
|
||||
case DESCR_PRIV_DATA_SPEC:
|
||||
// fprintf (stderr, "Got descriptor with tag = 0x%X\n", GetDescriptorTag(Ptr));
|
||||
// siDumpDescriptor (Ptr);
|
||||
case DESCR_NW_NAME:
|
||||
case DESCR_STUFFING:
|
||||
case DESCR_LINKAGE:
|
||||
case DESCR_TERR_DEL_SYS:
|
||||
case DESCR_ML_NW_NAME:
|
||||
case DESCR_PRIV_DATA_SPEC:
|
||||
case DESCR_CELL_LIST:
|
||||
case DESCR_CELL_FREQ_LINK:
|
||||
case DESCR_ANNOUNCEMENT_SUPPORT:
|
||||
@ -378,8 +541,7 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
break;
|
||||
|
||||
default:
|
||||
/* fprintf (stderr, "forbidden descriptor 0x%x in NIT\n",
|
||||
GetDescriptorTag(Ptr));*/
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in NIT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -396,12 +558,12 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
case DESCR_CA_IDENT:
|
||||
case DESCR_ML_BQ_NAME:
|
||||
case DESCR_PRIV_DATA_SPEC:
|
||||
// fprintf (stderr, "Got descriptor with tag = 0x%X\n", GetDescriptorTag(Ptr));
|
||||
siParseDescriptor (Descriptors, Ptr);
|
||||
break;
|
||||
|
||||
default:
|
||||
/*fprintf (stderr, "forbidden descriptor 0x%x in BAT\n",
|
||||
GetDescriptorTag(Ptr));*/
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in BAT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -426,8 +588,7 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
break;
|
||||
|
||||
default:
|
||||
/* fprintf (stderr, "forbidden descriptor 0x%x in SDT\n",
|
||||
GetDescriptorTag(Ptr)); */
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in SDT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -470,8 +631,7 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
break;
|
||||
|
||||
default:
|
||||
/*fprintf (stderr, "forbidden descriptor 0x%x in EIT\n",
|
||||
GetDescriptorTag(Ptr));*/
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in EIT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -484,8 +644,7 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
break;
|
||||
|
||||
default:
|
||||
/*fprintf (stderr, "forbidden descriptor 0x%x in TOT\n",
|
||||
GetDescriptorTag(Ptr));*/
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in TOT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@ -522,15 +681,28 @@ void siParseDescriptors (struct LIST *Descriptors, u_char *Buffer,
|
||||
break;
|
||||
|
||||
default:
|
||||
/* fprintf (stderr, "forbidden descriptor 0x%x in PMT\n",
|
||||
GetDescriptorTag(Ptr)); */
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in PMT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
case TID_CAT:
|
||||
switch (GetDescriptorTag(Ptr))
|
||||
{
|
||||
case DESCR_CA_SYSTEM:
|
||||
case DESCR_CA:
|
||||
case DESCR_CA_IDENT:
|
||||
siParseDescriptor (Descriptors, Ptr);
|
||||
break;
|
||||
|
||||
default:
|
||||
// fprintf (stderr, "forbidden descriptor 0x%x in CAT\n", GetDescriptorTag(Ptr));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
fprintf (stderr, "descriptor 0x%x in unsupported table 0x%x\n",
|
||||
GetDescriptorTag(Ptr), TableID);
|
||||
// fprintf (stderr, "descriptor 0x%x in unsupported table 0x%x\n", GetDescriptorTag(Ptr), TableID);
|
||||
break;
|
||||
}
|
||||
DescriptorLength += GetDescriptorLength (Ptr);
|
||||
@ -550,6 +722,7 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
if (!Descriptors || !Buffer) return;
|
||||
|
||||
Ptr = Buffer;
|
||||
// fprintf (stderr, "Got descriptor with tag = 0x%X\n", GetDescriptorTag(Buffer));
|
||||
|
||||
switch (GetDescriptorTag(Buffer))
|
||||
{
|
||||
@ -558,10 +731,12 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
CastAncillaryDataDescriptor(Buffer)->ancillary_data_identifier);
|
||||
break;
|
||||
|
||||
case DESCR_NW_NAME:
|
||||
case DESCR_BOUQUET_NAME:
|
||||
Text = siGetDescriptorText (Buffer + DESCR_BOUQUET_NAME_LEN,
|
||||
Text = siGetDescriptorName (Buffer + DESCR_BOUQUET_NAME_LEN,
|
||||
GetDescriptorLength (Buffer) - DESCR_BOUQUET_NAME_LEN);
|
||||
CreateBouquetNameDescriptor (Descriptor, Text);
|
||||
// fprintf (stderr, "Got descriptor with tag = 0x%X, text = '%s'\n", GetDescriptorTag(Buffer), Text);
|
||||
CreateBouquetNameDescriptor (Descriptor, Text, GetDescriptorTag(Buffer));
|
||||
break;
|
||||
|
||||
case DESCR_COMPONENT:
|
||||
@ -577,9 +752,9 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
break;
|
||||
|
||||
case DESCR_SERVICE:
|
||||
Text = siGetDescriptorText (Buffer + DESCR_SERVICE_LEN,
|
||||
Text = siGetDescriptorName (Buffer + DESCR_SERVICE_LEN,
|
||||
CastServiceDescriptor(Buffer)->provider_name_length);
|
||||
Text2 = siGetDescriptorText (Buffer + DESCR_SERVICE_LEN +
|
||||
Text2 = siGetDescriptorName (Buffer + DESCR_SERVICE_LEN +
|
||||
CastServiceDescriptor(Buffer)->provider_name_length + 1,
|
||||
*((u_char *)(Buffer + DESCR_SERVICE_LEN +
|
||||
CastServiceDescriptor(Buffer)->provider_name_length)));
|
||||
@ -598,7 +773,7 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
break;
|
||||
|
||||
case DESCR_SHORT_EVENT:
|
||||
Text = siGetDescriptorText (Buffer + DESCR_SHORT_EVENT_LEN,
|
||||
Text = siGetDescriptorName (Buffer + DESCR_SHORT_EVENT_LEN,
|
||||
CastShortEventDescriptor(Buffer)->event_name_length);
|
||||
Text2 = siGetDescriptorText (Buffer + DESCR_SHORT_EVENT_LEN +
|
||||
CastShortEventDescriptor(Buffer)->event_name_length + 1,
|
||||
@ -623,6 +798,7 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
CastExtendedEventDescriptor(Buffer)->lang_code3, Text);
|
||||
Length = CastExtendedEventDescriptor(Buffer)->length_of_items;
|
||||
Ptr += DESCR_EXTENDED_EVENT_LEN;
|
||||
// printf ("EEDesc #%d, %s\n", CastExtendedEventDescriptor(Buffer)->descriptor_number, Text);
|
||||
while ((Length > 0) && (Length < GetDescriptorLength (Buffer)))
|
||||
{
|
||||
Text = siGetDescriptorText (Ptr + ITEM_EXTENDED_EVENT_LEN,
|
||||
@ -631,6 +807,7 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
CastExtendedEventItem(Ptr)->item_description_length + 1,
|
||||
*((u_char *)(Ptr + ITEM_EXTENDED_EVENT_LEN +
|
||||
CastExtendedEventItem(Ptr)->item_description_length)));
|
||||
// printf ("EEItem #%d, %s, %s\n", CastExtendedEventDescriptor(Buffer)->descriptor_number, Text, Text2);
|
||||
AddExtendedEventItem (Descriptor, Text2, Text);
|
||||
Length -= ITEM_EXTENDED_EVENT_LEN + CastExtendedEventItem(Ptr)->item_description_length +
|
||||
*((u_char *)(Ptr + ITEM_EXTENDED_EVENT_LEN +
|
||||
@ -642,15 +819,85 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
break;
|
||||
|
||||
case DESCR_CA_IDENT:
|
||||
CreateCaIdentifierDescriptor (Descriptor,
|
||||
(GetDescriptorLength(Buffer) - DESCR_CA_IDENTIFIER_LEN) / 2);
|
||||
Length = GetDescriptorLength (Buffer) - DESCR_CA_IDENTIFIER_LEN;
|
||||
CreateCaIdentifierDescriptor (Descriptor, Length / 2);
|
||||
Ptr += DESCR_CA_IDENTIFIER_LEN; i = 0;
|
||||
while (Length > 0)
|
||||
{ SetCaIdentifierID(Descriptor, i, *((u_short *) Ptr));
|
||||
{ SetCaIdentifierID(Descriptor, i, ((*((u_char *) Ptr)<<8) + *((u_char *) (Ptr+1))));
|
||||
Length -= 2; Ptr += 2; i++; }
|
||||
break;
|
||||
|
||||
case DESCR_CA:
|
||||
{
|
||||
struct CaDescriptor *CD;
|
||||
|
||||
Length = GetDescriptorLength (Buffer) - DESCR_CA_LEN;
|
||||
CreateCaDescriptor (Descriptor,
|
||||
HILO(CastCaDescriptor(Buffer)->CA_type),
|
||||
HILO(CastCaDescriptor(Buffer)->CA_PID), Length);
|
||||
Ptr += DESCR_CA_LEN; i = 0;
|
||||
while (Length > 0)
|
||||
{ SetCaData(Descriptor, i, *Ptr);
|
||||
Length --; Ptr ++; i++; }
|
||||
|
||||
/*
|
||||
* The following analyses are more or less directly copied from
|
||||
* MultiDec 8.4b Sources. Thanx to Espresso for his great work !!
|
||||
*/
|
||||
CD = (struct CaDescriptor *) Descriptor;
|
||||
|
||||
// fprintf (stderr, "TableID: %02x - CA - Type: 0x%04x, PID: %d\n", TempTableID, CD->CA_type, CD->CA_PID);
|
||||
|
||||
if ((CD->CA_type >> 8) == 0x01) /* SECA */
|
||||
{
|
||||
CD->ProviderID = (GetCaData (CD, 0) << 8) | GetCaData (CD, 1);
|
||||
}
|
||||
else if ((CD->CA_type >> 8) == 0x05) /* Viaccess ? (France Telecom) */
|
||||
{
|
||||
i=0;
|
||||
while (i < CD->DataLength)
|
||||
{
|
||||
if ((GetCaData (CD, i) == 0x14) && (GetCaData (CD, i+1) == 0x03))
|
||||
{
|
||||
CD->ProviderID = (GetCaData (CD, i+2) << 16) |
|
||||
(GetCaData (CD, i+3) << 8) |
|
||||
(GetCaData (CD, i+4) & 0xf0);
|
||||
i = CD->DataLength;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
}
|
||||
if (CD->CA_type==0x0100) /* SECA 1 */
|
||||
{
|
||||
/* bptr=MyPtr+19;
|
||||
|
||||
i=19;
|
||||
while ( i+4 < ca_info->len ) {
|
||||
if ( (*bptr&0xE0) == 0xE0 ) {
|
||||
CA_ECM=(( *bptr&0x1f)<<8)+*(bptr+1);
|
||||
Prov_Ident = ( *(bptr+2)<<8) | *(bptr+3);
|
||||
j=0;
|
||||
while ( j < ProgrammNeu[ProgrammNummer].CA_Anzahl ) {
|
||||
if (( ProgrammNeu[ProgrammNummer].CA_System[j].CA_Typ == CA_Typ )
|
||||
&& ( ProgrammNeu[ProgrammNummer].CA_System[j].ECM == CA_ECM )) break;
|
||||
j++;
|
||||
};
|
||||
|
||||
if ( j < MAX_CA_SYSTEMS ) {
|
||||
if ( j >= ProgrammNeu[ProgrammNummer].CA_Anzahl )
|
||||
ProgrammNeu[ProgrammNummer].CA_Anzahl++;
|
||||
ProgrammNeu[ProgrammNummer].CA_System[j].CA_Typ =CA_Typ;
|
||||
ProgrammNeu[ProgrammNummer].CA_System[j].ECM =CA_ECM ;
|
||||
ProgrammNeu[ProgrammNummer].CA_System[j].Provider_Id = Prov_Ident;
|
||||
};
|
||||
}
|
||||
i+=0x0f;
|
||||
bptr+=0x0f;
|
||||
}; */
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_CONTENT:
|
||||
CreateContentDescriptor (Descriptor,
|
||||
(GetDescriptorLength(Buffer) - DESCR_CONTENT_LEN) / 2);
|
||||
@ -705,12 +952,6 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
HILO (CastTimeShiftedEventDescriptor(Ptr)->reference_event_id));
|
||||
break;
|
||||
|
||||
case DESCR_CA:
|
||||
CreateConditionalAccessDescriptor (Descriptor,
|
||||
*(Ptr + 1) + 2, // we'll need the entire raw data!
|
||||
Ptr);
|
||||
break;
|
||||
|
||||
case DESCR_ISO_639_LANGUAGE:
|
||||
CreateIso639LanguageDescriptor (Descriptor,
|
||||
CastIso639LanguageDescriptor(Buffer)->lang_code1,
|
||||
@ -789,6 +1030,80 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_SAT_DEL_SYS:
|
||||
// fprintf (stderr, "got descriptor 0x%x\n", GetDescriptorTag(Buffer));
|
||||
{
|
||||
descr_satellite_delivery_system_t *sds;
|
||||
sds = (descr_satellite_delivery_system_t *) Ptr;
|
||||
if (CheckBcdChar (sds->frequency1) && CheckBcdChar (sds->frequency2) &&
|
||||
CheckBcdChar (sds->frequency3) && CheckBcdChar (sds->frequency4) &&
|
||||
CheckBcdChar (sds->orbital_position1) &&
|
||||
CheckBcdChar (sds->orbital_position2) &&
|
||||
CheckBcdChar (sds->symbol_rate1) && CheckBcdChar (sds->symbol_rate1) &&
|
||||
CheckBcdChar (sds->symbol_rate3) && (sds->fec_inner != 0) && (sds->modulation == 1))
|
||||
{
|
||||
CreateSatelliteDeliverySystemDescriptor (Descriptor,
|
||||
BcdCharToInt (sds->frequency1) * 10 * 1000 * 1000 +
|
||||
BcdCharToInt (sds->frequency2) * 100 * 1000 +
|
||||
BcdCharToInt (sds->frequency3) * 1000 +
|
||||
BcdCharToInt (sds->frequency4) * 10,
|
||||
(sds->west_east_flag ? 1 : -1) *
|
||||
(BcdCharToInt (sds->orbital_position1) * 100 +
|
||||
BcdCharToInt (sds->orbital_position2)),
|
||||
sds->polarization,
|
||||
BcdCharToInt (sds->symbol_rate1) * 10 * 1000 +
|
||||
BcdCharToInt (sds->symbol_rate2) * 100 +
|
||||
BcdCharToInt (sds->symbol_rate3),
|
||||
sds->fec_inner);
|
||||
}
|
||||
/* else
|
||||
{
|
||||
fprintf (stderr, "Illegal sds descriptor\n");
|
||||
siDumpDescriptor (Buffer);
|
||||
} */
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_SERVICE_LIST:
|
||||
// fprintf (stderr, "got descriptor 0x%x\n", GetDescriptorTag(Buffer));
|
||||
CreateServiceListDescriptor (Descriptor);
|
||||
Length = GetDescriptorLength (Buffer) - DESCR_SERVICE_LIST_LEN;
|
||||
Ptr += DESCR_SERVICE_LIST_LEN;
|
||||
while (Length > 0)
|
||||
{
|
||||
AddServiceListEntry (Descriptor,
|
||||
HILO (CastServiceListDescriptorLoop(Ptr)->service_id),
|
||||
CastServiceListDescriptorLoop(Ptr)->service_type);
|
||||
Length -= DESCR_SERVICE_LIST_LEN;
|
||||
Ptr += DESCR_SERVICE_LIST_LEN;
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_LOCAL_TIME_OFF:
|
||||
CreateLocalTimeOffsetDescriptor (Descriptor);
|
||||
Length = GetDescriptorLength (Buffer) - DESCR_LOCAL_TIME_OFFSET_LEN;
|
||||
Ptr += DESCR_LOCAL_TIME_OFFSET_LEN;
|
||||
while (Length > 0)
|
||||
{
|
||||
time_t ct, co, no;
|
||||
ct = MjdToEpochTime (CastLocalTimeOffsetEntry(Ptr)->time_of_change_mjd) +
|
||||
BcdTimeToSeconds (CastLocalTimeOffsetEntry(Ptr)->time_of_change_time);
|
||||
co = (BcdCharToInt(CastLocalTimeOffsetEntry(Ptr)->local_time_offset_h) * 3600 +
|
||||
BcdCharToInt(CastLocalTimeOffsetEntry(Ptr)->local_time_offset_m) * 60) *
|
||||
((CastLocalTimeOffsetEntry(Ptr)->local_time_offset_polarity) ? -1 : 1);
|
||||
no = (BcdCharToInt(CastLocalTimeOffsetEntry(Ptr)->next_time_offset_h) * 3600 +
|
||||
BcdCharToInt(CastLocalTimeOffsetEntry(Ptr)->next_time_offset_m) * 60) *
|
||||
((CastLocalTimeOffsetEntry(Ptr)->local_time_offset_polarity) ? -1 : 1);
|
||||
AddLocalTimeOffsetEntry (Descriptor,
|
||||
CastLocalTimeOffsetEntry(Ptr)->country_code1,
|
||||
CastLocalTimeOffsetEntry(Ptr)->country_code2,
|
||||
CastLocalTimeOffsetEntry(Ptr)->country_code3,
|
||||
CastLocalTimeOffsetEntry(Ptr)->country_region_id, co, ct, no);
|
||||
Length -= LOCAL_TIME_OFFSET_ENTRY_LEN;
|
||||
Ptr += LOCAL_TIME_OFFSET_ENTRY_LEN;
|
||||
}
|
||||
break;
|
||||
|
||||
case DESCR_VIDEO_STREAM:
|
||||
case DESCR_AUDIO_STREAM:
|
||||
case DESCR_HIERARCHY:
|
||||
@ -804,15 +1119,11 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
case DESCR_SMOOTHING_BUFFER:
|
||||
case DESCR_STD:
|
||||
case DESCR_IBP:
|
||||
case DESCR_NW_NAME:
|
||||
case DESCR_SERVICE_LIST:
|
||||
case DESCR_SAT_DEL_SYS:
|
||||
case DESCR_CABLE_DEL_SYS:
|
||||
case DESCR_VBI_DATA:
|
||||
case DESCR_VBI_TELETEXT:
|
||||
case DESCR_MOSAIC:
|
||||
case DESCR_TELEPHONE:
|
||||
case DESCR_LOCAL_TIME_OFF:
|
||||
case DESCR_TERR_DEL_SYS:
|
||||
case DESCR_ML_NW_NAME:
|
||||
case DESCR_ML_BQ_NAME:
|
||||
@ -833,6 +1144,8 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
case DESCR_CELL_FREQ_LINK:
|
||||
case DESCR_ANNOUNCEMENT_SUPPORT:
|
||||
default:
|
||||
// fprintf (stderr, "Unsupported descriptor with tag = 0x%02X\n", GetDescriptorTag(Ptr));
|
||||
// siDumpDescriptor (Buffer);
|
||||
/* fprintf (stderr, "unsupported descriptor 0x%x\n",
|
||||
GetDescriptorTag(Buffer)); */
|
||||
break;
|
||||
@ -845,14 +1158,19 @@ void siParseDescriptor (struct LIST *Descriptors, u_char *Buffer)
|
||||
/*
|
||||
* ToDo: ETSI conformal text definition
|
||||
*/
|
||||
char *siGetDescriptorText (u_char *Buffer, int Length)
|
||||
#define GDT_TEXT_DESCRIPTOR 0
|
||||
#define GDT_NAME_DESCRIPTOR 1
|
||||
char *siGetDescriptorTextHandler (u_char *, int , int );
|
||||
|
||||
char *siGetDescriptorTextHandler (u_char *Buffer, int Length, int type)
|
||||
{
|
||||
char *tmp, *result;
|
||||
int i;
|
||||
|
||||
if ((Length < 0) || (Length > 4095))
|
||||
return (xSetText ("text error"));
|
||||
if (*Buffer == 0x05 || (*Buffer >= 0x20 && *Buffer <= 0xff))
|
||||
/* ASSENIZATION: removing coding detection - suppose they are all ANSI */
|
||||
// if (*Buffer == 0x05 || (*Buffer >= 0x20 && *Buffer <= 0xff))
|
||||
{
|
||||
xMemAlloc (Length+1, &result);
|
||||
tmp = result;
|
||||
@ -860,15 +1178,16 @@ char *siGetDescriptorText (u_char *Buffer, int Length)
|
||||
{
|
||||
if (*Buffer == 0) break;
|
||||
|
||||
if ((*Buffer >= ' ' && *Buffer <= '~') ||
|
||||
if ((*Buffer >= ' ' && *Buffer <= '~') || (*Buffer == '\n') ||
|
||||
(*Buffer >= 0xa0 && *Buffer <= 0xff)) *tmp++ = *Buffer;
|
||||
if (*Buffer == 0x8A || *Buffer == '\n') *tmp++ = '\n';
|
||||
if (*Buffer == 0x8A) *tmp++ = '\n';
|
||||
if (*Buffer == 0x86 || *Buffer == 0x87) *tmp++ = ' ';
|
||||
if ((*Buffer == 0x86 || *Buffer == 0x87) && !(GDT_NAME_DESCRIPTOR & type)) *tmp++ = ' ';
|
||||
Buffer++;
|
||||
}
|
||||
*tmp = '\0';
|
||||
}
|
||||
else
|
||||
/* else
|
||||
{
|
||||
switch (*Buffer)
|
||||
{
|
||||
@ -881,11 +1200,22 @@ char *siGetDescriptorText (u_char *Buffer, int Length)
|
||||
case 0x12: result = xSetText ("Coding according to KSC 5601"); break;
|
||||
default: result = xSetText ("Unknown coding"); break;
|
||||
}
|
||||
}
|
||||
} */
|
||||
|
||||
return (result);
|
||||
}
|
||||
|
||||
char *siGetDescriptorText (u_char *Buffer, int Length)
|
||||
{
|
||||
return siGetDescriptorTextHandler (Buffer, Length, GDT_TEXT_DESCRIPTOR);
|
||||
}
|
||||
|
||||
char *siGetDescriptorName (u_char *Buffer, int Length)
|
||||
{
|
||||
return siGetDescriptorTextHandler (Buffer, Length, GDT_NAME_DESCRIPTOR);
|
||||
}
|
||||
|
||||
|
||||
// CRC32 lookup table for polynomial 0x04c11db7
|
||||
|
||||
static u_long crc_table[256] = {
|
||||
|
Loading…
Reference in New Issue
Block a user