From 30dfd2e7019b9727ca761440b1ec4fe511a1143a Mon Sep 17 00:00:00 2001 From: Klaus Schmidinger Date: Sun, 17 Oct 2004 11:50:21 +0200 Subject: [PATCH] Now only saving channels.conf after a modification made by the user --- HISTORY | 4 ++++ channels.c | 14 +++++++------- channels.h | 15 +++++++++++---- menu.c | 6 +++--- svdrp.c | 8 ++++---- vdr.c | 29 ++++++++++++++++++++--------- 6 files changed, 49 insertions(+), 27 deletions(-) diff --git a/HISTORY b/HISTORY index 68d17671..53a94720 100644 --- a/HISTORY +++ b/HISTORY @@ -3029,3 +3029,7 @@ Video Disk Recorder Revision History - If one PID can't be added, the whole cDevice::AttachReceiver() will now fail and all PIDs added so far will be deleted (thanks to Marco Schlüßler for pointing out this one). +- Now only saving channels.conf after a modification made by the user (avoids + lots of disk access due to automatic channel updates). Automatic channel + modifications will be saved every 10 minutes if no recording is currently + active. diff --git a/channels.c b/channels.c index 021b6174..ba5fd8c1 100644 --- a/channels.c +++ b/channels.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: channels.c 1.25 2004/04/03 13:42:06 kls Exp $ + * $Id: channels.c 1.26 2004/10/17 11:21:39 kls Exp $ */ #include "channels.h" @@ -749,7 +749,7 @@ cChannels Channels; cChannels::cChannels(void) { maxNumber = 0; - modified = false; + modified = CHANNELSMOD_NONE; } bool cChannels::Load(const char *FileName, bool AllowComments, bool MustExist) @@ -863,15 +863,15 @@ bool cChannels::SwitchTo(int Number) return channel && cDevice::PrimaryDevice()->SwitchChannel(channel, true); } -void cChannels::SetModified(void) +void cChannels::SetModified(bool ByUser) { - modified = true; + modified = ByUser ? CHANNELSMOD_USER : !modified ? CHANNELSMOD_AUTO : modified; } -bool cChannels::Modified(void) +int cChannels::Modified(void) { - bool Result = modified; - modified = false; + int Result = modified; + modified = CHANNELSMOD_NONE; return Result; } diff --git a/channels.h b/channels.h index f5c9fbe1..23a8fa13 100644 --- a/channels.h +++ b/channels.h @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: channels.h 1.17 2004/04/03 13:40:47 kls Exp $ + * $Id: channels.h 1.18 2004/10/17 10:33:38 kls Exp $ */ #ifndef __CHANNELS_H @@ -26,6 +26,10 @@ #define CHANNELMOD_TRANSP 0x20 #define CHANNELMOD_RETUNE (CHANNELMOD_PIDS | CHANNELMOD_CA | CHANNELMOD_TRANSP) +#define CHANNELSMOD_NONE 0 +#define CHANNELSMOD_AUTO 1 +#define CHANNELSMOD_USER 2 + #define MAXAPIDS 32 #define MAXCAIDS 8 @@ -178,7 +182,7 @@ public: class cChannels : public cRwLock, public cConfig { private: int maxNumber; - bool modified; + int modified; int beingEdited; public: cChannels(void); @@ -196,8 +200,11 @@ public: bool HasUniqueChannelID(cChannel *NewChannel, cChannel *OldChannel = NULL); bool SwitchTo(int Number); int MaxNumber(void) { return maxNumber; } - void SetModified(void); - bool Modified(void); + void SetModified(bool ByUser = false); + int Modified(void); + ///< Returns 0 if no channels have been modified, 1 if an automatic + ///< modification has been made, and 2 if the user has made a modification. + ///< Calling this function resets the 'modified' flag to 0. cChannel *NewChannel(const cChannel *Transponder, const char *Name, int Nid, int Tid, int Sid, int Rid = 0); }; diff --git a/menu.c b/menu.c index f8bb0f17..e3fe69a8 100644 --- a/menu.c +++ b/menu.c @@ -4,7 +4,7 @@ * See the main source file 'vdr.c' for copyright information and * how to reach the author. * - * $Id: menu.c 1.313 2004/10/16 16:10:42 kls Exp $ + * $Id: menu.c 1.314 2004/10/17 10:28:27 kls Exp $ */ #include "menu.h" @@ -308,7 +308,7 @@ eOSState cMenuEditChannel::ProcessKey(eKeys Key) isyslog("added channel %d %s", channel->Number(), data.ToText()); state = osUser1; } - Channels.SetModified(); + Channels.SetModified(true); } else { Skins.Message(mtError, tr("Channel settings are not unique!")); @@ -396,7 +396,7 @@ void cMenuChannels::Propagate(void) for (cMenuChannelItem *ci = (cMenuChannelItem *)First(); ci; ci = (cMenuChannelItem *)ci->Next()) ci->Set(); Display(); - Channels.SetModified(); + Channels.SetModified(true); } eOSState cMenuChannels::Switch(void) diff --git a/svdrp.c b/svdrp.c index 87f146e5..788b1682 100644 --- a/svdrp.c +++ b/svdrp.c @@ -10,7 +10,7 @@ * and interact with the Video Disk Recorder - or write a full featured * graphical interface that sits on top of an SVDRP connection. * - * $Id: svdrp.c 1.63 2004/06/13 13:38:38 kls Exp $ + * $Id: svdrp.c 1.64 2004/10/17 10:28:47 kls Exp $ */ #include "svdrp.h" @@ -484,7 +484,7 @@ void cSVDRP::CmdDELC(const char *Option) } Channels.Del(channel); Channels.ReNumber(); - Channels.SetModified(); + Channels.SetModified(true); isyslog("channel %s deleted", Option); Reply(250, "Channel \"%s\" deleted", Option); } @@ -876,7 +876,7 @@ void cSVDRP::CmdMODC(const char *Option) if (Channels.HasUniqueChannelID(&ch, channel)) { *channel = ch; Channels.ReNumber(); - Channels.SetModified(); + Channels.SetModified(true); isyslog("modifed channel %d %s", channel->Number(), channel->ToText()); Reply(250, "%d %s", channel->Number(), channel->ToText()); } @@ -951,7 +951,7 @@ void cSVDRP::CmdNEWC(const char *Option) *channel = ch; Channels.Add(channel); Channels.ReNumber(); - Channels.SetModified(); + Channels.SetModified(true); isyslog("new channel %d %s", channel->Number(), channel->ToText()); Reply(250, "%d %s", channel->Number(), channel->ToText()); } diff --git a/vdr.c b/vdr.c index bb4276a6..6d76f178 100644 --- a/vdr.c +++ b/vdr.c @@ -22,7 +22,7 @@ * * The project's page is at http://www.cadsoft.de/vdr * - * $Id: vdr.c 1.186 2004/10/10 12:47:56 kls Exp $ + * $Id: vdr.c 1.187 2004/10/17 11:50:21 kls Exp $ */ #include @@ -58,10 +58,11 @@ #include "transfer.h" #include "videodir.h" -#define MINCHANNELWAIT 10 // seconds to wait between failed channel switchings -#define ACTIVITYTIMEOUT 60 // seconds before starting housekeeping -#define SHUTDOWNWAIT 300 // seconds to wait in user prompt before automatic shutdown -#define MANUALSTART 600 // seconds the next timer must be in the future to assume manual start +#define MINCHANNELWAIT 10 // seconds to wait between failed channel switchings +#define ACTIVITYTIMEOUT 60 // seconds before starting housekeeping +#define SHUTDOWNWAIT 300 // seconds to wait in user prompt before automatic shutdown +#define MANUALSTART 600 // seconds the next timer must be in the future to assume manual start +#define CHANNELSAVEDELTA 600 // seconds before saving channels.conf after automatic modifications static int Interrupted = 0; @@ -546,10 +547,20 @@ int main(int argc, char *argv[]) } } // Handle channel modifications: - if (!Channels.BeingEdited() && Channels.Modified()) { - if (Channels.Lock(false, 100)) { - Channels.Save(); //XXX only after user changes??? - Timers.Save(); + if (!Channels.BeingEdited()) { + int modified = Channels.Modified(); + static time_t ChannelSaveTimeout = 0; + if (modified == CHANNELSMOD_USER) + ChannelSaveTimeout = 1; // triggers an immediate save + else if (modified && !ChannelSaveTimeout) + ChannelSaveTimeout = time(NULL) + CHANNELSAVEDELTA; + bool timeout = ChannelSaveTimeout == 1 || ChannelSaveTimeout && time(NULL) > ChannelSaveTimeout && !cRecordControls::Active(); + if ((modified || timeout) && Channels.Lock(false, 100)) { + if (timeout) { + Channels.Save(); + Timers.Save(); + ChannelSaveTimeout = 0; + } for (cChannel *Channel = Channels.First(); Channel; Channel = Channels.Next(Channel)) { if (Channel->Modification(CHANNELMOD_RETUNE)) { cRecordControls::ChannelDataModified(Channel);