From 4bba577a8bd6ac06445d34db3a0f7bdae37c120d Mon Sep 17 00:00:00 2001
From: Klaus Schmidinger <vdr@tvdr.de>
Date: Sat, 26 Jan 2002 13:42:15 +0100
Subject: Improved error handling in the editing process; message prompt at the
 end of editing process

---
 HISTORY  |  4 ++++
 dvbapi.c | 71 +++++++++++++++++++++++++++++++++++++++++++++++++++++-----------
 dvbapi.h |  6 +++++-
 i18n.c   | 18 +++++++++++++++-
 vdr.c    |  9 ++++++--
 5 files changed, 92 insertions(+), 16 deletions(-)

diff --git a/HISTORY b/HISTORY
index c94ef15e..9b782e6a 100644
--- a/HISTORY
+++ b/HISTORY
@@ -907,3 +907,7 @@ Video Disk Recorder Revision History
 - Fixed handling file names that contain single quotes (') or dollar signs ($)
   in the call to the shutdown command (option '-s') and the recording command
   (option '-r').
+- Improved error handling in the editing process; the resulting file will be
+  deleted if an error occured.
+- A message is now prompted at the end of the editing process, indicating
+  whether the process succeeded or failed.
diff --git a/dvbapi.c b/dvbapi.c
index c8642e4a..5751546b 100644
--- a/dvbapi.c
+++ b/dvbapi.c
@@ -7,7 +7,7 @@
  * DVD support initially written by Andreas Schultz <aschultz@warp10.net>
  * based on dvdplayer-0.5 by Matjaz Thaler <matjaz.thaler@guest.arnes.si>
  *
- * $Id: dvbapi.c 1.143 2002/01/13 16:21:48 kls Exp $
+ * $Id: dvbapi.c 1.144 2002/01/26 13:42:15 kls Exp $
  */
 
 //#define DVDDEBUG        1
@@ -116,7 +116,7 @@ public:
   cIndexFile(const char *FileName, bool Record);
   ~cIndexFile();
   bool Ok(void) { return index != NULL; }
-  void Write(uchar PictureType, uchar FileNumber, int FileOffset);
+  bool Write(uchar PictureType, uchar FileNumber, int FileOffset);
   bool Get(int Index, uchar *FileNumber, int *FileOffset, uchar *PictureType = NULL, int *Length = NULL);
   int GetNextIFrame(int Index, bool Forward, uchar *FileNumber = NULL, int *FileOffset = NULL, int *Length = NULL, bool StayOffEnd = false);
   int Get(uchar FileNumber, int FileOffset);
@@ -249,7 +249,7 @@ bool cIndexFile::CatchUp(int Index)
   return false;
 }
 
-void cIndexFile::Write(uchar PictureType, uchar FileNumber, int FileOffset)
+bool cIndexFile::Write(uchar PictureType, uchar FileNumber, int FileOffset)
 {
   if (f >= 0) {
      tIndex i = { FileOffset, PictureType, FileNumber, 0 };
@@ -257,10 +257,11 @@ void cIndexFile::Write(uchar PictureType, uchar FileNumber, int FileOffset)
         esyslog(LOG_ERR, "ERROR: can't write to index file");
         close(f);
         f = -1;
-        return;
+        return false;
         }
      last++;
      }
+  return f >= 0;
 }
 
 bool cIndexFile::Get(int Index, uchar *FileNumber, int *FileOffset, uchar *PictureType, int *Length)
