]> git.vomp.tv Git - vompclient-marten.git/commitdiff
Live radio prebuffering display - code upgrades for connection lost handling
authorChris Tallon <chris@vomp.tv>
Sun, 11 May 2008 15:38:24 +0000 (15:38 +0000)
committerChris Tallon <chris@vomp.tv>
Sun, 11 May 2008 15:38:24 +0000 (15:38 +0000)
channel.cc
command.cc
player.cc
playerliveradio.cc
playerliveradio.h
playerlivetv.cc
playerlivetv.h
playerradio.cc
recording.cc
vtimerlist.cc
vvideolivetv.cc

index d4367b5c678da4865c5aa4251488d347b383974f..052d0425df8bd20b3e605b92b3e3c41b314f3c13 100644 (file)
@@ -22,6 +22,7 @@
 
 #include "vdr.h"
 #include "log.h"
+#include "command.h"
 
 Channel::Channel()
 {
@@ -67,7 +68,12 @@ void Channel::loadPids()
   }
 
   VDR::getInstance()->getChannelPids(this); // FIXME sort out this system
-
+  if (!VDR::getInstance()->isConnected())
+  {
+    Command::getInstance()->connectionLost();
+    return;
+  }
+        
   Log::getInstance()->log("Channel", Log::DEBUG, "C.%lu loaded, VPid=%lu, numApids=%lu, numDpids=%lu, numSpids=%lu TPid=%lu",
       number, vpid, numAPids, numDPids, numSPids, tpid);
   for (ULONG i = 0; i < numAPids; i++)
index e00328b73c0fbbd7e6074ecddddc0a4f410128ae..16fa00a0d49cceb0d598e01024d01dd5018fc93a 100644 (file)
@@ -400,6 +400,7 @@ void Command::processMessage(Message* m)
         boxstack->removeAll();
         boxstack->update(wallpaper);
         I18n::initialize();
+        if (!VDR::getInstance()->isConnected()) { connectionLost(); break; }
         VWelcome* vw = new VWelcome();
         vw->draw();
         boxstack->add(vw);
@@ -593,6 +594,8 @@ void Command::buildCrashedBox()
 void Command::doJustConnected(VConnect* vconnect)
 {
   I18n::initialize();
+  if (!VDR::getInstance()->isConnected()) { connectionLost(); return; }
+  
   Video* video = Video::getInstance();
   Audio* audio = Audio::getInstance();  
   boxstack->remove(vconnect);
index 3937d203c4c856faa3d4698733e63c02d10f5f4b..74ed2868c61c8a2803cd43924ea3c319aa8f6b8d 100644 (file)
--- a/player.cc
+++ b/player.cc
@@ -822,12 +822,19 @@ void Player::restartAtFramePI(ULONG newFrame)
   vdr->getNextIFrame(nextiframeNumber, 0, &filePos, &iframeNumber, &iframeLength);
 
   buffer = vdr->getBlock(filePos, iframeLength, &amountReceived);
-  videoLength = demuxer->stripAudio(buffer, amountReceived);
-  video->displayIFrame(buffer, videoLength);
-  video->displayIFrame(buffer, videoLength); // If you do it twice, it works :)
-  free(buffer);
-
-  currentFrameNumber = iframeNumber;
+  if (!vdr->isConnected())
+  {
+    if (buffer) free(buffer);
+    doConnectionLost();
+  }
+  else
+  {
+    videoLength = demuxer->stripAudio(buffer, amountReceived);
+    video->displayIFrame(buffer, videoLength);
+    video->displayIFrame(buffer, videoLength); // If you do it twice, it works :)
+    free(buffer);
+    currentFrameNumber = iframeNumber;
+  }
 }
 
 void Player::doConnectionLost()
@@ -1242,6 +1249,14 @@ void Player::threadFeedScan()
 //    logger->log("Player", Log::DEBUG, "XXX Got frame");
 
     threadBuffer = vdr->getBlock(filePos, iframeLength, &amountReceived);
+    
+    if (!vdr->isConnected())
+    {
+      if (threadBuffer) free(threadBuffer);
+      doConnectionLost();
+      break;
+    }
+    
 #ifndef WIN32
     gettimeofday(&clock1, NULL);
     if (clock2.tv_sec != 0)
