]> git.vomp.tv Git - vompclient.git/commitdiff
Windows port
authorChris Tallon <chris@vomp.tv>
Sun, 7 May 2006 23:58:51 +0000 (23:58 +0000)
committerChris Tallon <chris@vomp.tv>
Sun, 7 May 2006 23:58:51 +0000 (23:58 +0000)
19 files changed:
audiomvp.cc
audiomvp.h
audiowin.cc
audiowin.h
draintarget.h
dsock.cc
dsock.h
dssourcefilter.h
dssourcepin.cc
threadwin.cc
vdr.cc
vdr.h
video.h
videomvp.cc
videomvp.h
videowin.cc
videowin.h
vrecordinglist.cc
winmain.cc

index d9218c69074eba5daee4da4db4940e6562860340..1a42351b0af38eea2b7e862afb3c90943a04cf6e 100644 (file)
@@ -246,3 +246,8 @@ UINT AudioMVP::DeliverMediaSample(MediaPacket packet, UCHAR* buffer, UINT *sampl
 {
   return 0;
 }
+
+void AudioMVP::ResetTimeOffsets()
+{
+}
+
index a9223b3afe3ec55a53661bd55fd8d919d9a4d3fb..cf29478f1ee952e7432ab03ee6b1ae25aa60d101 100644 (file)
@@ -60,6 +60,7 @@ class AudioMVP : public Audio
     //Writing Data to Audiodevice -- unused in MVP code so far
     virtual UINT DeliverMediaSample(MediaPacket packet, UCHAR* buffer, UINT *samplepos);
     virtual long long SetStartOffset(long long curreftime, bool *rsync) { return 0; };
+    virtual void ResetTimeOffsets();
 
 #ifdef DEV
     int test();
index db3f932baaaf08e01084c8f6814b1058891c2452..40b51b62239976ab1208f172c2ec275439fb165b 100644 (file)
@@ -29,12 +29,14 @@ AudioWin::AudioWin()
 {
   initted = 0;
   firstsynched=false;
 
 
 }
 
 AudioWin::~AudioWin()
 {
+       
 
 }
 
@@ -165,10 +167,10 @@ UINT AudioWin::DeliverMediaSample(MediaPacket packet,
     *samplepos+=headerstrip;
     if ( packet.synched ) {
       vw->DeliverAudioMediaSample();//write out old data
-      if (packet.presentation_time<0) { //Preroll?
+   /*   if (packet.presentation_time<0) { //Preroll?
         *samplepos=packet.length;//if we have not processed at least one
         return packet.length;//synched packet ignore it!
-      }
+      }*/
 
       reftime1=packet.presentation_time;
       reftime2=reftime1+1;
@@ -185,9 +187,9 @@ UINT AudioWin::DeliverMediaSample(MediaPacket packet,
   UINT ms_pos;
   UINT haveToCopy;
   if (!vw->getCurrentAudioMediaSample(&ms) || ms==NULL) {// get the current sample
-    samplepos=0;
+    //samplepos=0;
     MILLISLEEP(10);
-    return 0;
+    return *samplepos;
   }
   ms_pos=ms->GetActualDataLength();
   ms_length=ms->GetSize();
@@ -195,9 +197,9 @@ UINT AudioWin::DeliverMediaSample(MediaPacket packet,
   if ((ms_length-ms_pos)<1) {
     vw->DeliverAudioMediaSample(); //we are full!
     if (!vw->getCurrentAudioMediaSample(&ms) || ms==NULL) {// get the current sample
-      samplepos=0;
+      //samplepos=0;
       MILLISLEEP(10);
-      return 0;
+      return *samplepos;
     }
     ms_pos=ms->GetActualDataLength();
     ms_length=ms->GetSize();
@@ -214,13 +216,18 @@ UINT AudioWin::DeliverMediaSample(MediaPacket packet,
     if (packet.synched) {
       ms->SetSyncPoint(TRUE);
       ms->SetTime(&reftime1,&reftime2);
+        
       //ms->SetTime(NULL,NULL);
       ms->SetMediaTime(NULL, NULL);
+         if (reftime1<0) ms->SetPreroll(TRUE);
+         else ms->SetPreroll(FALSE);
     }else {
       ms->SetSyncPoint(FALSE);
       ms->SetTime(NULL,NULL);
       ms->SetMediaTime(NULL, NULL);
-      ms->SetSyncPoint(TRUE);
+         ms->SetPreroll(FALSE);
+          MessageBox(0,"here I'm","Hallo",0);
+    //  ms->SetSyncPoint(TRUE);
     }
   }
 
@@ -239,9 +246,15 @@ long long AudioWin::SetStartOffset(long long curreftime, bool *rsync){
   return vw->SetStartAudioOffset(curreftime,rsync);
 }
 
+void AudioWin::ResetTimeOffsets() {
+  VideoWin *vw=(VideoWin*)Video::getInstance();
+  return vw->ResetTimeOffsets();
+}
+
 #ifdef DEV
 int AudioWin::test()
 {
   return 0;
 }
 #endif
+\r
index a31bf91677f9f52fd1f175a1f51fbed99e85154d..2e6eb1adb532185c7d452a923c2ecf7593a26812 100644 (file)
@@ -52,6 +52,7 @@ class AudioWin : public Audio
     // Writing Data to Audiodevice
     virtual UINT DeliverMediaSample(MediaPacket packet, UCHAR* buffer, UINT *samplepos);
     virtual long long SetStartOffset(long long curreftime, bool *rsync);
+       virtual void ResetTimeOffsets();
 
 private:
   bool firstsynched;
@@ -61,3 +62,4 @@ private:
 };
 
 #endif
+\r
index 4196e2acb6de8b7ed91248a3f39866551bf007d5..7923b2ef96acd972c48b83f84234798ba7a69cb0 100644 (file)
@@ -58,9 +58,11 @@ writen samplepos=samplepos+writebytes!
 If samplepos>=packet.length is returned, the next packet can be used for the next call.*/
 
   virtual long long SetStartOffset(long long curreftime, bool *rsync)=0;
+  virtual void ResetTimeOffsets()=0;
 };
 
 
 
 
-#endif
\ No newline at end of file
+#endif
+
index 0d65c77bc1290fd9eab2e115c7052618ffa839e1..4d7d98b94ed1a0f8bcfac10f942895c53dc3f38b 100644 (file)
--- a/dsock.cc
+++ b/dsock.cc
 
 #include "dsock.h"
 
+ULONG DatagramSocket::iterate_ip = 0;
+
 DatagramSocket::DatagramSocket(short port)
 {
   theInstance = this;
   myPort = port;
   addrlen = sizeof(struct sockaddr);
+}
+
+DatagramSocket::~DatagramSocket()
+{
+  CLOSESOCKET(socketnum);
+}
+
+DatagramSocket* DatagramSocket::theInstance = 0;
+DatagramSocket* DatagramSocket::getInstance(void)
+{
+  return theInstance;
+}
 
+int DatagramSocket::init()
+{
+  CLOSESOCKET(socketnum);
   if ((socketnum = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) == -1)
-  { perror("socket"); exit(1); }
+  { perror("socket"); return 0; }
 
   myAddr.sin_family = AF_INET;         // host byte order
   myAddr.sin_port = htons(myPort);     // short, network byte order
-  myAddr.sin_addr.s_addr = INADDR_ANY; // auto-fill with my IP
+  myAddr.sin_addr.s_addr = getIPNumber(iterate_ip++); // auto-fill with my IP
   memset(&(myAddr.sin_zero), 0, 8);    // zero the rest of the struct
 
   if (bind(socketnum, (struct sockaddr *)&myAddr, addrlen) == -1)
-  { perror("bind"); exit(1); }
+  { perror("bind"); return 0; }
 
   FD_ZERO(&readfds);
   FD_SET(socketnum, &readfds);
@@ -44,17 +61,8 @@ DatagramSocket::DatagramSocket(short port)
 
   int allowed = 1;
   setsockopt(socketnum, SOL_SOCKET, SO_BROADCAST, (char*)&allowed, sizeof(allowed));
-}
 
-DatagramSocket::~DatagramSocket()
-{
-  CLOSESOCKET(socketnum);
-}
-
-DatagramSocket* DatagramSocket::theInstance = 0;
-DatagramSocket* DatagramSocket::getInstance(void)
-{
-  return theInstance;
+  return 1;
 }
 
 unsigned char DatagramSocket::waitforMessage(unsigned char how)
@@ -188,3 +196,26 @@ void DatagramSocket::send(char *ipa, short port, char *message, int length)
   }
 }
 
+ULONG DatagramSocket::getIPNumber(ULONG num)
+{
+  char buffer[100];
+  ULONG returnaddress;
+
+  if (gethostname(buffer,sizeof(buffer))==SOCKET_ERROR)
+  {
+    return INADDR_ANY; //well take any address, if we fail
+  }
+
+  struct hostent *hosts=gethostbyname(buffer);
+  if (hosts==NULL)
+  {
+    return INADDR_ANY; //well take any address, if we fail
+  }
+
+  int num_ip=0;
+  for (num_ip=0;hosts->h_addr_list[num_ip]!=NULL;num_ip++);
+
+  int get_ip=(num%num_ip);//Just wrap around, if no interface are present any more
+  memcpy(&returnaddress, hosts->h_addr_list[get_ip], sizeof(ULONG));
+  return returnaddress;
+}
diff --git a/dsock.h b/dsock.h
index ba99d47d6c13a3f3e27060c48ea6607a92879bd3..734bd050b38d7aec62eea4a0f9bdd26eb3de8b6b 100644 (file)
--- a/dsock.h
+++ b/dsock.h
 #define DSOCK_H
 
 #ifndef WIN32
-
 #include <netinet/in.h>
+#include <netdb.h>
 #include <sys/socket.h>
 #include <unistd.h>
 #include <arpa/inet.h>
+#include <sys/time.h>
+#define SOCKET_ERROR 0
 #else
 #include <winsock2.h>
 #include <Ws2tcpip.h>
+#include <sys/timeb.h>
 #endif
 
-
 #include <sys/types.h>
-#ifndef WIN32
-#include <sys/time.h>
-#else
-#include <sys/timeb.h>
-#endif
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -53,6 +50,7 @@ class DatagramSocket
     DatagramSocket(short);             // port
     ~DatagramSocket();
     static DatagramSocket* getInstance(void);
+    int init();
     unsigned char waitforMessage(unsigned char); // int =0-block =1-new wait =2-continue wait
     int getDataLength(void) const;
     char *getData(void);               // returns a pointer to the data
@@ -61,6 +59,8 @@ class DatagramSocket
     void send(char *, short, char *, int); // send wants: IP Address ddn style, port,
                                            // data, length of data
   private:
+    ULONG getIPNumber(ULONG num);
+    static ULONG iterate_ip;
     const static char DSOCKDEBUG = 0;
     static DatagramSocket* theInstance;
     int socketnum;                  // Socket descriptor
index e0d45975e9622317b4dfbe087feea0b7502f4765..c23c9959c65abe9fded57104f54dae9fc14b0b5c 100644 (file)
 [uuid("EB87AB22-7A95-49c3-8CCE-2F6D61A87009")]
 class DsSourceFilter: public CBaseFilter {
 public:
-  DsSourceFilter();
-  ~DsSourceFilter();
-  CCritSec* GetLock(){return &crit_sec;};
-  virtual int GetPinCount();
-  virtual CBasePin *GetPin(int n);
-  int getCurrentAudioMediaSample(IMediaSample** ms);
-  int DeliverAudioMediaSample(IMediaSample* ms);
-  int getCurrentVideoMediaSample(IMediaSample** ms);
-  int DeliverVideoMediaSample(IMediaSample* ms);
+       DsSourceFilter();
+       ~DsSourceFilter();
+       CCritSec* GetLock(){return &crit_sec;};
+       virtual int GetPinCount();
+       virtual CBasePin *GetPin(int n);
+       int getCurrentAudioMediaSample(IMediaSample** ms);
+       int DeliverAudioMediaSample(IMediaSample* ms);
+       int getCurrentVideoMediaSample(IMediaSample** ms);
+       int DeliverVideoMediaSample(IMediaSample* ms);
+       REFERENCE_TIME getStartOffset(){return m_tStart;};
 protected:
-  CCritSec crit_sec;
-  DsSourcePin *audiopin;
-  DsSourcePin *videopin;
+       CCritSec crit_sec;
+       DsSourcePin *audiopin;
+       DsSourcePin *videopin;
 
 
 };
 
-#endif
\ No newline at end of file
+#endif
index 70286eeff8540e735b19aa951d602d4fe7396372..0ce629a15fdadbc3f3e7f25c7f941e877dca3d3c 100644 (file)
 #include <mmreg.h>
 
 DsSourcePin::DsSourcePin(DsSourceFilter *pFilter,
-             CCritSec *pLock,HRESULT *phr,LPCWSTR pName,bool audio):
+                                                CCritSec *pLock,HRESULT *phr,LPCWSTR pName,bool audio):
 CBaseOutputPin(NAME("dssourcepin"),pFilter,pLock,phr,pName)
 {
-  isaudiopin=audio;
-  m_pFilter=pFilter;
+       isaudiopin=audio;
+       m_pFilter=pFilter;
 
 }
 
 DsSourcePin::~DsSourcePin()
 {
-
+       
 
 }
 
 HRESULT DsSourcePin::GetMediaType(int iPosition, CMediaType *pmt)
 {
-  HRESULT hr;
-  ASSERT(pmt);
-  pmt->InitMediaType();
-  if (isaudiopin){
-    if (iPosition==0) {
-      pmt->SetType(&MEDIATYPE_Audio);
-      MPEG1WAVEFORMAT wfe;
-      ZeroMemory(&wfe,sizeof(wfe));
-      wfe.wfx.cbSize=22;
-      wfe.wfx.nSamplesPerSec=48000;
-      wfe.wfx.nChannels=2;
-      wfe.wfx.nAvgBytesPerSec=32000;
-      wfe.wfx.nBlockAlign=768;
-      wfe.wfx.wFormatTag=WAVE_FORMAT_MPEG;
-      wfe.fwHeadLayer=2;
-      wfe.dwHeadBitrate=256000;
-      wfe.fwHeadMode=ACM_MPEG_STEREO;
-      wfe.fwHeadModeExt=1;
-      wfe.wHeadEmphasis=1;
-      wfe.fwHeadFlags=ACM_MPEG_ID_MPEG1 |ACM_MPEG_ORIGINALHOME | ACM_MPEG_PROTECTIONBIT;
-      pmt->SetSubtype(&MEDIASUBTYPE_MPEG2_AUDIO);
-      pmt->SetFormatType(&FORMAT_WaveFormatEx);
-      pmt->SetFormat((BYTE*)&wfe,sizeof(wfe));
-      pmt->SetSampleSize(0);
-      hr=S_OK;
-
-
+       HRESULT hr;
+       ASSERT(pmt);
+       pmt->InitMediaType();
+       if (isaudiopin){
+               if (iPosition==0) {
+                       pmt->SetType(&MEDIATYPE_Audio);
+                       MPEG1WAVEFORMAT wfe;
+                       ZeroMemory(&wfe,sizeof(wfe));
+                       wfe.wfx.cbSize=22;
+                       wfe.wfx.nSamplesPerSec=48000;
+                       wfe.wfx.nChannels=2;
+                       wfe.wfx.nAvgBytesPerSec=32000;
+                       wfe.wfx.nBlockAlign=768;
+                       wfe.wfx.wFormatTag=WAVE_FORMAT_MPEG;
+                       wfe.fwHeadLayer=2;
+                       wfe.dwHeadBitrate=256000;
+                       wfe.fwHeadMode=ACM_MPEG_STEREO;
+                       wfe.fwHeadModeExt=1;
+                       wfe.wHeadEmphasis=1;
+                       wfe.fwHeadFlags=ACM_MPEG_ID_MPEG1 |ACM_MPEG_ORIGINALHOME | ACM_MPEG_PROTECTIONBIT;
+                       pmt->SetSubtype(&MEDIASUBTYPE_MPEG2_AUDIO);
+                       pmt->SetFormatType(&FORMAT_WaveFormatEx);
+                       pmt->SetFormat((BYTE*)&wfe,sizeof(wfe));
+                       pmt->SetSampleSize(0);
+                       hr=S_OK;
+
+               
         } else  {
-      hr=VFW_S_NO_MORE_ITEMS ;
-    }
-  } else {
-    if (iPosition == 0) {
-      pmt->SetType(&MEDIATYPE_Video);
-      hr=S_OK;
-      pmt->SetSubtype(&MEDIASUBTYPE_MPEG2_VIDEO);
+                       hr=VFW_S_NO_MORE_ITEMS ;
+               }
+       } else {
+               if (iPosition == 0) {
+                       pmt->SetType(&MEDIATYPE_Video);
+                       hr=S_OK;
+                       pmt->SetSubtype(&MEDIASUBTYPE_MPEG2_VIDEO);
             pmt->SetFormatType(&FORMAT_MPEG2Video);
 
             MPEG2VIDEOINFO hdr;
@@ -84,11 +84,11 @@ HRESULT DsSourcePin::GetMediaType(int iPosition, CMediaType *pmt)
             hdr.hdr.bmiHeader.biWidth = 720;
             hdr.hdr.bmiHeader.biHeight = 568;
             pmt->SetFormat((BYTE*)&hdr,sizeof(hdr));
-    } else {
-      hr=VFW_S_NO_MORE_ITEMS;
-    }
-  }
-  return hr ;
+               } else {
+                       hr=VFW_S_NO_MORE_ITEMS;
+               }
+       }
+       return hr ;
 }
 
 // No description
@@ -99,45 +99,54 @@ HRESULT DsSourcePin::CheckMediaType(const CMediaType *pmt)
     if (isaudiopin) {
         bool subtype=false;
 #if 0 /* For future demands ac3 */
-    subtype=pmt->subtype==(MEDIASUBTYPE_DOLBY_AC3);
+               subtype=pmt->subtype==(MEDIASUBTYPE_DOLBY_AC3);
 #endif
-    subtype=(pmt->subtype==(MEDIASUBTYPE_MPEG2_AUDIO));
+               subtype=(pmt->subtype==(MEDIASUBTYPE_MPEG2_AUDIO));
         if (pmt->majortype==MEDIATYPE_Audio && subtype) {
-      res = S_OK ;
+                       res = S_OK ;
         } else {
             res = S_FALSE ;
-        }
+        }    
     } else {
         if (pmt->majortype==MEDIATYPE_Video &&
                   pmt-> subtype==MEDIASUBTYPE_MPEG2_VIDEO) {
-      res = S_OK ;
+                       res = S_OK ;
         } else {
             res = S_FALSE ;
-        }
+        }  
     }
     return res;
 }
 
 HRESULT DsSourcePin::DecideBufferSize(IMemAllocator *pa,ALLOCATOR_PROPERTIES *all_pp){
-  HRESULT hr;
+       HRESULT hr;
     CAutoLock al(m_pFilter->GetLock());
     CheckPointer(pa, E_POINTER);
     CheckPointer(all_pp, E_POINTER);
-    if (all_pp->cBuffers*all_pp->cbBuffer < 300*64*1024)
-    {
-        all_pp->cBuffers = 300;
-        all_pp->cbBuffer = 64*1024;
-    }
+       if (isaudiopin) {
+               if (all_pp->cBuffers*all_pp->cbBuffer < 300*64*1024)
+               {
+                       all_pp->cBuffers = 300;
+                       all_pp->cbBuffer = 64*1024;
+               }
+       } else {
+               if (all_pp->cBuffers*all_pp->cbBuffer < 300*64*1024)
+               {
+                       all_pp->cBuffers = 300;
+                       all_pp->cbBuffer = 64*1024;
+               }
+       }
+
     ALLOCATOR_PROPERTIES all_pp_cur;
     hr =pa->SetProperties(all_pp,&all_pp_cur);
-    if (FAILED(hr))
+    if (FAILED(hr)) 
     {
         return hr;
     }
-    if (all_pp_cur.cbBuffer*all_pp_cur.cBuffers < all_pp->cBuffers*all_pp->cbBuffer)
+    if (all_pp_cur.cbBuffer*all_pp_cur.cBuffers < all_pp->cBuffers*all_pp->cbBuffer) 
     {
         return E_FAIL;
     }
 
     return S_OK;
-}
\ No newline at end of file
+}
index 2d445bdfd194b9650daf65bccd575561cdd4144f..4d1daf796b875dc7bf95c2a36120d2680c6fab17 100644 (file)
-/*
-    Copyright 2004-2005 Chris Tallon
-
-    This file is part of VOMP.
-
-    VOMP is free software; you can redistribute it and/or modify
-    it under the terms of the GNU General Public License as published by
-    the Free Software Foundation; either version 2 of the License, or
-    (at your option) any later version.
-
-    VOMP is distributed in the hope that it will be useful,
-    but WITHOUT ANY WARRANTY; without even the implied warranty of
-    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-    GNU General Public License for more details.
-
-    You should have received a copy of the GNU General Public License
-    along with VOMP; if not, write to the Free Software
-    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
-*/
-
-#include "threadwin.h"
-
-// Undeclared functions, only for use in this file to start the thread
-DWORD WINAPI threadInternalStart(void *arg)
-{
-  Thread *t = (Thread *)arg;
-  t->threadInternalStart2();
-  return 0;
-}
-
-int ThreadWin::threadStart()
-{
-  threadCond = CreateEvent(NULL,/*FALSE*/TRUE,FALSE,NULL);
-  if (threadCond == NULL) return 0;
-  threadCondMutex = CreateMutex(NULL,FALSE,NULL);
-  if (threadCondMutex == NULL)
-  {
-    CloseHandle(threadCond);
-    return 0;
-  }
-
-  threadActive = 1;
-  DWORD threadId;
-  pthread = CreateThread(NULL, 0, threadInternalStart, (void*)this,0, &threadId);
-  if (pthread == NULL)
-  {
-    CloseHandle(threadCond);
-    CloseHandle(threadCondMutex);
-    return 0;
-  }
-  return 1;
-}
-
-void ThreadWin::threadStop()
-{
-  threadActive = 0;
-  // Signal thread here in case it's waiting
-  threadSignal();
-  WaitForSingleObject(pthread, INFINITE);
-  this->threadPostStopCleanup();
-}
-
-void ThreadWin::threadCancel()
-{
-  threadActive = 0;
-  //TerminateThread(pthread, 0);
-  threadSignalNoLock();
-  WaitForSingleObject(pthread, INFINITE);
-  this->threadPostStopCleanup();
-}
-
-void ThreadWin::threadCheckExit()
-{
-  if (!threadActive) ExitThread(NULL);
-}
-
-void ThreadWin::threadLock()
-{
-  WaitForSingleObject(threadCondMutex, INFINITE);
-}
-
-void ThreadWin::threadUnlock()
-{
-  ReleaseMutex(threadCondMutex);
-}
-
-void ThreadWin::threadSignal()
-{
-  WaitForSingleObject(threadCondMutex, INFINITE);
- // PulseEvent(threadCond);
-  SetEvent(threadCond);
-  ReleaseMutex(threadCondMutex);
-}
-
-void ThreadWin::threadSignalNoLock()
-{
-//    PulseEvent(threadCond);
-  SetEvent(threadCond);
-}
-
-void ThreadWin::threadWaitForSignal()
-{
-  threadUnlock();
-  WaitForSingleObject(threadCond,INFINITE);
-  ResetEvent(threadCond);
-  threadLock();
-}
-
-void ThreadWin::threadWaitForSignalTimed(struct timespec* ts)
-{
-  threadUnlock();
-  HANDLE handles[2] ={threadCond, NULL};
-  LARGE_INTEGER duration;
-  duration.QuadPart=(ts->tv_sec*1000*1000*10+ts->tv_nsec/100)+WINDOWS_TIME_BASE_OFFSET;
-  handles[1]=CreateWaitableTimer(NULL,TRUE,NULL);
-  SetWaitableTimer(handles[1], &duration, 0, NULL, NULL, 0);
-  WaitForMultipleObjects(2,handles,FALSE,INFINITE);
-  ResetEvent(threadCond);
-  CloseHandle(handles[1]);
-  threadLock();
-}
-
-void ThreadWin::threadSetKillable()
-{
-  //WIN32:Ignore or use a separate Event Object to simulate this
-}
+/*\r
+    Copyright 2004-2005 Chris Tallon\r
+\r
+    This file is part of VOMP.\r
+\r
+    VOMP is free software; you can redistribute it and/or modify\r
+    it under the terms of the GNU General Public License as published by\r
+    the Free Software Foundation; either version 2 of the License, or\r
+    (at your option) any later version.\r
+\r
+    VOMP is distributed in the hope that it will be useful,\r
+    but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
+    GNU General Public License for more details.\r
+\r
+    You should have received a copy of the GNU General Public License\r
+    along with VOMP; if not, write to the Free Software\r
+    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r
+*/\r
+\r
+#include "threadwin.h"\r
+\r
+// Undeclared functions, only for use in this file to start the thread\r
+DWORD WINAPI threadInternalStart(void *arg)\r
+{\r
+  Thread *t = (Thread *)arg;\r
+  t->threadInternalStart2();\r
+  return 0;\r
+}\r
+\r
+int ThreadWin::threadStart()\r
+{\r
+  threadCond = CreateEvent(NULL,/*FALSE*/TRUE,FALSE,NULL);\r
+  if (threadCond == NULL) return 0;\r
+  threadCondMutex = CreateMutex(NULL,FALSE,NULL);\r
+  if (threadCondMutex == NULL)\r
+  {\r
+    CloseHandle(threadCond);\r
+    return 0;\r
+  }\r
+\r
+  threadActive = 1;\r
+  DWORD threadId;\r
+  pthread = CreateThread(NULL, 0, threadInternalStart, (void*)this,0, &threadId);\r
+  if (pthread == NULL)\r
+  {\r
+    CloseHandle(threadCond);\r
+    CloseHandle(threadCondMutex);\r
+    return 0;\r
+  }\r
+  return 1;\r
+}\r
+\r
+void ThreadWin::threadStop()\r
+{\r
+  threadActive = 0;\r
+  // Signal thread here in case it's waiting\r
+  threadSignal();\r
+  WaitForSingleObject(pthread, INFINITE);\r
+  this->threadPostStopCleanup();\r
+}\r
+\r
+void ThreadWin::threadCancel()\r
+{\r
+  threadActive = 0;\r
+  //TerminateThread(pthread, 0);\r
+  threadSignalNoLock();\r
+  WaitForSingleObject(pthread, INFINITE);\r
+  this->threadPostStopCleanup();\r
+}\r
+\r
+void ThreadWin::threadCheckExit()\r
+{\r
+  if (!threadActive) ExitThread(NULL);\r
+}\r
+\r
+void ThreadWin::threadLock()\r
+{\r
+  WaitForSingleObject(threadCondMutex, INFINITE);\r
+}\r
+\r
+void ThreadWin::threadUnlock()\r
+{\r
+  ReleaseMutex(threadCondMutex);\r
+}\r
+\r
+void ThreadWin::threadSignal()\r
+{\r
+  WaitForSingleObject(threadCondMutex, INFINITE);\r
+ // PulseEvent(threadCond);\r
+  SetEvent(threadCond);\r
+  ReleaseMutex(threadCondMutex);\r
+}\r
+\r
+void ThreadWin::threadSignalNoLock()\r
+{\r
+//    PulseEvent(threadCond);\r
+       SetEvent(threadCond);\r
+}\r
+\r
+void ThreadWin::threadWaitForSignal()\r
+{\r
+  threadUnlock();\r
+  WaitForSingleObject(threadCond,INFINITE);\r
+  ResetEvent(threadCond);\r
+  threadLock();\r
+}\r
+\r
+void ThreadWin::threadWaitForSignalTimed(struct timespec* ts)\r
+{\r
+       threadUnlock();\r
+       HANDLE handles[2] ={threadCond, NULL};\r
+       LARGE_INTEGER duration;\r
+       duration.QuadPart=(((LONGLONG)ts->tv_sec)*1000LL*1000LL*10LL+((LONGLONG)ts->tv_nsec)/100LL)+WINDOWS_TIME_BASE_OFFSET;\r
+       SYSTEMTIME debug;\r
+       FILETIME debugfile;\r
+       GetSystemTime(&debug);\r
+       SystemTimeToFileTime(&debug,&debugfile);\r
+       \r
+       handles[1]=CreateWaitableTimer(NULL,TRUE,NULL);\r
+       SetWaitableTimer(handles[1], &duration, 0, NULL, NULL, 0);\r
+       WaitForMultipleObjects(2,handles,FALSE,INFINITE);\r
+       ResetEvent(threadCond);\r
+       CloseHandle(handles[1]);\r
+       threadLock();\r
+}\r
+\r
+void ThreadWin::threadSetKillable()\r
+{\r
+  //WIN32:Ignore or use a separate Event Object to simulate this\r
+}\r
+\r
diff --git a/vdr.cc b/vdr.cc
index 2db53f8c106b403f1fbe4a4aaa212e503a614cb3..50006677845f84ada42f12c57a1418de33e892ba 100644 (file)
--- a/vdr.cc
+++ b/vdr.cc
@@ -26,8 +26,8 @@ VDR* VDR::instance = NULL;
 #define MUTEX_LOCK(mutex) pthread_mutex_lock(mutex)
 #define MUTEX_UNLOCK(mutex) pthread_mutex_unlock(mutex)
 #else
