Mercurial > libavcodec.hg
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 ; |