]> git.ipfire.org Git - thirdparty/tvheadend.git/commitdiff
epggrab: fix the epgid match, prefer epgid then name and lastly number, fixes #3227
authorJaroslav Kysela <perex@perex.cz>
Fri, 30 Oct 2015 10:35:33 +0000 (11:35 +0100)
committerJaroslav Kysela <perex@perex.cz>
Fri, 30 Oct 2015 10:40:24 +0000 (11:40 +0100)
src/epggrab/channel.c
src/epggrab/private.h

index fe06053d54c2fb0f07f0dcd129b18798c6124ca3..24e91e7cc7ad9e11b252fe1e96dd6708338dc851 100644 (file)
@@ -36,26 +36,78 @@ SKEL_DECLARE(epggrab_channel_skel, epggrab_channel_t);
  * EPG Grab Channel functions
  * *************************************************************************/
 
-/* Check if channels match */
-int epggrab_channel_match ( epggrab_channel_t *ec, channel_t *ch )
+static inline int
+is_paired( epggrab_channel_t *ec )
 {
-  const char *chid, *s;
-  htsmsg_field_t *f;
+  return !ec->only_one || !LIST_FIRST(&ec->channels);
+}
 
-  if (!ec || !ch || !ch->ch_epgauto || !ch->ch_enabled || ch->ch_epg_parent ||
-      !ec->enabled) return 0;
-  if (ec->only_one && LIST_FIRST(&ec->channels)) return 0; // ignore already paired
+static inline int
+epggrab_channel_check ( epggrab_channel_t *ec, channel_t *ch )
+{
+  if (!ec || !ch || !ch->ch_epgauto || !ch->ch_enabled)
+    return 0;
+  if (ch->ch_epg_parent || !ec->enabled)
+    return 0;
+  if (is_paired(ec))
+    return 0; // ignore already paired
+  return 1;
+}
 
+/* Check if channels match by epgid */
+int epggrab_channel_match_epgid ( epggrab_channel_t *ec, channel_t *ch )
+{
+  const char *chid;
+
+  if (ec->id == NULL)
+    return 0;
+  if (!epggrab_channel_check(ec, ch))
+    return 0;
   chid = channel_get_epgid(ch);
-  if (ec->name && !strcmp(ec->name, chid)) return 1;
+  if (chid && !strcmp(ec->id, chid))
+    return 1;
+  return 0;
+}
+
+/* Check if channels match by name */
+int epggrab_channel_match_name ( epggrab_channel_t *ec, channel_t *ch )
+{
+  const char *name, *s;
+  htsmsg_field_t *f;
+
+  if (!epggrab_channel_check(ec, ch))
+    return 0;
+
+  name = channel_get_name(ch);
+  if (name == NULL)
+    return 0;
+
+  if (ec->name && !strcmp(ec->name, name))
+    return 1;
+
   if (ec->names)
     HTSMSG_FOREACH(f, ec->names)
       if ((s = htsmsg_field_get_str(f)) != NULL)
-        if (!strcmp(s, chid)) return 1;
+        if (!strcmp(s, name))
+          return 1;
+
+  return 0;
+}
+
+/* Check if channels match by number */
+int epggrab_channel_match_number ( epggrab_channel_t *ec, channel_t *ch )
+{
+  if (ec->lcn == 0)
+    return 0;
+
+  if (!epggrab_channel_check(ec, ch))
+    return 0;
+
   if (ec->lcn && ec->lcn == channel_get_number(ch)) return 1;
   return 0;
 }
 
+
 /* Destroy */
 void
 epggrab_channel_link_delete
@@ -122,15 +174,6 @@ epggrab_channel_map ( idnode_t *ec, idnode_t *ch, void *origin )
   return epggrab_channel_link((epggrab_channel_t *)ec, (channel_t *)ch, origin);
 }
 
