Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
DVR/EPG: improve the EPG running check (pause/warm)
  • Loading branch information
perexg committed Nov 22, 2015
1 parent 7e0e78c commit e06589a
Show file tree
Hide file tree
Showing 6 changed files with 71 additions and 23 deletions.
3 changes: 2 additions & 1 deletion src/dvr/dvr.h
Expand Up @@ -155,6 +155,7 @@ typedef struct dvr_entry {

time_t de_running_start;
time_t de_running_stop;
time_t de_running_pause;

char *de_owner;
char *de_creator;
Expand Down Expand Up @@ -514,7 +515,7 @@ void dvr_event_removed(epg_broadcast_t *e);

void dvr_event_updated(epg_broadcast_t *e);

void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running);
void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, epg_running_t running);

dvr_entry_t *dvr_entry_find_by_id(int id);

Expand Down
24 changes: 21 additions & 3 deletions src/dvr/dvr_db.c
Expand Up @@ -1615,7 +1615,7 @@ void dvr_event_updated(epg_broadcast_t *e)
/**
* Event running status is updated
*/
void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running)
void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, epg_running_t running)
{
dvr_entry_t *de;
const char *srcname;
Expand All @@ -1626,9 +1626,17 @@ void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running)
if (!dvr_entry_get_epg_running(de)) {
atomic_exchange_time_t(&de->de_running_start, 0);
atomic_exchange_time_t(&de->de_running_stop, 0);
atomic_exchange_time_t(&de->de_running_pause, 0);
continue;
}
if (running && de->de_dvb_eid == e->dvb_eid) {
if (running == EPG_RUNNING_NOW && de->de_dvb_eid == e->dvb_eid) {
if (de->de_running_pause) {
tvhdebug("dvr", "dvr entry %s event %s on %s - EPG unpause",
idnode_uuid_as_sstr(&de->de_id),
epg_broadcast_get_title(e, NULL),
channel_get_name(e->channel));
atomic_exchange_time_t(&de->de_running_pause, 0);
}
if (!de->de_running_start) {
tvhdebug("dvr", "dvr entry %s event %s on %s - EPG marking start",
idnode_uuid_as_sstr(&de->de_id),
Expand All @@ -1644,7 +1652,8 @@ void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running)
epg_broadcast_get_title(e, NULL),
channel_get_name(e->channel));
}
} else if ((!running && de->de_dvb_eid == e->dvb_eid) || running) {
} else if ((running == EPG_RUNNING_STOP && de->de_dvb_eid == e->dvb_eid) ||
running == EPG_RUNNING_NOW) {
/*
* make checking more robust
* sometimes, the running bits are parsed randomly for a few moments
Expand All @@ -1662,6 +1671,7 @@ void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running)
channel_get_name(de->de_channel));
}
atomic_exchange_time_t(&de->de_running_stop, dispatch_clock);
atomic_exchange_time_t(&de->de_running_pause, 0);
if (de->de_sched_state == DVR_RECORDING && de->de_running_start) {
de->de_dont_reschedule = 1;
dvr_stop_recording(de, SM_CODE_OK, 0, 0);
Expand All @@ -1670,6 +1680,14 @@ void dvr_event_running(epg_broadcast_t *e, epg_source_t esrc, int running)
epg_broadcast_get_title(e, NULL),
channel_get_name(de->de_channel));
}
} else if (running == EPG_RUNNING_PAUSE && de->de_dvb_eid == e->dvb_eid) {
if (!de->de_running_pause) {
tvhdebug("dvr", "dvr entry %s event %s on %s - EPG pause",
idnode_uuid_as_sstr(&de->de_id),
epg_broadcast_get_title(e, NULL),
channel_get_name(e->channel));
atomic_exchange_time_t(&de->de_running_pause, dispatch_clock);
}
}
}
}
Expand Down
24 changes: 18 additions & 6 deletions src/dvr/dvr_rec.c
Expand Up @@ -1195,7 +1195,8 @@ dvr_thread(void *aux)
streaming_message_t *sm, *sm2;
th_pkt_t *pkt, *pkt2, *pkt3;
streaming_start_t *ss = NULL;
int run = 1, started = 0, muxing = 0, comm_skip, epg_running = 0, rs;
int run = 1, started = 0, muxing = 0, comm_skip, rs;
int epg_running = 0, epg_pause = 0;
int commercial = COMMERCIAL_UNKNOWN;
int running_disabled;
int64_t packets = 0, dts_offset = PTS_UNSET;
Expand Down Expand Up @@ -1226,7 +1227,9 @@ dvr_thread(void *aux)
running_start = atomic_add_time_t(&de->de_running_start, 0);
running_stop = atomic_add_time_t(&de->de_running_stop, 0);
if (running_start > 0) {
epg_running = running_start >= running_stop;
epg_running = running_start >= running_stop ? 1 : 0;
if (epg_running && atomic_add_time_t(&de->de_running_pause, 0) >= running_start)
epg_running = 2;
} else if (running_stop == 0) {
if (start_time + 2 >= dispatch_clock) {
TAILQ_INSERT_TAIL(&backlog, sm, sm_link);
Expand All @@ -1251,7 +1254,7 @@ dvr_thread(void *aux)
rs = DVR_RS_RUNNING;
if (!epg_running)
rs = DVR_RS_EPG_WAIT;
else if (pkt->pkt_commercial == COMMERCIAL_YES)
else if (pkt->pkt_commercial == COMMERCIAL_YES || epg_running == 2)
rs = DVR_RS_COMMERCIAL;
dvr_rec_set_state(de, rs, 0);

Expand All @@ -1264,8 +1267,12 @@ dvr_thread(void *aux)
break;
}

if (commercial != pkt->pkt_commercial)
if (epg_pause != (epg_running == 2)) {
epg_pause = epg_running == 2;
muxer_add_marker(prch->prch_muxer);
} else if (commercial != pkt->pkt_commercial) {
muxer_add_marker(prch->prch_muxer);
}

commercial = pkt->pkt_commercial;

Expand Down Expand Up @@ -1313,12 +1320,17 @@ dvr_thread(void *aux)
break;

case SMT_MPEGTS:
dvr_rec_set_state(de, !epg_running ? DVR_RS_EPG_WAIT : DVR_RS_RUNNING, 0);
rs = DVR_RS_RUNNING;
if (!epg_running)
rs = DVR_RS_EPG_WAIT;
else if (epg_running == 2)
rs = DVR_RS_COMMERCIAL;
dvr_rec_set_state(de, rs, 0);

if (ss == NULL)
break;

if (!epg_running) {
if ((rs == DVR_RS_COMMERCIAL && comm_skip) || !epg_running) {
if (packets && running_start == 0) {
dvr_streaming_restart(de, &run);
packets = 0;
Expand Down
12 changes: 6 additions & 6 deletions src/epg.c
Expand Up @@ -1418,7 +1418,7 @@ static void _epg_channel_timer_callback ( void *p )

/* Clear now/next */
if ((cur = ch->ch_epg_now)) {
if (cur->running) {
if (cur->running != EPG_RUNNING_STOP) {
/* running? don't do anything */
gtimer_arm(&ch->ch_epg_timer, _epg_channel_timer_callback, ch, 2);
return;
Expand Down Expand Up @@ -1685,22 +1685,22 @@ epg_broadcast_t *epg_broadcast_find_by_eid ( channel_t *ch, uint16_t eid )
}

void epg_broadcast_notify_running
( epg_broadcast_t *broadcast, epg_source_t esrc, int running )
( epg_broadcast_t *broadcast, epg_source_t esrc, epg_running_t running )
{
channel_t *ch;
epg_broadcast_t *now;
int orunning = broadcast->running;

broadcast->running = !!running;
broadcast->running = running;
ch = broadcast->channel;
now = ch ? ch->ch_epg_now : NULL;
if (!running) {
if (running == EPG_RUNNING_STOP) {
if (now == broadcast && orunning == broadcast->running)
broadcast->stop = dispatch_clock - 1;
} else {
if (broadcast != now && now) {
now->running = 0;
dvr_event_running(now, esrc, 0);
now->running = EPG_RUNNING_STOP;
dvr_event_running(now, esrc, EPG_RUNNING_STOP);
}
}
dvr_event_running(broadcast, esrc, running);
Expand Down
13 changes: 10 additions & 3 deletions src/epg.h
Expand Up @@ -60,10 +60,17 @@ extern int epg_in_load;
*
*/
typedef enum {
EPG_SOURCE_NONE = 0,
EPG_SOURCE_EIT = 1,
EPG_SOURCE_NONE = 0,
EPG_SOURCE_EIT = 1,
} epg_source_t;

typedef enum {
EPG_RUNNING_STOP = 0,
EPG_RUNNING_WARM = 1,
EPG_RUNNING_NOW = 2,
EPG_RUNNING_PAUSE = 3,
} epg_running_t;

/* ************************************************************************
* Genres
* ***********************************************************************/
Expand Down Expand Up @@ -470,7 +477,7 @@ epg_broadcast_t *epg_broadcast_find_by_id ( uint32_t id );
epg_broadcast_t *epg_broadcast_clone
( struct channel *channel, epg_broadcast_t *src, int *save );
void epg_broadcast_notify_running
( epg_broadcast_t *b, epg_source_t esrc, int running );
( epg_broadcast_t *b, epg_source_t esrc, epg_running_t running );

/* Mutators */
int epg_broadcast_set_episode
Expand Down
18 changes: 14 additions & 4 deletions src/epggrab/module/eit.c
Expand Up @@ -409,6 +409,7 @@ static int _eit_process_event_one
epg_broadcast_t *ebc;
epg_episode_t *ee;
epg_serieslink_t *es;
epg_running_t run;
eit_event_t ev;

/* Core fields */
Expand Down Expand Up @@ -548,10 +549,19 @@ static int _eit_process_event_one
if (ev.desc) lang_str_destroy(ev.desc);

/* use running flag only for current broadcast */
if (running && tableid == 0x4e && sect == 0)
epg_broadcast_notify_running(ebc, EPG_SOURCE_EIT, running == 4);
if (running && running != 4 && tableid == 0x4e && sect == 1)
epg_broadcast_notify_running(ebc, EPG_SOURCE_EIT, 0);
if (running && tableid == 0x4e) {
if (sect == 0) {
switch (running) {
case 2: run = EPG_RUNNING_WARM; break;
case 3: run = EPG_RUNNING_PAUSE; break;
case 4: run = EPG_RUNNING_NOW; break;
default: run = EPG_RUNNING_STOP; break;
}
epg_broadcast_notify_running(ebc, EPG_SOURCE_EIT, run);
} else if (sect == 1 && running != 2 && running != 3 && running != 4) {
epg_broadcast_notify_running(ebc, EPG_SOURCE_EIT, EPG_RUNNING_STOP);
}
}

return 0;
}
Expand Down

0 comments on commit e06589a

Please sign in to comment.