index 7a271126bce19524aaf57a3a4d8f6d4f9ad3ce22..5e798ae7577a138c70eb57ac9acd35c285acbe2e 100644 (file)
@@ -150,6 +150,22 @@ void PlayerLiveRadio::call(void* caller)
 
 void PlayerLiveRadio::streamReceive(ULONG flag, void* data, ULONG len)
 {
+  // Flag:
+  // 0 = normal stream packet
+  // 1 = stream end
+
+  if (flag == 1)
+  {
+    if (data) abort();
+    
+    Message* m = new Message();
+    m->from = this;
+    m->to = messageReceiver;
+    m->message = Message::PLAYER_EVENT;
+    m->parameter = PlayerLiveRadio::STREAM_END;
+    messageQueue->postMessageFromOuterSpace(m);
+  }
+  
   if (streamChunks.size() < 11)
   {
     StreamChunk s;
@@ -181,9 +197,9 @@ void PlayerLiveRadio::chunkToDemuxer()
 {
   StreamChunk s = streamChunks.front();
   streamChunks.pop();
-  logger->log("PlayerLiveRadio", Log::DEBUG, "About to call demuxer with %p %lu", s.data, s.len);
-  int a = demuxer->put((UCHAR*)s.data, s.len);
-  logger->log("PlayerLiveRadio", Log::DEBUG, "put %i to demuxer", a);
+  //logger->log("PlayerLiveRadio", Log::DEBUG, "About to call demuxer with %p %lu", s.data, s.len);
+  /*int a =*/ demuxer->put((UCHAR*)s.data, s.len);
+  //logger->log("PlayerLiveRadio", Log::DEBUG, "put %i to demuxer", a);
   free(s.data);  
 }
 
@@ -309,6 +325,24 @@ void PlayerLiveRadio::switchState(UCHAR newState)
   }  
 }
 
+bool PlayerLiveRadio::checkError()
+{
+  if (!vdr->isConnected())
+  {
+    switchState(S_STOP);
+    
+    Message* m = new Message();
+    m->from = this;
+    m->to = messageReceiver;
+    m->message = Message::PLAYER_EVENT;
+    m->parameter = PlayerLiveRadio::CONNECTION_LOST;
+    messageQueue->postMessageFromOuterSpace(m);
+    
+    return true;
+  }   
+  return false;
+}
+
 void PlayerLiveRadio::optimizeInstructionQueue()
 {
   // Walk the list
@@ -321,7 +355,6 @@ void PlayerLiveRadio::optimizeInstructionQueue()
     i = instructions.front();
     if (i.instruction == I_SETCHANNEL)
     {
-      logger->log("PlayerLiveRadio", Log::DEBUG, "Optimised out setch to %i", i.channelIndex);
       instructions.pop();  // if this is the first of more than 1 command, currently it cannot possibly be relevant
     }
     else if (i.instruction == I_STOP)
@@ -352,25 +385,38 @@ void PlayerLiveRadio::threadMethod()
 
         switchState(S_PREBUFFERING);
 
-        Channel* chan = (*chanList)[i.channelIndex];
-        chan->loadPids();
-
-        if (chan->numAPids > 0) 
+        if (!checkError())
         {
-          demuxer->setAID(chan->apids[0].pid,0);
-          logger->log("PlayerLiveRadio", Log::DEBUG, "Demuxer pids: %u %u", chan->vpid, chan->apids[0].pid);
+          Channel* chan = (*chanList)[i.channelIndex];
+          chan->loadPids();
+
+          if (chan->numAPids > 0) 
+          {
+            demuxer->setAID(chan->apids[0].pid,0);
+            logger->log("PlayerLiveRadio", Log::DEBUG, "Demuxer pids: %u %u", chan->vpid, chan->apids[0].pid);
+          }
+          else 
+          {
+            logger->log("PlayerLiveRadio", Log::WARN, "Demuxer no pids!");
+          }
+
+          int streamSuccess = vdr->streamChannel(chan->number, this);
+          if (!checkError() && !streamSuccess)
+          {      
+            Message* m = new Message();
+            m->from = this;
+            m->to = messageReceiver;
+            m->message = Message::PLAYER_EVENT;
+            m->parameter = PlayerLiveRadio::STREAM_END;
+            messageQueue->postMessageFromOuterSpace(m);
+          }
         }
-        else 
-        {
-          logger->log("PlayerLiveRadio", Log::WARN, "Demuxer no pids!");
-        }
-
-        vdr->streamChannel(chan->number, this);
       }
       else if (i.instruction == I_STOP)
       {
         logger->log("PlayerLiveRadio", Log::DEBUG, "Stopping");
         switchState(S_STOP);
+        checkError();
 
         stopNow = true;
         break;
@@ -384,10 +430,23 @@ void PlayerLiveRadio::threadMethod()
       chunkToDemuxer();
 
       if (state == S_PREBUFFERING)
-      {        
-        if (++preBufferCount == preBufferAmount)
+      {
+        ++preBufferCount;
+        ULONG percentDone = (ULONG)(preBufferCount / (float)preBufferAmount * 100);
+        logger->log("PlayerLiveRadio", Log::DEBUG, "Prebuffering %lu%%", percentDone);
+        
+        Message* m = new Message();
+        m->from = this;
+        m->to = messageReceiver;
+        m->message = Message::PLAYER_EVENT;
+        m->parameter = PlayerLiveRadio::PREBUFFERING;
+        m->tag = percentDone;
+        messageQueue->postMessageFromOuterSpace(m);
+
+        if (preBufferCount == preBufferAmount)
         {
           switchState(S_PLAY);
+          checkError();
         }
       }
     }
index abf91451ddc66483e185577b51b73a9bf2c55b88..9f6aee3be62a80eda12927883b5dc34f11abff9c 100644 (file)
@@ -79,7 +79,8 @@ class PlayerLiveRadio : public PlayerLive, public Thread_TYPE, public Callback,
     const static UCHAR STREAM_END = 3;
     const static UCHAR ASPECT43 = 4;
     const static UCHAR ASPECT169 = 5;
-
+    const static UCHAR PREBUFFERING = 6;
+    
   protected:
     void threadMethod();
     void threadPostStopCleanup() {};
@@ -107,6 +108,7 @@ class PlayerLiveRadio : public PlayerLive, public Thread_TYPE, public Callback,
     const static UCHAR S_PREBUFFERING = 2;
     const static UCHAR S_PLAY = 3;
     void switchState(UCHAR newState);
+    bool checkError();
 
     bool stopNow;
     int preBufferCount;
index 905794945a17d9f62d9d73beed8bba11e2c3a11b..d0591ea331406fd37a9aee1db25a99f53a922f5d 100644 (file)
@@ -500,6 +500,24 @@ void PlayerLiveTV::switchState(UCHAR newState)
   }  
 }
 