-/* Match and link (basically combines two funcs above for ease) */
-int epggrab_channel_match_and_link ( epggrab_channel_t *ec, channel_t *ch )
-{
-  int r = epggrab_channel_match(ec, ch);
-  if (r)
-    epggrab_channel_link(ec, ch, NULL);
-  return r;
-}
-
 /* Set name */
 int epggrab_channel_set_name ( epggrab_channel_t *ec, const char *name )
 {
@@ -206,16 +249,48 @@ int epggrab_channel_set_number ( epggrab_channel_t *ec, int major, int minor )
   return save;
 }
 
+/* Autolink EPG channel to channel */
+static int
+epggrab_channel_autolink_one( epggrab_channel_t *ec, channel_t *ch )
+{
+  if (epggrab_channel_match_epgid(ec, ch))
+    return epggrab_channel_link(ec, ch, NULL);
+  else if (epggrab_channel_match_name(ec, ch))
+    return epggrab_channel_link(ec, ch, NULL);
+  else if (epggrab_channel_match_number(ec, ch))
+    return epggrab_channel_link(ec, ch, NULL);
+  return 0;
+}
+
+/* Autolink EPG channel to channel */
+static int
+epggrab_channel_autolink( epggrab_channel_t *ec )
+{
+  channel_t *ch;
+
+  CHANNEL_FOREACH(ch)
+    if (epggrab_channel_match_epgid(ec, ch))
+      if (epggrab_channel_link(ec, ch, NULL))
+        return 1;
+  CHANNEL_FOREACH(ch)
+    if (epggrab_channel_match_name(ec, ch))
+      if (epggrab_channel_link(ec, ch, NULL))
+        return 1;
+  CHANNEL_FOREACH(ch)
+    if (epggrab_channel_match_number(ec, ch))
+      if (epggrab_channel_link(ec, ch, NULL))
+        return 1;
+  return 0;
+}
+
 /* Channel settings updated */
 void epggrab_channel_updated ( epggrab_channel_t *ec )
 {
-  channel_t *ch;
   if (!ec) return;
 
   /* Find a link */
-  if (!ec->only_one || !LIST_FIRST(&ec->channels))
-    CHANNEL_FOREACH(ch)
-      if (epggrab_channel_match_and_link(ec, ch)) break;
+  if (!is_paired(ec))
+    epggrab_channel_autolink(ec);
 
   /* Save */
   epggrab_channel_save(ec);
@@ -380,12 +455,14 @@ void epggrab_channel_end_scan ( epggrab_module_t *mod )
 void epggrab_channel_add ( channel_t *ch )
 {
   epggrab_module_t *mod;
-  epggrab_channel_t *egc;
+  epggrab_channel_t *ec;
 
   LIST_FOREACH(mod, &epggrab_modules, link)
-    RB_FOREACH(egc, &mod->channels, link)
-      if (epggrab_channel_match_and_link(egc, ch))
-        break;
+    RB_FOREACH(ec, &mod->channels, link) {
+      if (!is_paired(ec))
+        if (epggrab_channel_autolink_one(ec, ch))
+          break;
+    }
 }
 
 void epggrab_channel_rem ( channel_t *ch )
index 0fa93d73b795dcccac59aa3e28e3503973d356b0..d3b999dfa968b33712f7b7fbd7c33ff8278a4e20 100644 (file)
@@ -46,9 +46,9 @@ void      epggrab_module_channels_load ( const char *modid );
  * Channel processing
  * *************************************************************************/
 
-int  epggrab_channel_match ( epggrab_channel_t *ec, struct channel *ch );
-int  epggrab_channel_match_and_link
-  ( epggrab_channel_t *ec, struct channel *ch );
+int  epggrab_channel_match_epgid ( epggrab_channel_t *ec, struct channel *ch );
+int  epggrab_channel_match_name ( epggrab_channel_t *ec, struct channel *ch );
+int  epggrab_channel_match_number ( epggrab_channel_t *ec, struct channel *ch );
 
 epggrab_channel_t *epggrab_channel_create
   ( epggrab_module_t *owner, htsmsg_t *conf, const char *uuid );