summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--HISTORY7
-rw-r--r--eit.c54
-rw-r--r--eit.h5
-rwxr-xr-xepg2html.pl95
4 files changed, 158 insertions, 3 deletions
diff --git a/HISTORY b/HISTORY
index 485f24a2..27634ec5 100644
--- a/HISTORY
+++ b/HISTORY
@@ -311,3 +311,10 @@ Video Disk Recorder Revision History
can receive a certain channel on the primary interface. This is currently in
an early state and may still cause some problems, but it appears to work nice
already.
+
+2000-11-26: Version 0.69
+
+- The EPG data is now dumped into the file /video/epg.data every ten minutes.
+ Use the Perl script 'epg2html.pl' to convert the raw EPG data into a simple
+ HTML programme listing.
+
diff --git a/eit.c b/eit.c
index 79855282..52dc6618 100644
--- a/eit.c
+++ b/eit.c
@@ -13,7 +13,7 @@
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
- * $Id: eit.c 1.9 2000/11/18 13:42:28 kls Exp $
+ * $Id: eit.c 1.10 2000/11/25 12:51:06 kls Exp $
***************************************************************************/
#include "eit.h"
@@ -33,6 +33,8 @@
#include <sys/types.h>
#include <time.h>
#include <unistd.h>
+#include "config.h"
+#include "videodir.h"
// --- cMJD ------------------------------------------------------------------
@@ -393,6 +395,21 @@ unsigned short cEventInfo::GetServiceID() const
return uServiceID;
}
+/** */
+void cEventInfo::Dump(FILE *f) const
+{
+ if (tTime + lDuration >= time(NULL)) {
+ fprintf(f, "E %u %ld %ld\n", uEventID, tTime, lDuration);
+ if (!isempty(pTitle))
+ fprintf(f, "T %s\n", pTitle);
+ if (!isempty(pSubtitle))
+ fprintf(f, "S %s\n", pSubtitle);
+ if (!isempty(pExtendedDescription))
+ fprintf(f, "D %s\n", pExtendedDescription);
+ fprintf(f, "e\n");
+ }
+}
+
// --- cSchedule -------------------------------------------------------------
cSchedule::cSchedule(unsigned short servid)
@@ -529,6 +546,19 @@ void cSchedule::Cleanup(time_t tTime)
}
}
+/** */
+void cSchedule::Dump(FILE *f) const
+{
+ cChannel *channel = Channels.GetByServiceID(uServiceID);
+ if (channel)
+ {
+ fprintf(f, "C %u %s\n", uServiceID, channel->name);
+ for (cEventInfo *p = Events.First(); p; p = Events.Next(p))
+ p->Dump(f);
+ fprintf(f, "c\n");
+ }
+}
+
// --- cSchedules ------------------------------------------------------------
cSchedules::cSchedules()
@@ -590,6 +620,13 @@ void cSchedules::Cleanup()
}
}
+/** */
+void cSchedules::Dump(FILE *f) const
+{
+ for (cSchedule *p = First(); p; p = Next(p))
+ p->Dump(f);
+}
+
// --- cEIT ------------------------------------------------------------------
#define DEC(N) dec << setw(N) << setfill(int('0'))
@@ -1105,6 +1142,7 @@ void cSIProcessor::Action()
unsigned int seclen;
unsigned int pid;
time_t lastCleanup = time(NULL);
+ time_t lastDump = time(NULL);
struct pollfd pfd;
while(true)
@@ -1123,6 +1161,19 @@ void cSIProcessor::Action()
schedulesMutex.Unlock();
lastCleanup = now;
}
+ if (now - lastDump > 600)
+ {
+ LOCK_THREAD;
+
+ schedulesMutex.Lock();
+ FILE *f = fopen(AddDirectory(VideoDirectory, "epg.data"), "w");
+ if (f) {
+ schedules->Dump(f);
+ fclose(f);
+ }
+ lastDump = now;
+ schedulesMutex.Unlock();
+ }
}
/* wait data become ready from the bitfilter */
@@ -1283,4 +1334,3 @@ bool cSIProcessor::RefreshFilters()
return ret;
}
-
diff --git a/eit.h b/eit.h
index d5c4ebdc..bedead75 100644
--- a/eit.h
+++ b/eit.h
@@ -13,7 +13,7 @@
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
- * $Id: eit.h 1.3 2000/11/17 16:14:27 kls Exp $
+ * $Id: eit.h 1.4 2000/11/24 14:35:22 kls Exp $
***************************************************************************/
#ifndef __EIT_H
@@ -66,6 +66,7 @@ public:
unsigned short GetServiceID(void) const;
int GetChannelNumber(void) const { return nChannelNumber; }
void SetChannelNumber(int ChannelNumber) const { ((cEventInfo *)this)->nChannelNumber = ChannelNumber; } // doesn't modify the EIT data, so it's ok to make it 'const'
+ void Dump(FILE *f) const;
};
class cSchedule : public cListObject {
@@ -92,6 +93,7 @@ public:
const cEventInfo *GetEvent(time_t tTime) const;
const cEventInfo *GetEventNumber(int n) const { return Events.Get(n); }
int NumEvents(void) const { return Events.Count(); }
+ void Dump(FILE *f) const;
};
class cSchedules : public cList<cSchedule> {
@@ -107,6 +109,7 @@ public:
~cSchedules();
const cSchedule *GetSchedule(unsigned short servid) const;
const cSchedule *GetSchedule(void) const;
+ void Dump(FILE *f) const;
};
typedef struct sip_filter {
diff --git a/epg2html.pl b/epg2html.pl
new file mode 100755
index 00000000..06d76b74
--- /dev/null
+++ b/epg2html.pl
@@ -0,0 +1,95 @@
+#!/usr/bin/perl
+
+# A simple EPG to HTML converter
+#
+# Converts the EPG data written by 'vdr' into the file /video/epg.data
+# into a simple HTML programme listing, consisting of one file per channel
+# plus an 'index.htm' file. All output files are written into the current
+# directory.
+#
+# Usage: epg2html.pl < /video/epg.data
+#
+# See the main source file 'vdr.c' for copyright information and
+# how to reach the author.
+#
+# $Id: epg2html.pl 1.1 2000/11/26 15:23:39 kls Exp $
+
+@Index = ();
+
+sub GetDay
+{
+ return substr(localtime(shift), 0, 10);
+}
+
+sub GetTime
+{
+ return substr(localtime(shift), 11, 5);
+}
+
+sub Tags
+{
+ my $s = shift;
+ $s =~ s/\&/&amp;/g;
+ $s =~ s/</&lt;/g;
+ $s =~ s/>/&gt;/g;
+ return $s;
+}
+
+while (<>) {
+ chomp;
+ if (/^C ([^ ]+) *(.*)/) {
+ my $Channel = $2;
+ (my $Page = $Channel) =~ s/ /_/g;
+ $Channel = Tags($Channel);
+ push(@Index, qq{<a href="$Page.htm">$Channel</a><br>\n});
+ my %Events = ();
+ while (<>) {
+ if (/^E (.*) (.*) (.*)/) {
+ (my $Time, $Duration) = ($2, $3);
+ my $Title = "", $Subtitle = "", $Description = "";
+ while (<>) {
+ if (/^T (.*)/) { $Title = Tags($1); }
+ elsif (/^S (.*)/) { $Subtitle = Tags($1); }
+ elsif (/^D (.*)/) { $Description = Tags($1); }
+ elsif (/^e/) {
+ $Events{$Time} = [($Duration, $Title, $Subtitle, $Description)];
+ last;
+ }
+ }
+ }
+ elsif (/^c/) {
+ my @Schedule = ();
+ my $Day = "";
+ for $t (sort keys %Events) {
+ (my $Duration, $Title, $Subtitle, $Description) = @{$Events{$t}};
+ my $d = GetDay($t);
+ if ($d ne $Day) {
+ push(@Schedule, "</table>\n") if ($Day && @Schedule);
+ push(@Schedule, "<h2>$d</h2>\n");
+ push(@Schedule, "<table cellspacing=2>\n");
+ $Day = $d;
+ }
+ my $Entry = $Title;
+ $Entry .= "<br><i>$Subtitle</i>" if $Subtitle;
+ $Entry .= "<br>$Description" if $Description;
+ push(@Schedule, "<tr><td valign=top>" . GetTime($t) . "</td><td>$Entry</td></tr>\n");
+ }
+ push(@Schedule, "</table>\n") if (@Schedule);
+ open(PAGE, ">$Page.htm") or die $!;
+ print PAGE "<html>\n<head><title>$Channel</title><head>\n<body>\n";
+ print PAGE "<h1>$Channel</h1>\n";
+ print PAGE @Schedule;
+ print PAGE "</body>\n</html>\n";
+ close(PAGE);
+ last;
+ }
+ }
+ }
+ }
+
+open(INDEX, ">index.htm") or die $!;
+print INDEX "<html>\n<head><title>EPG Index</title><head>\n<body>\n";
+print INDEX sort { lc($a) cmp lc($b) } @Index;
+print INDEX "</body>\n</html>\n";
+close(INDEX);
+