@@ -2305,6 +2306,7 @@ void cTransferBuffer::Output(void)
 
 class cCuttingBuffer : public cThread {
 private:
+  const char *error;
   bool active;
   int fromFile, toFile;
   cFileName *fromFileName, *toFileName;
@@ -2315,10 +2317,12 @@ protected:
 public:
   cCuttingBuffer(const char *FromFileName, const char *ToFileName);
   virtual ~cCuttingBuffer();
+  const char *Error(void) { return error; }
   };
 
 cCuttingBuffer::cCuttingBuffer(const char *FromFileName, const char *ToFileName)
 {
+  error = NULL;
   active = false;
   fromFile = toFile = -1;
   fromFileName = toFileName = NULL;
@@ -2376,11 +2380,15 @@ void cCuttingBuffer::Action(void)
                  }
               if (fromFile >= 0) {
                  Length = ReadFrame(fromFile, buffer,  Length, sizeof(buffer));
-                 if (Length < 0)
+                 if (Length < 0) {
+                    error = "ReadFrame";
                     break;
+                    }
                  }
-              else
+              else {
+                 error = "fromFile";
                  break;
+                 }
               }
            else
               break;
@@ -2392,14 +2400,22 @@ void cCuttingBuffer::Action(void)
                  break;
               if (FileSize > MEGABYTE(Setup.MaxVideoFileSize)) {
                  toFile = toFileName->NextFile();
-                 if (toFile < 0)
+                 if (toFile < 0) {
+                    error = "toFile 1";
                     break;
+                    }
                  FileSize = 0;
                  }
               LastIFrame = 0;
               }
-           safe_write(toFile, buffer, Length);
-           toIndex->Write(PictureType, toFileName->Number(), FileSize);
+           if (safe_write(toFile, buffer, Length) != Length) {
+              error = "safe_write";
+              break;
+              }
+           if (!toIndex->Write(PictureType, toFileName->Number(), FileSize)) {
+              error = "toIndex";
+              break;
+              }
            FileSize += Length;
            if (!LastIFrame)
               LastIFrame = toIndex->Last();
@@ -2418,8 +2434,10 @@ void cCuttingBuffer::Action(void)
                  CurrentFileNumber = 0; // triggers SetOffset before reading next frame
                  if (Setup.SplitEditedFiles) {
                     toFile = toFileName->NextFile();
-                    if (toFile < 0)
+                    if (toFile < 0) {
+                       error = "toFile 2";
                        break;
+                       }
                     FileSize = 0;
                     }
                  }
@@ -2438,10 +2456,14 @@ void cCuttingBuffer::Action(void)
 
 char *cVideoCutter::editedVersionName = NULL;
 cCuttingBuffer *cVideoCutter::cuttingBuffer = NULL;
