src/eitd/SIevents.cpp: add back old event parse code

This commit is contained in:
[CST] Focus
2012-05-21 14:33:38 +04:00
parent 0fe0923457
commit f11cea68e7
2 changed files with 268 additions and 1 deletions

View File

@@ -43,6 +43,36 @@
const std::string languangeOFF = "OFF";
struct descr_generic_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
} __attribute__ ((packed)) ;
struct descr_short_event_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
unsigned language_code_hi : 8;
unsigned language_code_mid : 8;
unsigned language_code_lo : 8;
unsigned event_name_length : 8;
} __attribute__ ((packed)) ;
struct descr_extended_event_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
unsigned descriptor_number : 4;
unsigned last_descriptor_number : 4;
unsigned iso_639_2_language_code_hi : 8;
unsigned iso_639_2_language_code_mid : 8;
unsigned iso_639_2_language_code_lo : 8;
unsigned length_of_items : 8;
} __attribute__ ((packed)) ;
inline unsigned min(unsigned a, unsigned b)
{
return b < a ? b : a;
}
SIevent::SIevent(const t_original_network_id _original_network_id, const t_transport_stream_id _transport_stream_id, const t_service_id _service_id,
const unsigned short _event_id)
{
@@ -55,6 +85,29 @@ SIevent::SIevent(const t_original_network_id _original_network_id, const t_trans
running = 0;
}
SIevent::SIevent(const struct eit_event *e)
{
eventID = (e->event_id_hi << 8) | e->event_id_lo;
time_t start_time = changeUTCtoCtime(((const unsigned char *)e) + 2);
unsigned long duration = 0;
if (!((e->duration_hi == 0xff) && (e->duration_mid == 0xff) && (e->duration_lo == 0xff)))
duration = ((e->duration_hi)>>4)*10*3600L + ((e->duration_hi)&0x0f)*3600L +
((e->duration_mid)>>4)*10*60L + ((e->duration_mid)&0x0f)*60L +
((e->duration_lo)>>4)*10 + ((e->duration_lo)&0x0f);
if (start_time && duration)
times.insert(SItime(start_time, duration));
running = (int)e->running_status;
table_id = 0xFF; /* not set */
version = 0xFF;
service_id = 0;
original_network_id = 0;
transport_stream_id = 0;
}
void SIevent::parse(Event &event)
{
int tsidonid = (transport_stream_id << 16) | original_network_id;
@@ -150,6 +203,132 @@ void SIevent::parse(Event &event)
}
}
void SIevent::parseDescriptors(const uint8_t *des, unsigned len)
{
struct descr_generic_header *desc;
/* we pass the buffer including the eit_event header, so we have to
* skip it here... */
des += sizeof(struct eit_event);
len -= sizeof(struct eit_event);
while(len>=sizeof(struct descr_generic_header)) {
desc=(struct descr_generic_header *)des;
/*printf("Type: %s\n", decode_descr(desc->descriptor_tag)); */
if(desc->descriptor_tag==0x4D)
parseShortEventDescriptor((const uint8_t *)desc, len);
else if(desc->descriptor_tag==0x4E)
parseExtendedEventDescriptor((const uint8_t *)desc, len);
else if(desc->descriptor_tag==0x54)
parseContentDescriptor((const uint8_t *)desc, len);
else if(desc->descriptor_tag==0x50)
parseComponentDescriptor((const uint8_t *)desc, len);
else if(desc->descriptor_tag==0x55)
parseParentalRatingDescriptor((const uint8_t *)desc, len);
else if(desc->descriptor_tag==0x4A) {
parseLinkageDescriptor((const uint8_t *)desc, len);
}
#if 0
else if(desc->descriptor_tag==0x69)
parsePDCDescriptor((const char *)desc, e, len);
#endif
if((unsigned)(desc->descriptor_length+2)>len)
break;
len-=desc->descriptor_length+2;
des+=desc->descriptor_length+2;
}
}
void SIevent::parseShortEventDescriptor(const uint8_t *buf, unsigned maxlen)
{
struct descr_short_event_header *evt=(struct descr_short_event_header *)buf;
if((evt->descriptor_length+sizeof(descr_generic_header) > maxlen) ||
(evt->descriptor_length<sizeof(struct descr_short_event_header)-sizeof(descr_generic_header)))
return;
int tsidonid = (transport_stream_id << 16) | original_network_id;
char lang[] = {tolower(evt->language_code_hi), tolower(evt->language_code_mid), tolower(evt->language_code_lo), '\0'};
std::string language(lang);
int table = getCountryCodeDefaultMapping(language);
buf+=sizeof(struct descr_short_event_header);
if(evt->event_name_length)
setName(language, convertDVBUTF8((const char*) buf, evt->event_name_length, table, tsidonid));
buf+=evt->event_name_length;
unsigned char textlength=*((unsigned char *)buf);
if(textlength > 2)
setText(language, convertDVBUTF8((const char*) (++buf), textlength, table, tsidonid));
}
void SIevent::parseExtendedEventDescriptor(const uint8_t *buf, unsigned maxlen)
{
struct descr_extended_event_header *evt=(struct descr_extended_event_header *)buf;
if((evt->descriptor_length+sizeof(descr_generic_header)>maxlen) ||
(evt->descriptor_length<sizeof(struct descr_extended_event_header)-sizeof(descr_generic_header)))
return;
int tsidonid = (transport_stream_id << 16) | original_network_id;
char lang[] = {tolower(evt->iso_639_2_language_code_hi), tolower(evt->iso_639_2_language_code_mid), tolower(evt->iso_639_2_language_code_lo), '\0'};
std::string language(lang);
int table = getCountryCodeDefaultMapping(language);
unsigned char *items=(unsigned char *)(buf+sizeof(struct descr_extended_event_header));
while(items < (unsigned char *)(buf + sizeof(struct descr_extended_event_header) + evt->length_of_items)) {
if(*items) {
itemDescription.append(convertDVBUTF8((const char *)(items+1), min(maxlen-(items+1-buf), *items), table, tsidonid));
itemDescription.append("\n");
}
items+=1+*items;
if(*items) {
item.append(convertDVBUTF8((const char *)(items+1), min(maxlen-(items+1-buf), *items), table, tsidonid));
item.append("\n");
}
items+=1+*items;
}
if(*items)
appendExtendedText(language, convertDVBUTF8((const char *)(items+1), min(maxlen-(items+1-buf), (*items)), table, tsidonid));
}
void SIevent::parseContentDescriptor(const uint8_t *buf, unsigned maxlen)
{
struct descr_generic_header *cont=(struct descr_generic_header *)buf;
if(cont->descriptor_length+sizeof(struct descr_generic_header)>maxlen)
return;
const uint8_t *classification=buf+sizeof(struct descr_generic_header);
while(classification <= buf+sizeof(struct descr_generic_header)+cont->descriptor_length-2) {
contentClassification+=std::string((const char *)classification, 1);
userClassification+=std::string((const char *)classification+1, 1);
classification+=2;
}
}
void SIevent::parseComponentDescriptor(const uint8_t *buf, unsigned maxlen)
{
if(maxlen>=sizeof(struct descr_component_header))
components.insert(SIcomponent((const struct descr_component_header *)buf));
}
void SIevent::parseParentalRatingDescriptor(const uint8_t *buf, unsigned maxlen)
{
struct descr_generic_header *cont=(struct descr_generic_header *)buf;
if(cont->descriptor_length+sizeof(struct descr_generic_header)>maxlen)
return;
const uint8_t *s=buf+sizeof(struct descr_generic_header);
while(s<buf+sizeof(struct descr_generic_header)+cont->descriptor_length-4) {
ratings.insert(SIparentalRating(std::string((const char *)s, 3), *(s+3)));
s+=4;
}
}
void SIevent::parseLinkageDescriptor(const uint8_t *buf, unsigned maxlen)
{
if(maxlen>=sizeof(struct descr_linkage_header)) {
SIlinkage l((const struct descr_linkage_header *)buf);
linkage_descs.insert(linkage_descs.end(), l);
}
}
char SIevent::getFSK() const
{
for (SIparentalRatings::iterator it = ratings.begin(); it != ratings.end(); ++it)

View File

@@ -32,6 +32,67 @@
#include <dvbsi++/event_information_section.h>
#include "edvbstring.h"
struct eit_event {
unsigned event_id_hi : 8;
unsigned event_id_lo : 8;
unsigned start_time_hi : 8;
unsigned start_time_hi2 : 8;
unsigned start_time_mid : 8;
unsigned start_time_lo2 : 8;
unsigned start_time_lo : 8;
unsigned duration_hi : 8;
unsigned duration_mid : 8;
unsigned duration_lo : 8;
#if __BYTE_ORDER == __BIG_ENDIAN
unsigned running_status : 3;
unsigned free_CA_mode : 1;
unsigned descriptors_loop_length_hi : 4;
#else
unsigned descriptors_loop_length_hi : 4;
unsigned free_CA_mode : 1;
unsigned running_status : 3;
#endif
unsigned descriptors_loop_length_lo : 8;
} __attribute__ ((packed)) ;
struct descr_component_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
#if __BYTE_ORDER == __BIG_ENDIAN
unsigned reserved_future_use : 4;
unsigned stream_content : 4;
#else
unsigned stream_content : 4;
unsigned reserved_future_use : 4;
#endif
unsigned component_type : 8;
unsigned component_tag : 8;
unsigned iso_639_2_language_code_hi : 8;
unsigned iso_639_2_language_code_mid : 8;
unsigned iso_639_2_language_code_lo : 8;
} __attribute__ ((packed)) ;
struct descr_linkage_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
unsigned transport_stream_id_hi : 8;
unsigned transport_stream_id_lo : 8;
unsigned original_network_id_hi : 8;
unsigned original_network_id_lo : 8;
unsigned service_id_hi : 8;
unsigned service_id_lo : 8;
unsigned linkage_type : 8;
} __attribute__ ((packed)) ;
struct descr_pdc_header {
unsigned descriptor_tag : 8;
unsigned descriptor_length : 8;
unsigned pil0 : 8;
unsigned pil1 : 8;
unsigned pil2 : 8;
} __attribute__ ((packed)) ;
class SIlinkage {
public:
unsigned char linkageType;
@@ -47,6 +108,14 @@ public:
serviceId = 0;
}
SIlinkage(const struct descr_linkage_header *link) {
linkageType = link->linkage_type;
transportStreamId = (link->transport_stream_id_hi << 8) | link->transport_stream_id_lo;
originalNetworkId = (link->original_network_id_hi << 8) | link->original_network_id_lo;
serviceId = (link->service_id_hi << 8) | link->service_id_lo;
if (link->descriptor_length > sizeof(struct descr_linkage_header) - 2)
name = convertDVBUTF8(((const char *)link)+sizeof(struct descr_linkage_header), link->descriptor_length-(sizeof(struct descr_linkage_header)-2), 0, 0);
}
void dump(void) const {
printf("Linakge Type: 0x%02hhx\n", linkageType);
@@ -113,6 +182,15 @@ class SIcomponent
componentType=0;
componentTag=0;
}
SIcomponent(const struct descr_component_header *comp) {
streamContent=comp->stream_content;
componentType=comp->component_type;
componentTag=comp->component_tag;
if(comp->descriptor_length>sizeof(struct descr_component_header)-2)
component=convertDVBUTF8(((const char *)comp)+sizeof(struct descr_component_header),
comp->descriptor_length-(sizeof(struct descr_component_header)-2), 0, 0);
}
void dump(void) const {
if(component.length())
printf("Component: %s\n", component.c_str());
@@ -264,6 +342,13 @@ class SIevent
std::map<std::string, std::string> langExtendedText;
int running;
void parseShortEventDescriptor(const uint8_t *buf, unsigned maxlen);
void parseExtendedEventDescriptor(const uint8_t *buf, unsigned maxlen);
void parseContentDescriptor(const uint8_t *buf, unsigned maxlen);
void parseComponentDescriptor(const uint8_t *buf, unsigned maxlen);
void parseParentalRatingDescriptor(const uint8_t *buf, unsigned maxlen);
void parseLinkageDescriptor(const uint8_t *buf, unsigned maxlen);
protected:
int saveXML0(FILE *f) const;
int saveXML2(FILE *f) const;
@@ -298,7 +383,10 @@ class SIevent
version = 0xFF;
running = false;
}
SIevent(const struct eit_event *e);
void parse(Event &event);
void parseDescriptors(const uint8_t *des, unsigned len);
// Name aus dem Short-Event-Descriptor
std::string getName() const;