+bool PlayerLiveTV::checkError()
+{
+  if (!vdr->isConnected())
+  {
+    switchState(S_STOP);
+    
+    Message* m = new Message();
+    m->from = this;
+    m->to = messageReceiver;
+    m->message = Message::PLAYER_EVENT;
+    m->parameter = PlayerLiveTV::CONNECTION_LOST;
+    messageQueue->postMessageFromOuterSpace(m);
+    
+    return true;
+  }   
+  return false;
+}
+
 void PlayerLiveTV::optimizeInstructionQueue()
 {
   // Walk the list
@@ -530,6 +548,8 @@ void PlayerLiveTV::threadMethod()
       switchState(S_PREBUFFERING);
       videoStartup = false;
       preBufferCount = 0;
+      
+      checkError();
     }  
   
     while(!instructions.empty())
@@ -544,35 +564,39 @@ void PlayerLiveTV::threadMethod()
         logger->log("PlayerLiveTV", Log::DEBUG, "start new stream");
 
         switchState(S_VIDEOSTARTUP);
-
-        Channel* chan = (*chanList)[i.channelIndex];
-        chan->loadPids();
-        demuxer->setVID(chan->vpid);
-        if (chan->numAPids > 0) 
-        {
-          demuxer->setAID(chan->apids[0].pid,0);
-          logger->log("PlayerLiveTV", Log::DEBUG, "Demuxer pids: %u %u", chan->vpid, chan->apids[0].pid);
-        }
-        else 
+        
+        if (!checkError())
         {
-          logger->log("PlayerLiveTV", Log::WARN, "Demuxer video pid only: %u", chan->vpid);
-        }
-
-        int streamSuccess = vdr->streamChannel(chan->number, this);
-        if (!streamSuccess)
-        {      
-          Message* m = new Message();
-          m->from = this;
-          m->to = messageReceiver;
-          m->message = Message::PLAYER_EVENT;
-          m->parameter = PlayerLiveTV::STREAM_END;
-          messageQueue->postMessageFromOuterSpace(m);
+          Channel* chan = (*chanList)[i.channelIndex];
+          chan->loadPids();
+          demuxer->setVID(chan->vpid);
+          if (chan->numAPids > 0) 
+          {
+            demuxer->setAID(chan->apids[0].pid,0);
+            logger->log("PlayerLiveTV", Log::DEBUG, "Demuxer pids: %u %u", chan->vpid, chan->apids[0].pid);
+          }
+          else 
+          {
+            logger->log("PlayerLiveTV", Log::WARN, "Demuxer video pid only: %u", chan->vpid);
+          }
+
+          int streamSuccess = vdr->streamChannel(chan->number, this);
+          if (!checkError() && !streamSuccess)
+          {      
+            Message* m = new Message();
+            m->from = this;
+            m->to = messageReceiver;
+            m->message = Message::PLAYER_EVENT;
+            m->parameter = PlayerLiveTV::STREAM_END;
+            messageQueue->postMessageFromOuterSpace(m);
+          }
         }
       }
       else if (i.instruction == I_STOP)
       {
         logger->log("PlayerLiveTV", Log::DEBUG, "Stopping");
         switchState(S_STOP);
+        checkError();
 
         stopNow = true;
         break;
@@ -602,6 +626,7 @@ void PlayerLiveTV::threadMethod()
         if (preBufferCount == preBufferAmount)
         {
           switchState(S_PLAY);
+          checkError();
         }
       }
     }
