mpegts linuxdvb: loads of tidying up of network/mux code
This commit is contained in:
parent
896345228c
commit
400e8c61ea
8 changed files with 327 additions and 220 deletions
|
@ -411,10 +411,10 @@ mpegts_input_t *mpegts_input_create0
|
|||
|
||||
mpegts_network_t *mpegts_network_create0
|
||||
( mpegts_network_t *mn, const idclass_t *idc, const char *uuid,
|
||||
const char *name );
|
||||
const char *name, htsmsg_t *conf );
|
||||
|
||||
#define mpegts_network_create(t, u, n)\
|
||||
(struct t*)mpegts_network_create0(calloc(1, sizeof(struct t)), &t##_class, u, n)
|
||||
#define mpegts_network_create(t, u, n, c)\
|
||||
(struct t*)mpegts_network_create0(calloc(1, sizeof(struct t)), &t##_class, u, n, c)
|
||||
|
||||
void mpegts_network_schedule_initial_scan
|
||||
( mpegts_network_t *mm );
|
||||
|
@ -439,7 +439,7 @@ mpegts_mux_t *mpegts_mux_create0
|
|||
|
||||
void mpegts_mux_initial_scan_done ( mpegts_mux_t *mm );
|
||||
|
||||
void mpegts_mux_load_one ( mpegts_mux_t *mm, htsmsg_t *c );
|
||||
void mpegts_mux_save ( mpegts_mux_t *mm, htsmsg_t *c );
|
||||
|
||||
mpegts_mux_instance_t *mpegts_mux_instance_create0
|
||||
( mpegts_mux_instance_t *mmi, const idclass_t *class, const char *uuid,
|
||||
|
|
|
@ -30,10 +30,12 @@
|
|||
#include <dirent.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
/*
|
||||
/* **************************************************************************
|
||||
* Class definition
|
||||
*/
|
||||
* *************************************************************************/
|
||||
|
||||
extern const idclass_t mpegts_mux_class;
|
||||
|
||||
const idclass_t linuxdvb_mux_class =
|
||||
{
|
||||
.ic_super = &mpegts_mux_class,
|
||||
|
@ -84,9 +86,9 @@ const idclass_t linuxdvb_mux_atsc_class =
|
|||
}
|
||||
};
|
||||
|
||||
/*
|
||||
* Mux Objects
|
||||
*/
|
||||
/* **************************************************************************
|
||||
* Class methods
|
||||
* *************************************************************************/
|
||||
|
||||
static void
|
||||
linuxdvb_mux_config_save ( mpegts_mux_t *mm )
|
||||
|
@ -94,7 +96,7 @@ linuxdvb_mux_config_save ( mpegts_mux_t *mm )
|
|||
linuxdvb_mux_t *lm = (linuxdvb_mux_t*)mm;
|
||||
linuxdvb_network_t *ln = (linuxdvb_network_t*)mm->mm_network;
|
||||
htsmsg_t *c = htsmsg_create_map();
|
||||
idnode_save(&mm->mm_id, c);
|
||||
mpegts_mux_save(mm, c);
|
||||
dvb_mux_conf_save(ln->ln_type, &lm->lm_tuning, c);
|
||||
hts_settings_save(c, "input/linuxdvb/networks/%s/muxes/%s/config",
|
||||
idnode_uuid_as_str(&mm->mm_network->mn_id),
|
||||
|
@ -143,6 +145,10 @@ linuxdvb_mux_close_table ( mpegts_mux_t *mm, mpegts_table_t *mt )
|
|||
}
|
||||
#endif
|
||||
|
||||
/* **************************************************************************
|
||||
* Creation/Config
|
||||
* *************************************************************************/
|
||||
|
||||
linuxdvb_mux_t *
|
||||
linuxdvb_mux_create0
|
||||
( linuxdvb_network_t *ln,
|
||||
|
@ -150,10 +156,12 @@ linuxdvb_mux_create0
|
|||
const char *uuid, htsmsg_t *conf )
|
||||
{
|
||||
const idclass_t *idc;
|
||||
const char *str;
|
||||
mpegts_mux_t *mm;
|
||||
linuxdvb_mux_t *lm;
|
||||
|
||||
/* Search for existing */
|
||||
dvb_mux_conf_t dmc0;
|
||||
htsmsg_t *c, *e;
|
||||
htsmsg_field_t *f;
|
||||
|
||||
/* Class */
|
||||
if (ln->ln_type == FE_QPSK)
|
||||
|
@ -165,7 +173,20 @@ linuxdvb_mux_create0
|
|||
else if (ln->ln_type == FE_ATSC)
|
||||
idc = &linuxdvb_mux_atsc_class;
|
||||
else {
|
||||
tvhlog(LOG_ERR, "linuxdvb", "unknown FE type %d", ln->ln_type);
|
||||
tvherror("linuxdvb", "unknown FE type %d", ln->ln_type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Load mux config */
|
||||
if (conf && !dmc) {
|
||||
dmc = &dmc0;
|
||||
if ((str = dvb_mux_conf_load(ln->ln_type, &dmc0, conf))) {
|
||||
tvherror( "linuxdvb", "failed to load mux config [%s]", str);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
if (!dmc) {
|
||||
tvherror("linuxdvb", "no mux configuration provided");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -174,49 +195,23 @@ linuxdvb_mux_create0
|
|||
(mpegts_network_t*)ln, onid, tsid, conf)))
|
||||
return NULL;
|
||||
lm = (linuxdvb_mux_t*)mm;
|
||||
|
||||
/* Tuning */
|
||||
memcpy(&lm->lm_tuning, dmc, sizeof(dvb_mux_conf_t));
|
||||
|
||||
/* Callbacks */
|
||||
lm->mm_display_name = linuxdvb_mux_display_name;
|
||||
lm->mm_config_save = linuxdvb_mux_config_save;
|
||||
lm->mm_create_instances = linuxdvb_mux_create_instances;
|
||||
|
||||
return (linuxdvb_mux_t*)mm;
|
||||
}
|
||||
|
||||
linuxdvb_mux_t *
|
||||
linuxdvb_mux_create1
|
||||
( linuxdvb_network_t *ln, const char *uuid, htsmsg_t *conf )
|
||||
{
|
||||
const char *str;
|
||||
htsmsg_t *c, *e;
|
||||
htsmsg_field_t *f;
|
||||
linuxdvb_mux_t *lm;
|
||||
dvb_mux_conf_t dmc;
|
||||
|
||||
/* Check tuning */
|
||||
memset(&dmc, 0, sizeof(dmc));
|
||||
if (conf) {
|
||||
if ((str = dvb_mux_conf_load(ln->ln_type, &dmc, conf))) {
|
||||
tvhlog(LOG_ERR, "linuxdvb", "failed to load mux config [%s]", str);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
lm = linuxdvb_mux_create0(ln, MPEGTS_ONID_NONE,
|
||||
MPEGTS_TSID_NONE, &dmc, uuid, conf);
|
||||
if (!lm) return NULL;
|
||||
|
||||
/* No config */
|
||||
if (!conf)
|
||||
return lm;
|
||||
|
||||
/* Config */
|
||||
memcpy(&lm->lm_tuning, &dmc, sizeof(dmc));
|
||||
if (!conf) return lm;
|
||||
|
||||
/* Services */
|
||||
if ((c = hts_settings_load_r(1, "input/linuxdvb/networks/%s/muxes/%s/services",
|
||||
"TODO", uuid))) {
|
||||
c = hts_settings_load_r(1, "input/linuxdvb/networks/%s/muxes/%s/services",
|
||||
idnode_uuid_as_str(&ln->mn_id),
|
||||
idnode_uuid_as_str(&mm->mm_id));
|
||||
if (c) {
|
||||
HTSMSG_FOREACH(f, c) {
|
||||
if (!(e = htsmsg_get_map_by_field(f))) continue;
|
||||
if (!(e = htsmsg_get_map(e, "config"))) continue;
|
||||
|
|
|
@ -30,16 +30,22 @@
|
|||
#include <dirent.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
/* ****************************************************************************
|
||||
* Class definition
|
||||
* ***************************************************************************/
|
||||
|
||||
extern const idclass_t mpegts_network_class;
|
||||
|
||||
static const char *
|
||||
ln_type_getstr ( void *ptr )
|
||||
mpegts_network_class_get_lntype
|
||||
( void * ptr )
|
||||
{
|
||||
return dvb_type2str(((linuxdvb_network_t*)ptr)->ln_type);
|
||||
}
|
||||
|
||||
static void
|
||||
ln_type_setstr ( void *ptr, const char *str )
|
||||
static void
|
||||
mpegts_network_class_set_lntype
|
||||
( void *ptr, const char *str )
|
||||
{
|
||||
((linuxdvb_network_t*)ptr)->ln_type = dvb_str2type(str);
|
||||
}
|
||||
|
@ -52,21 +58,15 @@ const idclass_t linuxdvb_network_class =
|
|||
.ic_properties = (const property_t[]){
|
||||
{ PROPDEF2("type", "Network Type",
|
||||
PT_STR, linuxdvb_network_t, ln_type, 1),
|
||||
.str_get = ln_type_getstr,
|
||||
.str_set = ln_type_setstr },
|
||||
.str_get = mpegts_network_class_get_lntype,
|
||||
.str_set = mpegts_network_class_set_lntype },
|
||||
{}
|
||||
}
|
||||
};
|
||||
|
||||
static void
|
||||
linuxdvb_network_config_save ( mpegts_network_t *mn )
|
||||
{
|
||||
htsmsg_t *c = htsmsg_create_map();
|
||||
idnode_save(&mn->mn_id, c);
|
||||
hts_settings_save(c, "input/linuxdvb/networks/%s/config",
|
||||
idnode_uuid_as_str(&mn->mn_id));
|
||||
htsmsg_destroy(c);
|
||||
}
|
||||
/* ****************************************************************************
|
||||
* Class methods
|
||||
* ***************************************************************************/
|
||||
|
||||
static mpegts_mux_t *
|
||||
linuxdvb_network_find_mux
|
||||
|
@ -84,10 +84,21 @@ linuxdvb_network_find_mux
|
|||
return mm;
|
||||
}
|
||||
|
||||
static void
|
||||
linuxdvb_network_config_save ( mpegts_network_t *mn )
|
||||
{
|
||||
htsmsg_t *c = htsmsg_create_map();
|
||||
idnode_save(&mn->mn_id, c);
|
||||
hts_settings_save(c, "input/linuxdvb/networks/%s/config",
|
||||
idnode_uuid_as_str(&mn->mn_id));
|
||||
htsmsg_destroy(c);
|
||||
}
|
||||
|
||||
static mpegts_mux_t *
|
||||
linuxdvb_network_create_mux
|
||||
( mpegts_mux_t *mm, uint16_t onid, uint16_t tsid, dvb_mux_conf_t *dmc )
|
||||
{
|
||||
// TODO: should we have a mux_find wrapper?
|
||||
linuxdvb_network_t *ln = (linuxdvb_network_t*)mm->mm_network;
|
||||
mm = linuxdvb_network_find_mux(ln, dmc);
|
||||
if (!mm) {
|
||||
|
@ -102,9 +113,14 @@ static mpegts_service_t *
|
|||
linuxdvb_network_create_service
|
||||
( mpegts_mux_t *mm, uint16_t sid, uint16_t pmt_pid )
|
||||
{
|
||||
return linuxdvb_service_create0((linuxdvb_mux_t*)mm, sid, pmt_pid, NULL, NULL);
|
||||
return linuxdvb_service_create0((linuxdvb_mux_t*)mm, sid,
|
||||
pmt_pid, NULL, NULL);
|
||||
}
|
||||
|
||||
/* ****************************************************************************
|
||||
* Creation/Config
|
||||
* ***************************************************************************/
|
||||
|
||||
static linuxdvb_network_t *
|
||||
linuxdvb_network_create0
|
||||
( const char *uuid, htsmsg_t *conf )
|
||||
|
@ -114,7 +130,7 @@ linuxdvb_network_create0
|
|||
htsmsg_field_t *f;
|
||||
|
||||
/* Create */
|
||||
if (!(ln = mpegts_network_create(linuxdvb_network, uuid, NULL)))
|
||||
if (!(ln = mpegts_network_create(linuxdvb_network, uuid, NULL, conf)))
|
||||
return NULL;
|
||||
|
||||
/* Callbacks */
|
||||
|
@ -126,9 +142,6 @@ linuxdvb_network_create0
|
|||
if (!conf)
|
||||
return ln;
|
||||
|
||||
/* Load configuration */
|
||||
idnode_load(&ln->mn_id, conf);
|
||||
|
||||
/* Load muxes */
|
||||
if ((c = hts_settings_load_r(1, "input/linuxdvb/networks/%s/muxes", uuid))) {
|
||||
HTSMSG_FOREACH(f, c) {
|
||||
|
@ -138,18 +151,9 @@ linuxdvb_network_create0
|
|||
}
|
||||
}
|
||||
|
||||
linuxdvb_network_config_save((mpegts_network_t*)ln);
|
||||
|
||||
return ln;
|
||||
}
|
||||
|
||||
linuxdvb_network_t*
|
||||
linuxdvb_network_find_by_uuid(const char *uuid)
|
||||
{
|
||||
idnode_t *in = idnode_find(uuid, &linuxdvb_network_class);
|
||||
return (linuxdvb_network_t*)in;
|
||||
}
|
||||
|
||||
void linuxdvb_network_init ( void )
|
||||
{
|
||||
htsmsg_t *c, *e;
|
||||
|
@ -165,3 +169,20 @@ void linuxdvb_network_init ( void )
|
|||
}
|
||||
htsmsg_destroy(c);
|
||||
}
|
||||
|
||||
/* ****************************************************************************
|
||||
* Search
|
||||
* ***************************************************************************/
|
||||
|
||||
linuxdvb_network_t*
|
||||
linuxdvb_network_find_by_uuid(const char *uuid)
|
||||
{
|
||||
idnode_t *in = idnode_find(uuid, &linuxdvb_network_class);
|
||||
return (linuxdvb_network_t*)in;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Editor Configuration
|
||||
*
|
||||
* vim:sts=2:ts=2:sw=2:et
|
||||
*****************************************************************************/
|
||||
|
|
|
@ -186,8 +186,10 @@ struct linuxdvb_mux
|
|||
linuxdvb_mux_t *linuxdvb_mux_create0
|
||||
(linuxdvb_network_t *ln, uint16_t onid, uint16_t tsid,
|
||||
const dvb_mux_conf_t *dmc, const char *uuid, htsmsg_t *conf);
|
||||
linuxdvb_mux_t *linuxdvb_mux_create1
|
||||
(linuxdvb_network_t *ln, const char *uuid, htsmsg_t *conf);
|
||||
|
||||
#define linuxdvb_mux_create1(n, u, c)\
|
||||
linuxdvb_mux_create0(n, MPEGTS_ONID_NONE, MPEGTS_TSID_NONE,\
|
||||
NULL, u, c)
|
||||
|
||||
/*
|
||||
* Service
|
||||
|
|
|
@ -109,9 +109,9 @@ mpegts_input_recv_packets
|
|||
/* Re-sync */
|
||||
} else {
|
||||
// TODO: set flag (to avoid spam)
|
||||
tvhlog(LOG_DEBUG, "tsdemux", "%s ts sync lost", "TODO");
|
||||
tvhdebug("tsdemux", "%s ts sync lost", "TODO");
|
||||
if (ts_resync(tsb, &len, &i)) break;
|
||||
tvhlog(LOG_DEBUG, "tsdemux", "%s ts sync found", "TODO");
|
||||
tvhdebug("tsdemux", "%s ts sync found", "TODO");
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -23,6 +23,13 @@
|
|||
|
||||
#include <assert.h>
|
||||
|
||||
static void
|
||||
mpegts_mux_initial_scan_timeout ( void *aux );
|
||||
|
||||
/* ****************************************************************************
|
||||
* Mux instance (input linkage)
|
||||
* ***************************************************************************/
|
||||
|
||||
const idclass_t mpegts_mux_instance_class =
|
||||
{
|
||||
.ic_class = "mpegts_mux_instance",
|
||||
|
@ -37,16 +44,21 @@ mpegts_mux_instance_create0
|
|||
mpegts_input_t *mi, mpegts_mux_t *mm )
|
||||
{
|
||||
idnode_insert(&mmi->mmi_id, uuid, class);
|
||||
// TODO: does this need to be an idnode?
|
||||
|
||||
/* Setup links */
|
||||
mmi->mmi_mux = mm;
|
||||
mmi->mmi_input = mi; // TODO: is this required?
|
||||
mmi->mmi_input = mi;
|
||||
|
||||
LIST_INSERT_HEAD(&mm->mm_instances, mmi, mmi_mux_link);
|
||||
|
||||
return mmi;
|
||||
}
|
||||
|
||||
/* ****************************************************************************
|
||||
* Class definition
|
||||
* ***************************************************************************/
|
||||
|
||||
static void
|
||||
mpegts_mux_class_save ( idnode_t *self )
|
||||
{
|
||||
|
@ -74,6 +86,10 @@ const idclass_t mpegts_mux_class =
|
|||
}
|
||||
};
|
||||
|
||||
/* ****************************************************************************
|
||||
* Class methods
|
||||
* ***************************************************************************/
|
||||
|
||||
static void
|
||||
mpegts_mux_display_name ( mpegts_mux_t *mm, char *buf, size_t len )
|
||||
{
|
||||
|
@ -92,124 +108,34 @@ mpegts_mux_is_enabled ( mpegts_mux_t *mm )
|
|||
return mm->mm_enabled;
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_onid ( mpegts_mux_t *mm, uint16_t onid )
|
||||
{
|
||||
char buf[256];
|
||||
if (onid == mm->mm_onid)
|
||||
return 0;
|
||||
mm->mm_onid = onid;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s onid set to %d", buf, onid);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_tsid ( mpegts_mux_t *mm, uint16_t tsid )
|
||||
{
|
||||
char buf[256];
|
||||
if (tsid == mm->mm_tsid)
|
||||
return 0;
|
||||
mm->mm_tsid = tsid;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s tsid set to %d", buf, tsid);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_crid_authority ( mpegts_mux_t *mm, const char *defauth )
|
||||
{
|
||||
char buf[256];
|
||||
if (defauth && !strcmp(defauth, mm->mm_crid_authority ?: ""))
|
||||
return 0;
|
||||
tvh_str_update(&mm->mm_crid_authority, defauth);
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s crid authority set to %s", buf, defauth);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_initial_scan_link ( mpegts_mux_t *mm )
|
||||
mpegts_mux_create_instances ( mpegts_mux_t *mm )
|
||||
{
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
|
||||
assert(mn != NULL);
|
||||
assert(mm->mm_initial_scan_status == MM_SCAN_DONE);
|
||||
|
||||
mm->mm_initial_scan_status = MM_SCAN_PENDING;
|
||||
TAILQ_INSERT_TAIL(&mn->mn_initial_scan_pending_queue, mm,
|
||||
mm_initial_scan_link);
|
||||
mn->mn_initial_scan_num++;
|
||||
tvhtrace("mpegts", "added mm %p to initial scan for mn %p pending %d",
|
||||
mm, mn, mn->mn_initial_scan_num);
|
||||
mpegts_network_schedule_initial_scan(mn);
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_initial_scan_timeout ( void *aux )
|
||||
{
|
||||
mpegts_mux_t *mm = aux;
|
||||
tvhlog(LOG_DEBUG, "mpegts", "initial scan timed out for mm %p", mm);
|
||||
mpegts_mux_initial_scan_done(mm);
|
||||
}
|
||||
|
||||
static int
|
||||
mpegts_mux_has_subscribers ( mpegts_mux_t *mm )
|
||||
{
|
||||
service_t *t;
|
||||
mpegts_mux_instance_t *mmi = mm->mm_active;
|
||||
if (mmi) {
|
||||
LIST_FOREACH(t, &mmi->mmi_input->mi_transports, s_active_link)
|
||||
if (((mpegts_service_t*)t)->s_dvb_mux == mm)
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_mux_initial_scan_done ( mpegts_mux_t *mm )
|
||||
{
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
tvhlog(LOG_DEBUG, "mpegts", "initial scan complete for mm %p", mm);
|
||||
gtimer_disarm(&mm->mm_initial_scan_timeout);
|
||||
assert(mm->mm_initial_scan_status == MM_SCAN_CURRENT);
|
||||
mn->mn_initial_scan_num--;
|
||||
mm->mm_initial_scan_status = MM_SCAN_DONE;
|
||||
TAILQ_REMOVE(&mn->mn_initial_scan_current_queue, mm, mm_initial_scan_link);
|
||||
mpegts_network_schedule_initial_scan(mn);
|
||||
|
||||
/* Stop */
|
||||
if (!mpegts_mux_has_subscribers(mm))
|
||||
mm->mm_stop(mm);
|
||||
|
||||
/* Save */
|
||||
mm->mm_initial_scan_done = 1;
|
||||
mm->mm_config_save(mm);
|
||||
}
|
||||
|
||||
static int
|
||||
mpegts_mux_start ( mpegts_mux_t *mm, const char *reason, int weight )
|
||||
{
|
||||
char buf[128];
|
||||
char buf[256], buf2[256];
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
mpegts_mux_instance_t *mmi;
|
||||
|
||||
tvhtrace("mpegts", "mm %p starting for '%s' (weight %d)",
|
||||
mm, reason, weight);
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhinfo("mpegts", "%s - starting for '%s' (weight %d)",
|
||||
buf, reason, weight);
|
||||
|
||||
/* Already tuned */
|
||||
if (mm->mm_active) {
|
||||
tvhtrace("mpegts", "mm %p already active", mm);
|
||||
tvhtrace("mpegts", "%s - already active", buf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Create mux instances (where needed) */
|
||||
mm->mm_create_instances(mm);
|
||||
if (!LIST_FIRST(&mm->mm_instances))
|
||||
tvhtrace("mpegts", "mm %p has no instances", mm);
|
||||
if (!LIST_FIRST(&mm->mm_instances)) {
|
||||
tvhtrace("mpegts", "%s - has no instances", buf);
|
||||
return SM_CODE_NO_FREE_ADAPTER;
|
||||
}
|
||||
|
||||
/* Find */
|
||||
// TODO: don't like this is unbounded, if for some reason mi_start_mux()
|
||||
|
@ -224,13 +150,12 @@ mpegts_mux_start ( mpegts_mux_t *mm, const char *reason, int weight )
|
|||
break;
|
||||
}
|
||||
if (mmi)
|
||||
tvhtrace("mpegts", "found free mmi %p", mmi);
|
||||
tvhtrace("mpegts", "%s - found free mmi %p", buf, mmi);
|
||||
else
|
||||
tvhtrace("mpegts", "no input is free");
|
||||
tvhtrace("mpegts", "%s - no input is free", buf);
|
||||
|
||||
/* Try and remove a lesser instance */
|
||||
if (!mmi) {
|
||||
#if 0
|
||||
LIST_FOREACH(mmi, &mm->mm_instances, mmi_mux_link) {
|
||||
|
||||
/* Bad - skip */
|
||||
|
@ -243,30 +168,30 @@ mpegts_mux_start ( mpegts_mux_t *mm, const char *reason, int weight )
|
|||
}
|
||||
|
||||
if (mmi)
|
||||
tvhtrace("mpegts", "found mmi %p to boot", mmi);
|
||||
#endif
|
||||
tvhtrace("mpegts", "%s - found mmi %p to boot", buf, mmi);
|
||||
|
||||
/* No free input */
|
||||
if (!mmi) {
|
||||
tvhlog(LOG_DEBUG, "mpegts", "no input available");
|
||||
else {
|
||||
tvhdebug("mpegts", "%s - no input available", buf);
|
||||
return SM_CODE_NO_FREE_ADAPTER;
|
||||
}
|
||||
}
|
||||
|
||||
/* Tune */
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhlog(LOG_INFO, "mpegts", "tuning %s", buf);
|
||||
mmi->mmi_input->mi_display_name(mmi->mmi_input, buf2, sizeof(buf2));
|
||||
tvhinfo("mpegts", "%s - tuning on %s", buf, buf2);
|
||||
if (!mmi->mmi_input->mi_start_mux(mmi->mmi_input, mmi)) {
|
||||
tvhdebug("mpegts", "%s - started", buf);
|
||||
LIST_INSERT_HEAD(&mmi->mmi_input->mi_mux_active, mmi, mmi_active_link);
|
||||
mm->mm_active = mmi;
|
||||
break;
|
||||
}
|
||||
tvhtrace("mpegts", "failed to run mmi %p", mmi);
|
||||
tvhwarn("mpegts", "%s - failed to start, try another", buf);
|
||||
}
|
||||
|
||||
/* Initial scanning */
|
||||
if (mm->mm_initial_scan_status == MM_SCAN_PENDING) {
|
||||
tvhtrace("mpegts", "adding mm %p to current scan Q", mm);
|
||||
tvhtrace("mpegts", "%s - adding to current scan Q", buf);
|
||||
TAILQ_REMOVE(&mn->mn_initial_scan_pending_queue, mm, mm_initial_scan_link);
|
||||
mm->mm_initial_scan_status = MM_SCAN_CURRENT;
|
||||
TAILQ_INSERT_TAIL(&mn->mn_initial_scan_current_queue, mm, mm_initial_scan_link);
|
||||
|
@ -279,20 +204,22 @@ mpegts_mux_start ( mpegts_mux_t *mm, const char *reason, int weight )
|
|||
static void
|
||||
mpegts_mux_stop ( mpegts_mux_t *mm )
|
||||
{
|
||||
char buf[256];
|
||||
service_t *s, *t;
|
||||
mpegts_mux_instance_t *mmi = mm->mm_active;
|
||||
mpegts_input_t *mi;
|
||||
|
||||
tvhtrace("mpegts", "stopping mux %p", mm);
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhdebug("mpegts", "%s - stopping mux", buf);
|
||||
|
||||
if (mmi) {
|
||||
mi = mmi->mmi_input;
|
||||
mi->mi_stop_mux(mi, mmi);
|
||||
mm->mm_active = NULL;
|
||||
LIST_REMOVE(mmi, mmi_active_link);
|
||||
tvhtrace("mpegts", "active first = %p", LIST_FIRST(&mi->mi_mux_active));
|
||||
|
||||
/* Flush all subscribers */
|
||||
tvhtrace("mpegts", "%s - flush subscribers", buf);
|
||||
s = LIST_FIRST(&mi->mi_transports);
|
||||
while (s) {
|
||||
t = s;
|
||||
|
@ -304,6 +231,7 @@ mpegts_mux_stop ( mpegts_mux_t *mm )
|
|||
}
|
||||
|
||||
/* Flush all tables */
|
||||
tvhtrace("mpegts", "%s - flush tables", buf);
|
||||
mpegts_table_flush_all(mm);
|
||||
|
||||
/* Alert listeners */
|
||||
|
@ -311,6 +239,7 @@ mpegts_mux_stop ( mpegts_mux_t *mm )
|
|||
|
||||
/* Scanning */
|
||||
if (mm->mm_initial_scan_status == MM_SCAN_CURRENT) {
|
||||
tvhtrace("mpegts", "%s - add to pending scan Q", buf);
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
TAILQ_REMOVE(&mn->mn_initial_scan_current_queue, mm, mm_initial_scan_link);
|
||||
mm->mm_initial_scan_status = MM_SCAN_PENDING;
|
||||
|
@ -322,51 +251,114 @@ mpegts_mux_stop ( mpegts_mux_t *mm )
|
|||
mm->mm_active = NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_create_instances ( mpegts_mux_t *mm )
|
||||
{
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_open_table ( mpegts_mux_t *mm, mpegts_table_t *mt )
|
||||
{
|
||||
char buf[256];
|
||||
if (mt->mt_pid >= 0x2000)
|
||||
return;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
if (!mm->mm_table_filter[mt->mt_pid])
|
||||
tvhtrace("mpegts", "mm %p opened table pid %04X (%d)",
|
||||
mm, mt->mt_pid, mt->mt_pid);
|
||||
tvhtrace("mpegts", "%s - opened table %s pid %04X (%d)",
|
||||
buf, mt->mt_name, mt->mt_pid, mt->mt_pid);
|
||||
mm->mm_table_filter[mt->mt_pid] = 1;
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_close_table ( mpegts_mux_t *mm, mpegts_table_t *mt )
|
||||
{
|
||||
char buf[256];
|
||||
if (mt->mt_pid >= 0x2000)
|
||||
return;
|
||||
tvhtrace("mpegts", "mm %p closed table pid %04X (%d)",
|
||||
mm, mt->mt_pid, mt->mt_pid);
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhtrace("mpegts", "%s - closed table %s pid %04X (%d)",
|
||||
buf, mt->mt_name, mt->mt_pid, mt->mt_pid);
|
||||
mm->mm_table_filter[mt->mt_pid] = 0;
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_mux_load_one ( mpegts_mux_t *mm, htsmsg_t *c )
|
||||
{
|
||||
uint32_t u32;
|
||||
|
||||
/* ONID */
|
||||
if (!htsmsg_get_u32(c, "onid", &u32))
|
||||
mm->mm_onid = u32;
|
||||
/* **************************************************************************
|
||||
* Scanning
|
||||
* *************************************************************************/
|
||||
|
||||
/* TSID */
|
||||
if (!htsmsg_get_u32(c, "tsid", &u32))
|
||||
mm->mm_tsid = u32;
|
||||
static int
|
||||
mpegts_mux_has_subscribers ( mpegts_mux_t *mm )
|
||||
{
|
||||
service_t *t;
|
||||
mpegts_mux_instance_t *mmi = mm->mm_active;
|
||||
if (mmi) {
|
||||
LIST_FOREACH(t, &mmi->mmi_input->mi_transports, s_active_link)
|
||||
if (((mpegts_service_t*)t)->s_dvb_mux == mm)
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_initial_scan_link ( mpegts_mux_t *mm )
|
||||
{
|
||||
char buf1[256], buf2[256];
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
|
||||
assert(mn != NULL);
|
||||
assert(mm->mm_initial_scan_status == MM_SCAN_DONE);
|
||||
|
||||
mm->mm_initial_scan_status = MM_SCAN_PENDING;
|
||||
TAILQ_INSERT_TAIL(&mn->mn_initial_scan_pending_queue, mm,
|
||||
mm_initial_scan_link);
|
||||
mn->mn_initial_scan_num++;
|
||||
|
||||
mn->mn_display_name(mn, buf1, sizeof(buf1));
|
||||
mm->mm_display_name(mm, buf2, sizeof(buf2));
|
||||
tvhdebug("mpegts", "%s - added %s to scan pending q",
|
||||
buf1, buf2);
|
||||
mpegts_network_schedule_initial_scan(mn);
|
||||
}
|
||||
|
||||
static void
|
||||
mpegts_mux_initial_scan_timeout ( void *aux )
|
||||
{
|
||||
char buf[256];
|
||||
mpegts_mux_t *mm = aux;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhdebug("mpegts", "%s - initial scan timed", buf);
|
||||
mpegts_mux_initial_scan_done(mm);
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_mux_initial_scan_done ( mpegts_mux_t *mm )
|
||||
{
|
||||
char buf[256];
|
||||
mpegts_network_t *mn = mm->mm_network;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhinfo("mpegts", "%s - initial scan complete", buf);
|
||||
gtimer_disarm(&mm->mm_initial_scan_timeout);
|
||||
assert(mm->mm_initial_scan_status == MM_SCAN_CURRENT);
|
||||
mn->mn_initial_scan_num--;
|
||||
mm->mm_initial_scan_status = MM_SCAN_DONE;
|
||||
TAILQ_REMOVE(&mn->mn_initial_scan_current_queue, mm, mm_initial_scan_link);
|
||||
mpegts_network_schedule_initial_scan(mn);
|
||||
|
||||
/* Stop */
|
||||
if (!mpegts_mux_has_subscribers(mm)) {
|
||||
tvhtrace("mpegts", "%s - no active subscribers, stop", buf);
|
||||
mm->mm_stop(mm);
|
||||
}
|
||||
|
||||
/* Save */
|
||||
mm->mm_initial_scan_done = 1;
|
||||
mm->mm_config_save(mm);
|
||||
}
|
||||
|
||||
/* **************************************************************************
|
||||
* Creation / Config
|
||||
* *************************************************************************/
|
||||
|
||||
mpegts_mux_t *
|
||||
mpegts_mux_create0
|
||||
( mpegts_mux_t *mm, const idclass_t *class, const char *uuid,
|
||||
mpegts_network_t *mn, uint16_t onid, uint16_t tsid, htsmsg_t *conf )
|
||||
{
|
||||
char buf[256];
|
||||
idnode_insert(&mm->mm_id, uuid, class);
|
||||
|
||||
/* Enabled by default */
|
||||
|
@ -403,9 +395,56 @@ mpegts_mux_create0
|
|||
if (!mm->mm_initial_scan_done || !mn->mn_skipinitscan)
|
||||
mpegts_mux_initial_scan_link(mm);
|
||||
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
tvhtrace("mpegts", "%s - created", buf);
|
||||
|
||||
return mm;
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_mux_save ( mpegts_mux_t *mm, htsmsg_t *c )
|
||||
{
|
||||
idnode_save(&mm->mm_id, c);
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_onid ( mpegts_mux_t *mm, uint16_t onid )
|
||||
{
|
||||
char buf[256];
|
||||
if (onid == mm->mm_onid)
|
||||
return 0;
|
||||
mm->mm_onid = onid;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s - set onid %04X (%d)", buf, onid, onid);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_tsid ( mpegts_mux_t *mm, uint16_t tsid )
|
||||
{
|
||||
char buf[256];
|
||||
if (tsid == mm->mm_tsid)
|
||||
return 0;
|
||||
mm->mm_tsid = tsid;
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s - set tsid %04X (%d)", buf, tsid, tsid);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_mux_set_crid_authority ( mpegts_mux_t *mm, const char *defauth )
|
||||
{
|
||||
char buf[256];
|
||||
if (defauth && !strcmp(defauth, mm->mm_crid_authority ?: ""))
|
||||
return 0;
|
||||
tvh_str_update(&mm->mm_crid_authority, defauth);
|
||||
mm->mm_display_name(mm, buf, sizeof(buf));
|
||||
mm->mm_config_save(mm);
|
||||
tvhtrace("mpegts", "%s - set crid authority %s", buf, defauth);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/******************************************************************************
|
||||
* Editor Configuration
|
||||
|
|
|
@ -20,10 +20,23 @@
|
|||
|
||||
#include <assert.h>
|
||||
|
||||
/* ****************************************************************************
|
||||
* Class definition
|
||||
* ***************************************************************************/
|
||||
|
||||
static void
|
||||
mpegts_network_class_save
|
||||
( idnode_t *in )
|
||||
{
|
||||
mpegts_network_t *mn = (mpegts_network_t*)in;
|
||||
mn->mn_config_save(mn);
|
||||
}
|
||||
|
||||
const idclass_t mpegts_network_class =
|
||||
{
|
||||
.ic_class = "mpegts_network",
|
||||
.ic_caption = "MPEGTS Network",
|
||||
.ic_save = mpegts_network_class_save,
|
||||
.ic_properties = (const property_t[]){
|
||||
{ PROPDEF1("networkname", "Network Name",
|
||||
PT_STR, mpegts_network_t, mn_network_name) },
|
||||
|
@ -37,6 +50,10 @@ const idclass_t mpegts_network_class =
|
|||
}
|
||||
};
|
||||
|
||||
/* ****************************************************************************
|
||||
* Class methods
|
||||
* ***************************************************************************/
|
||||
|
||||
static void
|
||||
mpegts_network_display_name
|
||||
( mpegts_network_t *mn, char *buf, size_t len )
|
||||
|
@ -65,6 +82,10 @@ mpegts_network_create_service
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/* ****************************************************************************
|
||||
* Scanning
|
||||
* ***************************************************************************/
|
||||
|
||||
static void
|
||||
mpegts_network_initial_scan(void *aux)
|
||||
{
|
||||
|
@ -87,36 +108,61 @@ mpegts_network_schedule_initial_scan ( mpegts_network_t *mn )
|
|||
gtimer_arm(&mn->mn_initial_scan_timer, mpegts_network_initial_scan, mn, 0);
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_network_add_input ( mpegts_network_t *mn, mpegts_input_t *mi )
|
||||
{
|
||||
mi->mi_network = mn;
|
||||
LIST_INSERT_HEAD(&mn->mn_inputs, mi, mi_network_link);
|
||||
}
|
||||
/* ****************************************************************************
|
||||
* Creation/Config
|
||||
* ***************************************************************************/
|
||||
|
||||
mpegts_network_t *
|
||||
mpegts_network_create0
|
||||
( mpegts_network_t *mn, const idclass_t *idc, const char *uuid,
|
||||
const char *netname )
|
||||
const char *netname, htsmsg_t *conf )
|
||||
{
|
||||
char buf[256];
|
||||
|
||||
/* Setup idnode */
|
||||
idnode_insert(&mn->mn_id, uuid, idc);
|
||||
if (conf)
|
||||
idnode_load(&mn->mn_id, conf);
|
||||
|
||||
/* Default callbacks */
|
||||
mn->mn_display_name = mpegts_network_display_name;
|
||||
mn->mn_config_save = mpegts_network_config_save;
|
||||
mn->mn_create_mux = mpegts_network_create_mux;
|
||||
mn->mn_create_service = mpegts_network_create_service;
|
||||
|
||||
/* Network name */
|
||||
if (netname) mn->mn_network_name = strdup(netname);
|
||||
|
||||
/* Init Qs */
|
||||
TAILQ_INIT(&mn->mn_initial_scan_pending_queue);
|
||||
TAILQ_INIT(&mn->mn_initial_scan_current_queue);
|
||||
|
||||
mn->mn_display_name(mn, buf, sizeof(buf));
|
||||
tvhtrace("mpegts", "created network %s", buf);
|
||||
return mn;
|
||||
}
|
||||
|
||||
void
|
||||
mpegts_network_add_input ( mpegts_network_t *mn, mpegts_input_t *mi )
|
||||
{
|
||||
char buf1[256], buf2[265];
|
||||
mi->mi_network = mn;
|
||||
LIST_INSERT_HEAD(&mn->mn_inputs, mi, mi_network_link);
|
||||
mn->mn_display_name(mn, buf1, sizeof(buf1));
|
||||
mi->mi_display_name(mi, buf2, sizeof(buf2));
|
||||
tvhdebug("mpegts", "%s - added input %s", buf1, buf2);
|
||||
}
|
||||
|
||||
int
|
||||
mpegts_network_set_nid
|
||||
( mpegts_network_t *mn, uint16_t nid )
|
||||
{
|
||||
char buf[256];
|
||||
if (mn->mn_nid == nid)
|
||||
return 0;
|
||||
mn->mn_nid = nid;
|
||||
mn->mn_display_name(mn, buf, sizeof(buf));
|
||||
tvhdebug("mpegts", "%s - set nid %04X (%d)", buf, nid, nid);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
@ -124,9 +170,12 @@ int
|
|||
mpegts_network_set_network_name
|
||||
( mpegts_network_t *mn, const char *name )
|
||||
{
|
||||
char buf[256];
|
||||
if (!name || !strcmp(name, mn->mn_network_name ?: ""))
|
||||
return 0;
|
||||
tvh_str_update(&mn->mn_network_name, name);
|
||||
mn->mn_display_name(mn, buf, sizeof(buf));
|
||||
tvhdebug("mpegts", "%s - set name %s", buf, name);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
|
|
@ -82,8 +82,9 @@ void _tvhlog_hexdump ( const char *file, int line,
|
|||
#define tvhlog_hexdump(...) (void)0
|
||||
#endif
|
||||
|
||||
#define tvhdebug(...) tvhlog(LOG_DEBUG, ##__VA_ARGS__)
|
||||
#define tvhdebug(...) tvhlog(LOG_DEBUG, ##__VA_ARGS__)
|
||||
#define tvhinfo(...) tvhlog(LOG_INFO, ##__VA_ARGS__)
|
||||
#define tvhwarn(...) tvhlog(LOG_WARNING, ##__VA_ARGS__)
|
||||
#define tvherror(...) tvhlog(LOG_ERR, ##__VA_ARGS__)
|
||||
|
||||
#endif /* __TVH_LOGGING_H__ */
|
||||
|
|
Loading…
Add table
Reference in a new issue