]> git.vomp.tv Git - vompclient.git/blob - videovpeogl.cc
Preliminray OMX h264 playback stuff not finished yet
[vompclient.git] / videovpeogl.cc
1 /*
2     Copyright 2004-2005 Chris Tallon, 2009 Marten Richter
3
4     This file is part of VOMP.
5
6     VOMP is free software; you can redistribute it and/or modify
7     it under the terms of the GNU General Public License as published by
8     the Free Software Foundation; either version 2 of the License, or
9     (at your option) any later version.
10
11     VOMP is distributed in the hope that it will be useful,
12     but WITHOUT ANY WARRANTY; without even the implied warranty of
13     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14     GNU General Public License for more details.
15
16     You should have received a copy of the GNU General Public License
17     along with VOMP; if not, write to the Free Software
18     Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
19 */
20
21 #include "videovpeogl.h"
22 #include "audiovpe.h"
23 #include "mtdraspberry.h"
24 #include "demuxer.h"
25 #include "osdopengl.h"
26
27 // temp
28 #include "log.h"
29
30 //A lot of parts of this file are heavily inspired by xbmc omx implementations
31
32 VideoVPEOGL::VideoVPEOGL()
33 {
34   if (instance) return;
35
36   lastpacketnum=-1;
37   omx_running=false;
38
39   omx_vid_dec=0;
40   cur_input_buf_omx=NULL;
41   
42 }
43
44 VideoVPEOGL::~VideoVPEOGL()
45 {
46   instance = NULL;
47 }
48
49 int VideoVPEOGL::init(UCHAR tformat)
50 {
51   if (initted) return 0;
52   initted = 1;
53
54 //  if ((fdVideo = open("/dev/vdec_dev", O_WRONLY)) < 0) return 0;
55
56   if (!setFormat(tformat))           { shutdown(); return 0; }
57   if (!setConnection(COMPOSITERGB))  { shutdown(); return 0; }
58   if (!setAspectRatio(ASPECT4X3))    { shutdown(); return 0; }
59   if (!setMode(NORMAL))              { shutdown(); return 0; }
60   if (!setSource())                  { shutdown(); return 0; }
61   if (!attachFrameBuffer())          { shutdown(); return 0; }
62
63   setTVsize(ASPECT4X3);
64
65 /*  if (format == PAL) setLetterboxBorder("38");
66   else setLetterboxBorder("31");*/
67
68   /* new stuff */
69
70
71   stop();
72
73
74   return 1;
75 }
76
77 int VideoVPEOGL::initUsingOSDObjects()
78 {
79         EGLDisplay i_egl_display;
80         EGLSurface i_egl_surface;
81         EGLContext i_egl_context;
82         OsdOpenGL *osd=(OsdOpenGL*)osd->getInstance();
83         osd->getEGLObjs(&i_egl_display,&i_egl_surface,&i_egl_context);
84
85         egl_display=i_egl_display;
86         egl_surface=i_egl_surface;
87         egl_context=i_egl_context;
88
89
90 #ifdef VPE_OMX_SUPPORT
91 // we are called before the audio
92         OMX_ERRORTYPE error;
93         error=OMX_Init();
94         if (error!=OMX_ErrorNone) {
95                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX failed %x", error);
96                 return 0;
97         }
98
99         //our callbacks move to play?
100
101
102
103
104 #endif
105         return 1;
106 }
107
108
109 #ifdef VPE_OMX_SUPPORT
110
111 OMX_ERRORTYPE VideoVPEOGL::EventHandler_OMX(OMX_IN OMX_HANDLETYPE handle,OMX_IN OMX_PTR appdata,
112            OMX_IN OMX_EVENTTYPE event_type,OMX_IN OMX_U32 data1,
113            OMX_IN OMX_U32 data2,OMX_IN OMX_PTR event_data) {
114
115         Log::getInstance()->log("Video", Log::NOTICE, "eventHandler %x %x %x %x %x",handle,event_type,data1,data2,event_data);
116
117 /*      switch (event_type) {
118         case OMX_EventCmdComplete: {
119
120         } break;
121         }*/
122
123         return OMX_ErrorNone;
124
125 }
126
127 OMX_ERRORTYPE VideoVPEOGL::EmptyBufferDone_OMX(OMX_IN OMX_HANDLETYPE hcomp,OMX_IN OMX_PTR appdata,OMX_IN OMX_BUFFERHEADERTYPE* buffer){
128
129         Log::getInstance()->log("Video", Log::NOTICE, "EmptyBufferDone");
130         return OMX_ErrorNone;
131
132 }
133
134  OMX_ERRORTYPE VideoVPEOGL::FillBufferDone_OMX(OMX_IN OMX_HANDLETYPE hcomp, OMX_IN OMX_PTR appdata,OMX_IN OMX_BUFFERHEADERTYPE* buffer) {
135          Log::getInstance()->log("Video", Log::NOTICE, "FillBufferDone");
136         return OMX_ErrorNone;
137 }
138
139 #endif
140
141 int VideoVPEOGL::shutdown()
142 {
143   if (!initted) return 0;
144   initted = 0;
145
146 #ifdef VPE_OMX_SUPPORT
147   DeAllocateCodecsOMX();
148   OMX_Deinit();
149 #endif
150   eglDestroyContext(egl_display,egl_context);
151 //  close(fdVideo);
152   return 1;
153 }
154
155
156
157
158 int VideoVPEOGL::setTVsize(UCHAR ttvsize)
159 {
160 /*  tvsize = ttvsize;
161
162   // Override the aspect ratio usage, temporarily use to set the video chip mode
163   if (!setAspectRatio(tvsize))       { shutdown(); return 0; }
164   close(fdVideo);
165   if ((fdVideo = open("/dev/vdec_dev", O_WRONLY)) < 0) return 0;
166   if (!setSource())                  { shutdown(); return 0; }
167   if (!attachFrameBuffer())          { shutdown(); return 0; }
168
169   // Reopening the fd causes the scart aspect line to go back to 4:3
170   // Set this again to the same as the tv screen size
171   if (!setAspectRatio(tvsize))       { shutdown(); return 0; }
172
173   // mode == LETTERBOX is invalid if the TV is widescreen
174   if (tvsize == ASPECT16X9) setMode(NORMAL);
175 */
176   return 1;
177 }
178
179 int VideoVPEOGL::setDefaultAspect()
180 {
181   return setAspectRatio(tvsize);
182 }
183
184
185
186 int VideoVPEOGL::setFormat(UCHAR tformat)
187 {
188   if (!initted) return 0;
189   if ((tformat != PAL) && (tformat != NTSC)) return 0;
190   format = tformat;
191
192 //  if (ioctl(fdVideo, AV_SET_VID_DISP_FMT, format) != 0) return 0;
193
194   if (format == NTSC)
195   {
196     screenWidth = 720;
197     screenHeight = 480;
198   }
199   if (format == PAL)
200   {
201     screenWidth = 720;
202     screenHeight = 576;
203   }
204
205   return 1;
206 }
207
208 int VideoVPEOGL::setConnection(UCHAR tconnection)
209 {
210   if (!initted) return 0;
211   if ((tconnection != COMPOSITERGB) && (tconnection != SVIDEO)) return 0;
212   connection = tconnection;
213
214 //  if (ioctl(fdVideo, AV_SET_VID_OUTPUT, connection) != 0) return 0;
215   return 1;
216 }
217
218 int VideoVPEOGL::setAspectRatio(UCHAR taspectRatio)
219 {
220   if (!initted) return 0;
221   if ((taspectRatio != ASPECT4X3) && (taspectRatio != ASPECT16X9)) return 0;
222   aspectRatio = taspectRatio;
223
224   Log::getInstance()->log("Video", Log::DEBUG, "Setting aspect to %i", aspectRatio);
225
226 //  if (ioctl(fdVideo, AV_SET_VID_RATIO, aspectRatio) != 0) return 0;
227   return 1;
228 }
229
230 int VideoVPEOGL::setMode(UCHAR tmode)
231 {
232   if (!initted) return 0;
233
234   if ((tmode == LETTERBOX) && (tvsize == ASPECT16X9)) return 0; // invalid mode
235
236   if ((tmode != NORMAL) && (tmode != LETTERBOX) && (tmode != UNKNOWN2) && (tmode != QUARTER) && (tmode != EIGHTH)
237       && (tmode != ZOOM) && (tmode != UNKNOWN6)) return 0;
238   mode = tmode;
239
240 //  if (ioctl(fdVideo, AV_SET_VID_MODE, mode) != 0) return 0;
241   return 1;
242 }
243
244 int VideoVPEOGL::signalOff()
245 {
246 //  if (ioctl(fdVideo, AV_SET_VID_DENC, 0) != 0) return 0;
247   return 1;
248 }
249
250 int VideoVPEOGL::signalOn()
251 {
252 //  if (ioctl(fdVideo, AV_SET_VID_DENC, 1) != 0) return 0;
253   return 1;
254 }
255
256 int VideoVPEOGL::setSource()
257 {
258   if (!initted) return 0;
259
260   // What does this do...
261 //  if (ioctl(fdVideo, AV_SET_VID_SRC, 1) != 0) return 0;
262   return 1;
263 }
264
265 int VideoVPEOGL::setPosition(int x, int y)
266 {
267   if (!initted) return 0;
268
269 //  vid_pos_regs_t pos_d;
270 //  pos_d.x = x;
271 //  pos_d.y = y;
272
273 /*  vid_pos_regs_t pos_d;
274
275   memset(&pos_d, 0, sizeof(pos_d));
276
277   pos_d.dest.y = y;
278   pos_d.dest.x = x;
279 /*
280 typedef struct {
281   int w;
282   int h;
283   int scale;
284   int x1;
285   int y;
286   int x;
287   int y2;
288   int x3;
289   int y3;
290   int x4;
291   int y4;
292 } vid_pos_regs_t;
293 */
294
295 /*
296   pos_d.w = 100;
297   pos_d.h = 30;
298   pos_d.scale = 2;
299   pos_d.x1 = 0;
300   pos_d.y = 100;            // Top left X
301   pos_d.x = 50;            // Top left Y
302   pos_d.y2 = 30;
303   pos_d.x3 = 60;
304   pos_d.y3 = 90;
305   pos_d.x4 = 120;
306   pos_d.y4 = 150;
307 */
308
309 //  if (ioctl(fdVideo, AV_SET_VID_POSITION, &pos_d) != 0) return 0;
310   return 1;
311 }
312
313 int VideoVPEOGL::sync()
314 {
315   if (!initted) return 0;
316
317 //  if (ioctl(fdVideo, AV_SET_VID_SYNC, 2) != 0) return 0;
318   return 1;
319 }
320
321
322
323
324 int VideoVPEOGL::play()
325 {
326   if (!initted) return 0;
327 #ifdef VPE_OMX_SUPPORT
328   if (AllocateCodecsOMX()) {
329
330           return 1;
331           // Otherwise fall back to ffmpeg
332   }
333 #endif
334
335 //  if (ioctl(fdVideo, AV_SET_VID_PLAY, 0) != 0) return 0;
336   return 1;
337 }
338
339 #ifdef VPE_OMX_SUPPORT
340 int VideoVPEOGL::AllocateCodecsOMX()
341 {
342         OMX_ERRORTYPE error;
343         static OMX_CALLBACKTYPE callbacks= {&EventHandler_OMX,&EmptyBufferDone_OMX,&FillBufferDone_OMX};
344
345         Log::getInstance()->log("Video", Log::NOTICE, "Allocate Codecs OMX");
346         //Clock, move later to audio
347
348         error=OMX_GetHandle(&omx_clock,VPE_OMX_CLOCK,NULL,&callbacks);
349
350
351         if (error!=OMX_ErrorNone){
352                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX clock failed %x", error);
353                 DeAllocateCodecsOMX();
354                 return 0;
355         }
356
357
358
359         OMX_PORT_PARAM_TYPE p_param;
360         p_param.nSize=sizeof(p_param);
361         p_param.nVersion.nVersion=OMX_VERSION;
362         error=OMX_GetParameter(omx_clock,OMX_IndexParamOtherInit,&p_param);
363         if (error!=OMX_ErrorNone){
364                 Log::getInstance()->log("Video", Log::DEBUG, "Init clock OMX_GetParameter failed %x", error);
365                 DeAllocateCodecsOMX();
366                 return 0;
367         }
368         omx_clock_output_port=p_param.nStartPortNumber+1;
369
370
371         OMX_TIME_CONFIG_CLOCKSTATETYPE clock_conf;
372         clock_conf.nSize=sizeof(clock_conf);
373         clock_conf.nVersion.nVersion=OMX_VERSION;
374         clock_conf.eState=OMX_TIME_ClockStateWaitingForStartTime;
375         clock_conf.nStartTime=0;
376         clock_conf.nOffset=0;
377         clock_conf.nWaitMask=OMX_CLOCKPORT0;
378         error=OMX_SetParameter(omx_clock,OMX_IndexConfigTimeClockState,&clock_conf);
379         if (error!=OMX_ErrorNone){
380                 Log::getInstance()->log("Video", Log::DEBUG, "Clock IndexConfigTimeClockState failed %x", error);
381         }
382
383
384
385         if (h264) {
386                 error=OMX_GetHandle(&omx_vid_dec,VPE_OMX_H264_DECODER,NULL,&callbacks);
387         } else {
388                 error=OMX_GetHandle(&omx_vid_dec,VPE_OMX_MPEG2_DECODER,NULL,&callbacks);
389         }
390
391         if (error!=OMX_ErrorNone){
392                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX video decoder failed %x", error);
393                 DeAllocateCodecsOMX();
394                 return 0;
395         }
396
397         p_param.nSize=sizeof(p_param);
398         p_param.nVersion.nVersion=OMX_VERSION;
399         error=OMX_GetParameter(omx_vid_dec,OMX_IndexParamVideoInit,&p_param);
400         if (error!=OMX_ErrorNone){
401                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX h264 decoder OMX_GetParameter failed %x", error);
402                 DeAllocateCodecsOMX();
403             return 0;
404         }
405         omx_codec_input_port=p_param.nStartPortNumber;
406         omx_codec_output_port=p_param.nStartPortNumber+1;
407
408
409         error=OMX_GetHandle(&omx_vid_sched,VPE_OMX_VIDEO_SCHED,NULL,&callbacks);
410         if (error!=OMX_ErrorNone){
411                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX video scheduler failed %x", error);
412                 DeAllocateCodecsOMX();
413                 return 0;
414         }
415
416
417
418         error=OMX_GetParameter(omx_vid_sched,OMX_IndexParamVideoInit,&p_param);
419         if (error!=OMX_ErrorNone){
420                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX video scheduler OMX_GetParameter failed %x", error);
421                 DeAllocateCodecsOMX();
422                 return 0;
423         }
424         omx_shed_input_port=p_param.nStartPortNumber;
425         omx_shed_output_port=p_param.nStartPortNumber+1;
426         omx_shed_clock_port=p_param.nStartPortNumber+2;
427
428
429         error=OMX_GetHandle(&omx_vid_rend,VPE_OMX_VIDEO_SCHED,NULL,&callbacks);
430         if (error!=OMX_ErrorNone){
431                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX video rend failed %x", error);
432                 DeAllocateCodecsOMX();
433                 return 0;
434         }
435
436         error=OMX_GetParameter(omx_vid_rend,OMX_IndexParamVideoInit,&p_param);
437         if (error!=OMX_ErrorNone){
438                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX video rend OMX_GetParameter failed %x", error);
439                 DeAllocateCodecsOMX();
440                 return 0;
441         }
442         omx_rend_input_port=p_param.nStartPortNumber;
443         omx_rend_output_port=p_param.nStartPortNumber+1;
444
445         //Setuo chain
446
447         error=OMX_SetupTunnel(omx_clock,omx_clock_output_port,omx_vid_sched,omx_shed_clock_port);
448         if (error!=OMX_ErrorNone){
449                 Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel clock to sched failed %x %d %d", error,omx_clock_output_port,omx_shed_clock_port);
450                 DeAllocateCodecsOMX();
451                 return 0;
452         }
453
454
455         error=OMX_SendCommand(omx_clock,OMX_CommandStateSet,OMX_StateExecuting,0);
456         if (error!=OMX_ErrorNone){
457                 Log::getInstance()->log("Video", Log::DEBUG, "clock Send Command to OMX State Executing %x", error);
458                 return 0;
459         }
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474         OMX_VIDEO_PARAM_PORTFORMATTYPE ft_type;
475         ft_type.nSize=sizeof(ft_type);
476         ft_type.nVersion.nVersion=OMX_VERSION;
477
478         ft_type.nPortIndex=omx_codec_input_port;
479         if (h264) {
480                 ft_type.eCompressionFormat=OMX_VIDEO_CodingAVC;
481         } else {
482                 ft_type.eCompressionFormat=OMX_VIDEO_CodingMPEG2;
483         }
484
485
486         error=OMX_SendCommand(omx_vid_dec,OMX_CommandStateSet,OMX_StateIdle,0);
487         if (error!=OMX_ErrorNone){
488                 Log::getInstance()->log("Video", Log::DEBUG, "vid_dec Send Command to OMX State Idle %x", error);
489                 return 0;
490         }
491
492         Demuxer* demux=Demuxer::getInstance();
493
494     ft_type.xFramerate=demux->getFrameRate()*(1<<16);
495         error=OMX_SetParameter(omx_vid_dec,OMX_IndexParamVideoPortFormat,&ft_type);
496         if (error!=OMX_ErrorNone){
497                 Log::getInstance()->log("Video", Log::DEBUG, "Init OMX_IndexParamVideoPortFormat failed %x", error);
498         }
499 /*
500         if (h264) {
501                 OMX_NALSTREAMFORMATTYPE nalu_type;
502                 nalu_type.nSize=sizeof(nalu_type);
503                 nalu_type.nVersion.nVersion=OMX_VERSION;
504                 nalu_type.nPortIndex=omx_input_port;
505
506                 error=OMX_GetParameter(omx_vid_dec,(OMX_INDEXTYPE)OMX_IndexParamNalStreamFormatSupported, &nalu_type);
507
508                 if (error!=OMX_ErrorNone) {
509                         Log::getInstance()->log("Video", Log::DEBUG, "Getting Nalutypes failed  %x", error);
510                 }
511                 Log::getInstance()->log("Video", Log::DEBUG, "Nalutypes %x", nalu_type.eNaluFormat);
512                 omx_nalu_format=nalu_type.eNaluFormat;
513         }*/
514
515
516
517         if (!PrepareInputBufsOMX()) {
518                 return 0;
519         }
520
521
522         error=OMX_SetupTunnel(omx_vid_dec,omx_codec_output_port,omx_vid_sched,omx_shed_input_port);
523         if (error!=OMX_ErrorNone){
524                 Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel dec to sched failed %x", error);
525                 DeAllocateCodecsOMX();
526                 return 0;
527         }
528
529
530
531         error=OMX_SetupTunnel(omx_vid_sched,omx_shed_output_port,omx_vid_rend,omx_rend_input_port);
532         if (error!=OMX_ErrorNone){
533                 Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel  sched to rend failed %x", error);
534                 DeAllocateCodecsOMX();
535                 return 0;
536         }
537
538
539
540
541
542
543 /*
544         error=OMX_SendCommand(omx_vid_sched,OMX_CommandStateSet,OMX_StateIdle,0);
545         if (error!=OMX_ErrorNone){
546                 Log::getInstance()->log("Video", Log::DEBUG, "vid_rend Send Command to OMX State Idle %x", error);
547                 return 0;
548         }
549
550         error=OMX_SendCommand(omx_vid_rend,OMX_CommandStateSet,OMX_StateIdle,0);
551         if (error!=OMX_ErrorNone){
552                 Log::getInstance()->log("Video", Log::DEBUG, "vid_rend Send Command to OMX State Idle %x", error);
553                 return 0;
554         }*/
555
556
557
558
559                 /*      Code for querying  supported formats well it says everything is supported ?
560                  * ft_type.nIndex=0;
561                         do {
562                                 error=OMX_GetParameter(omx_vid_dec,OMX_IndexParamVideoPortFormat,&ft_type);
563                                 if (error!=OMX_ErrorNone && error != OMX_ErrorNoMore) {
564                                         Log::getInstance()->log("Video", Log::DEBUG, "Init OMX h264 decoder OMX_SetParameter failed %x", error);
565                                         omx_can_h264=false;
566                                 } else {
567                                         Log::getInstance()->log("Video", Log::DEBUG, "OMX format found %x", ft_type.eCompressionFormat);
568                                         omx_can_h264=true;
569                                 }
570                                 ft_type.nIndex++;
571                         }while (error==OMX_ErrorNone);*/
572
573
574                 //todo alloc buffers
575
576
577                 /*
578
579 int getHorizontalSize() { return horizontal_size; }
580     int getVerticalSize() { return vertical_size; }
581     int getAspectRatio() { return aspect_ratio; }
582     int getFrameRate() { return frame_rate; }
583
584
585
586
587         }*/
588
589
590
591
592
593
594
595
596
597         return 1;
598 }
599
600
601
602 int VideoVPEOGL::PrepareInputBufsOMX()
603 {
604         OMX_ERRORTYPE error;
605         OMX_PARAM_PORTDEFINITIONTYPE port_def_type;
606         port_def_type.nSize=sizeof(port_def_type);
607         port_def_type.nVersion.nVersion=OMX_VERSION;
608         port_def_type.nPortIndex=omx_codec_input_port;
609
610         error=OMX_GetParameter(omx_vid_dec,OMX_IndexParamPortDefinition, &port_def_type);
611
612         if (error!=OMX_ErrorNone){
613                         Log::getInstance()->log("Video", Log::DEBUG, "Get OMX OMX_IndexParamPortDefinition failed %x", error);
614         }
615         input_bufs_omx_mutex.Lock();
616         for (unsigned int i=0; i< port_def_type.nBufferCountMin;i++) {
617
618                 unsigned char* new_buffer_data=(unsigned char*)malloc(port_def_type.nBufferSize);
619                 OMX_BUFFERHEADERTYPE *buf_head=NULL;
620                 error=OMX_UseBuffer(omx_vid_dec,&buf_head,omx_codec_input_port,NULL,port_def_type.nBufferSize,new_buffer_data);
621                 if (error!=OMX_ErrorNone){
622                         Log::getInstance()->log("Video", Log::DEBUG, "Use OMX_UseBuffer failed %x", error);
623                         input_bufs_omx_mutex.Unlock();
624                         return 0;
625                 }
626                 input_bufs_omx_all.push_back(buf_head);
627                 input_bufs_omx_free.push_back(buf_head);
628         }
629         input_bufs_omx_mutex.Unlock();
630         omx_first_frame=true;
631         omx_running=true;
632         firstsynched=false;
633         cur_input_buf_omx=NULL;
634
635         return 1;
636 }
637
638 int VideoVPEOGL::DestroyInputBufsOMX()
639 {
640         OMX_ERRORTYPE error;
641
642         cur_input_buf_omx=NULL;
643         input_bufs_omx_mutex.Lock();
644         for (int i=0; i< input_bufs_omx_all.size();i++) {
645                 free(input_bufs_omx_all[i]->pBuffer);
646                 input_bufs_omx_all[i]->pBuffer=NULL;
647                 error=OMX_FreeBuffer(omx_vid_dec,omx_codec_input_port,input_bufs_omx_all[i]);
648                 if (error!=OMX_ErrorNone){
649                         Log::getInstance()->log("Video", Log::DEBUG, "Use OMX_FreeBuffer failed %x", error);
650                         input_bufs_omx_mutex.Unlock();
651                         return 0;
652                 }
653         }
654         input_bufs_omx_all.clear();
655         input_bufs_omx_free.clear();
656         input_bufs_omx_mutex.Unlock();
657
658 }
659
660
661
662
663 int VideoVPEOGL::DeAllocateCodecsOMX()
664 {
665         OMX_ERRORTYPE error;
666         if (omx_vid_dec) {
667                 DestroyInputBufsOMX();
668
669                 //todo flushing
670                 error=OMX_SetupTunnel(omx_vid_rend,omx_rend_input_port,NULL,NULL);
671                 if (error!=OMX_ErrorNone){
672                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
673
674                 }
675                 error=OMX_SetupTunnel(omx_vid_sched,omx_shed_output_port,NULL,NULL);
676                 if (error!=OMX_ErrorNone){
677                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
678
679                 }
680                 error=OMX_SetupTunnel(omx_vid_sched,omx_shed_input_port,NULL,NULL);
681                 if (error!=OMX_ErrorNone){
682                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
683
684                 }
685                 error=OMX_SetupTunnel(omx_vid_sched,omx_shed_clock_port,NULL,NULL);
686                 if (error!=OMX_ErrorNone){
687                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
688
689                 }
690
691                 error=OMX_SetupTunnel(omx_clock,omx_clock_output_port,NULL,NULL);
692                 if (error!=OMX_ErrorNone){
693                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
694
695                 }
696
697                 error=OMX_SetupTunnel(omx_vid_dec,omx_codec_output_port,NULL,NULL);
698                 if (error!=OMX_ErrorNone){
699                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
700
701                 }
702                 error=OMX_SetupTunnel(omx_vid_dec,omx_codec_input_port,NULL,NULL);
703                 if (error!=OMX_ErrorNone){
704                         Log::getInstance()->log("Video", Log::DEBUG, "OMX_Setup tunnel teardown failed %x", error);
705
706                 }
707
708
709
710                 error=OMX_FreeHandle(omx_vid_dec);
711                 error=OMX_FreeHandle(omx_vid_sched);
712                 error=OMX_FreeHandle(omx_vid_rend);
713                 error=OMX_FreeHandle(omx_clock);
714                 omx_vid_dec=NULL;
715                 if (error!=OMX_ErrorNone) {
716                         Log::getInstance()->log("Video", Log::DEBUG, "FreeHandle failed %d", error);
717                 }
718         }
719
720         return 1;
721 }
722
723 #endif
724
725 int VideoVPEOGL::stop()
726 {
727   if (!initted) return 0;
728
729 #ifdef VPE_OMX_SUPPORT
730   //Check if ffmpeg mode
731   DeAllocateCodecsOMX();
732 #endif
733
734   
735
736 //  if (ioctl(fdVideo, AV_SET_VID_STOP, 0) != 0) return 0;
737   return 1;
738 }
739
740 int VideoVPEOGL::reset()
741 {
742   if (!initted) return 0;
743  
744 //  if (ioctl(fdVideo, AV_SET_VID_RESET, 0x11) != 0) return 0;
745   return 1;
746 }
747
748 int VideoVPEOGL::pause()
749 {
750   if (!initted) return 0;
751
752 //  if (ioctl(fdVideo, AV_SET_VID_PAUSE, 0) != 0) return 0;
753   return 1;
754 }
755
756 int VideoVPEOGL::unPause() // FIXME get rid - same as play!!
757 {
758   if (!initted) return 0;
759 //  if (ioctl(fdVideo, AV_SET_VID_PLAY, 0) != 0) return 0;
760   return 1;
761 }
762
763 int VideoVPEOGL::fastForward()
764 {
765   if (!initted) return 0;
766
767 //  if (ioctl(fdVideo, AV_SET_VID_FFWD, 1) != 0) return 0;
768   return 1;
769 }
770
771 int VideoVPEOGL::unFastForward()
772 {
773   if (!initted) return 0;
774
775 //  if (ioctl(fdVideo, AV_SET_VID_RESET, 0x11) != 0) return 0; // don't need this.
776
777  //// if (ioctl(fdVideo, AV_SET_VID_PLAY, 0) != 0) return 0;
778   return 1;
779 }
780
781 int VideoVPEOGL::attachFrameBuffer()
782 {
783   if (!initted) return 0;
784
785 //  if (ioctl(fdVideo, AV_SET_VID_FB, 0) != 0) return 0;
786   return 1;
787 }
788
789 int VideoVPEOGL::blank(void)
790 {
791 //  if (ioctl(fdVideo, AV_SET_VID_FB, 1) != 0) return 0;
792 //  if (ioctl(fdVideo, AV_SET_VID_FB, 0) != 0) return 0;
793   return 1;
794 }
795
796 ULLONG VideoVPEOGL::getCurrentTimestamp()
797 {
798 /*  sync_data_t timestamps;
799   if (ioctl(fdVideo, AV_GET_VID_TIMESTAMPS, &timestamps) == 0)
800   {
801     // FIXME are these the right way around?
802
803     timestamps.stc = (timestamps.stc >> 31 ) | (timestamps.stc & 1);
804     timestamps.pts = (timestamps.pts >> 31 ) | (timestamps.pts & 1);
805
806     return timestamps.stc;
807   }
808   else
809   {
810     return 0;
811   }*/
812   return 0;
813 }
814
815 ULONG VideoVPEOGL::timecodeToFrameNumber(ULLONG timecode)
816 {
817   if (format == PAL) return (ULONG)(((double)timecode / (double)90000) * (double)25);
818   else               return (ULONG)(((double)timecode / (double)90000) * (double)30);
819 }
820
821 #ifdef DEV
822 int VideoVPEOGL::test()
823 {
824   return 0;
825
826 //  ULLONG stc = 0;
827 //  return ioctl(fdVideo, AV_SET_VID_STC, &stc);
828 /*
829  // reset();
830   return 1;
831 */
832 }
833
834 int VideoVPEOGL::test2()
835 {
836   return 0;
837 }
838 #endif
839
840 void VideoVPEOGL::PrepareMediaSample(const MediaPacketList& mplist,UINT samplepos)
841 {
842   mediapacket = mplist.front();
843 }
844
845 UINT VideoVPEOGL::DeliverMediaSample(UCHAR* buffer, UINT *samplepos)
846 {
847   DeliverMediaPacket(mediapacket, buffer, samplepos);
848   if (*samplepos == mediapacket.length) {
849     *samplepos = 0;
850     return 1;
851   }
852   else return 0;
853 }
854
855
856 UINT VideoVPEOGL::DeliverMediaPacket(MediaPacket packet,
857                 const UCHAR* buffer,
858                 UINT *samplepos)
859 {
860
861         /*First Check, if we have an audio sample*/
862
863         if (packet.type == MPTYPE_VIDEO_H264)
864         {
865                 h264=true;
866         }
867         else
868         {
869                 h264=false;
870         }
871         //Later add fail back code for ffmpeg
872         /*if (!videoon) {
873                 *samplepos+=packet.length;
874                 return packet.length;
875         }*/
876
877 #ifdef VPE_OMX_SUPPORT
878         if (!omx_running) return 0; // if we are not runnig do not do this
879
880
881         /*First Check, if we have an audio sample*/
882         if (iframemode) {
883                 //samplepos=0;
884                 MILLISLEEP(10);
885                 return 0; //Not in iframe mode!
886         }
887
888
889
890         UINT headerstrip=0;
891         if (packet.disconti) {
892                 firstsynched=false;
893                 if (cur_input_buf_omx) {
894                         OMX_ERRORTYPE error=OMX_EmptyThisBuffer(omx_vid_dec,cur_input_buf_omx);
895                         if (error!=OMX_ErrorNone){
896                                 Log::getInstance()->log("Video", Log::DEBUG, "OMX_EmptyThisBuffer failed %x", error);
897                         }
898                         cur_input_buf_omx=NULL;
899                 }
900         }
901
902         /*Inspect PES-Header */
903
904
905
906
907         if (*samplepos==0) {//stripheader
908                 headerstrip=buffer[packet.pos_buffer+8]+9/*is this right*/;
909                 *samplepos+=headerstrip;
910                 if ( packet.synched ) {
911                         if (cur_input_buf_omx) {
912                                 OMX_ERRORTYPE error=OMX_EmptyThisBuffer(omx_vid_dec,cur_input_buf_omx);
913
914                                 cur_input_buf_omx=NULL;//write out old data
915                         }
916                 //      reftime1=packet.presentation_time;
917                 //      reftime2=reftime1+1;
918                         firstsynched=true;
919                 } else {
920                         if (!firstsynched) {//
921                                 *samplepos=packet.length;//if we have not processed at least one
922                                 return packet.length;//synched packet ignore it!
923                         }
924                 }
925         }
926
927         if (!cur_input_buf_omx) {
928                 input_bufs_omx_mutex.Lock();
929                 if (input_bufs_omx_free.size()==0) {
930                         input_bufs_omx_mutex.Unlock();
931                         return 0; // we do not have a free media sample
932
933                 }
934                 cur_input_buf_omx=input_bufs_omx_free.front();
935                 cur_input_buf_omx->nFilledLen=0;
936                 cur_input_buf_omx->nOffset=0;
937                 input_bufs_omx_free.pop_front();
938                 input_bufs_omx_mutex.Unlock();
939         }
940
941
942
943
944
945         if (cur_input_buf_omx->nFilledLen==0) {//will only be changed on first packet
946                 /*if (packet.disconti) {
947                         ms->SetDiscontinuity(TRUE);
948                 } else {
949                         ms->SetDiscontinuity(FALSE);
950                 }*/
951                 //if (packet.synched) {
952
953
954                         //lastreftimePTS=packet.pts;
955                    if (omx_first_frame) { // TODO time
956                            cur_input_buf_omx->nFlags=OMX_BUFFERFLAG_STARTTIME;
957                    } else
958
959                 //}
960                 //else
961                 //{
962                         cur_input_buf_omx->nFlags=OMX_BUFFERFLAG_TIME_UNKNOWN;
963
964
965                         //  ms->SetSyncPoint(TRUE);
966                 //}
967
968         }
969         unsigned int haveToCopy=packet.length-*samplepos;
970
971         if (haveToCopy> (cur_input_buf_omx->nAllocLen-cur_input_buf_omx->nFilledLen)) {
972                 cur_input_buf_omx->pBuffer=(OMX_U8*)realloc(cur_input_buf_omx->pBuffer,cur_input_buf_omx->nFilledLen+haveToCopy);
973                 cur_input_buf_omx->nAllocLen=cur_input_buf_omx->nFilledLen+haveToCopy;
974         }
975         memcpy(cur_input_buf_omx->pBuffer,buffer+packet.pos_buffer+*samplepos,haveToCopy);
976         cur_input_buf_omx->nFilledLen=cur_input_buf_omx->nFilledLen+haveToCopy;
977
978
979
980         *samplepos+=haveToCopy;
981
982         return haveToCopy+headerstrip;
983
984 #else
985
986         *samplepos+=packet.length; //yet not implemented//bad idea
987         return packet.length;
988 #endif
989 }
990
991
992
993
994
995
996 void VideoVPEOGL::ResetTimeOffsets()
997 {
998 }
999
1000 bool VideoVPEOGL::displayIFrame(const UCHAR* buffer, UINT length)
1001 {
1002   //write(fdVideo, buffer, length);
1003         if (!iframemode) EnterIframePlayback();
1004 //      WriteOutTS(buffer,length, h264?MPTYPE_VIDEO_H264 :MPTYPE_VIDEO_MPEG2 );
1005  
1006   lastpacketnum=-1;
1007   return true;
1008 }
1009
1010 int VideoVPEOGL::EnterIframePlayback()
1011 {
1012
1013         return 0;
1014 }
1015