index c82e37d99b23c3dba953248cea9bc95af2c7ebe6..9ddf19d401f42087673dccc9c01d251f6fe3ea8f 100644 (file)
@@ -113,6 +113,7 @@ class PlayerLiveTV : public PlayerLive, public Thread_TYPE, public Callback, pub
     const static UCHAR S_PREBUFFERING = 3;
     const static UCHAR S_PLAY = 4;
     void switchState(UCHAR newState);
+    bool checkError();
 
     bool videoStartup;
     bool stopNow;
index 783276b7139c8e768b112b5a301819f6fc2dbd0e..0dd2161652ef33908325877fd929b7b95631fcd3 100644 (file)
@@ -105,6 +105,7 @@ int PlayerRadio::init(ULLONG tlengthBytes, ULONG tlengthPackets)
     {
       logger->log("PlayerRadio", Log::ERR, "Failed to get start block");
       shutdown();
+      if (!vdr->isConnected()) doConnectionLost();
       return 0;
     }
 
@@ -140,6 +141,7 @@ bool PlayerRadio::setLengthSeconds()
   if (!buffer)
   {
     logger->log("PlayerRadio", Log::ERR, "Failed to get end block");
+    if (!vdr->isConnected()) doConnectionLost();    
     return false;
   }
 
index 220430e063164cd806b55fed90011b3bef7b8ab4..9e8bdd3035dcd67d4b7ca9d49a8448ea0545b4a8 100644 (file)
@@ -24,6 +24,7 @@
 #include "mark.h"
 #include "log.h"
 #include "demuxer.h"
+#include "command.h"
 
 Recording* Recording::recInfoFor = NULL;
 RecInfo* Recording::recInfo = NULL;
@@ -103,6 +104,8 @@ void Recording::loadRecInfo()
   recInfoFor = this;
   recInfo = vdr->getRecInfo(fileName);
   Log::getInstance()->log("Recording", Log::DEBUG, "Recording has loaded recInfo %p", recInfo);
+  
+  if (!VDR::getInstance()->isConnected()) Command::getInstance()->connectionLost();
 }
 
 void Recording::dropRecInfo()
@@ -115,6 +118,7 @@ void Recording::dropRecInfo()
 void Recording::loadMarks()
 {
   markList = vdr->getMarks(fileName);
+  if (!VDR::getInstance()->isConnected()) Command::getInstance()->connectionLost();
 }
 
 bool Recording::isRadio()
@@ -137,8 +141,9 @@ bool Recording::isRadio()
 
   free(buffer);
 
-  // FIXME
   vdr->stopStreaming();
+  if (!VDR::getInstance()->isConnected()) Command::getInstance()->connectionLost();
+  
   Log::getInstance()->log("Recording", Log::DEBUG, "Recording has messed about and worked out radio = %u", !hasVideo);
 
 
index e6c154eeeaf9e56531ef0e3c2e1eb18c2934c7be..b2bfd60bd677cf95132c0f274bcedb3b7d65b08c 100644 (file)
@@ -342,6 +342,7 @@ void VTimerList::processMessage(Message* m)
 
   
     ULONG retval = VDR::getInstance()->deleteTimer(recTimer);
+    if (!VDR::getInstance()->isConnected()) { Command::getInstance()->connectionLost(); return; }
     Log::getInstance()->log("VTimerList", Log::DEBUG, "Got return fron delete timer: %lu", retval);
     
     if (retval != 10)
index 7197cd739624ac4dd1c6b4decb6a5e63e4962140..925f6f407339171272bce2df45c35676aa9e1fa0 100644 (file)
@@ -898,11 +898,7 @@ void VVideoLiveTV::processMessage(Message* m)
       case PlayerLiveTV::CONNECTION_LOST: // connection lost detected
       {
         Log::getInstance()->log("VVideoLiveTV", Log::DEBUG, "Received connection lost from player");
-        // I can't handle this, send it to command
-        Message* m2 = new Message();
-        m2->to = Command::getInstance();
-        m2->message = Message::CONNECTION_LOST;
-        Command::getInstance()->postMessageNoLock(m2);
+        Command::getInstance()->connectionLost();
         break;
       }