-#define MUTEX_LOCK(mutex) WaitForSingleObject(mutex, INFINITE )
-#define MUTEX_UNLOCK(mutex) ReleaseMutex(mutex)
+#define MUTEX_LOCK(mutex) WaitForSingleObject(*(mutex), INFINITE )
+#define MUTEX_UNLOCK(mutex) ReleaseMutex(*(mutex))
 #endif
 
 
@@ -41,7 +41,7 @@ VDR::VDR()
 #ifndef WIN32
   pthread_mutex_init(&mutex, NULL);
 #else
-  mutex=CreateMutex(NULL,TRUE,NULL);
+  mutex=CreateMutex(NULL,FALSE,NULL);
 #endif
   packetLength = 0;
   packetPos = 0;
@@ -84,8 +84,8 @@ void VDR::findServers(vector<VDRServer>& servers)
 {
   findingServer = 1;
   char* message = "VOMP";
-  DatagramSocket ds(port);
 
+  DatagramSocket ds(port);
   int haveAtLeastOne = 0;
   int retval;
   int waitType = 1;
@@ -93,6 +93,7 @@ void VDR::findServers(vector<VDRServer>& servers)
   {
     if (waitType == 1)
     {
+      ds.init();
       logger->log("VDR", Log::NOTICE, "Broadcasting for server");
       ds.send("255.255.255.255", 3024, message, strlen(message));
     }
@@ -757,6 +758,43 @@ ULLONG VDR::positionFromFrameNumber(ULONG frameNumber)
   return position;
 }
 
+ULONG VDR::frameNumberFromPosition(ULLONG position)
+{
+  unsigned long totalLength = 16;
+  UCHAR* buffer = new UCHAR[totalLength];
+
+  *(unsigned long*)&buffer[0] = htonl(totalLength - 4);
+  *(unsigned long*)&buffer[4] = htonl(VDR_FRAMEFROMPOS);
+  *(ULLONG*)&buffer[8] = htonll(position);
+
+  MUTEX_LOCK(&mutex);
+  if (!connected) { MUTEX_UNLOCK(&mutex); return 0; }
+
+  unsigned int a = tcp->sendPacket(buffer, totalLength);
+  delete []buffer;
+
+  if (a != totalLength)
+  {
+    disconnect();
+    MUTEX_UNLOCK(&mutex);
+    return 0;
+  }
+
+  if (!getPacket())
+  {
+    MUTEX_UNLOCK(&mutex);
+    return 0;
+  }
+
+  ULONG framenumber = extractULONG();
+  freePacket();
+  MUTEX_UNLOCK(&mutex);
+
+  Log::getInstance()->log("VDR", Log::DEBUG, "VDR said new framenumber is: %u", framenumber);
+
+  return framenumber;
+}
+
 EventList* VDR::getChannelSchedule(ULONG number)
 {
   time_t now;
diff --git a/vdr.h b/vdr.h
index 7bb41701b573f5d61b2ec9db2a84b6cc954302cb..aeb7b58cf14586af6bf1537147ce758af104a532 100644 (file)
--- a/vdr.h
+++ b/vdr.h
@@ -141,6 +141,7 @@ class VDR
     ULLONG     streamRecording(Recording* rec);
     ULLONG     rescanRecording();
     ULLONG     positionFromFrameNumber(ULONG frameNumber);
+       ULONG      frameNumberFromPosition(ULLONG position);
 
     ChannelList* getChannelsList(ULONG type);
     int          streamChannel(ULONG number);
@@ -195,6 +196,7 @@ class VDR
     const static ULONG VDR_GETTIMERS           = 14;
     const static ULONG VDR_SETTIMER            = 15;
     const static ULONG VDR_POSFROMFRAME        = 16;
+       const static ULONG VDR_FRAMEFROMPOS        = 17;
 
     int  getPacket();
     void freePacket();
@@ -206,3 +208,4 @@ class VDR
 };
 
 #endif
+
diff --git a/video.h b/video.h
index 91d04591c47c3006fe549a54c6485465016f4b0a..69de304acc088011520111f99a9a08cd816334bf 100644 (file)
--- a/video.h
+++ b/video.h
@@ -57,8 +57,10 @@ class Video: public DrainTarget
     virtual ULONG timecodeToFrameNumber(ULLONG timecode)=0;
     virtual int getFD()=0;
     virtual ULLONG getCurrentTimestamp()=0;
-  virtual void turnVideoOn(){};
-  virtual void turnVideoOff(){};
+
+    virtual void turnVideoOn(){};
+    virtual void turnVideoOff(){};
+    virtual ULLONG frameNumberToTimecode(ULONG timecode) { return 0; };
 
 #ifdef DEV
     virtual int test() { return 0; }
index 8869322bc73aae786eb27a510b4bd814e55ce49a..6e7c61bb3c5c6c5fb092ba00892c7af1343de8a4 100644 (file)
@@ -378,3 +378,7 @@ UINT VideoMVP::DeliverMediaSample(MediaPacket packet, UCHAR* buffer, UINT *sampl
 {
   return 0;
 }
+
+void VideoMVP::ResetTimeOffsets()
+{
+}
index b98418552c1dc342189042cd8dc440d7237005ae..f2a2aaf8bc6c2235da7fa02e40b184b2c8c1b10c 100644 (file)
@@ -72,6 +72,7 @@ class VideoMVP : public Video
     //Writing Data to Videodevice
     virtual UINT DeliverMediaSample(MediaPacket packet, UCHAR* buffer, UINT *samplepos);
     virtual long long SetStartOffset(long long curreftime, bool *rsync) { return 0; };
+    virtual void ResetTimeOffsets();
 
 #ifdef DEV
     int test();
index f7e7da678a426bc461482c971531a5b610a947a5..8c1962d20e14498f74336c099a1253c032e1e462 100644 (file)
 */
 
 #include "videowin.h"
+#include "log.h"
 #include "dssourcefilter.h"
+#include "dsallocator.h"
+#include "vdr.h"
 
-
+void AdjustWindow();
 
 
 
@@ -29,7 +32,12 @@ VideoWin::VideoWin()
 {
   dsgraphbuilder=NULL;
   dsmediacontrol=NULL;
+  dsvmrrenderer=NULL;
+  dsrefclock=NULL;
+  dsmediafilter=NULL;
   sourcefilter=NULL;
+  allocatorvmr=NULL;
+  dsvmrsurfnotify=NULL;
   filtermutex=CreateMutex(NULL,FALSE,NULL);
   offsetnotset=true;
   offsetvideonotset=true;
@@ -42,6 +50,8 @@ VideoWin::VideoWin()
   cur_video_media_sample=NULL;
   videoon=true;
   audioon=true;
+  pseudotvsize=0;
 
 
 }
@@ -50,6 +60,7 @@ VideoWin::~VideoWin()
 {
   CleanupDS();
   CloseHandle(filtermutex);
 
 
   instance = NULL;
@@ -60,18 +71,21 @@ int VideoWin::init(UCHAR tformat)
   if (initted) return 0;
 
   initted = 1;
+  tvsize=Video::ASPECT16X9; //Internally Vomp should think we are a 16:9 TV
+  
   if (!setFormat(tformat)){ shutdown(); return 0; }
   return 1;
 }
 
 int VideoWin::setTVsize(UCHAR ttvsize)
 {
+  pseudotvsize=ttvsize;
   return 1;
 }
 
 int VideoWin::setDefaultAspect()
 {
-  return setAspectRatio(tvsize);
+  return setAspectRatio(Video::ASPECT4X3);
 }
 
 int VideoWin::shutdown()
@@ -114,7 +128,7 @@ int VideoWin::setAspectRatio(UCHAR taspectRatio)
   if (!initted) return 0;
   if ((taspectRatio != ASPECT4X3) && (taspectRatio != ASPECT16X9)) return 0;
   aspectRatio = taspectRatio;
-
+  AdjustWindow();
   return 1;
 }
 
@@ -122,11 +136,12 @@ int VideoWin::setMode(UCHAR tmode)
 {
   if (!initted) return 0;
 
-  if ((tmode == LETTERBOX) && (tvsize == ASPECT16X9)) return 0; // invalid mode
+  //if ((tmode == LETTERBOX) && (tvsize == ASPECT16X9)) return 0; // invalid mode
 
   if ((tmode != NORMAL) && (tmode != LETTERBOX) && (tmode != UNKNOWN2) && (tmode != QUARTER) && (tmode != EIGHTH)
       && (tmode != ZOOM) && (tmode != UNKNOWN6)) return 0;
   mode = tmode;
+  AdjustWindow();
 
   return 1;
 }
@@ -174,6 +189,7 @@ int VideoWin::play()
 
   //Build filter graph
   HRESULT hres;
   if (hres=CoCreateInstance(CLSID_FilterGraph,NULL,CLSCTX_INPROC_SERVER,
     IID_IGraphBuilder,(void**)&dsgraphbuilder)!=S_OK) {
       return 0;
@@ -185,37 +201,88 @@ int VideoWin::play()
 //   dsgraphbuilder->RenderFile(L"D:\\Projekte\\VTP Client\\test.mpa" ,NULL);
    //So this is the real code, this prevents the feeder from calling noexisting objects!
    WaitForSingleObject(filtermutex,INFINITE);
-   offsetnotset=true;
-   offsetvideonotset=true;
-   offsetaudionotset=true;
    firstsynched=false;
    sourcefilter=new DsSourceFilter(); //Creating our Source filter for pushing Data
    // to DirectShow
    if (hres=dsgraphbuilder->AddFilter(sourcefilter,L"Vomp Win Source Filter")!=S_OK) {
+        Log::getInstance()->log("VideoWin", Log::WARN , "Failed adding Vomp Source Filter!");
      CleanupDS();
      ReleaseMutex(filtermutex);
      return 0;
    }
-   if (audioon) {
+   //if (audioon) {
      if (hres=dsgraphbuilder->Render(sourcefilter->GetPin(0)/*audio*/)!=S_OK) {
+          Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering audio!");
        CleanupDS();
        ReleaseMutex(filtermutex);
        return 0;
      }
-   }
+   //}
 #ifdef DO_VIDEO
-   if (videoon) {
-     if (hres=dsgraphbuilder->Render(sourcefilter->GetPin(1)/*video*/)!=S_OK) {
-       CleanupDS();
-       ReleaseMutex(filtermutex);
-       return 0;
-     }
+    if (videoon) {
+               //We alloc the vmr9 as next step
+               if (hres=CoCreateInstance(CLSID_VideoMixingRenderer9,0,
+                       CLSCTX_INPROC_SERVER,IID_IBaseFilter,(void**) &dsvmrrenderer)!=S_OK) {
+                       Log::getInstance()->log("VideoWin", Log::WARN ,"Failed creating VMR9 renderer!");
+                       CleanupDS();
+                       ReleaseMutex(filtermutex);
+               }
+                       /*VMR 9 stuff**/
+               if (hres=dsgraphbuilder->AddFilter(dsvmrrenderer,L"VMR9")!=S_OK) {
+                       CleanupDS();
+                       Log::getInstance()->log("VideoWin", Log::WARN ,"Failed adding VMR9 renderer!");
+                       ReleaseMutex(filtermutex);
+                       return 0;
+               }
+               IVMRFilterConfig9* vmrfilconfig;
+               if (dsvmrrenderer->QueryInterface(IID_IVMRFilterConfig9,(void**)&vmrfilconfig)!=S_OK) {
+                       CleanupDS();
+                       Log::getInstance()->log("VideoWin", Log::WARN ,"Failed getting VMR9 Filterconfig interface!");
+                       ReleaseMutex(filtermutex);
+                       return 0;
+               }
+               vmrfilconfig->SetRenderingMode(VMR9Mode_Renderless);
+               vmrfilconfig->Release();
+               
+               if (dsvmrrenderer->QueryInterface(IID_IVMRSurfaceAllocatorNotify9,(void**)& dsvmrsurfnotify)!=S_OK) {
+                       CleanupDS();
+                       Log::getInstance()->log("VideoWin", Log::WARN ,"Failed getting VMR9 Surface Allocator interface!");
+                       ReleaseMutex(filtermutex);
+                       return 0;
+               }
+               allocatorvmr=new DsAllocator();
+               dsvmrsurfnotify->AdviseSurfaceAllocator(NULL,allocatorvmr);
+               allocatorvmr->AdviseNotify(dsvmrsurfnotify);
+
+
+
+               /*VMR 9 stuff end */
+               IFilterGraph2*fg2=NULL;
+               if (dsgraphbuilder->QueryInterface(IID_IFilterGraph2,(void**)&fg2)!=S_OK) {
+                       Log::getInstance()->log("VideoWin", Log::WARN , "Failed querying for FilterGraph2 Interface!");
+                       CleanupDS();
+                       ReleaseMutex(filtermutex);
+                       return 0;
+               }
+               if (hres=fg2->RenderEx(sourcefilter->GetPin(1)/*video*/,
+                               AM_RENDEREX_RENDERTOEXISTINGRENDERERS,NULL)!=S_OK) {
+                       Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering Video!");
+                       CleanupDS();
+                       ReleaseMutex(filtermutex);
+                       return 0;
+               }
    }
 #endif
-
-
+   if (hres=CoCreateInstance(CLSID_SystemClock,NULL,CLSCTX_INPROC_SERVER,
+    IID_IReferenceClock,(void**)&dsrefclock)!=S_OK) {
+      return 0;
+   }
+   
+   dsgraphbuilder->QueryInterface(IID_IMediaFilter,(void **) &dsmediafilter);
+   dsmediafilter->SetSyncSource(dsrefclock);
 
    dsgraphbuilder->QueryInterface(IID_IMediaControl,(void **) &dsmediacontrol);
+
    dsmediacontrol->Run();
    ReleaseMutex(filtermutex);
   return 1;
@@ -235,6 +302,7 @@ int VideoWin::reset()
 {
   if (!initted) return 0;
 
+
   return 1;
 }
 
@@ -284,7 +352,19 @@ int VideoWin::getFD()
 
 ULLONG VideoWin::getCurrentTimestamp()
 {
-  return 0;
+       REFERENCE_TIME cr_time,startoffset;
+       
+       if (!dsrefclock || !sourcefilter) return 0;
+       
+       dsrefclock->GetTime(&cr_time);
+       startoffset=sourcefilter->getStartOffset();
+       cr_time-=startoffset;
+       cr_time-=lastreftimeRT;
+       ULLONG result=frameNumberToTimecode(
+               VDR::getInstance()->frameNumberFromPosition(lastreftimeBYTE));
+       result+=(ULLONG)(cr_time/10000LL*90LL);
+       return result;
+
 }
 
 ULONG VideoWin::timecodeToFrameNumber(ULLONG timecode)
@@ -293,6 +373,12 @@ ULONG VideoWin::timecodeToFrameNumber(ULLONG timecode)
   else               return (ULONG)(((double)timecode / (double)90000) * (double)30);
 }
 
+ULLONG VideoWin::frameNumberToTimecode(ULONG framenumber)
+{
+  if (format == PAL) return (ULLONG)(((double)framenumber * (double)90000) / (double)25);
+  else               return (ULLONG)(((double)framenumber * (double)90000) / (double)30);
+}
+
 void VideoWin::CleanupDS()
 {
   WaitForSingleObject(filtermutex,INFINITE);
@@ -304,6 +390,28 @@ void VideoWin::CleanupDS()
     cur_video_media_sample->Release();
     cur_video_media_sample=NULL;
   }
+  if (dsvmrsurfnotify) {
+         dsvmrsurfnotify->Release();
+         dsvmrsurfnotify=NULL;
+  }
+  if (dsvmrrenderer) {
+         dsvmrrenderer->Release();
+         dsvmrrenderer=NULL;
+  }
+  if (allocatorvmr) {
+         allocatorvmr->Release();
+         allocatorvmr=NULL;
+  }
+  if (dsrefclock) {
+         dsrefclock->Release();
+         dsrefclock=NULL;
+  }
+  if (dsmediafilter) {
+         dsmediafilter->Release();
+         dsmediafilter=NULL;
+  }
 
   if (dsmediacontrol) {
     dsmediacontrol->Stop();
@@ -350,10 +458,10 @@ UINT VideoWin::DeliverMediaSample(MediaPacket packet,
     *samplepos+=headerstrip;
     if ( packet.synched ) {
       DeliverVideoMediaSample();//write out old data
-      if (packet.presentation_time<0) { //Preroll?
+   /*   if (packet.presentation_time<0) { //Preroll?
         *samplepos=packet.length;//if we have not processed at least one
         return packet.length;//synched packet ignore it!
-      }
+      }*/
 
       reftime1=packet.presentation_time;
       reftime2=reftime1+1;
@@ -402,11 +510,19 @@ UINT VideoWin::DeliverMediaSample(MediaPacket packet,
       ms->SetTime(&reftime1,&reftime2);
       //ms->SetTime(NULL,NULL);
       ms->SetMediaTime(NULL, NULL);
+         if (reftime1<0) ms->SetPreroll(TRUE);
+         else ms->SetPreroll(FALSE);
+         /*Timecode handling*/
+         lastreftimeRT=reftime1;
+         lastreftimeBYTE=packet.recording_byte_pos;
+
     }else {
       ms->SetSyncPoint(FALSE);
       ms->SetTime(NULL,NULL);
       ms->SetMediaTime(NULL, NULL);
-      ms->SetSyncPoint(TRUE);
+         ms->SetPreroll(FALSE);
+        
+    //  ms->SetSyncPoint(TRUE);
     }
   }
 
@@ -492,6 +608,8 @@ long long VideoWin::SetStartOffset(long long curreftime, bool *rsync)
     startoffset=curreftime;//offset is set for audio
     offsetnotset=false;
     offsetvideonotset=false;
+       
+       
   } else {
     if (offsetvideonotset) {
       offsetvideonotset=false;
@@ -500,8 +618,8 @@ long long VideoWin::SetStartOffset(long long curreftime, bool *rsync)
       if ( (curreftime-lastrefvideotime)>10000000LL
         || (curreftime-lastrefvideotime)<-10000000LL) {//if pts jumps to big resync
         startoffset+=curreftime-lastrefvideotime;
-        //lastrefaudiotime+=curreftime-lastrefvideotime;
-        *rsync=true;
+        lastrefaudiotime+=curreftime-lastrefvideotime;
+        //*rsync=true;
         offsetaudionotset=true;
 
       }
@@ -520,7 +638,7 @@ long long VideoWin::SetStartAudioOffset(long long curreftime, bool *rsync)
     startoffset=curreftime;
     offsetnotset=false;
     offsetaudionotset=false;
-  } else {
+  }else {
     if (offsetaudionotset) {
       offsetaudionotset=false;
       *rsync=true;
@@ -529,7 +647,7 @@ long long VideoWin::SetStartAudioOffset(long long curreftime, bool *rsync)
         || (curreftime-lastrefaudiotime)<-10000000LL) {//if pts jumps to big resync
         startoffset+=curreftime-lastrefaudiotime;
         lastrefvideotime+=curreftime-lastrefaudiotime;
-        *rsync=true;
+        //*rsync=true;
         offsetvideonotset=true;
 
       }
@@ -540,7 +658,14 @@ long long VideoWin::SetStartAudioOffset(long long curreftime, bool *rsync)
   return startoffset;
 
 }
-
+void VideoWin::ResetTimeOffsets() {
+  offsetnotset=true; //called from demuxer
+  offsetvideonotset=true;
+  offsetaudionotset=true;
+  startoffset=0;
+  lastrefaudiotime=0;
+  lastrefvideotime=0;
+}
 
 
 #ifdef DEV
@@ -554,3 +679,4 @@ int VideoWin::test2()
   return 0;
 }
 #endif
+\r
index 6b4f2cb7a27a422e7b1fcac375c62e16ea555b8b..36e8052e6f82837aa7638f20d7e1ee4a0feb53bb 100644 (file)
@@ -25,6 +25,8 @@
 #include <string.h>
 #include <winsock2.h>
 #include <dshow.h>
+#include <d3d9.h>
+#include <vmr9.h>
 
 #include "defines.h"
 #include "video.h"
@@ -32,6 +34,7 @@
 #define DS_DEBUG
 
 class DsSourceFilter;
+class DsAllocator;
 
 class VideoWin : public Video
 {
@@ -45,7 +48,10 @@ class VideoWin : public Video
     int setFormat(UCHAR format);
     int setConnection(UCHAR connection);
     int setAspectRatio(UCHAR aspectRatio);   // This one does the pin 8 scart widescreen switching
-    int setMode(UCHAR mode);
+       UCHAR getAspectRatio(){return aspectRatio;};
+       UCHAR getMode(){return mode;};
+       UCHAR getPseudoTVsize() {return pseudotvsize;};
+       int setMode(UCHAR mode);
     int setTVsize(UCHAR size);               // Is the TV a widescreen?
     int setDefaultAspect();
     int setSource();
@@ -63,6 +69,7 @@ class VideoWin : public Video
     int signalOff();
     int attachFrameBuffer(); // What does this do?
     ULONG timecodeToFrameNumber(ULLONG timecode);
+       ULLONG frameNumberToTimecode(ULONG framenumber);
     int getFD();
     ULLONG getCurrentTimestamp();
 
@@ -75,8 +82,9 @@ class VideoWin : public Video
     int getCurrentVideoMediaSample(IMediaSample** ms);
     int DeliverVideoMediaSample();
 
-    long long SetStartOffset(long long curreftime, bool *rsync);
+    virtual long long SetStartOffset(long long curreftime, bool *rsync);
     long long SetStartAudioOffset(long long curreftime, bool *rsync);
+       virtual void ResetTimeOffsets();
 
     void SetAudioState(bool state){audioon=state;};
 
@@ -92,8 +100,13 @@ private:
   IGraphBuilder* dsgraphbuilder;
   IMediaSample* cur_audio_media_sample;
   IMediaSample* cur_video_media_sample;
+  IBaseFilter* dsvmrrenderer;
+  IVMRSurfaceAllocatorNotify9  *dsvmrsurfnotify;
+  IReferenceClock *dsrefclock;
+  IMediaFilter* dsmediafilter;
 
   DsSourceFilter* sourcefilter;
+  DsAllocator* allocatorvmr;
   HANDLE filtermutex;
   void CleanupDS();
   bool offsetnotset;
@@ -106,9 +119,13 @@ private:
   bool firstsynched;
   bool audioon;
   bool videoon;
+  UCHAR pseudotvsize;
+  REFERENCE_TIME lastreftimeRT;
+  ULLONG lastreftimeBYTE;
 #ifdef DS_DEBUG
   DWORD graphidentifier;
 #endif
 };
 
 #endif
+\r
index aea31cae9c338af2d3d0ac4711629d9ecf7d1dd1..3965fd26c658dac35215d7b14b48582c40f64c1e 100644 (file)
@@ -330,11 +330,16 @@ int VRecordingList::handleCommand(int command)
     case Remote::DF_DOWN:
     case Remote::DOWN:
     {
+      Log::getInstance()->log("P", Log::DEBUG, "1");
       sl.down();
+      Log::getInstance()->log("P", Log::DEBUG, "1.5");
       sl.draw();
+      Log::getInstance()->log("P", Log::DEBUG, "2");
 
       doShowingBar();
+      Log::getInstance()->log("P", Log::DEBUG, "3");
       viewman->updateView(this);
+      Log::getInstance()->log("P", Log::DEBUG, "4");
       return 2;
     }
     case Remote::SKIPBACK:
index 5ad7e89d1a78495af6e2a84728715057211e7455..d1efe844dcf836f35d83365b2fb07fe1b8847ad1 100644 (file)
@@ -69,8 +69,8 @@ void MILLISLEEP(ULONG a)
 
 DWORD WINAPI commandthreadStart(void *arg)
 {
-   command->run();
-   return 0;
+        command->run();
+        return 0;
 }
 
 bool InitApp(HINSTANCE hinst,int cmdshow);
@@ -82,18 +82,18 @@ HACCEL acc;
 INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmdshow)
 {
   //On Windows we have to init a window, we use DXUT
-  if (!InitApp(hinst,cmdshow)) return false;
+       if (!InitApp(hinst,cmdshow)) return false;
   //Starting Network support
-  WSADATA wsadat;
+  WSADATA wsadat; 
   int result = WSAStartup(MAKEWORD(2,2),&wsadat);
   if (result!=NO_ERROR) {
         ERROR_MSG("Initialising WinSocked: Error at WSAStartup()\n");
-    return 0;
+               return 0;
   }
   result= CoInitializeEx(NULL,COINIT_MULTITHREADED );//Initialize COM for DirectShow
   if (result!=S_OK) {
-    ERROR_MSG("Initialising COM: Error at Coinitialize()\n");
-    return 0;
+         ERROR_MSG("Initialising COM: Error at Coinitialize()\n");
+         return 0;
   }
 
 
@@ -117,8 +117,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     ERROR_MSG("Could not create objects. Memory problems?\n");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   // Get logging module started --------------------------------------------------------------------------------------
@@ -127,12 +127,12 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     ERROR_MSG("Could not initialise log object. Aborting.\n");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   logger->log("Core", Log::INFO, "Starting up...");
-
+  
 
 
   // Init modules ----------------------------------------------------------------------------------------------------
@@ -147,8 +147,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Remote module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = led->init(0);
@@ -160,8 +160,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "LED module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = mtd->init("/dev/mtd1");
@@ -173,8 +173,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Mtd module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = timers->init();
@@ -186,8 +186,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Timers module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   UCHAR videoFormat = (UCHAR)mtd->getPALorNTSC();
@@ -204,8 +204,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Video module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = osd->init((void*)&win);
@@ -217,8 +217,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "OSD module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = audio->init(Audio::MPEG2_PES);
@@ -230,8 +230,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Audio module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = vdr->init(3024);
@@ -243,8 +243,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "VDR module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = viewman->init();
@@ -256,8 +256,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "ViewMan module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   success = command->init();
@@ -269,8 +269,8 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   {
     logger->log("Core", Log::EMERG, "Command module failed to initialise");
     shutdown(1);
-  WSACleanup();
-  return 0;
+       WSACleanup();
+       return 0;
   }
 
   // Other init ------------------------------------------------------------------------------------------------------
@@ -280,27 +280,27 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
   // Run main loop ---------------------------------------------------------------------------------------------------
 
   // Ok, all major device components and other bits are loaded and ready
-
+  
   HANDLE commandthread;
- commandthread= CreateThread(NULL, 0, commandthreadStart, NULL,0,
-    NULL);
+ commandthread= CreateThread(NULL, 0, commandthreadStart, NULL,0, 
+         NULL);
   MSG message;
   message.message=WM_NULL;
   bool run=true;
   while(run && WaitForSingleObject(commandthread,0)==WAIT_TIMEOUT) {
-    if (PeekMessage(&message, NULL, 0,0,PM_REMOVE)!=0) {
-      if (TranslateAccelerator(win,acc,&message)==NULL) {
-        TranslateMessage(&message);
-        DispatchMessage(&message);
-        switch (message.message) {
-        case WM_QUIT:
-          run=false; //TODO post exit to command Messages
-        };
-      }
-    } else {
-      //Render
-      ((OsdWin*)osd)->Render();
-    }
+         if (PeekMessage(&message, NULL, 0,0,PM_REMOVE)!=0) {
+                 if (TranslateAccelerator(win,acc,&message)==NULL) {
+                         TranslateMessage(&message);
+                         DispatchMessage(&message);
+                         switch (message.message) {
+                         case WM_QUIT:
+                                 run=false; //TODO post exit to command Messages
+                         };
+                 }
+         } else {
+                 //Render
+                 ((OsdWin*)osd)->Render();
+         }
   }
   // When that returns quit ------------------------------------------------------------------------------------------
   WaitForSingleObject(commandthread,INFINITE);
@@ -310,23 +310,91 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd
 
 }
 
+
+
+void CalculateWindowSize(RECT * size,ULONG size_mode) {
+       DWORD width, height;
+       DWORD adjheight,adjwidth;
+       DWORD flags =WS_VISIBLE | WS_POPUP | WS_CAPTION | WS_SYSMENU 
+                 |WS_MINIMIZEBOX | WS_SIZEBOX |WS_MAXIMIZEBOX;
+       RECT wnted={50,50,150,150};
+       AdjustWindowRect(&wnted,flags ,false);
+       adjwidth=-wnted.left+wnted.right-100;
+       adjheight=-wnted.top+wnted.bottom-100;
+       width=size->right-size->left-adjwidth;
+       height=size->bottom-size->top-adjheight;
+       UCHAR mode=video->getMode();
+       UCHAR aspect=((VideoWin*)video)->getAspectRatio();
+       UCHAR tvsize=((VideoWin*)video)->getPseudoTVsize();
+       double aspectrt=4./3.;
+       if (tvsize==Video::ASPECT16X9) {
+               if (aspect==Video::ASPECT16X9) {
+                       aspectrt=4./3.; //looks strange, but it is a 16:9 tv
+               } else if (aspect==Video::ASPECT4X3) {
+                       aspectrt=4./3./(16./9.)*(4./3.); //I hope this is correct
+               }
+       } else if (tvsize==Video::ASPECT4X3) {
+               if (aspect==Video::ASPECT16X9) {
+                       if (mode==Video::LETTERBOX) {
+                               aspectrt=16./9.;
+                       } else {
+                               aspectrt=4./3.;
+                       }
+               } if (aspect==Video::ASPECT4X3) {
+                       aspectrt=4./3.;
+               }
+       }
+       switch (size_mode) {
+       case WMSZ_BOTTOM:
+       case WMSZ_BOTTOMRIGHT:
+       case WMSZ_TOP:
+       case WMSZ_TOPRIGHT:
+       width=(ULONG)(((double)height)*aspectrt);
+       size->right=size->left+width+adjwidth;
+       break;
+       case WMSZ_BOTTOMLEFT:
+       case WMSZ_TOPLEFT:
+       width=(ULONG)(((double)height)*aspectrt);
+       size->left=size->right-width-adjwidth;
+       break;
+       case WMSZ_LEFT:
+       case WMSZ_RIGHT:
+       height=(ULONG)(((double)width)/aspectrt);
+       size->bottom=size->top+height+adjheight;
+       break;
+       }
+}
+
+void AdjustWindow() {
+       RECT winrect;
+       GetWindowRect(win,&winrect);
+       CalculateWindowSize(&winrect,WMSZ_BOTTOM);
+       MoveWindow(win,winrect.left,
+               winrect.top,winrect.right-winrect.left,winrect.bottom-winrect.top,true);
+
+}
+
 LONG FAR PASCAL WindowProc(HWND win, UINT msg, WPARAM wparam, LPARAM lparam)
 {
    switch (msg) {
    case WM_DESTROY: {
-     //TODO: call command
-     logger->log("Core", Log::NOTICE, "Window closed, shutting down...");
+          //TODO: call command
+          logger->log("Core", Log::NOTICE, "Window closed, shutting down...");
        command->stop(); // FIXME this is probably not safe - use the messaging system / is that even safe?
-     ((RemoteWin*)Remote::getInstance())->Signal();
-     PostQuitMessage(0);
-  }break;
-  case WM_SIZE: {
+          ((RemoteWin*)Remote::getInstance())->Signal();
+          PostQuitMessage(0);
+       }break;
+   case WM_SIZING: {
+          CalculateWindowSize((RECT*) lparam,wparam);
+          return TRUE;
+                                  }break;
+       case WM_SIZE: {
         int width = LOWORD(lparam);
         int height = HIWORD(lparam);
          //Call device
         }
         break;
-   case WM_PAINT:
+        case WM_PAINT:
         RECT r;
         PAINTSTRUCT ps;
         if (GetUpdateRect(win, &r, FALSE)) {
@@ -335,30 +403,30 @@ LONG FAR PASCAL WindowProc(HWND win, UINT msg, WPARAM wparam, LPARAM lparam)
             EndPaint(win, &ps);
         }
         break;
-   case WM_KEYDOWN:
-     if (((RemoteWin*)remote)->ReceiveButtonVK(wparam)) {
-       return 0L; //We process that Key
-     } else {
-       return DefWindowProc(win, msg, wparam, lparam);
-     }
-
-     break;
-  case WM_APPCOMMAND:
-    if (((RemoteWin*)remote)->ReceiveButtonAP(GET_APPCOMMAND_LPARAM(lparam))){
-      return TRUE; //yes we process that message
-    } else {
-      return DefWindowProc(win, msg, wparam, lparam);
-    }
-
-    break;
-  case WM_COMMAND:
-    if (((RemoteWin*)remote)->ReceiveButtonAP(LOWORD(wparam))){
-      return 0; //yes we process that message
-    } else {
-      return DefWindowProc(win, msg, wparam, lparam);
-    }
-
-    break;
+        case WM_KEYDOWN:
+                if (((RemoteWin*)remote)->ReceiveButtonVK(wparam)) {
+                        return 0L; //We process that Key
+                } else {
+                        return DefWindowProc(win, msg, wparam, lparam);
+                }
+
+                break;
+       case WM_APPCOMMAND:
+               if (((RemoteWin*)remote)->ReceiveButtonAP(GET_APPCOMMAND_LPARAM(lparam))){
+                       return TRUE; //yes we process that message
+               } else {
+                       return DefWindowProc(win, msg, wparam, lparam);
+               }
+
+               break;
+       case WM_COMMAND:
+               if (((RemoteWin*)remote)->ReceiveButtonAP(LOWORD(wparam))){
+                       return 0; //yes we process that message
+               } else {
+                       return DefWindowProc(win, msg, wparam, lparam);
+               }
+
+               break;
     default:
         return DefWindowProc(win, msg, wparam, lparam);
     }
@@ -367,9 +435,9 @@ LONG FAR PASCAL WindowProc(HWND win, UINT msg, WPARAM wparam, LPARAM lparam)
 
 
 bool InitApp(HINSTANCE hinst,int cmdshow) {
-  WNDCLASS wcs;
-  DWORD flags;
-  wcs.style = CS_HREDRAW | CS_VREDRAW;
+       WNDCLASS wcs;
+       DWORD flags;
+       wcs.style = CS_HREDRAW | CS_VREDRAW;
     wcs.lpfnWndProc = WindowProc;
     wcs.cbClsExtra = 0;
     wcs.cbWndExtra = sizeof(DWORD);
@@ -379,20 +447,20 @@ bool InitApp(HINSTANCE hinst,int cmdshow) {
     wcs.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
     wcs.lpszMenuName = NULL;
     wcs.lpszClassName = "vomp";
-  acc=LoadAccelerators(hinst,MAKEINTRESOURCE(VOMPACCELERATOR));
-  if (!RegisterClass(&wcs))
+       acc=LoadAccelerators(hinst,MAKEINTRESOURCE(VOMPACCELERATOR));
+       if (!RegisterClass(&wcs))
         return false;
-  flags =WS_VISIBLE | WS_POPUP | WS_CAPTION | WS_SYSMENU
+       flags =WS_VISIBLE | WS_POPUP | WS_CAPTION | WS_SYSMENU 
                  |WS_MINIMIZEBOX | WS_SIZEBOX |WS_MAXIMIZEBOX;
-  RECT wnted={0,0,720,576};
-  AdjustWindowRect(&wnted,flags ,false);
-  win=CreateWindow("vomp","vomp",flags, CW_USEDEFAULT,CW_USEDEFAULT,
-    wnted.right-wnted.left,wnted.bottom-wnted.top,NULL,NULL,hinst,NULL);
-  if (!win)
+       RECT wnted={50,50,768+50,576+50};
+       AdjustWindowRect(&wnted,flags ,false);
+       win=CreateWindow("vomp","vomp",flags, CW_USEDEFAULT,CW_USEDEFAULT,
+               wnted.right-wnted.left,wnted.bottom-wnted.top,NULL,NULL,hinst,NULL);
+       if (!win)
         return FALSE;
-  ShowWindow(win,SW_SHOWNORMAL);
+       ShowWindow(win,SW_SHOWNORMAL);
     UpdateWindow(win);
-  return TRUE;
+       return TRUE;
 }
 
 
@@ -509,11 +577,11 @@ ULLONG htonll(ULLONG a)
 
     return b;
   #endif*///This macro switching does not work for windows, here is a implementation without
-  // using BYTE_ORDER
-  //#define ntohll(x) (((_int64)(ntohl((int)((x << 32) >> 32))) << 32) |
+       // using BYTE_ORDER
+       //#define ntohll(x) (((_int64)(ntohl((int)((x << 32) >> 32))) << 32) | 
                  //    (unsigned int)ntohl(((int)(x >> 32)))) //By Runner
 
-  return (((ULLONG)htonl((ULONG)((a<<32)>> 32))<<32)
-    |(ULONG)htonl(((ULONG) (a >> 32))));
+       return (((ULLONG)htonl((ULONG)((a<<32)>> 32))<<32) 
+               |(ULONG)htonl(((ULONG) (a >> 32))));
 }
-#endif
\ No newline at end of file
+#endif