r878: This is Cinelerra 2.1.
[cinelerra_cv/ct.git] / quicktime / qtffmpeg.c
blob44c908fa78f519031583a09aa1ed988b530a739d
1 #include "colormodels.h"
2 #include "funcprotos.h"
3 #include <pthread.h>
4 #include "quicktime.h"
5 #include "qtffmpeg.h"
6 #include "qtprivate.h"
7 #include <string.h>
8 // FFMPEG front end for quicktime.
17 int ffmpeg_initialized = 0;
18 pthread_mutex_t ffmpeg_lock = PTHREAD_MUTEX_INITIALIZER;
25 quicktime_ffmpeg_t* quicktime_new_ffmpeg(int cpus,
26 int fields,
27 int ffmpeg_id,
28 int w,
29 int h,
30 quicktime_stsd_table_t *stsd_table)
32 quicktime_ffmpeg_t *ptr = calloc(1, sizeof(quicktime_ffmpeg_t));
33 quicktime_esds_t *esds = &stsd_table->esds;
34 quicktime_avcc_t *avcc = &stsd_table->avcc;
35 int i;
37 ptr->fields = fields;
38 ptr->width = w;
39 ptr->height = h;
40 ptr->ffmpeg_id = ffmpeg_id;
41 //printf("quicktime_new_ffmpeg 1 %d\n", ptr->ffmpeg_id);
42 if(ffmpeg_id == CODEC_ID_SVQ1)
44 ptr->width_i = quicktime_quantize32(ptr->width);
45 ptr->height_i = quicktime_quantize32(ptr->height);
47 else
49 ptr->width_i = quicktime_quantize16(ptr->width);
50 ptr->height_i = quicktime_quantize16(ptr->height);
53 pthread_mutex_lock(&ffmpeg_lock);
54 if(!ffmpeg_initialized)
56 ffmpeg_initialized = 1;
57 avcodec_init();
58 avcodec_register_all();
61 for(i = 0; i < fields; i++)
63 ptr->decoder[i] = avcodec_find_decoder(ptr->ffmpeg_id);
64 if(!ptr->decoder[i])
66 printf("quicktime_new_ffmpeg: avcodec_find_decoder returned NULL.\n");
67 quicktime_delete_ffmpeg(ptr);
68 return 0;
71 AVCodecContext *context = ptr->decoder_context[i] = avcodec_alloc_context();
72 static char fake_data[] = { 0, 0, 0, 0, 0, 0, 0, 0 };
73 context->width = ptr->width_i;
74 context->height = ptr->height_i;
75 // context->width = w;
76 // context->height = h;
77 context->extradata = fake_data;
78 context->extradata_size = 0;
79 if(esds->mpeg4_header && esds->mpeg4_header_size)
81 context->extradata = esds->mpeg4_header;
82 context->extradata_size = esds->mpeg4_header_size;
84 if(avcc->data && avcc->data_size)
86 context->extradata = avcc->data;
87 context->extradata_size = avcc->data_size;
89 if(cpus > 1)
91 avcodec_thread_init(context, cpus);
92 context->thread_count = cpus;
94 if(avcodec_open(context,
95 ptr->decoder[i]) < 0)
97 printf("quicktime_new_ffmpeg: avcodec_open failed.\n");
98 quicktime_delete_ffmpeg(ptr);
100 ptr->last_frame[i] = -1;
102 pthread_mutex_unlock(&ffmpeg_lock);
104 return ptr;
109 void quicktime_delete_ffmpeg(quicktime_ffmpeg_t *ptr)
111 int i;
112 if(ptr)
114 pthread_mutex_lock(&ffmpeg_lock);
115 for(i = 0; i < ptr->fields; i++)
117 if(ptr->decoder_context[i])
119 avcodec_close(ptr->decoder_context[i]);
120 free(ptr->decoder_context[i]);
123 pthread_mutex_unlock(&ffmpeg_lock);
127 if(ptr->temp_frame) free(ptr->temp_frame);
128 if(ptr->work_buffer) free(ptr->work_buffer);
131 free(ptr);
136 static int decode_wrapper(quicktime_t *file,
137 quicktime_video_map_t *vtrack,
138 quicktime_ffmpeg_t *ffmpeg,
139 int frame_number,
140 int current_field,
141 int track,
142 int drop_it)
144 int got_picture = 0;
145 int result = 0;
146 int bytes = 0;
147 int header_bytes = 0;
148 char *compressor = vtrack->track->mdia.minf.stbl.stsd.table[0].format;
149 quicktime_trak_t *trak = vtrack->track;
150 quicktime_stsd_table_t *stsd_table = &trak->mdia.minf.stbl.stsd.table[0];
152 //printf("decode_wrapper %d\n", frame_number);
153 quicktime_set_video_position(file, frame_number, track);
155 bytes = quicktime_frame_size(file, frame_number, track);
156 if(frame_number == 0)
158 header_bytes = stsd_table->esds.mpeg4_header_size;
161 if(!ffmpeg->work_buffer || ffmpeg->buffer_size < bytes + header_bytes)
163 if(ffmpeg->work_buffer) free(ffmpeg->work_buffer);
164 ffmpeg->buffer_size = bytes + header_bytes;
165 ffmpeg->work_buffer = calloc(1, ffmpeg->buffer_size + 100);
168 if(header_bytes)
169 memcpy(ffmpeg->work_buffer, stsd_table->esds.mpeg4_header, header_bytes);
171 if(!quicktime_read_data(file,
172 ffmpeg->work_buffer + header_bytes,
173 bytes))
174 result = -1;
177 if(!result)
181 // No way to determine if there was an error based on nonzero status.
182 // Need to test row pointers to determine if an error occurred.
183 if(drop_it)
184 ffmpeg->decoder_context[current_field]->skip_frame = AVDISCARD_NONREF /* AVDISCARD_BIDIR */;
185 else
186 ffmpeg->decoder_context[current_field]->skip_frame = AVDISCARD_DEFAULT;
187 result = avcodec_decode_video(ffmpeg->decoder_context[current_field],
188 &ffmpeg->picture[current_field],
189 &got_picture,
190 ffmpeg->work_buffer,
191 bytes + header_bytes);
195 if(ffmpeg->picture[current_field].data[0])
197 result = 0;
199 else
201 // ffmpeg can't recover if the first frame errored out, like in a direct copy
202 // sequence.
203 result = 1;
206 #ifdef ARCH_X86
207 asm("emms");
208 #endif
211 return result;
214 // Get amount chroma planes are downsampled from luma plane.
215 // Used for copying planes into cache.
216 static int get_chroma_factor(quicktime_ffmpeg_t *ffmpeg, int current_field)
218 switch(ffmpeg->decoder_context[current_field]->pix_fmt)
220 case PIX_FMT_YUV420P:
221 return 4;
222 break;
223 case PIX_FMT_YUV422:
224 return 2;
225 break;
226 case PIX_FMT_YUV422P:
227 return 2;
228 break;
229 case PIX_FMT_YUV410P:
230 return 9;
231 break;
232 default:
233 fprintf(stderr,
234 "get_chroma_factor: unrecognized color model %d\n",
235 ffmpeg->decoder_context[current_field]->pix_fmt);
236 return 9;
237 break;
241 int quicktime_ffmpeg_decode(quicktime_ffmpeg_t *ffmpeg,
242 quicktime_t *file,
243 unsigned char **row_pointers,
244 int track)
246 quicktime_video_map_t *vtrack = &(file->vtracks[track]);
247 quicktime_trak_t *trak = vtrack->track;
248 int current_field = vtrack->current_position % ffmpeg->fields;
249 int input_cmodel;
250 int result = 0;
251 int seeking_done = 0;
252 int i;
254 // Try frame cache
255 result = quicktime_get_frame(vtrack->frame_cache,
256 vtrack->current_position,
257 &ffmpeg->picture[current_field].data[0],
258 &ffmpeg->picture[current_field].data[1],
259 &ffmpeg->picture[current_field].data[2]);
262 // Didn't get frame
263 if(!result)
265 // Codecs which work without locking:
266 // H264
267 // MPEG-4
268 // pthread_mutex_lock(&ffmpeg_lock);
270 //printf("quicktime_ffmpeg_decode 1 %d\n", ffmpeg->last_frame[current_field]);
272 if(ffmpeg->last_frame[current_field] == -1 &&
273 ffmpeg->ffmpeg_id != CODEC_ID_H264)
275 int current_frame = vtrack->current_position;
276 // For certain codecs,
277 // must decode frame with stream header first but only the first frame in the
278 // field sequence has a stream header.
279 result = decode_wrapper(file,
280 vtrack,
281 ffmpeg,
282 current_field,
283 current_field,
284 track,
286 // Reset position because decode wrapper set it
287 quicktime_set_video_position(file, current_frame, track);
288 ffmpeg->last_frame[current_field] = current_field;
292 // Handle seeking
293 // Seeking requires keyframes
294 if(quicktime_has_keyframes(file, track) &&
295 // Not next frame
296 vtrack->current_position != ffmpeg->last_frame[current_field] + ffmpeg->fields &&
297 // Same frame requested twice
298 vtrack->current_position != ffmpeg->last_frame[current_field])
300 int frame1;
301 int first_frame;
302 int frame2 = vtrack->current_position;
303 int current_frame = frame2;
304 int do_i_frame = 1;
306 // If an interleaved codec, the opposite field would have been decoded in the previous
307 // seek.
308 if(!quicktime_has_frame(vtrack->frame_cache, vtrack->current_position + 1))
309 quicktime_reset_cache(vtrack->frame_cache);
311 // Get first keyframe of same field
312 frame1 = current_frame;
315 frame1 = quicktime_get_keyframe_before(file,
316 frame1 - 1,
317 track);
318 }while(frame1 > 0 && (frame1 % ffmpeg->fields) != current_field);
319 //printf("quicktime_ffmpeg_decode 1 %d\n", frame1);
321 // For MPEG-4, get another keyframe before first keyframe.
322 // The Sanyo tends to glitch with only 1 keyframe.
323 // Not enough memory.
324 if( 0 /* frame1 > 0 && ffmpeg->ffmpeg_id == CODEC_ID_MPEG4 */)
328 frame1 = quicktime_get_keyframe_before(file,
329 frame1 - 1,
330 track);
331 }while(frame1 > 0 && (frame1 & ffmpeg->fields) != current_field);
332 //printf("quicktime_ffmpeg_decode 2 %d\n", frame1);
335 // Keyframe is before last decoded frame and current frame is after last decoded
336 // frame, so instead of rerendering from the last keyframe we can rerender from
337 // the last decoded frame.
338 if(frame1 < ffmpeg->last_frame[current_field] &&
339 frame2 > ffmpeg->last_frame[current_field])
341 frame1 = ffmpeg->last_frame[current_field] + ffmpeg->fields;
342 do_i_frame = 0;
345 first_frame = frame1;
347 //printf("quicktime_ffmpeg_decode 2 %d\n", ffmpeg->last_frame[current_field]);
348 while(frame1 <= frame2)
350 result = decode_wrapper(file,
351 vtrack,
352 ffmpeg,
353 frame1,
354 current_field,
355 track,
356 // Don't drop if we want to cache it
357 0 /* (frame1 < frame2) */);
359 if(ffmpeg->picture[current_field].data[0] &&
360 // FFmpeg seems to glitch out if we include the first frame.
361 frame1 > first_frame)
363 int y_size = ffmpeg->picture[current_field].linesize[0] * ffmpeg->height_i;
364 int u_size = y_size / get_chroma_factor(ffmpeg, current_field);
365 int v_size = y_size / get_chroma_factor(ffmpeg, current_field);
366 quicktime_put_frame(vtrack->frame_cache,
367 frame1,
368 ffmpeg->picture[current_field].data[0],
369 ffmpeg->picture[current_field].data[1],
370 ffmpeg->picture[current_field].data[2],
371 y_size,
372 u_size,
373 v_size);
376 // For some codecs,
377 // may need to do the same frame twice if it is the first I frame.
378 if(do_i_frame)
380 result = decode_wrapper(file,
381 vtrack,
382 ffmpeg,
383 frame1,
384 current_field,
385 track,
387 do_i_frame = 0;
389 frame1 += ffmpeg->fields;
392 vtrack->current_position = frame2;
393 seeking_done = 1;
396 // Not decoded in seeking process
397 if(!seeking_done &&
398 // Same frame not requested
399 vtrack->current_position != ffmpeg->last_frame[current_field])
401 result = decode_wrapper(file,
402 vtrack,
403 ffmpeg,
404 vtrack->current_position,
405 current_field,
406 track,
410 // pthread_mutex_unlock(&ffmpeg_lock);
413 ffmpeg->last_frame[current_field] = vtrack->current_position;
416 // Hopefully this setting will be left over if the cache was used.
417 switch(ffmpeg->decoder_context[current_field]->pix_fmt)
419 case PIX_FMT_YUV420P:
420 input_cmodel = BC_YUV420P;
421 break;
422 case PIX_FMT_YUV422:
423 input_cmodel = BC_YUV422;
424 break;
425 case PIX_FMT_YUV422P:
426 input_cmodel = BC_YUV422P;
427 break;
428 case PIX_FMT_YUV410P:
429 input_cmodel = BC_YUV9P;
430 break;
431 default:
432 fprintf(stderr,
433 "quicktime_ffmpeg_decode: unrecognized color model %d\n",
434 ffmpeg->decoder_context[current_field]->pix_fmt);
435 input_cmodel = BC_YUV420P;
436 break;
439 if(ffmpeg->picture[current_field].data[0])
441 unsigned char **input_rows;
443 input_rows =
444 malloc(sizeof(unsigned char*) *
445 ffmpeg->decoder_context[current_field]->height);
448 for(i = 0; i < ffmpeg->decoder_context[current_field]->height; i++)
449 input_rows[i] = ffmpeg->picture[current_field].data[0] +
450 i *
451 ffmpeg->decoder_context[current_field]->width *
452 cmodel_calculate_pixelsize(input_cmodel);
455 cmodel_transfer(row_pointers, /* Leave NULL if non existent */
456 input_rows,
457 row_pointers[0], /* Leave NULL if non existent */
458 row_pointers[1],
459 row_pointers[2],
460 ffmpeg->picture[current_field].data[0], /* Leave NULL if non existent */
461 ffmpeg->picture[current_field].data[1],
462 ffmpeg->picture[current_field].data[2],
463 file->in_x, /* Dimensions to capture from input frame */
464 file->in_y,
465 file->in_w,
466 file->in_h,
467 0, /* Dimensions to project on output frame */
469 file->out_w,
470 file->out_h,
471 input_cmodel,
472 file->color_model,
473 0, /* When transfering BC_RGBA8888 to non-alpha this is the background color in 0xRRGGBB hex */
474 ffmpeg->picture[current_field].linesize[0], /* For planar use the luma rowspan */
475 ffmpeg->width);
476 free(input_rows);
480 return result;