From ac9622bb8ad8d660fca4e77460c970f72c344afa Mon Sep 17 00:00:00 2001 From: Klaus Schmidinger Date: Sun, 20 Oct 2002 12:28:55 +0200 Subject: Timers now internally have a pointer to their channel --- config.c | 377 +-------------------------------------------------------------- 1 file changed, 1 insertion(+), 376 deletions(-) (limited to 'config.c') diff --git a/config.c b/config.c index f4ef7b86..7cea98ed 100644 --- a/config.c +++ b/config.c @@ -4,13 +4,12 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: config.c 1.110 2002/10/19 11:34:01 kls Exp $ + * $Id: config.c 1.111 2002/10/19 15:49:51 kls Exp $ */ #include "config.h" #include #include -#include "channels.h" //XXX timers! #include "i18n.h" #include "interface.h" #include "plugin.h" @@ -20,339 +19,6 @@ // format characters in order to allow any number of blanks after a numeric // value! -// -- cTimer ----------------------------------------------------------------- - -char *cTimer::buffer = NULL; - -cTimer::cTimer(bool Instant) -{ - startTime = stopTime = 0; - recording = pending = false; - active = Instant ? taActInst : taInactive; - cChannel *ch = Channels.GetByNumber(cDevice::CurrentChannel()); - channel = ch ? ch->Number() : 0; - time_t t = time(NULL); - struct tm tm_r; - struct tm *now = localtime_r(&t, &tm_r); - day = now->tm_mday; - start = now->tm_hour * 100 + now->tm_min; - stop = now->tm_hour * 60 + now->tm_min + Setup.InstantRecordTime; - stop = (stop / 60) * 100 + (stop % 60); - if (stop >= 2400) - stop -= 2400; -//TODO VPS??? - priority = Setup.DefaultPriority; - lifetime = Setup.DefaultLifetime; - *file = 0; - firstday = 0; - summary = NULL; - if (Instant && ch) - snprintf(file, sizeof(file), "%s%s", Setup.MarkInstantRecord ? "@" : "", *Setup.NameInstantRecord ? Setup.NameInstantRecord : ch->Name()); -} - -cTimer::cTimer(const cEventInfo *EventInfo) -{ - startTime = stopTime = 0; - recording = pending = false; - active = true; - cChannel *ch = Channels.GetByServiceID(EventInfo->GetServiceID()); - channel = ch ? ch->Number() : 0; - time_t tstart = EventInfo->GetTime(); - time_t tstop = tstart + EventInfo->GetDuration() + Setup.MarginStop * 60; - tstart -= Setup.MarginStart * 60; - struct tm tm_r; - struct tm *time = localtime_r(&tstart, &tm_r); - day = time->tm_mday; - start = time->tm_hour * 100 + time->tm_min; - time = localtime_r(&tstop, &tm_r); - stop = time->tm_hour * 100 + time->tm_min; - if (stop >= 2400) - stop -= 2400; - priority = Setup.DefaultPriority; - lifetime = Setup.DefaultLifetime; - *file = 0; - const char *Title = EventInfo->GetTitle(); - if (!isempty(Title)) - strn0cpy(file, EventInfo->GetTitle(), sizeof(file)); - firstday = 0; - summary = NULL; -} - -cTimer::~cTimer() -{ - free(summary); -} - -cTimer& cTimer::operator= (const cTimer &Timer) -{ - memcpy(this, &Timer, sizeof(*this)); - if (summary) - summary = strdup(summary); - return *this; -} - -bool cTimer::operator< (const cListObject &ListObject) -{ - cTimer *ti = (cTimer *)&ListObject; - time_t t1 = StartTime(); - time_t t2 = ti->StartTime(); - return t1 < t2 || (t1 == t2 && priority > ti->priority); -} - -const char *cTimer::ToText(cTimer *Timer) -{ - free(buffer); - strreplace(Timer->file, ':', '|'); - strreplace(Timer->summary, '\n', '|'); - asprintf(&buffer, "%d:%d:%s:%04d:%04d:%d:%d:%s:%s\n", Timer->active, Timer->channel, PrintDay(Timer->day, Timer->firstday), Timer->start, Timer->stop, Timer->priority, Timer->lifetime, Timer->file, Timer->summary ? Timer->summary : ""); - strreplace(Timer->summary, '|', '\n'); - strreplace(Timer->file, '|', ':'); - return buffer; -} - -const char *cTimer::ToText(void) -{ - return ToText(this); -} - -int cTimer::TimeToInt(int t) -{ - return (t / 100 * 60 + t % 100) * 60; -} - -int cTimer::ParseDay(const char *s, time_t *FirstDay) -{ - char *tail; - int d = strtol(s, &tail, 10); - if (FirstDay) - *FirstDay = 0; - if (tail && *tail) { - d = 0; - if (tail == s) { - const char *first = strchr(s, '@'); - int l = first ? first - s : strlen(s); - if (l == 7) { - for (const char *p = s + 6; p >= s; p--) { - d <<= 1; - d |= (*p != '-'); - } - d |= 0x80000000; - } - if (FirstDay && first) { - ++first; - if (strlen(first) == 10) { - struct tm tm_r; - if (3 == sscanf(first, "%d-%d-%d", &tm_r.tm_year, &tm_r.tm_mon, &tm_r.tm_mday)) { - tm_r.tm_year -= 1900; - tm_r.tm_mon--; - tm_r.tm_hour = tm_r.tm_min = tm_r.tm_sec = 0; - tm_r.tm_isdst = -1; // makes sure mktime() will determine the correct DST setting - *FirstDay = mktime(&tm_r); - } - } - else - d = 0; - } - } - } - else if (d < 1 || d > 31) - d = 0; - return d; -} - -const char *cTimer::PrintDay(int d, time_t FirstDay) -{ -#define DAYBUFFERSIZE 32 - static char buffer[DAYBUFFERSIZE]; - if ((d & 0x80000000) != 0) { - char *b = buffer; - const char *w = tr("MTWTFSS"); - while (*w) { - *b++ = (d & 1) ? *w : '-'; - d >>= 1; - w++; - } - if (FirstDay) { - struct tm tm_r; - localtime_r(&FirstDay, &tm_r); - b += strftime(b, DAYBUFFERSIZE - (b - buffer), "@%Y-%m-%d", &tm_r); - } - *b = 0; - } - else - sprintf(buffer, "%d", d); - return buffer; -} - -const char *cTimer::PrintFirstDay(void) -{ - if (firstday) { - const char *s = PrintDay(day, firstday); - if (strlen(s) == 18) - return s + 8; - } - return ""; // not NULL, so the caller can always use the result -} - -bool cTimer::Parse(const char *s) -{ - char *buffer1 = NULL; - char *buffer2 = NULL; - free(summary); - summary = NULL; - //XXX Apparently sscanf() doesn't work correctly if the last %a argument - //XXX results in an empty string (this first occured when the EIT gathering - //XXX was put into a separate thread - don't know why this happens... - //XXX As a cure we copy the original string and add a blank. - //XXX If anybody can shed some light on why sscanf() failes here, I'd love - //XXX to hear about that! - char *s2 = NULL; - int l2 = strlen(s); - while (l2 > 0 && isspace(s[l2 - 1])) - l2--; - if (s[l2 - 1] == ':') { - s2 = MALLOC(char, l2 + 3); - strcat(strn0cpy(s2, s, l2 + 1), " \n"); - s = s2; - } - if (8 <= sscanf(s, "%d :%d :%a[^:]:%d :%d :%d :%d :%a[^:\n]:%a[^\n]", &active, &channel, &buffer1, &start, &stop, &priority, &lifetime, &buffer2, &summary)) { - if (summary && !*skipspace(summary)) { - free(summary); - summary = NULL; - } - //TODO add more plausibility checks - day = ParseDay(buffer1, &firstday); - strn0cpy(file, buffer2, MaxFileName); - strreplace(file, '|', ':'); - strreplace(summary, '|', '\n'); - free(buffer1); - free(buffer2); - free(s2); - return day != 0; - } - free(s2); - return false; -} - -bool cTimer::Save(FILE *f) -{ - return fprintf(f, ToText()) > 0; -} - -bool cTimer::IsSingleEvent(void) -{ - return (day & 0x80000000) == 0; -} - -int cTimer::GetMDay(time_t t) -{ - struct tm tm_r; - return localtime_r(&t, &tm_r)->tm_mday; -} - -int cTimer::GetWDay(time_t t) -{ - struct tm tm_r; - int weekday = localtime_r(&t, &tm_r)->tm_wday; - return weekday == 0 ? 6 : weekday - 1; // we start with monday==0! -} - -bool cTimer::DayMatches(time_t t) -{ - return IsSingleEvent() ? GetMDay(t) == day : (day & (1 << GetWDay(t))) != 0; -} - -time_t cTimer::IncDay(time_t t, int Days) -{ - struct tm tm_r; - tm tm = *localtime_r(&t, &tm_r); - tm.tm_mday += Days; // now tm_mday may be out of its valid range - int h = tm.tm_hour; // save original hour to compensate for DST change - tm.tm_isdst = -1; // makes sure mktime() will determine the correct DST setting - t = mktime(&tm); // normalize all values - tm.tm_hour = h; // compensate for DST change - return mktime(&tm); // calculate final result -} - -time_t cTimer::SetTime(time_t t, int SecondsFromMidnight) -{ - struct tm tm_r; - tm tm = *localtime_r(&t, &tm_r); - tm.tm_hour = SecondsFromMidnight / 3600; - tm.tm_min = (SecondsFromMidnight % 3600) / 60; - tm.tm_sec = SecondsFromMidnight % 60; - tm.tm_isdst = -1; // makes sure mktime() will determine the correct DST setting - return mktime(&tm); -} - -char *cTimer::SetFile(const char *File) -{ - if (!isempty(File)) - strn0cpy(file, File, sizeof(file)); - return file; -} - -bool cTimer::Matches(time_t t) -{ - startTime = stopTime = 0; - if (t == 0) - t = time(NULL); - - int begin = TimeToInt(start); // seconds from midnight - int length = TimeToInt(stop) - begin; - if (length < 0) - length += SECSINDAY; - - int DaysToCheck = IsSingleEvent() ? 61 : 7; // 61 to handle months with 31/30/31 - for (int i = -1; i <= DaysToCheck; i++) { - time_t t0 = IncDay(t, i); - if (DayMatches(t0)) { - time_t a = SetTime(t0, begin); - time_t b = a + length; - if ((!firstday || a >= firstday) && t <= b) { - startTime = a; - stopTime = b; - break; - } - } - } - if (!startTime) - startTime = firstday; // just to have something that's more than a week in the future - else if (t > startTime || t > firstday + SECSINDAY + 3600) // +3600 in case of DST change - firstday = 0; - return active && startTime <= t && t < stopTime; // must stop *before* stopTime to allow adjacent timers -} - -time_t cTimer::StartTime(void) -{ - if (!startTime) - Matches(); - return startTime; -} - -time_t cTimer::StopTime(void) -{ - if (!stopTime) - Matches(); - return stopTime; -} - -void cTimer::SetRecording(bool Recording) -{ - recording = Recording; - isyslog("timer %d %s", Index() + 1, recording ? "start" : "stop"); -} - -void cTimer::SetPending(bool Pending) -{ - pending = Pending; -} - -void cTimer::Skip(void) -{ - firstday = IncDay(SetTime(StartTime(), 0), 1); -} - // --- cCommand ------------------------------------------------------------- char *cCommand::result = NULL; @@ -476,47 +142,6 @@ bool cCaDefinition::Parse(const char *s) cCommands Commands; cCommands RecordingCommands; -// -- cTimers ---------------------------------------------------------------- - -cTimers Timers; - -cTimer *cTimers::GetTimer(cTimer *Timer) -{ - cTimer *ti = (cTimer *)First(); - while (ti) { - if (ti->channel == Timer->channel && ti->day == Timer->day && ti->start == Timer->start && ti->stop == Timer->stop) - return ti; - ti = (cTimer *)ti->Next(); - } - return NULL; -} - -cTimer *cTimers::GetMatch(time_t t) -{ - cTimer *t0 = NULL; - cTimer *ti = First(); - while (ti) { - if (!ti->recording && ti->Matches(t)) { - if (!t0 || ti->priority > t0->priority) - t0 = ti; - } - ti = (cTimer *)ti->Next(); - } - return t0; -} - -cTimer *cTimers::GetNextActiveTimer(void) -{ - cTimer *t0 = NULL; - cTimer *ti = First(); - while (ti) { - if (ti->active && (!t0 || *ti < *t0)) - t0 = ti; - ti = (cTimer *)ti->Next(); - } - return t0; -} - // -- cSVDRPhosts ------------------------------------------------------------ cSVDRPhosts SVDRPhosts; -- cgit v1.2.3