Add support for content type for events.
This is (and will be) based on the content types described in EN 300 468 Still a lot to do
This commit is contained in:
parent
4487e78ee4
commit
2e0c9fa636
5 changed files with 85 additions and 7 deletions
|
@ -36,6 +36,7 @@
|
|||
#define DVB_DESC_SERVICE_LIST 0x41
|
||||
#define DVB_DESC_SHORT_EVENT 0x4d
|
||||
#define DVB_DESC_SERVICE 0x48
|
||||
#define DVB_DESC_CONTENT 0x54
|
||||
#define DVB_DESC_TELETEXT 0x56
|
||||
#define DVB_DESC_SUBTITLE 0x59
|
||||
#define DVB_DESC_AC3 0x6a
|
||||
|
|
14
dvb_tables.c
14
dvb_tables.c
|
@ -227,6 +227,7 @@ dvb_eit_callback(th_dvb_mux_instance_t *tdmi, uint8_t *ptr, int len,
|
|||
|
||||
char title[256];
|
||||
char desc[5000];
|
||||
epg_content_type_t *ect;
|
||||
|
||||
if(tableid < 0x4e || tableid > 0x6f)
|
||||
return -1;
|
||||
|
@ -269,7 +270,10 @@ dvb_eit_callback(th_dvb_mux_instance_t *tdmi, uint8_t *ptr, int len,
|
|||
|
||||
if(dllen > len)
|
||||
break;
|
||||
|
||||
|
||||
ect = NULL;
|
||||
*title = 0;
|
||||
*desc = 0;
|
||||
while(dllen > 0) {
|
||||
dtag = ptr[0];
|
||||
dlen = ptr[1];
|
||||
|
@ -286,6 +290,12 @@ dvb_eit_callback(th_dvb_mux_instance_t *tdmi, uint8_t *ptr, int len,
|
|||
desc, sizeof(desc)) < 0)
|
||||
duration = 0;
|
||||
break;
|
||||
|
||||
case DVB_DESC_CONTENT:
|
||||
if(dlen >= 2)
|
||||
/* We only support one content type per event atm. */
|
||||
ect = epg_content_type_find_by_dvbcode(*ptr);
|
||||
break;
|
||||
}
|
||||
|
||||
len -= dlen; ptr += dlen; dllen -= dlen;
|
||||
|
@ -293,7 +303,7 @@ dvb_eit_callback(th_dvb_mux_instance_t *tdmi, uint8_t *ptr, int len,
|
|||
|
||||
if(duration > 0) {
|
||||
epg_update_event_by_id(ch, event_id, start_time, duration,
|
||||
title, desc);
|
||||
title, desc, ect);
|
||||
|
||||
}
|
||||
}
|
||||
|
|
55
epg.c
55
epg.c
|
@ -36,6 +36,8 @@ static pthread_mutex_t epg_mutex = PTHREAD_MUTEX_INITIALIZER;
|
|||
struct event_list epg_hash[EPG_HASH_ID_WIDTH];
|
||||
static dtimer_t epg_channel_maintain_timer;
|
||||
|
||||
epg_content_group_t *epg_content_groups[16];
|
||||
|
||||
void
|
||||
epg_lock(void)
|
||||
{
|
||||
|
@ -63,6 +65,16 @@ epg_event_set_desc(event_t *e, const char *desc)
|
|||
e->e_desc = strdup(desc);
|
||||
}
|
||||
|
||||
void
|
||||
epg_event_set_content_type(event_t *e, epg_content_type_t *ect)
|
||||
{
|
||||
if(e->e_content_type != NULL)
|
||||
LIST_REMOVE(e, e_content_type_link);
|
||||
|
||||
e->e_content_type = ect;
|
||||
if(ect != NULL)
|
||||
LIST_INSERT_HEAD(&ect->ect_events, e, e_content_type_link);
|
||||
}
|
||||
|
||||
event_t *
|
||||
epg_event_find_by_time0(struct event_queue *q, time_t start)
|
||||
|
@ -157,6 +169,9 @@ epg_event_build(struct event_queue *head, time_t start, int duration)
|
|||
void
|
||||
epg_event_free(event_t *e)
|
||||
{
|
||||
if(e->e_content_type != NULL)
|
||||
LIST_REMOVE(e, e_content_type_link);
|
||||
|
||||
free((void *)e->e_title);
|
||||
free((void *)e->e_desc);
|
||||
free(e);
|
||||
|
@ -261,7 +276,7 @@ check_overlap(th_channel_t *ch, event_t *e)
|
|||
static void
|
||||
epg_event_create(th_channel_t *ch, time_t start, int duration,
|
||||
const char *title, const char *desc, int source,
|
||||
uint16_t id, refstr_t *icon)
|
||||
uint16_t id, refstr_t *icon, epg_content_type_t *ect)
|
||||
{
|
||||
unsigned int l;
|
||||
time_t now;
|
||||
|
@ -317,6 +332,7 @@ epg_event_create(th_channel_t *ch, time_t start, int duration,
|
|||
|
||||
if(title != NULL) epg_event_set_title(e, title);
|
||||
if(desc != NULL) epg_event_set_desc(e, desc);
|
||||
if(ect != NULL) epg_event_set_content_type(e, ect);
|
||||
}
|
||||
|
||||
check_overlap(ch, e);
|
||||
|
@ -328,7 +344,7 @@ epg_event_create(th_channel_t *ch, time_t start, int duration,
|
|||
void
|
||||
epg_update_event_by_id(th_channel_t *ch, uint16_t event_id,
|
||||
time_t start, int duration, const char *title,
|
||||
const char *desc)
|
||||
const char *desc, epg_content_type_t *ect)
|
||||
{
|
||||
event_t *e;
|
||||
|
||||
|
@ -359,11 +375,12 @@ epg_update_event_by_id(th_channel_t *ch, uint16_t event_id,
|
|||
|
||||
epg_event_set_title(e, title);
|
||||
epg_event_set_desc(e, desc);
|
||||
epg_event_set_content_type(e, ect);
|
||||
|
||||
} else {
|
||||
|
||||
epg_event_create(ch, start, duration, title, desc,
|
||||
EVENT_SRC_DVB, event_id, NULL);
|
||||
EVENT_SRC_DVB, event_id, NULL, ect);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -463,12 +480,42 @@ epg_transfer_events(th_channel_t *ch, struct event_queue *src,
|
|||
TAILQ_FOREACH(e, src, e_link) {
|
||||
|
||||
epg_event_create(ch, e->e_start, e->e_duration, e->e_title,
|
||||
e->e_desc, EVENT_SRC_XMLTV, 0, refstr_dup(icon));
|
||||
e->e_desc, EVENT_SRC_XMLTV, 0, refstr_dup(icon),
|
||||
e->e_content_type);
|
||||
cnt++;
|
||||
}
|
||||
epg_unlock();
|
||||
}
|
||||
|
||||
/**
|
||||
* Find a content type
|
||||
*/
|
||||
epg_content_type_t *
|
||||
epg_content_type_find_by_dvbcode(uint8_t dvbcode)
|
||||
{
|
||||
epg_content_group_t *ecg;
|
||||
epg_content_type_t *ect;
|
||||
int group = dvbcode >> 4;
|
||||
int type = dvbcode & 0xf;
|
||||
char buf[20];
|
||||
|
||||
ecg = epg_content_groups[group];
|
||||
if(ecg == NULL) {
|
||||
ecg = epg_content_groups[group] = calloc(1, sizeof(epg_content_group_t));
|
||||
snprintf(buf, sizeof(buf), "group%d", group);
|
||||
ecg->ecg_name = strdup(buf);
|
||||
}
|
||||
|
||||
ect = ecg->ecg_types[type];
|
||||
if(ect == NULL) {
|
||||
ect = ecg->ecg_types[type] = calloc(1, sizeof(epg_content_type_t));
|
||||
snprintf(buf, sizeof(buf), "type%d", type);
|
||||
ect->ect_name = strdup(buf);
|
||||
}
|
||||
|
||||
return ect;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
|
|
4
epg.h
4
epg.h
|
@ -43,7 +43,7 @@ void epg_event_set_desc(event_t *e, const char *desc);
|
|||
|
||||
void epg_update_event_by_id(th_channel_t *ch, uint16_t event_id,
|
||||
time_t start, int duration, const char *title,
|
||||
const char *desc);
|
||||
const char *desc, epg_content_type_t *ect);
|
||||
|
||||
void epg_transfer_events(th_channel_t *ch, struct event_queue *src,
|
||||
const char *srcname, refstr_t *icon);
|
||||
|
@ -52,4 +52,6 @@ void event_time_txt(time_t start, int duration, char *out, int outlen);
|
|||
|
||||
event_t *epg_event_find_current_or_upcoming(th_channel_t *ch);
|
||||
|
||||
epg_content_type_t *epg_content_type_find_by_dvbcode(uint8_t dvbcode);
|
||||
|
||||
#endif /* EPG_H */
|
||||
|
|
18
tvhead.h
18
tvhead.h
|
@ -778,6 +778,21 @@ typedef struct th_subscription {
|
|||
|
||||
} th_subscription_t;
|
||||
|
||||
/**
|
||||
* EPG content group
|
||||
*
|
||||
* Based on the content types defined in EN 300 468
|
||||
*/
|
||||
typedef struct epg_content_type {
|
||||
const char *ect_name;
|
||||
struct event_list ect_events;
|
||||
} epg_content_type_t;
|
||||
|
||||
|
||||
typedef struct epg_content_group {
|
||||
const char *ecg_name;
|
||||
struct epg_content_type *ecg_types[16];
|
||||
} epg_content_group_t;
|
||||
|
||||
|
||||
/*
|
||||
|
@ -787,6 +802,9 @@ typedef struct event {
|
|||
TAILQ_ENTRY(event) e_link;
|
||||
LIST_ENTRY(event) e_hash_link;
|
||||
|
||||
LIST_ENTRY(event) e_content_type_link;
|
||||
epg_content_type_t *e_content_type;
|
||||
|
||||
time_t e_start; /* UTC time */
|
||||
int e_duration; /* in seconds */
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue