From: Jaroslav Kysela Date: Tue, 21 Nov 2017 15:43:16 +0000 (+0100) Subject: service: elementary streams - cleanups, add modify, destroy functions X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=2d1311c2347ff2fb2e8443fc3ec8f6a3cb079802;p=thirdparty%2Ftvheadend.git service: elementary streams - cleanups, add modify, destroy functions --- diff --git a/src/input/mpegts/dvb_psi.c b/src/input/mpegts/dvb_psi.c index c116747b6..a1cc346bc 100644 --- a/src/input/mpegts/dvb_psi.c +++ b/src/input/mpegts/dvb_psi.c @@ -2183,7 +2183,8 @@ psi_desc_add_ca tvhdebug(mt->mt_subsys, "%s: caid %04X (%s) provider %08X pid %04X", mt->mt_name, caid, caid2name(caid), provid, pid); - if((st = service_stream_find((service_t*)t, pid)) == NULL) { + st = service_stream_find((service_t*)t, pid); + if (st == NULL || st->es_type != SCT_CA) { st = service_stream_create((service_t*)t, pid, SCT_CA); r |= PMT_UPDATE_NEW_CA_STREAM; } @@ -2302,13 +2303,12 @@ psi_desc_teletext(mpegts_service_t *t, const uint8_t *ptr, int size, // higher than normal MPEG TS (0x2000 ++) int pid = DVB_TELETEXT_BASE + page; - if((st = service_stream_find((service_t*)t, pid)) == NULL) { + st = service_stream_find((service_t*)t, pid); + if (st == NULL || st->es_type != SCT_TEXTSUB) { r |= PMT_UPDATE_NEW_STREAM; st = service_stream_create((service_t*)t, pid, SCT_TEXTSUB); - st->es_delete_me = 1; } - lang = lang_code_get2((const char*)ptr, 3); if(memcmp(st->es_lang,lang,3)) { r |= PMT_UPDATE_LANGUAGE; @@ -2544,9 +2544,10 @@ psi_parse_pmt len -= dlen; ptr += dlen; dllen -= dlen; } - if(hts_stream_type != SCT_UNKNOWN) { + if (hts_stream_type != SCT_UNKNOWN) { - if((st = service_stream_find((service_t*)t, pid)) == NULL) { + st = service_stream_find((service_t*)t, pid); + if (st == NULL || st->es_type != hts_stream_type) { update |= PMT_UPDATE_NEW_STREAM; st = service_stream_create((service_t*)t, pid, hts_stream_type); } @@ -2610,11 +2611,7 @@ psi_parse_pmt /* Handle PCR 'elementary stream' */ if (!pcr_shared) { - st = service_stream_type_find((service_t *)t, SCT_PCR); - if (st) - st->es_pid = t->s_pcr_pid; - else - st = service_stream_create((service_t*)t, t->s_pcr_pid, SCT_PCR); + st = service_stream_type_modify((service_t *)t, t->s_pcr_pid, SCT_PCR); st->es_delete_me = 0; } diff --git a/src/input/mpegts/mpegts_service.c b/src/input/mpegts/mpegts_service.c index 46e9c248d..0a1cafdb5 100644 --- a/src/input/mpegts/mpegts_service.c +++ b/src/input/mpegts/mpegts_service.c @@ -785,6 +785,10 @@ mpegts_service_create0 /* defaults for older version */ s->s_dvb_created = dispatch_clock; + if (!conf) { + if (sid) s->s_dvb_service_id = sid; + if (pmt_pid) s->s_pmt_pid = pmt_pid; + } if (service_create0((service_t*)s, STYPE_STD, class, uuid, S_MPEG_TS, conf) == NULL) @@ -792,10 +796,7 @@ mpegts_service_create0 /* Create */ sbuf_init(&s->s_tsbuf); - if (!conf) { - if (sid) s->s_dvb_service_id = sid; - if (pmt_pid) s->s_pmt_pid = pmt_pid; - } else { + if (conf) { if (s->s_dvb_last_seen > gclk()) /* sanity check */ s->s_dvb_last_seen = gclk(); } diff --git a/src/service.c b/src/service.c index f0a30a320..80b6ac518 100644 --- a/src/service.c +++ b/src/service.c @@ -1065,6 +1065,8 @@ service_create0 const idclass_t *class, const char *uuid, int source_type, htsmsg_t *conf ) { + lock_assert(&global_lock); + if (idnode_insert(&t->s_id, uuid, class, 0)) { if (uuid) tvherror(LS_SERVICE, "invalid uuid '%s'", uuid); @@ -1072,8 +1074,6 @@ service_create0 return NULL; } - lock_assert(&global_lock); - if (service_type == STYPE_RAW) TAILQ_INSERT_TAIL(&service_raw_all, t, s_all_link); else @@ -1183,7 +1183,6 @@ service_make_nicename(service_t *t) service_stream_make_nicename(t, st); } - /** * Add a new stream to a service */ @@ -1228,8 +1227,6 @@ service_stream_create(service_t *t, int pid, return st; } - - /** * Find an elementary stream in a service */ @@ -1266,6 +1263,32 @@ service_stream_type_find(service_t *t, streaming_component_type_t type) return NULL; } +/** + * + */ +elementary_stream_t * +service_stream_type_modify(service_t *t, int pid, + streaming_component_type_t type) +{ + elementary_stream_t *es = service_stream_type_find(t, type); + if (!es) + return service_stream_create(t, pid, type); + if (es->es_pid != pid) + es->es_pid = pid; + return es; +} + +/** + * + */ +void +service_stream_type_destroy(service_t *t, streaming_component_type_t type) +{ + elementary_stream_t *es = service_stream_type_find(t, type); + if (es) + service_stream_destroy(t, es); +} + /** * */ @@ -2252,6 +2275,7 @@ void service_load ( service_t *t, htsmsg_t *c ) idnode_load(&t->s_id, c); + pthread_mutex_lock(&t->s_stream_mutex); if(!htsmsg_get_s32(c, "verified", &s32)) t->s_verified = s32; else @@ -2271,7 +2295,6 @@ void service_load ( service_t *t, htsmsg_t *c ) } } - pthread_mutex_lock(&t->s_stream_mutex); m = htsmsg_get_list(c, "stream"); if (m) { HTSMSG_FOREACH(f, m) { @@ -2335,7 +2358,9 @@ void service_load ( service_t *t, htsmsg_t *c ) } } if (!shared_pcr) - service_stream_create(t, t->s_pcr_pid, SCT_PCR); + service_stream_type_modify(t, t->s_pcr_pid, SCT_PCR); + else + service_stream_type_destroy(t, SCT_PCR); sort_elementary_streams(t); pthread_mutex_unlock(&t->s_stream_mutex); } diff --git a/src/service.h b/src/service.h index d7a17a0a9..b80b4716a 100644 --- a/src/service.h +++ b/src/service.h @@ -566,6 +566,10 @@ service_stream_type_find(service_t *t, streaming_component_type_t type); elementary_stream_t *service_stream_create(service_t *t, int pid, streaming_component_type_t type); +elementary_stream_t * +service_stream_type_modify(service_t *t, int pid, + streaming_component_type_t type); + void service_settings_write(service_t *t); const char *service_servicetype_txt(service_t *t); @@ -621,6 +625,8 @@ void service_restart_streams(service_t *t); void service_stream_destroy(service_t *t, elementary_stream_t *st); +void service_stream_type_destroy(service_t *t, streaming_component_type_t type); + void service_request_save(service_t *t, int restart); void service_source_info_free(source_info_t *si); diff --git a/src/tvheadend.h b/src/tvheadend.h index 73144562d..306a37b9f 100644 --- a/src/tvheadend.h +++ b/src/tvheadend.h @@ -285,14 +285,17 @@ typedef enum { SCT_NONE = -1, SCT_UNKNOWN = 0, SCT_RAW = 1, - SCT_PCR, + SCT_PCR, /* MPEG-TS PCR data */ + SCT_CAT, /* MPEG-TS CAT (EMM) data */ + SCT_CA, /* MPEG-TS ECM data */ + SCT_HBBTV, /* HBBTV info */ + /* standard codecs */ SCT_MPEG2VIDEO, SCT_MPEG2AUDIO, SCT_H264, SCT_AC3, SCT_TELETEXT, SCT_DVBSUB, - SCT_CA, SCT_AAC, /* AAC-LATM in MPEG-TS, ADTS + AAC in packet form */ SCT_MPEGTS, SCT_TEXTSUB, @@ -302,11 +305,9 @@ typedef enum { SCT_VORBIS, SCT_HEVC, SCT_VP9, - SCT_HBBTV, SCT_THEORA, SCT_OPUS, - SCT_CAT, /* MPEG-TS CAT (EMM) data */ - SCT_LAST = SCT_CAT + SCT_LAST = SCT_OPUS } streaming_component_type_t; #define SCT_MASK(t) (1 << (t))