summaryrefslogtreecommitdiff
path: root/recording.c
diff options
context:
space:
mode:
authorKlaus Schmidinger <vdr@tvdr.de>2005-09-25 11:00:57 +0200
committerKlaus Schmidinger <vdr@tvdr.de>2005-09-25 11:00:57 +0200
commit9e8aac388237e7afff6cae5bbf5ee08756633f53 (patch)
tree33df2762c84b7c0981c06cb557097be0080eda1b /recording.c
parent83985eff479b0a287b747160b33458de38b10732 (diff)
downloadvdr-9e8aac388237e7afff6cae5bbf5ee08756633f53.tar.gz
vdr-9e8aac388237e7afff6cae5bbf5ee08756633f53.tar.bz2
The list of recordings is now read in a separate thread
Diffstat (limited to 'recording.c')
-rw-r--r--recording.c96
1 files changed, 77 insertions, 19 deletions
diff --git a/recording.c b/recording.c
index 4a12b71e..ccdb71c4 100644
--- a/recording.c
+++ b/recording.c
@@ -4,7 +4,7 @@
* See the main source file 'vdr.c' for copyright information and
* how to reach the author.
*
- * $Id: recording.c 1.114 2005/09/17 09:14:36 kls Exp $
+ * $Id: recording.c 1.115 2005/09/25 10:40:31 kls Exp $
*/
#include "recording.h"
@@ -60,17 +60,23 @@
bool VfatFileSystem = false;
+static cRecordings DeletedRecordings(true);
+
void RemoveDeletedRecordings(void)
{
static time_t LastRemoveCheck = 0;
- if (time(NULL) - LastRemoveCheck > REMOVECHECKDELTA) {
+ if (LastRemoveCheck == 0) {
+ DeletedRecordings.Update();
+ LastRemoveCheck = time(NULL) - REMOVECHECKDELTA * 9 / 10;
+ }
+ else if (time(NULL) - LastRemoveCheck > REMOVECHECKDELTA) {
// Make sure only one instance of VDR does this:
cLockFile LockFile(VideoDirectory);
if (!LockFile.Lock())
return;
// Remove the oldest file that has been "deleted":
- cRecordings DeletedRecordings(true);
- if (DeletedRecordings.Load()) {
+ cThreadLock DeletedRecordingsLock(&DeletedRecordings);
+ if (DeletedRecordings.Count()) {
cRecording *r = DeletedRecordings.First();
cRecording *r0 = r;
while (r) {
@@ -80,11 +86,14 @@ void RemoveDeletedRecordings(void)
}
if (r0 && time(NULL) - r0->start > DELETEDLIFETIME * 3600) {
r0->Remove();
+ DeletedRecordings.Del(r0);
RemoveEmptyVideoDirectories();
LastRemoveCheck += REMOVELATENCY;
return;
}
}
+ else
+ DeletedRecordings.Update();
LastRemoveCheck = time(NULL);
}
}
@@ -104,8 +113,8 @@ void AssertFreeDiskSpace(int Priority)
return;
// Remove the oldest file that has been "deleted":
isyslog("low disk space while recording, trying to remove a deleted recording...");
- cRecordings DeletedRecordings(true);
- if (DeletedRecordings.Load()) {
+ cThreadLock DeletedRecordingsLock(&DeletedRecordings);
+ if (DeletedRecordings.Count()) {
cRecording *r = DeletedRecordings.First();
cRecording *r0 = r;
while (r) {
@@ -114,13 +123,20 @@ void AssertFreeDiskSpace(int Priority)
r = DeletedRecordings.Next(r);
}
if (r0 && r0->Remove()) {
+ DeletedRecordings.Del(r0);
LastFreeDiskCheck += REMOVELATENCY / Factor;
return;
}
}
+ // DeletedRecordings was empty, so to be absolutely sure there are no
+ // deleted recordings we need to double check:
+ DeletedRecordings.Update(true);
+ if (DeletedRecordings.Count())
+ return; // the next call will actually remove it
// No "deleted" files to remove, so let's see if we can delete a recording:
isyslog("...no deleted recording found, trying to delete an old recording...");
- if (Recordings.Load()) {
+ cThreadLock RecordingsLock(&Recordings);
+ if (Recordings.Count()) {
cRecording *r = Recordings.First();
cRecording *r0 = NULL;
while (r) {
@@ -454,6 +470,7 @@ cRecording::cRecording(const char *FileName)
name[p - FileName] = 0;
name = ExchangeChars(name, false);
}
+ GetResume();
// read an optional info file:
char *InfoFileName = NULL;
asprintf(&InfoFileName, "%s%s", fileName, INFOFILESUFFIX);
@@ -720,16 +737,38 @@ bool cRecording::Remove(void)
cRecordings Recordings;
cRecordings::cRecordings(bool Deleted)
+:cThread("video directory scanner")
{
deleted = Deleted;
lastUpdate = 0;
+ state = 0;
+}
+
+cRecordings::~cRecordings()
+{
+ Cancel(3);
+}
+
+void cRecordings::Action(void)
+{
+ Refresh();
+}
+
+void cRecordings::Refresh(bool Foreground)
+{
+ lastUpdate = time(NULL); // doing this first to make sure we don't miss anything
+ Lock();
+ Clear();
+ ChangeState();
+ Unlock();
+ ScanVideoDir(VideoDirectory, Foreground);
}
-void cRecordings::ScanVideoDir(const char *DirName)
+void cRecordings::ScanVideoDir(const char *DirName, bool Foreground)
{
cReadDir d(DirName);
struct dirent *e;
- while ((e = d.Next()) != NULL) {
+ while ((Foreground || Running()) && (e = d.Next()) != NULL) {
if (strcmp(e->d_name, ".") && strcmp(e->d_name, "..")) {
char *buffer;
asprintf(&buffer, "%s/%s", DirName, e->d_name);
@@ -749,13 +788,17 @@ void cRecordings::ScanVideoDir(const char *DirName)
if (S_ISDIR(st.st_mode)) {
if (endswith(buffer, deleted ? DELEXT : RECEXT)) {
cRecording *r = new cRecording(buffer);
- if (r->Name())
+ if (r->Name()) {
+ Lock();
Add(r);
+ ChangeState();
+ Unlock();
+ }
else
delete r;
}
else
- ScanVideoDir(buffer);
+ ScanVideoDir(buffer, Foreground);
}
}
free(buffer);
@@ -763,18 +806,28 @@ void cRecordings::ScanVideoDir(const char *DirName)
}
}
+bool cRecordings::StateChanged(int &State)
+{
+ int NewState = state;
+ bool Result = State != NewState;
+ State = state;
+ return Result;
+}
+
bool cRecordings::NeedsUpdate(void)
{
- return lastUpdate <= LastModifiedTime(AddDirectory(VideoDirectory, ".update"));
+ return lastUpdate < LastModifiedTime(AddDirectory(VideoDirectory, ".update"));
}
-bool cRecordings::Load(void)
+bool cRecordings::Update(bool Wait)
{
- lastUpdate = time(NULL); // doing this first to make sure we don't miss anything
- Clear();
- ScanVideoDir(VideoDirectory);
- Sort();
- return Count() > 0;
+ if (Wait) {
+ Refresh(true);
+ return Count() > 0;
+ }
+ else
+ Start();
+ return false;
}
cRecording *cRecordings::GetByName(const char *FileName)
@@ -788,18 +841,23 @@ cRecording *cRecordings::GetByName(const char *FileName)
void cRecordings::AddByName(const char *FileName)
{
+ LOCK_THREAD;
cRecording *recording = GetByName(FileName);
if (!recording) {
recording = new cRecording(FileName);
Add(recording);
+ ChangeState();
}
}
void cRecordings::DelByName(const char *FileName)
{
+ LOCK_THREAD;
cRecording *recording = GetByName(FileName);
- if (recording)
+ if (recording) {
Del(recording);
+ ChangeState();
+ }
}
// --- cMark -----------------------------------------------------------------