// Register our get_frame implementation
producer->get_frame = producer_get_frame;
+ // init mutexes
+ pthread_mutex_init( &self->audio_mutex, NULL );
+ pthread_mutex_init( &self->video_mutex, NULL );
+ pthread_mutex_init( &self->packets_mutex, NULL );
+ pthread_mutex_init( &self->open_mutex, NULL );
+
+ // init queues
+ self->apackets = mlt_deque_init();
+ self->vpackets = mlt_deque_init();
+
if ( strcmp( service, "avformat-novalidate" ) )
{
// Open the file
// Clean up
mlt_producer_close( producer );
producer = NULL;
+ producer_avformat_close( self );
}
else if ( self->seekable )
{
if ( ret >= 0 && pkt.stream_index == self->video_index && pkt.size > 0 )
{
get_aspect_ratio( properties, format->streams[ self->video_index ], codec_context, &pkt );
+ av_free_packet(&pkt);
break;
}
+ if ( ret >= 0 )
+ av_free_packet(&pkt);
}
}
else
// Lock the service
if ( take_lock )
{
- pthread_mutex_init( &self->audio_mutex, NULL );
- pthread_mutex_init( &self->video_mutex, NULL );
- pthread_mutex_init( &self->packets_mutex, NULL );
- pthread_mutex_init( &self->open_mutex, NULL );
pthread_mutex_lock( &self->audio_mutex );
pthread_mutex_lock( &self->video_mutex );
}
}
if ( filename )
free( filename );
- if ( !error )
- {
- self->apackets = mlt_deque_init();
- self->vpackets = mlt_deque_init();
- }
if ( self->dummy_context )
{
// extract alpha from planar formats
if ( ( pix_fmt == PIX_FMT_YUVA420P
-#if LIBAVUTIL_VERSION_INT >= ((51<<16)+(35<<8)+101)
+#if defined(FFUDIV) && LIBAVUTIL_VERSION_INT >= ((51<<16)+(35<<8)+101)
|| pix_fmt == PIX_FMT_YUVA444P
#endif
) &&
int image_size = 0;
// Get the image cache
- if ( ! self->image_cache && ! mlt_properties_get_int( properties, "noimagecache" ) )
+ if ( ! self->image_cache )
{
- self->image_cache = mlt_cache_init();
+ // if cache size supplied by environment variable
+ int cache_supplied = getenv( "MLT_AVFORMAT_CACHE" ) != NULL;
+ int cache_size = cache_supplied? atoi( getenv( "MLT_AVFORMAT_CACHE" ) ) : 0;
+
+ // cache size supplied via property
+ if ( mlt_properties_get( properties, "cache" ) )
+ {
+ cache_supplied = 1;
+ cache_size = mlt_properties_get_int( properties, "cache" );
+ }
+ if ( mlt_properties_get_int( properties, "noimagecache" ) )
+ cache_size = 0;
+ // create cache if not disabled
+ if ( !cache_supplied || cache_size > 0 )
+ self->image_cache = mlt_cache_init();
+ // set cache size if supplied
+ if ( self->image_cache && cache_supplied )
+ mlt_cache_set_size( self->image_cache, cache_size );
}
if ( self->image_cache )
{
// Turn on usage of new seek API and PTS for seeking
int use_pts = self->seekable &&
- codec_context->codec_id == CODEC_ID_H264 && codec_context->has_b_frames;
+ ( codec_context->codec_id == CODEC_ID_H264
+#if LIBAVCODEC_VERSION_INT >= ((52<<16)+(68<<8)+2)
+ || codec_context->codec_id == CODEC_ID_VP8
+#endif
+ );
if ( mlt_properties_get( properties, "use_pts" ) )
use_pts = mlt_properties_get_int( properties, "use_pts" );
double delay = mlt_properties_get_double( properties, "video_delay" );
if ( ret >= 0 && pkt.stream_index == self->video_index && pkt.size > 0 )
{
// Determine time code of the packet
- if ( pkt.pts == AV_NOPTS_VALUE )
+ if ( use_pts && pkt.pts == AV_NOPTS_VALUE )
{
self->invalid_pts_counter++;
if ( self->invalid_pts_counter > 20 )
#endif
// Reset some image properties
- mlt_properties_set_int( properties, "width", self->video_codec->width );
- mlt_properties_set_int( properties, "height", self->video_codec->height );
+ if ( self->video_codec )
+ {
+ mlt_properties_set_int( properties, "width", self->video_codec->width );
+ mlt_properties_set_int( properties, "height", self->video_codec->height );
+ }
// For DV, we'll just use the saved aspect ratio
if ( codec_context->codec_id != CODEC_ID_DVVIDEO )
get_aspect_ratio( properties, stream, self->video_codec, NULL );
}
// Initialize the resamplers and buffers
- for ( ; index < index_max; index++ )
+ for ( ; index < index_max && index < MAX_AUDIO_STREAMS; index++ )
{
// Get codec context
AVCodecContext *codec_context = self->audio_codec[ index ];
// We only deal with audio from the selected audio index
index = pkt.stream_index;
- if ( ret >= 0 && pkt.data && pkt.size > 0 && ( index == self->audio_index ||
+ if ( index < MAX_AUDIO_STREAMS && ret >= 0 && pkt.data && pkt.size > 0 && ( index == self->audio_index ||
( self->audio_index == INT_MAX && context->streams[ index ]->codec->codec_type == CODEC_TYPE_AUDIO ) ) )
{
int channels2 = ( self->audio_index == INT_MAX || !self->audio_resample[index] ) ?
else if ( context && index > -1 && audio_codec_init( self, index, properties ) )
{
// Set the frame properties
- if ( index < INT_MAX )
+ if ( index < MAX_AUDIO_STREAMS )
{
mlt_properties_set_int( frame_properties, "frequency", self->audio_codec[ index ]->sample_rate );
mlt_properties_set_int( frame_properties, "channels", self->audio_codec[ index ]->channels );