comparison libschroedingerenc.c @ 7253:2f5b98d0aa13 libavcodec

Fix pts handling when encoding with libschroedinger, closes issue 453. patch by Anuradha Suraparaju, anuradha rd.bbc.co uk
author diego
date Sat, 12 Jul 2008 20:12:18 +0000
parents e943e1409077
children e6348a5656e0
comparison
equal deleted inserted replaced
7252:e674db16f1c6 7253:2f5b98d0aa13
55 int frame_size; 55 int frame_size;
56 56
57 /** Schroedinger encoder handle*/ 57 /** Schroedinger encoder handle*/
58 SchroEncoder* encoder; 58 SchroEncoder* encoder;
59 59
60 /** buffer to store encoder output before writing it to the frame queue*/
61 unsigned char *enc_buf;
62
63 /** Size of encoder buffer*/
64 int enc_buf_size;
65
60 /** queue storing encoded frames */ 66 /** queue storing encoded frames */
61 FfmpegDiracSchroQueue enc_frame_queue; 67 FfmpegDiracSchroQueue enc_frame_queue;
62 68
63 /** end of sequence signalled */ 69 /** end of sequence signalled */
64 int eos_signalled; 70 int eos_signalled;
253 struct FfmpegDiracSchroEncodedFrame* p_frame_output = NULL; 259 struct FfmpegDiracSchroEncodedFrame* p_frame_output = NULL;
254 int go = 1; 260 int go = 1;
255 SchroBuffer *enc_buf; 261 SchroBuffer *enc_buf;
256 int presentation_frame; 262 int presentation_frame;
257 int parse_code; 263 int parse_code;
264 int last_frame_in_sequence = 0;
258 265
259 if(data == NULL) { 266 if(data == NULL) {
260 /* Push end of sequence if not already signalled. */ 267 /* Push end of sequence if not already signalled. */
261 if (!p_schro_params->eos_signalled) { 268 if (!p_schro_params->eos_signalled) {
262 schro_encoder_end_of_stream(encoder); 269 schro_encoder_end_of_stream(encoder);
283 case SCHRO_STATE_END_OF_STREAM: 290 case SCHRO_STATE_END_OF_STREAM:
284 enc_buf = schro_encoder_pull (encoder, 291 enc_buf = schro_encoder_pull (encoder,
285 &presentation_frame); 292 &presentation_frame);
286 assert (enc_buf->length > 0); 293 assert (enc_buf->length > 0);
287 assert (enc_buf->length <= buf_size); 294 assert (enc_buf->length <= buf_size);
295 parse_code = enc_buf->data[4];
296
297 /* All non-frame data is prepended to actual frame data to
298 * be able to set the pts correctly. So we don't write data
299 * to the frame output queue until we actually have a frame
300 */
301 p_schro_params->enc_buf = av_realloc (
302 p_schro_params->enc_buf,
303 p_schro_params->enc_buf_size + enc_buf->length
304 );
305
306 memcpy(p_schro_params->enc_buf+p_schro_params->enc_buf_size,
307 enc_buf->data, enc_buf->length);
308 p_schro_params->enc_buf_size += enc_buf->length;
309
310
311 if (state == SCHRO_STATE_END_OF_STREAM) {
312 p_schro_params->eos_pulled = 1;
313 go = 0;
314 }
315
316 if (!SCHRO_PARSE_CODE_IS_PICTURE(parse_code)) {
317 schro_buffer_unref (enc_buf);
318 break;
319 }
288 320
289 /* Create output frame. */ 321 /* Create output frame. */
290 p_frame_output = av_mallocz(sizeof(FfmpegDiracSchroEncodedFrame)); 322 p_frame_output = av_mallocz(sizeof(FfmpegDiracSchroEncodedFrame));
291 /* Set output data. */ 323 /* Set output data. */
292 p_frame_output->size = enc_buf->length; 324 p_frame_output->size = p_schro_params->enc_buf_size;
293 p_frame_output->p_encbuf = av_malloc(enc_buf->length); 325 p_frame_output->p_encbuf = p_schro_params->enc_buf;
294 memcpy(p_frame_output->p_encbuf, enc_buf->data, enc_buf->length);
295
296 parse_code = enc_buf->data[4];
297 if (SCHRO_PARSE_CODE_IS_INTRA(parse_code) && 326 if (SCHRO_PARSE_CODE_IS_INTRA(parse_code) &&
298 SCHRO_PARSE_CODE_IS_REFERENCE(parse_code)) { 327 SCHRO_PARSE_CODE_IS_REFERENCE(parse_code)) {
299 p_frame_output->key_frame = 1; 328 p_frame_output->key_frame = 1;
300 } 329 }
301 330
302 /* Parse the coded frame number from the bitstream. Bytes 14 331 /* Parse the coded frame number from the bitstream. Bytes 14
303 * through 17 represesent the frame number. */ 332 * through 17 represesent the frame number. */
304 if (SCHRO_PARSE_CODE_IS_PICTURE(parse_code))
305 {
306 assert (enc_buf->length >= 17);
307 p_frame_output->frame_num = (enc_buf->data[13] << 24) + 333 p_frame_output->frame_num = (enc_buf->data[13] << 24) +
308 (enc_buf->data[14] << 16) + 334 (enc_buf->data[14] << 16) +
309 (enc_buf->data[15] << 8) + 335 (enc_buf->data[15] << 8) +
310 enc_buf->data[16]; 336 enc_buf->data[16];
311 }
312 337
313 ff_dirac_schro_queue_push_back (&p_schro_params->enc_frame_queue, 338 ff_dirac_schro_queue_push_back (&p_schro_params->enc_frame_queue,
314 p_frame_output); 339 p_frame_output);
340 p_schro_params->enc_buf_size = 0;
341 p_schro_params->enc_buf = NULL;
342
315 schro_buffer_unref (enc_buf); 343 schro_buffer_unref (enc_buf);
316 344
317 if (state == SCHRO_STATE_END_OF_STREAM) {
318 p_schro_params->eos_pulled = 1;
319 go = 0;
320 }
321 break; 345 break;
322 346
323 case SCHRO_STATE_NEED_FRAME: 347 case SCHRO_STATE_NEED_FRAME:
324 go = 0; 348 go = 0;
325 break; 349 break;
332 return -1; 356 return -1;
333 } 357 }
334 } 358 }
335 359
336 /* Copy 'next' frame in queue. */ 360 /* Copy 'next' frame in queue. */
361
362 if (p_schro_params->enc_frame_queue.size == 1 &&
363 p_schro_params->eos_pulled)
364 last_frame_in_sequence = 1;
365
337 p_frame_output = 366 p_frame_output =
338 ff_dirac_schro_queue_pop (&p_schro_params->enc_frame_queue); 367 ff_dirac_schro_queue_pop (&p_schro_params->enc_frame_queue);
339 368
340 if (p_frame_output == NULL) 369 if (p_frame_output == NULL)
341 return 0; 370 return 0;
346 * do so since Dirac is a constant frame rate codec. It expects input 375 * do so since Dirac is a constant frame rate codec. It expects input
347 * to be of constant frame rate. */ 376 * to be of constant frame rate. */
348 avccontext->coded_frame->pts = p_frame_output->frame_num; 377 avccontext->coded_frame->pts = p_frame_output->frame_num;
349 enc_size = p_frame_output->size; 378 enc_size = p_frame_output->size;
350 379
380 /* Append the end of sequence information to the last frame in the
381 * sequence. */
382 if (last_frame_in_sequence && p_schro_params->enc_buf_size > 0)
383 {
384 memcpy (frame + enc_size, p_schro_params->enc_buf,
385 p_schro_params->enc_buf_size);
386 enc_size += p_schro_params->enc_buf_size;
387 av_freep (&p_schro_params->enc_buf);
388 p_schro_params->enc_buf_size = 0;
389 }
390
351 /* free frame */ 391 /* free frame */
352 SchroedingerFreeFrame (p_frame_output); 392 SchroedingerFreeFrame (p_frame_output);
353 393
354 return enc_size; 394 return enc_size;
355 } 395 }
364 schro_encoder_free(p_schro_params->encoder); 404 schro_encoder_free(p_schro_params->encoder);
365 405
366 /* Free data in the output frame queue. */ 406 /* Free data in the output frame queue. */
367 ff_dirac_schro_queue_free (&p_schro_params->enc_frame_queue, 407 ff_dirac_schro_queue_free (&p_schro_params->enc_frame_queue,
368 SchroedingerFreeFrame); 408 SchroedingerFreeFrame);
409
410
411 /* Free the encoder buffer. */
412 if (p_schro_params->enc_buf_size)
413 av_freep(&p_schro_params->enc_buf);
369 414
370 /* Free the video format structure. */ 415 /* Free the video format structure. */
371 av_freep(&p_schro_params->format); 416 av_freep(&p_schro_params->format);
372 417
373 return 0 ; 418 return 0 ;