quicktime.c
上传用户:kjfoods
上传日期:2020-07-06
资源大小:29949k
文件大小:38k
源码类别:

midi

开发平台:

Unix_Linux

  1. /*****************************************************************************
  2.  * quicktime.c: a quicktime decoder that uses the QT library/dll
  3.  *****************************************************************************
  4.  * Copyright (C) 2003, 2008 - 2009 the VideoLAN team
  5.  * $Id: e5b5778160a776e1dc439c7b07cc61e4efbc4f25 $
  6.  *
  7.  * Authors: Laurent Aimar <fenrir at via.ecp.fr>
  8.  *          Derk-Jan Hartman <hartman at videolan.org>>
  9.  *
  10.  * This program is free software; you can redistribute it and/or modify
  11.  * it under the terms of the GNU General Public License as published by
  12.  * the Free Software Foundation; either version 2 of the License, or
  13.  * (at your option) any later version.
  14.  *
  15.  * This program is distributed in the hope that it will be useful,
  16.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  17.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  18.  * GNU General Public License for more details.
  19.  *
  20.  * You should have received a copy of the GNU General Public License
  21.  * along with this program; if not, write to the Free Software
  22.  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
  23.  *****************************************************************************/
  24. /*****************************************************************************
  25.  * Preamble
  26.  *****************************************************************************/
  27. #ifdef HAVE_CONFIG_H
  28. # include "config.h"
  29. #endif
  30. #include <vlc_common.h>
  31. #include <vlc_plugin.h>
  32. #include <vlc_aout.h>
  33. #include <vlc_vout.h>
  34. #include <vlc_codec.h>
  35. #if !defined (__APPLE__) && !defined(WIN32)
  36. # define LOADER 1
  37. #endif
  38. #ifdef __APPLE__
  39. #include <QuickTime/QuickTimeComponents.h>
  40. #include <QuickTime/Movies.h>
  41. #include <QuickTime/ImageCodec.h>
  42. #endif
  43. /* for windows do we require Quicktime compents header? */
  44. #ifdef LOADER
  45. #include "qtx/qtxsdk/components.h"
  46. #include "wine/windef.h"
  47. #include "ldt_keeper.h"
  48. HMODULE   WINAPI LoadLibraryA(LPCSTR);
  49. FARPROC   WINAPI GetProcAddress(HMODULE,LPCSTR);
  50. int       WINAPI FreeLibrary(HMODULE);
  51. #endif
  52. /*****************************************************************************
  53.  * Module descriptor
  54.  *****************************************************************************/
  55. static int  Open ( vlc_object_t * );
  56. static void Close( vlc_object_t * );
  57. vlc_module_begin ()
  58.     set_description( N_("QuickTime library decoder") )
  59.     set_capability( "decoder", 0 )
  60.     set_category( CAT_INPUT )
  61.     set_subcategory( SUBCAT_INPUT_VCODEC )
  62.     set_callbacks( Open, Close )
  63. vlc_module_end ()
  64. /*****************************************************************************
  65.  * Local prototypes
  66.  *****************************************************************************/
  67. static int           OpenAudio( decoder_t * );
  68. static int           OpenVideo( decoder_t * );
  69. static aout_buffer_t *DecodeAudio( decoder_t *, block_t ** );
  70. static picture_t     *DecodeVideo( decoder_t *, block_t ** );
  71. #define FCC( a, b , c, d ) 
  72.     ((uint32_t)( ((a)<<24)|((b)<<16)|((c)<<8)|(d)))
  73. #ifndef __APPLE__
  74. typedef struct OpaqueSoundConverter*    SoundConverter;
  75. #ifndef LOADER
  76. typedef long                            OSType;
  77. typedef int                             OSErr;
  78. #endif
  79. typedef unsigned long                   UnsignedFixed;
  80. typedef uint8_t                         Byte;
  81. typedef struct SoundComponentData {
  82.     long                            flags;
  83.     OSType                          format;
  84.     short                           numChannels;
  85.     short                           sampleSize;
  86.     UnsignedFixed                   sampleRate;
  87.     long                            sampleCount;
  88.     Byte *                          buffer;
  89.     long                            reserved;
  90. } SoundComponentData;
  91. #endif /* __APPLE__ */
  92. struct decoder_sys_t
  93. {
  94.     /* library */
  95. #ifndef __APPLE__
  96. #ifdef LOADER
  97.     ldt_fs_t    *ldt_fs;
  98. #endif /* LOADER */
  99.     HMODULE qtml;
  100.     HINSTANCE qts;
  101.     OSErr (*InitializeQTML)             ( long flags );
  102.     OSErr (*TerminateQTML)              ( void );
  103. #endif /* __APPLE__ */
  104.     /* Audio */
  105.     int (*SoundConverterOpen)           ( const SoundComponentData *,
  106.                                           const SoundComponentData *,
  107.                                           SoundConverter* );
  108.     int (*SoundConverterClose)          ( SoundConverter );
  109.     int (*SoundConverterSetInfo)        ( SoundConverter , OSType, void * );
  110.     int (*SoundConverterGetBufferSizes) ( SoundConverter, unsigned long,
  111.                                           unsigned long*, unsigned long*,
  112.                                           unsigned long* );
  113.     int (*SoundConverterBeginConversion)( SoundConverter );
  114.     int (*SoundConverterEndConversion)  ( SoundConverter, void *,
  115.                                           unsigned long *, unsigned long *);
  116.     int (*SoundConverterConvertBuffer)  ( SoundConverter, const void *,
  117.                                           unsigned long, void *,
  118.                                           unsigned long *, unsigned long * );
  119.     SoundConverter      myConverter;
  120.     SoundComponentData  InputFormatInfo, OutputFormatInfo;
  121.     unsigned long   FramesToGet;
  122.     unsigned int    InFrameSize;
  123.     unsigned int    OutFrameSize;
  124. #ifndef WIN32
  125.     /* Video */
  126.     Component         (*FindNextComponent)
  127.         ( Component prev, ComponentDescription* desc );
  128.     ComponentInstance (*OpenComponent)
  129.         ( Component c );
  130.     ComponentResult   (*ImageCodecInitialize)
  131.         ( ComponentInstance ci, ImageSubCodecDecompressCapabilities * cap);
  132.     ComponentResult   (*ImageCodecGetCodecInfo)
  133.         ( ComponentInstance ci, CodecInfo *info );
  134.     ComponentResult   (*ImageCodecPreDecompress)
  135.         ( ComponentInstance ci, CodecDecompressParams * params );
  136.     ComponentResult   (*ImageCodecBandDecompress)
  137.         ( ComponentInstance ci, CodecDecompressParams * params );
  138.     PixMapHandle      (*GetGWorldPixMap)
  139.         ( GWorldPtr offscreenGWorld );
  140.     OSErr             (*QTNewGWorldFromPtr)
  141.         ( GWorldPtr *gw, OSType pixelFormat, const Rect *boundsRect,
  142.           CTabHandle cTable, /*GDHandle*/ void *aGDevice, /*unused*/
  143.           GWorldFlags flags, void *baseAddr, long rowBytes );
  144.     OSErr             (*NewHandleClear)( Size byteCount );
  145.     ComponentInstance       ci;
  146.     Rect                    OutBufferRect;   /* the dimensions of our GWorld */
  147.     GWorldPtr               OutBufferGWorld; /* a GWorld is some kind of
  148.                                                 description for a drawing
  149.                                                 environment */
  150.     ImageDescriptionHandle  framedescHandle;
  151.     CodecDecompressParams   decpar;          /* for ImageCodecPreDecompress()*/
  152.     CodecCapabilities       codeccap;        /* for decpar */
  153. #endif
  154.     /* Output properties */
  155.     uint8_t *           plane;
  156.     mtime_t             pts;
  157.     audio_date_t        date;
  158.     int                 i_late; /* video */
  159.     /* buffer */
  160.     unsigned int        i_buffer;
  161.     unsigned int        i_buffer_size;
  162.     uint8_t             *p_buffer;
  163.     /* Audio only */
  164.     uint8_t             out_buffer[1000000];    /* FIXME */
  165.     int                 i_out_frames;
  166.     int                 i_out;
  167. };
  168. static const int pi_channels_maps[6] =
  169. {
  170.     0,
  171.     AOUT_CHAN_CENTER,
  172.     AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT,
  173.     AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER,
  174.     AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_REARLEFT | AOUT_CHAN_REARLEFT,
  175.     AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER
  176.      | AOUT_CHAN_REARLEFT | AOUT_CHAN_REARLEFT
  177. };
  178. static int QTAudioInit( decoder_t * );
  179. static int QTVideoInit( decoder_t * );
  180. /*****************************************************************************
  181.  * Open: probe the decoder and return score
  182.  *****************************************************************************
  183.  * Tries to launch a decoder and return score so that the interface is able
  184.  * to choose.
  185.  *****************************************************************************/
  186. static int Open( vlc_object_t *p_this )
  187. {
  188.     decoder_t *p_dec = (decoder_t*)p_this;
  189. #ifdef __APPLE__
  190.     OSErr err;
  191.     SInt32 qtVersion, macosversion;
  192.     
  193.     err = Gestalt(gestaltQuickTimeVersion, &qtVersion);
  194.     err = Gestalt(gestaltSystemVersion, &macosversion);
  195. #ifndef NDEBUG
  196.     msg_Dbg( p_this, "Mac OS version is %#lx", macosversion );
  197.     msg_Dbg( p_this, "Quicktime version is %#lx", qtVersion );
  198. #endif
  199.     /* bail out. This plugin is soo Carbon, that it can't be used on 10.5 at all */
  200.     msg_Info( p_dec, "Your Mac OS version is to new to use this plugin for anything." );
  201.     return VLC_EGENERIC;
  202. #endif
  203.     switch( p_dec->fmt_in.i_codec )
  204.     {
  205.         case VLC_FOURCC('h','2','6','4'): /* H.264 */
  206.         case VLC_FOURCC('c','v','i','d'): /* Cinepak */
  207.         case VLC_FOURCC('I','V','4','1'): /* Indeo Video IV */
  208.         case VLC_FOURCC('i','v','4','1'): /* dto. */
  209. #ifdef __APPLE__
  210.         case VLC_FOURCC('p','x','l','t'): /* Pixlet */
  211. #endif
  212.         case VLC_FOURCC('d','v','1','n'): /* DVC Pro 100 NTSC */
  213.         case VLC_FOURCC('d','v','1','p'): /* DVC Pro 100 PAL */
  214.         case VLC_FOURCC('d','v','h','p'): /* DVC PRO HD 720p */
  215.         case VLC_FOURCC('d','v','h','6'): /* DVC PRO HD 1080i 60 */
  216.         case VLC_FOURCC('d','v','h','5'): /* DVC PRO HD 1080i 50 */
  217.         case VLC_FOURCC('S','V','Q','3'): /* Sorenson v3 */
  218.     /*    case VLC_FOURCC('S','V','Q','1'):  Sorenson v1
  219.         case VLC_FOURCC('Z','y','G','o'):
  220.         case VLC_FOURCC('V','P','3','1'):
  221.         case VLC_FOURCC('3','I','V','1'): */
  222.         case VLC_FOURCC('r','l','e',' '): /* QuickTime animation (RLE) */
  223.         case VLC_FOURCC('r','p','z','a'): /* QuickTime Apple Video */
  224.         case VLC_FOURCC('a','z','p','r'): /* QuickTime animation (RLE) */
  225. #ifdef LOADER
  226.         p_dec->p_sys = NULL;
  227.         p_dec->pf_decode_video = DecodeVideo;
  228.         p_dec->fmt_out.i_cat = VIDEO_ES;
  229.         return VLC_SUCCESS;
  230. #else
  231.         return OpenVideo( p_dec );
  232. #endif
  233. #ifdef __APPLE__
  234.         case VLC_FOURCC('I','L','B','C'): /* iLBC */
  235.             if ((err != noErr) || (qtVersion < 0x07500000)) 
  236.                 return VLC_EGENERIC;
  237.         case VLC_FOURCC('i','l','b','c'): /* iLBC */
  238.             if ((err != noErr) || (qtVersion < 0x07500000)) 
  239.                 return VLC_EGENERIC;
  240. #endif
  241.         case VLC_FOURCC('s','a','m','r'): /* 3GPP AMR audio */
  242.         case VLC_FOURCC('s','a','m','b'): /* 3GPP AMR-WB audio */
  243.         case VLC_FOURCC('m','p','4','a'): /* MPEG-4 audio */
  244.         case VLC_FOURCC('Q','D','M','C'): /* QDesign */
  245.         case VLC_FOURCC('Q','D','M','2'): /* QDesign* 2 */
  246.         case VLC_FOURCC('Q','c','l','p'): /* Qualcomm Purevoice Codec */
  247.         case VLC_FOURCC('Q','C','L','P'): /* Qualcomm Purevoice Codec */
  248.         case VLC_FOURCC('M','A','C','3'): /* MACE3 audio decoder */
  249.         case VLC_FOURCC('M','A','C','6'): /* MACE6 audio decoder */
  250.         case VLC_FOURCC('d','v','c','a'): /* DV Audio */
  251.         case VLC_FOURCC('s','o','w','t'): /* 16-bit Little Endian */
  252.         case VLC_FOURCC('t','w','o','s'): /* 16-bit Big Endian */
  253.         case VLC_FOURCC('a','l','a','w'): /* ALaw 2:1 */
  254.         case VLC_FOURCC('u','l','a','w'): /* mu-Law 2:1 */
  255.         case VLC_FOURCC('r','a','w',' '): /* 8-bit offset binaries */
  256.         case VLC_FOURCC('f','l','3','2'): /* 32-bit Floating Point */
  257.         case VLC_FOURCC('f','l','6','4'): /* 64-bit Floating Point */
  258.         case VLC_FOURCC('i','n','2','4'): /* 24-bit Interger */
  259.         case VLC_FOURCC('i','n','3','2'): /* 32-bit Integer */
  260.         case 0x0011:                            /* DVI IMA */
  261.         case 0x6D730002:                        /* Microsoft ADPCM-ACM */
  262.         case 0x6D730011:                        /* DVI Intel IMAADPCM-ACM */
  263. #ifdef LOADER
  264.         p_dec->p_sys = NULL;
  265.         p_dec->pf_decode_audio = DecodeAudio;
  266.         p_dec->fmt_out.i_cat = AUDIO_ES;
  267.         return VLC_SUCCESS;
  268. #else
  269.         return OpenAudio( p_dec );
  270. #endif
  271.         default:
  272.             return VLC_EGENERIC;
  273.     }
  274. }
  275. static vlc_mutex_t qt_mutex = VLC_STATIC_MUTEX;
  276. /*****************************************************************************
  277.  * Close:
  278.  *****************************************************************************/
  279. static void Close( vlc_object_t *p_this )
  280. {
  281.     decoder_t     *p_dec = (decoder_t*)p_this;
  282.     decoder_sys_t *p_sys = p_dec->p_sys;
  283.     /* get lock, avoid segfault */
  284.     vlc_mutex_lock( &qt_mutex );
  285.     if( p_dec->fmt_out.i_cat == AUDIO_ES )
  286.     {
  287.         int i_error;
  288.         unsigned long ConvertedFrames=0;
  289.         unsigned long ConvertedBytes=0;
  290.         i_error = p_sys->SoundConverterEndConversion( p_sys->myConverter, NULL,
  291.                                                       &ConvertedFrames,
  292.                                                       &ConvertedBytes );
  293.         msg_Dbg( p_dec, "SoundConverterEndConversion => %d", i_error );
  294.         i_error = p_sys->SoundConverterClose( p_sys->myConverter );
  295.         msg_Dbg( p_dec, "SoundConverterClose => %d", i_error );
  296.         free( p_sys->p_buffer );
  297.     }
  298.     else if( p_dec->fmt_out.i_cat == VIDEO_ES )
  299.     {
  300.         free( p_sys->plane );
  301.     }
  302. #ifndef __APPLE__
  303.     FreeLibrary( p_sys->qtml );
  304.     FreeLibrary( p_sys->qts );
  305.     msg_Dbg( p_dec, "FreeLibrary ok." );
  306. #else
  307.     ExitMovies();
  308. #endif
  309. #if 0
  310.     /* Segfault */
  311. #ifdef LOADER
  312.     Restore_LDT_Keeper( p_sys->ldt_fs );
  313.     msg_Dbg( p_dec, "Restore_LDT_Keeper" );
  314. #endif
  315. #endif
  316.     vlc_mutex_unlock( &qt_mutex );
  317.     free( p_sys );
  318. }
  319. /*****************************************************************************
  320.  * OpenAudio:
  321.  *****************************************************************************/
  322. static int OpenAudio( decoder_t *p_dec )
  323. {
  324.     decoder_sys_t *p_sys;
  325.     int             i_error;
  326.     char            fcc[4];
  327.     unsigned long   WantedBufferSize;
  328.     unsigned long   InputBufferSize = 0;
  329.     unsigned long   OutputBufferSize = 0;
  330.     /* get lock, avoid segfault */
  331.     vlc_mutex_lock( &qt_mutex );
  332.     p_sys = calloc( 1, sizeof( decoder_sys_t ) );
  333.     p_dec->p_sys = p_sys;
  334.     p_dec->pf_decode_audio = DecodeAudio;
  335.     memcpy( fcc, &p_dec->fmt_in.i_codec, 4 );
  336. #ifdef __APPLE__
  337.     EnterMovies();
  338. #endif
  339.     if( QTAudioInit( p_dec ) )
  340.     {
  341.         msg_Err( p_dec, "cannot initialize QT");
  342.         goto exit_error;
  343.     }
  344. #ifndef __APPLE__
  345.     if( ( i_error = p_sys->InitializeQTML( 6 + 16 ) ) )
  346.     {
  347.         msg_Dbg( p_dec, "error on InitializeQTML = %d", i_error );
  348.         goto exit_error;
  349.     }
  350. #endif
  351.     /* input format settings */
  352.     p_sys->InputFormatInfo.flags       = 0;
  353.     p_sys->InputFormatInfo.sampleCount = 0;
  354.     p_sys->InputFormatInfo.buffer      = NULL;
  355.     p_sys->InputFormatInfo.reserved    = 0;
  356.     p_sys->InputFormatInfo.numChannels = p_dec->fmt_in.audio.i_channels;
  357.     p_sys->InputFormatInfo.sampleSize  = p_dec->fmt_in.audio.i_bitspersample;
  358.     p_sys->InputFormatInfo.sampleRate  = p_dec->fmt_in.audio.i_rate;
  359.     p_sys->InputFormatInfo.format      = FCC( fcc[0], fcc[1], fcc[2], fcc[3] );
  360.     /* output format settings */
  361.     p_sys->OutputFormatInfo.flags       = 0;
  362.     p_sys->OutputFormatInfo.sampleCount = 0;
  363.     p_sys->OutputFormatInfo.buffer      = NULL;
  364.     p_sys->OutputFormatInfo.reserved    = 0;
  365.     p_sys->OutputFormatInfo.numChannels = p_dec->fmt_in.audio.i_channels;
  366.     p_sys->OutputFormatInfo.sampleSize  = 16;
  367.     p_sys->OutputFormatInfo.sampleRate  = p_dec->fmt_in.audio.i_rate;
  368.     p_sys->OutputFormatInfo.format      = FCC( 'N', 'O', 'N', 'E' );
  369.     i_error = p_sys->SoundConverterOpen( &p_sys->InputFormatInfo,
  370.                                          &p_sys->OutputFormatInfo,
  371.                                          &p_sys->myConverter );
  372.     if( i_error )
  373.     {
  374.         msg_Err( p_dec, "error on SoundConverterOpen = %d", i_error );
  375.         goto exit_error;
  376.     }
  377. #if 0
  378.     /* tell the sound converter we accept VBR formats */
  379.     i_error = SoundConverterSetInfo( p_dec->myConverter, siClientAcceptsVBR,
  380.                                      (void *)true );
  381. #endif
  382.     if( p_dec->fmt_in.i_extra > 36 + 8 )
  383.     {
  384.         i_error = p_sys->SoundConverterSetInfo( p_sys->myConverter,
  385.                                                 FCC( 'w', 'a', 'v', 'e' ),
  386.                                                 ((uint8_t*)p_dec->fmt_in.p_extra) + 36 + 8 );
  387.         msg_Dbg( p_dec, "error on SoundConverterSetInfo = %d", i_error );
  388.     }
  389.     WantedBufferSize = p_sys->OutputFormatInfo.numChannels *
  390.                        p_sys->OutputFormatInfo.sampleRate * 2;
  391.     p_sys->FramesToGet = 0;
  392.     i_error = p_sys->SoundConverterGetBufferSizes( p_sys->myConverter,
  393.                                                    WantedBufferSize,
  394.                                                    &p_sys->FramesToGet,
  395.                                                    &InputBufferSize,
  396.                                                    &OutputBufferSize );
  397.     msg_Dbg( p_dec, "WantedBufferSize=%li InputBufferSize=%li "
  398.              "OutputBufferSize=%li FramesToGet=%li",
  399.              WantedBufferSize, InputBufferSize, OutputBufferSize,
  400.              p_sys->FramesToGet );
  401.     p_sys->InFrameSize  = (InputBufferSize + p_sys->FramesToGet - 1 ) /
  402.                             p_sys->FramesToGet;
  403.     p_sys->OutFrameSize = OutputBufferSize / p_sys->FramesToGet;
  404.     msg_Dbg( p_dec, "frame size %d -> %d",
  405.              p_sys->InFrameSize, p_sys->OutFrameSize );
  406.     if( (i_error = p_sys->SoundConverterBeginConversion(p_sys->myConverter)) )
  407.     {
  408.         msg_Err( p_dec,
  409.                  "error on SoundConverterBeginConversion = %d", i_error );
  410.         goto exit_error;
  411.     }
  412.     es_format_Init( &p_dec->fmt_out, AUDIO_ES, AOUT_FMT_S16_NE );
  413.     p_dec->fmt_out.audio.i_rate = p_sys->OutputFormatInfo.sampleRate;
  414.     p_dec->fmt_out.audio.i_channels = p_sys->OutputFormatInfo.numChannels;
  415.     p_dec->fmt_out.audio.i_physical_channels =
  416.     p_dec->fmt_out.audio.i_original_channels =
  417.         pi_channels_maps[p_sys->OutputFormatInfo.numChannels];
  418.     aout_DateInit( &p_sys->date, p_dec->fmt_out.audio.i_rate );
  419.     p_sys->i_buffer      = 0;
  420.     p_sys->i_buffer_size = 100*1000;
  421.     p_sys->p_buffer      = malloc( p_sys->i_buffer_size );
  422.     if( !p_sys->p_buffer )
  423.         goto exit_error;
  424.     p_sys->i_out = 0;
  425.     p_sys->i_out_frames = 0;
  426.     vlc_mutex_unlock( &qt_mutex );
  427.     return VLC_SUCCESS;
  428. exit_error:
  429. #ifdef LOADER
  430.     Restore_LDT_Keeper( p_sys->ldt_fs );
  431. #endif
  432.     vlc_mutex_unlock( &qt_mutex );
  433.     free( p_sys );
  434.     return VLC_EGENERIC;
  435. }
  436. /*****************************************************************************
  437.  * DecodeAudio:
  438.  *****************************************************************************/
  439. static aout_buffer_t *DecodeAudio( decoder_t *p_dec, block_t **pp_block )
  440. {
  441.     decoder_sys_t *p_sys = p_dec->p_sys;
  442.     block_t     *p_block;
  443.     int         i_error;
  444. #ifdef LOADER
  445.     /* We must do open and close in the same thread (unless we do
  446.      * Setup_LDT_Keeper in the main thread before all others */
  447.     if( p_sys == NULL )
  448.     {
  449.         if( OpenAudio( p_dec ) )
  450.         {
  451.             /* Fatal */
  452.             p_dec->b_error = true;
  453.             return NULL;
  454.         }
  455.         p_sys = p_dec->p_sys;
  456.     }
  457. #endif
  458.     if( pp_block == NULL || *pp_block == NULL )
  459.     {
  460.         return NULL;
  461.     }
  462.     p_block = *pp_block;
  463.     if( p_sys->i_out_frames > 0 && p_sys->i_out >= p_sys->i_out_frames )
  464.     {
  465.         /* Ask new data */
  466.         p_sys->i_out = 0;
  467.         p_sys->i_out_frames = 0;
  468.         *pp_block = NULL;
  469.         return NULL;
  470.     }
  471.     if( p_sys->i_out_frames <= 0 )
  472.     {
  473.         p_sys->pts = p_block->i_pts;
  474.         mtime_t i_display_date = 0;
  475.         if( !(p_block->i_flags & BLOCK_FLAG_PREROLL) )
  476.             i_display_date = decoder_GetDisplayDate( p_dec, p_block->i_pts );
  477.         if( i_display_date > 0 && i_display_date < mdate() )
  478.         {
  479.             block_Release( p_block );
  480.             *pp_block = NULL;
  481.             return NULL;
  482.         }
  483.         /* Append data */
  484.         if( p_sys->i_buffer_size < p_sys->i_buffer + p_block->i_buffer )
  485.         {
  486.             p_sys->i_buffer_size = p_sys->i_buffer + p_block->i_buffer + 1024;
  487.             p_sys->p_buffer = realloc( p_sys->p_buffer, p_sys->i_buffer_size );
  488.         }
  489.         memcpy( &p_sys->p_buffer[p_sys->i_buffer], p_block->p_buffer,
  490.                 p_block->i_buffer );
  491.         p_sys->i_buffer += p_block->i_buffer;
  492.         if( p_sys->i_buffer > p_sys->InFrameSize )
  493.         {
  494.             int i_frames = p_sys->i_buffer / p_sys->InFrameSize;
  495.             unsigned long i_out_frames, i_out_bytes;
  496.             vlc_mutex_lock( &qt_mutex );
  497.             i_error = p_sys->SoundConverterConvertBuffer( p_sys->myConverter,
  498.                                                           p_sys->p_buffer,
  499.                                                           i_frames,
  500.                                                           p_sys->out_buffer,
  501.                                                           &i_out_frames,
  502.                                                           &i_out_bytes );
  503.             vlc_mutex_unlock( &qt_mutex );
  504.             /*
  505.             msg_Dbg( p_dec, "decoded %d frames -> %ld frames (error=%d)",
  506.                      i_frames, i_out_frames, i_error );
  507.             msg_Dbg( p_dec, "decoded %ld frames = %ld bytes",
  508.                      i_out_frames, i_out_bytes );
  509.             */
  510.             p_sys->i_buffer -= i_frames * p_sys->InFrameSize;
  511.             if( p_sys->i_buffer > 0 )
  512.             {
  513.                 memmove( &p_sys->p_buffer[0],
  514.                          &p_sys->p_buffer[i_frames * p_sys->InFrameSize],
  515.                          p_sys->i_buffer );
  516.             }
  517.             if( p_sys->pts != 0 &&
  518.                 p_sys->pts != aout_DateGet( &p_sys->date ) )
  519.             {
  520.                 aout_DateSet( &p_sys->date, p_sys->pts );
  521.             }
  522.             else if( !aout_DateGet( &p_sys->date ) )
  523.             {
  524.                 return NULL;
  525.             }
  526.             if( !i_error && i_out_frames > 0 )
  527.             {
  528.                 /* we have others samples */
  529.                 p_sys->i_out_frames = i_out_frames;
  530.                 p_sys->i_out = 0;
  531.             }
  532.         }
  533.     }
  534.     if( p_sys->i_out < p_sys->i_out_frames )
  535.     {
  536.         aout_buffer_t *p_out;
  537.         int  i_frames = __MIN( p_sys->i_out_frames - p_sys->i_out, 1000 );
  538.         p_out = decoder_NewAudioBuffer( p_dec, i_frames );
  539.         if( p_out )
  540.         {
  541.             p_out->start_date = aout_DateGet( &p_sys->date );
  542.             p_out->end_date = aout_DateIncrement( &p_sys->date, i_frames );
  543.             memcpy( p_out->p_buffer,
  544.                     &p_sys->out_buffer[2 * p_sys->i_out * p_dec->fmt_out.audio.i_channels],
  545.                     p_out->i_nb_bytes );
  546.             p_sys->i_out += i_frames;
  547.         }
  548.         return p_out;
  549.     }
  550.     return NULL;
  551. }
  552. /*****************************************************************************
  553.  * OpenVideo:
  554.  *****************************************************************************/
  555. static int OpenVideo( decoder_t *p_dec )
  556. {
  557. #ifndef WIN32
  558.     decoder_sys_t *p_sys = malloc( sizeof( decoder_sys_t ) );
  559.     if( !p_sys )
  560.         return VLC_ENOMEM;
  561.     long                                i_result;
  562.     ComponentDescription                desc;
  563.     Component                           prev;
  564.     ComponentResult                     cres;
  565.     ImageSubCodecDecompressCapabilities icap;   /* for ImageCodecInitialize() */
  566.     CodecInfo                           cinfo;  /* for ImageCodecGetCodecInfo() */
  567.     ImageDescription                    *id;
  568.     char                fcc[4];
  569.     int     i_vide = p_dec->fmt_in.i_extra;
  570.     uint8_t *p_vide = p_dec->fmt_in.p_extra;
  571.     p_dec->p_sys = p_sys;
  572.     p_dec->pf_decode_video = DecodeVideo;
  573.     p_sys->i_late = 0;
  574.     if( i_vide <= 0 )
  575.     {
  576.         msg_Err( p_dec, "missing extra info" );
  577.         free( p_sys );
  578.         return VLC_EGENERIC;
  579.     }
  580.     memcpy( fcc, &p_dec->fmt_in.i_codec, 4 );
  581.     msg_Dbg( p_dec, "quicktime_video %4.4s %dx%d",
  582.              fcc, p_dec->fmt_in.video.i_width, p_dec->fmt_in.video.i_height );
  583.     /* get lock, avoid segfault */
  584.     vlc_mutex_lock( &qt_mutex );
  585. #ifdef __APPLE__
  586.     EnterMovies();
  587. #endif
  588.     if( QTVideoInit( p_dec ) )
  589.     {
  590.         msg_Err( p_dec, "cannot initialize QT");
  591.         goto exit_error;
  592.     }
  593. #ifndef __APPLE__
  594.     if( ( i_result = p_sys->InitializeQTML( 6 + 16 ) ) )
  595.     {
  596.         msg_Dbg( p_dec, "error on InitializeQTML = %d", (int)i_result );
  597.         goto exit_error;
  598.     }
  599. #endif
  600.     /* init ComponentDescription */
  601.     memset( &desc, 0, sizeof( ComponentDescription ) );
  602.     desc.componentType      = FCC( 'i', 'm', 'd', 'c' );
  603.     desc.componentSubType   = FCC( fcc[0], fcc[1], fcc[2], fcc[3] );
  604.     desc.componentManufacturer = 0;
  605.     desc.componentFlags        = 0;
  606.     desc.componentFlagsMask    = 0;
  607.     if( !( prev = p_sys->FindNextComponent( NULL, &desc ) ) )
  608.     {
  609.         msg_Err( p_dec, "cannot find requested component" );
  610.         goto exit_error;
  611.     }
  612.     msg_Dbg( p_dec, "component id=0x%p", prev );
  613.     p_sys->ci =  p_sys->OpenComponent( prev );
  614.     msg_Dbg( p_dec, "component instance p=0x%p", p_sys->ci );
  615.     memset( &icap, 0, sizeof( ImageSubCodecDecompressCapabilities ) );
  616.     cres =  p_sys->ImageCodecInitialize( p_sys->ci, &icap );
  617.     msg_Dbg( p_dec, "ImageCodecInitialize->0x%X size=%d (%d)",
  618.              (int)cres, (int)icap.recordSize, (int)icap.decompressRecordSize);
  619.     memset( &cinfo, 0, sizeof( CodecInfo ) );
  620.     cres =  p_sys->ImageCodecGetCodecInfo( p_sys->ci, &cinfo );
  621.     msg_Dbg( p_dec,
  622.              "Flags: compr: 0x%x decomp: 0x%x format: 0x%x",
  623.              (unsigned int)cinfo.compressFlags,
  624.              (unsigned int)cinfo.decompressFlags,
  625.              (unsigned int)cinfo.formatFlags );
  626.     msg_Dbg( p_dec, "quicktime_video: Codec name: %.*s",
  627.              ((unsigned char*)&cinfo.typeName)[0],
  628.              ((unsigned char*)&cinfo.typeName)+1 );
  629.     /* make a yuy2 gworld */
  630.     p_sys->OutBufferRect.top    = 0;
  631.     p_sys->OutBufferRect.left   = 0;
  632.     p_sys->OutBufferRect.right  = p_dec->fmt_in.video.i_width;
  633.     p_sys->OutBufferRect.bottom = p_dec->fmt_in.video.i_height;
  634.     /* codec data FIXME use codec not SVQ3 */
  635.     msg_Dbg( p_dec, "vide = %d", i_vide  );
  636.     id = malloc( sizeof( ImageDescription ) + ( i_vide - 70 ) );
  637.     if( !id )
  638.         goto exit_error;
  639.     id->idSize          = sizeof( ImageDescription ) + ( i_vide - 70 );
  640.     id->cType           = FCC( fcc[0], fcc[1], fcc[2], fcc[3] );
  641.     id->version         = GetWBE ( p_vide +  0 );
  642.     id->revisionLevel   = GetWBE ( p_vide +  2 );
  643.     id->vendor          = GetDWBE( p_vide +  4 );
  644.     id->temporalQuality = GetDWBE( p_vide +  8 );
  645.     id->spatialQuality  = GetDWBE( p_vide + 12 );
  646.     id->width           = GetWBE ( p_vide + 16 );
  647.     id->height          = GetWBE ( p_vide + 18 );
  648.     id->hRes            = GetDWBE( p_vide + 20 );
  649.     id->vRes            = GetDWBE( p_vide + 24 );
  650.     id->dataSize        = GetDWBE( p_vide + 28 );
  651.     id->frameCount      = GetWBE ( p_vide + 32 );
  652.     memcpy( &id->name, p_vide + 34, 32 );
  653.     id->depth           = GetWBE ( p_vide + 66 );
  654.     id->clutID          = GetWBE ( p_vide + 68 );
  655.     if( i_vide > 70 )
  656.     {
  657.         memcpy( ((char*)&id->clutID) + 2, p_vide + 70, i_vide - 70 );
  658.     }
  659.     msg_Dbg( p_dec, "idSize=%d ver=%d rev=%d vendor=%d tempQ=%d "
  660.              "spaQ=%d w=%d h=%d dpi=%d%d dataSize=%d depth=%d frameCount=%d clutID=%d",
  661.              (int)id->idSize, id->version, id->revisionLevel, (int)id->vendor,
  662.              (int)id->temporalQuality, (int)id->spatialQuality,
  663.              (int)id->width, (int)id->height,
  664.              (int)id->hRes, (int)id->vRes,
  665.              (int)id->dataSize,
  666.              id->depth,
  667.              id->frameCount,
  668.              id->clutID );
  669.     p_sys->framedescHandle = (ImageDescriptionHandle) NewHandleClear( id->idSize );
  670.     memcpy( *p_sys->framedescHandle, id, id->idSize );
  671.     if( p_dec->fmt_in.video.i_width != 0 && p_dec->fmt_in.video.i_height != 0) 
  672.         p_sys->plane = malloc( p_dec->fmt_in.video.i_width * p_dec->fmt_in.video.i_height * 3 );
  673.     if( !p_sys->plane )
  674.         goto exit_error;
  675.     i_result = p_sys->QTNewGWorldFromPtr( &p_sys->OutBufferGWorld,
  676.                                           /*pixel format of new GWorld==YUY2 */
  677.                                           kYUVSPixelFormat,
  678.                                           /* we should benchmark if yvu9 is
  679.                                            * faster for svq3, too */
  680.                                           &p_sys->OutBufferRect,
  681.                                           0, 0, 0,
  682.                                           p_sys->plane,
  683.                                           p_dec->fmt_in.video.i_width * 2 );
  684.     msg_Dbg( p_dec, "NewGWorldFromPtr returned:%ld",
  685.              65536 - ( i_result&0xffff ) );
  686.     memset( &p_sys->decpar, 0, sizeof( CodecDecompressParams ) );
  687.     p_sys->decpar.imageDescription = p_sys->framedescHandle;
  688.     p_sys->decpar.startLine        = 0;
  689.     p_sys->decpar.stopLine         = ( **p_sys->framedescHandle ).height;
  690.     p_sys->decpar.frameNumber      = 1;
  691.     p_sys->decpar.matrixFlags      = 0;
  692.     p_sys->decpar.matrixType       = 0;
  693.     p_sys->decpar.matrix           = 0;
  694.     p_sys->decpar.capabilities     = &p_sys->codeccap;
  695.     p_sys->decpar.accuracy         = codecNormalQuality;
  696.     p_sys->decpar.srcRect          = p_sys->OutBufferRect;
  697.     p_sys->decpar.transferMode     = srcCopy;
  698.     p_sys->decpar.dstPixMap        = **p_sys->GetGWorldPixMap( p_sys->OutBufferGWorld );/*destPixmap;  */
  699.     cres =  p_sys->ImageCodecPreDecompress( p_sys->ci, &p_sys->decpar );
  700.     msg_Dbg( p_dec, "quicktime_video: ImageCodecPreDecompress cres=0x%X",
  701.              (int)cres );
  702.     es_format_Init( &p_dec->fmt_out, VIDEO_ES, VLC_FOURCC( 'Y', 'U', 'Y', '2' ));
  703.     p_dec->fmt_out.video.i_width = p_dec->fmt_in.video.i_width;
  704.     p_dec->fmt_out.video.i_height= p_dec->fmt_in.video.i_height;
  705.     p_dec->fmt_out.video.i_aspect = VOUT_ASPECT_FACTOR * p_dec->fmt_in.video.i_width / p_dec->fmt_in.video.i_height;
  706.  
  707.     vlc_mutex_unlock( &qt_mutex );
  708.     return VLC_SUCCESS;
  709. exit_error:
  710. #ifdef LOADER
  711.     Restore_LDT_Keeper( p_sys->ldt_fs );
  712. #endif
  713.     vlc_mutex_unlock( &qt_mutex );
  714. #endif /* !WIN32 */
  715.     return VLC_EGENERIC;
  716. }
  717. #ifndef WIN32
  718. /*****************************************************************************
  719.  * DecodeVideo:
  720.  *****************************************************************************/
  721. static picture_t *DecodeVideo( decoder_t *p_dec, block_t **pp_block )
  722. {
  723.     decoder_sys_t *p_sys = p_dec->p_sys;
  724.     block_t       *p_block;
  725.     picture_t     *p_pic;
  726.     mtime_t       i_pts;
  727.     ComponentResult cres;
  728. #ifdef LOADER
  729.     /* We must do open and close in the same thread (unless we do
  730.      * Setup_LDT_Keeper in the main thread before all others */
  731.     if( p_sys == NULL )
  732.     {
  733.         if( OpenVideo( p_dec ) )
  734.         {
  735.             /* Fatal */
  736.             p_dec->b_error = true;
  737.             return NULL;
  738.         }
  739.         p_sys = p_dec->p_sys;
  740.     }
  741. #endif
  742.     if( pp_block == NULL || *pp_block == NULL )
  743.     {
  744.         return NULL;
  745.     }
  746.     p_block = *pp_block;
  747.     *pp_block = NULL;
  748.  
  749.     i_pts = p_block->i_pts ? p_block->i_pts : p_block->i_dts;
  750.     mtime_t i_display_date = 0;
  751.     if( !(p_block->i_flags & BLOCK_FLAG_PREROLL) )
  752.         i_display_date = decoder_GetDisplayDate( p_dec, i_pts );
  753.     if( i_display_date > 0 && i_display_date < mdate() )
  754.     {
  755.         p_sys->i_late++;
  756.     }
  757.     else
  758.     {
  759.         p_sys->i_late = 0;
  760.     }
  761. #ifndef NDEBUG
  762.     msg_Dbg( p_dec, "bufsize: %d", (int)p_block->i_buffer);
  763. #endif
  764.     if( p_sys->i_late > 10 )
  765.     {
  766.         msg_Dbg( p_dec, "late buffer dropped (%"PRId64")", i_pts );
  767.         block_Release( p_block );
  768.         return NULL;
  769.     }
  770.  
  771.     vlc_mutex_lock( &qt_mutex );
  772.     if( ( p_pic = decoder_NewPicture( p_dec ) ) )
  773.     {
  774.         p_sys->decpar.data                  = (Ptr)p_block->p_buffer;
  775.         p_sys->decpar.bufferSize            = p_block->i_buffer;
  776.         (**p_sys->framedescHandle).dataSize = p_block->i_buffer;
  777.         cres = p_sys->ImageCodecBandDecompress( p_sys->ci, &p_sys->decpar );
  778.         ++p_sys->decpar.frameNumber;
  779.         if( cres &0xFFFF )
  780.         {
  781.             msg_Dbg( p_dec, "quicktime_video: ImageCodecBandDecompress"
  782.                      " cres=0x%X (-0x%X) %d :(",
  783.                      (int)cres,(int)-cres, (int)cres );
  784.         }
  785.         memcpy( p_pic->p[0].p_pixels, p_sys->plane,
  786.                 p_dec->fmt_in.video.i_width * p_dec->fmt_in.video.i_height * 2 );
  787.         p_pic->date = i_pts;
  788.     }
  789.  
  790.     vlc_mutex_unlock( &qt_mutex );
  791.     block_Release( p_block );
  792.     return p_pic;
  793. }
  794. #endif /* !WIN32 */
  795. /*****************************************************************************
  796.  * QTAudioInit:
  797.  *****************************************************************************/
  798. static int QTAudioInit( decoder_t *p_dec )
  799. {
  800.     decoder_sys_t *p_sys = p_dec->p_sys;
  801. #ifdef __APPLE__
  802.     p_sys->SoundConverterOpen       = (void*)SoundConverterOpen;
  803.     p_sys->SoundConverterClose      = (void*)SoundConverterClose;
  804.     p_sys->SoundConverterSetInfo    = (void*)SoundConverterSetInfo;
  805.     p_sys->SoundConverterGetBufferSizes = (void*)SoundConverterGetBufferSizes;
  806.     p_sys->SoundConverterConvertBuffer  = (void*)SoundConverterConvertBuffer;
  807.     p_sys->SoundConverterBeginConversion= (void*)SoundConverterBeginConversion;
  808.     p_sys->SoundConverterEndConversion  = (void*)SoundConverterEndConversion;
  809. #else
  810. #ifdef LOADER
  811.     p_sys->ldt_fs = Setup_LDT_Keeper();
  812. #endif /* LOADER */
  813.     p_sys->qts = LoadLibraryA( "QuickTime.qts" );
  814.     if( p_sys->qts == NULL )
  815.     {
  816.         msg_Dbg( p_dec, "failed loading QuickTime.qts" );
  817.         return VLC_EGENERIC;
  818.     }
  819.     p_sys->qtml = LoadLibraryA( "qtmlClient.dll" );
  820.     if( p_sys->qtml == NULL )
  821.     {
  822.         msg_Dbg( p_dec, "failed loading qtmlClient.dll" );
  823.         return VLC_EGENERIC;
  824.     }
  825.     p_sys->InitializeQTML               = (void *)GetProcAddress( p_sys->qtml, "InitializeQTML" );
  826.     p_sys->TerminateQTML                = (void *)GetProcAddress( p_sys->qtml, "TerminateQTML" );
  827.     p_sys->SoundConverterOpen           = (void *)GetProcAddress( p_sys->qtml, "SoundConverterOpen" );
  828.     p_sys->SoundConverterClose          = (void *)GetProcAddress( p_sys->qtml, "SoundConverterClose" );
  829.     p_sys->SoundConverterSetInfo        = (void *)GetProcAddress( p_sys->qtml, "SoundConverterSetInfo" );
  830.     p_sys->SoundConverterGetBufferSizes = (void *)GetProcAddress( p_sys->qtml, "SoundConverterGetBufferSizes" );
  831.     p_sys->SoundConverterConvertBuffer  = (void *)GetProcAddress( p_sys->qtml, "SoundConverterConvertBuffer" );
  832.     p_sys->SoundConverterEndConversion  = (void *)GetProcAddress( p_sys->qtml, "SoundConverterEndConversion" );
  833.     p_sys->SoundConverterBeginConversion= (void *)GetProcAddress( p_sys->qtml, "SoundConverterBeginConversion");
  834.     if( p_sys->InitializeQTML == NULL )
  835.     {
  836.         msg_Err( p_dec, "failed getting proc address InitializeQTML" );
  837.         return VLC_EGENERIC;
  838.     }
  839.     if( p_sys->SoundConverterOpen == NULL ||
  840.         p_sys->SoundConverterClose == NULL ||
  841.         p_sys->SoundConverterSetInfo == NULL ||
  842.         p_sys->SoundConverterGetBufferSizes == NULL ||
  843.         p_sys->SoundConverterConvertBuffer == NULL ||
  844.         p_sys->SoundConverterEndConversion == NULL ||
  845.         p_sys->SoundConverterBeginConversion == NULL )
  846.     {
  847.         msg_Err( p_dec, "failed getting proc address" );
  848.         return VLC_EGENERIC;
  849.     }
  850.     msg_Dbg( p_dec, "standard init done" );
  851. #endif /* else __APPLE__ */
  852.     return VLC_SUCCESS;
  853. }
  854. #ifndef WIN32
  855. /*****************************************************************************
  856.  * QTVideoInit:
  857.  *****************************************************************************/
  858. static int QTVideoInit( decoder_t *p_dec )
  859. {
  860.     decoder_sys_t *p_sys = p_dec->p_sys;
  861. #ifdef __APPLE__
  862.     p_sys->FindNextComponent        = (void*)FindNextComponent;
  863.     p_sys->OpenComponent            = (void*)OpenComponent;
  864.     p_sys->ImageCodecInitialize     = (void*)ImageCodecInitialize;
  865.     p_sys->ImageCodecGetCodecInfo   = (void*)ImageCodecGetCodecInfo;
  866.     p_sys->ImageCodecPreDecompress  = (void*)ImageCodecPreDecompress;
  867.     p_sys->ImageCodecBandDecompress = (void*)ImageCodecBandDecompress;
  868.     p_sys->GetGWorldPixMap          = (void*)GetGWorldPixMap;
  869.     p_sys->QTNewGWorldFromPtr       = (void*)QTNewGWorldFromPtr;
  870.     p_sys->NewHandleClear           = (void*)NewHandleClear;
  871. #else
  872. #ifdef LOADER
  873.     p_sys->ldt_fs = Setup_LDT_Keeper();
  874. #endif /* LOADER */
  875.     p_sys->qts = LoadLibraryA( "QuickTime.qts" );
  876.     if( p_sys->qts == NULL )
  877.     {
  878.         msg_Dbg( p_dec, "failed loading QuickTime.qts" );
  879.         return VLC_EGENERIC;
  880.     }
  881.     msg_Dbg( p_dec, "QuickTime.qts loaded" );
  882.     p_sys->qtml = LoadLibraryA( "qtmlClient.dll" );
  883.     if( p_sys->qtml == NULL )
  884.     {
  885.         msg_Dbg( p_dec, "failed loading qtmlClient.dll" );
  886.         return VLC_EGENERIC;
  887.     }
  888.     msg_Dbg( p_dec, "qtmlClient.dll loaded" );
  889.     /* (void*) to shut up gcc */
  890.     p_sys->InitializeQTML           = (void*)GetProcAddress( p_sys->qtml, "InitializeQTML" );
  891.     p_sys->FindNextComponent        = (void*)GetProcAddress( p_sys->qtml, "FindNextComponent" );
  892.     p_sys->OpenComponent            = (void*)GetProcAddress( p_sys->qtml, "OpenComponent" );
  893.     p_sys->ImageCodecInitialize     = (void*)GetProcAddress( p_sys->qtml, "ImageCodecInitialize" );
  894.     p_sys->ImageCodecGetCodecInfo   = (void*)GetProcAddress( p_sys->qtml, "ImageCodecGetCodecInfo" );
  895.     p_sys->ImageCodecPreDecompress  = (void*)GetProcAddress( p_sys->qtml, "ImageCodecPreDecompress" );
  896.     p_sys->ImageCodecBandDecompress = (void*)GetProcAddress( p_sys->qtml, "ImageCodecBandDecompress" );
  897.     p_sys->GetGWorldPixMap          = (void*)GetProcAddress( p_sys->qtml, "GetGWorldPixMap" );
  898.     p_sys->QTNewGWorldFromPtr       = (void*)GetProcAddress( p_sys->qtml, "QTNewGWorldFromPtr" );
  899.     p_sys->NewHandleClear           = (void*)GetProcAddress( p_sys->qtml, "NewHandleClear" );
  900.     if( p_sys->InitializeQTML == NULL )
  901.     {
  902.         msg_Dbg( p_dec, "failed getting proc address InitializeQTML" );
  903.         return VLC_EGENERIC;
  904.     }
  905.     if( p_sys->FindNextComponent == NULL ||
  906.         p_sys->OpenComponent == NULL ||
  907.         p_sys->ImageCodecInitialize == NULL ||
  908.         p_sys->ImageCodecGetCodecInfo == NULL ||
  909.         p_sys->ImageCodecPreDecompress == NULL ||
  910.         p_sys->ImageCodecBandDecompress == NULL ||
  911.         p_sys->GetGWorldPixMap == NULL ||
  912.         p_sys->QTNewGWorldFromPtr == NULL ||
  913.         p_sys->NewHandleClear == NULL )
  914.     {
  915.         msg_Err( p_dec, "failed getting proc address" );
  916.         return VLC_EGENERIC;
  917.     }
  918. #endif /* __APPLE__ */
  919.     return VLC_SUCCESS;
  920. }
  921. #endif /* !WIN32 */