+bool cVideoCutter::error = false;
+bool cVideoCutter::ended = false;
 
 bool cVideoCutter::Start(const char *FileName)
 {
   if (!cuttingBuffer) {
+     error = false;
+     ended = false;
      cRecording Recording(FileName);
      const char *evn = Recording.PrefixFileName('%');
      if (evn && RemoveVideoFile(evn) && MakeDirs(evn, true)) {
@@ -2456,8 +2478,17 @@ bool cVideoCutter::Start(const char *FileName)
 
 void cVideoCutter::Stop(void)
 {
+  bool Interrupted = cuttingBuffer && cuttingBuffer->Active();
+  const char *Error = cuttingBuffer ? cuttingBuffer->Error() : NULL;
   delete cuttingBuffer;
   cuttingBuffer = NULL;
+  if ((Interrupted || Error) && editedVersionName) {
+     if (Interrupted)
+        isyslog(LOG_INFO, "editing process has been interrupted");
+     if (Error)
+        esyslog(LOG_ERR, "ERROR: '%s' during editing process", Error);
+     RemoveVideoFile(editedVersionName); //XXX what if this file is currently being replayed?
+     }
 }
 
 bool cVideoCutter::Active(void)
@@ -2465,16 +2496,32 @@ bool cVideoCutter::Active(void)
   if (cuttingBuffer) {
      if (cuttingBuffer->Active())
         return true;
+     error = cuttingBuffer->Error();
      Stop();
-     cRecordingUserCommand::InvokeCommand(RUC_EDITEDRECORDING, editedVersionName);
+     if (!error)
+        cRecordingUserCommand::InvokeCommand(RUC_EDITEDRECORDING, editedVersionName);
      delete editedVersionName;
      editedVersionName = NULL;
+     ended = true;
      }
   return false;
 }
 
-// --- cDvbApi ---------------------------------------------------------------
+bool cVideoCutter::Error(void)
+{
+  bool result = error;
+  error = false;
+  return result;
+}
 
+bool cVideoCutter::Ended(void)
+{
+  bool result = ended;
+  ended = false;
+  return result;
+}
+
+// --- cDvbApi ---------------------------------------------------------------
 
 static const char *OstName(const char *Name, int n)
 {
diff --git a/dvbapi.h b/dvbapi.h
index aa4a5feb..73375719 100644
--- a/dvbapi.h
+++ b/dvbapi.h
@@ -4,7 +4,7 @@
  * See the main source file 'vdr.c' for copyright information and
  * how to reach the author.
  *
- * $Id: dvbapi.h 1.59 2001/11/24 11:03:16 kls Exp $
+ * $Id: dvbapi.h 1.60 2002/01/26 13:01:16 kls Exp $
  */
 
 #ifndef __DVBAPI_H
@@ -69,10 +69,14 @@ class cVideoCutter {
 private:
   static char *editedVersionName;
   static cCuttingBuffer *cuttingBuffer;
+  static bool error;
+  static bool ended;
 public:
   static bool Start(const char *FileName);
   static void Stop(void);
   static bool Active(void);
+  static bool Error(void);
+  static bool Ended(void);
   };
 
 class cDvbApi {
diff --git a/i18n.c b/i18n.c
index 41be3cca..746368a4 100644
--- a/i18n.c
+++ b/i18n.c
@@ -4,7 +4,7 @@
  * See the main source file 'vdr.c' for copyright information and
  * how to reach the author.
  *
- * $Id: i18n.c 1.46 2002/01/19 16:25:33 kls Exp $
+ * $Id: i18n.c 1.47 2002/01/26 13:05:54 kls Exp $
  *
  * Slovenian translations provided by Miha Setina <mihasetina@softhome.net>
  * Italian   translations provided by Alberto Carraro <bertocar@tin.it>
@@ -1382,6 +1382,22 @@ const tPhrase Phrases[] = {
     "Op�ration de montage lanc�e",
     "Redigeringsprosess startet",
   },
+  { "Editing process finished",
+    "Schnitt beendet",
+    "", // TODO
+    "", // TODO
+    "", // TODO
+    "", // TODO
+    "", // TODO
+  },
+  { "Editing process failed!",
+    "Schnitt gescheitert!",
+    "", // TODO
+    "", // TODO
+    "", // TODO
+    "", // TODO
+    "", // TODO
+  },
   { NULL }
   };
 
diff --git a/vdr.c b/vdr.c
index 572e16f1..17d84094 100644
--- a/vdr.c
+++ b/vdr.c
@@ -22,7 +22,7 @@
  *
  * The project's page is at http://www.cadsoft.de/people/kls/vdr
  *
- * $Id: vdr.c 1.91 2002/01/26 11:53:11 kls Exp $
+ * $Id: vdr.c 1.92 2002/01/26 13:35:05 kls Exp $
  */
 
 #include <getopt.h>
@@ -468,7 +468,12 @@ int main(int argc, char *argv[])
           }
         if (!Menu) {
            EITScanner.Process();
-           cVideoCutter::Active();
+           if (!cVideoCutter::Active() && cVideoCutter::Ended()) {
+              if (cVideoCutter::Error())
+                 Interface->Error(tr("Editing process failed!"));
+              else
+                 Interface->Info(tr("Editing process finished"));
+              }
            }
         if (!*Interact && (!cRecordControls::Active() || ForceShutdown)) {
            time_t Now = time(NULL);
-- 
cgit v1.2.3