Libav 0.7.1
|
00001 /* 00002 * Dirac encoder support via Schroedinger libraries 00003 * Copyright (c) 2008 BBC, Anuradha Suraparaju <asuraparaju at gmail dot com > 00004 * 00005 * This file is part of Libav. 00006 * 00007 * Libav is free software; you can redistribute it and/or 00008 * modify it under the terms of the GNU Lesser General Public 00009 * License as published by the Free Software Foundation; either 00010 * version 2.1 of the License, or (at your option) any later version. 00011 * 00012 * Libav is distributed in the hope that it will be useful, 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00015 * Lesser General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU Lesser General Public 00018 * License along with Libav; if not, write to the Free Software 00019 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 00020 */ 00021 00030 #undef NDEBUG 00031 #include <assert.h> 00032 00033 #include <schroedinger/schro.h> 00034 #include <schroedinger/schrodebug.h> 00035 #include <schroedinger/schrovideoformat.h> 00036 00037 #include "avcodec.h" 00038 #include "libdirac_libschro.h" 00039 #include "libschroedinger.h" 00040 #include "bytestream.h" 00041 00042 00044 typedef struct FfmpegSchroEncoderParams { 00046 SchroVideoFormat *format; 00047 00049 SchroFrameFormat frame_format; 00050 00052 AVFrame picture; 00053 00055 int frame_size; 00056 00058 SchroEncoder* encoder; 00059 00061 unsigned char *enc_buf; 00062 00064 int enc_buf_size; 00065 00067 FfmpegDiracSchroQueue enc_frame_queue; 00068 00070 int eos_signalled; 00071 00073 int eos_pulled; 00074 } FfmpegSchroEncoderParams; 00075 00079 static int SetSchroChromaFormat(AVCodecContext *avccontext) 00080 { 00081 int num_formats = sizeof(ffmpeg_schro_pixel_format_map) / 00082 sizeof(ffmpeg_schro_pixel_format_map[0]); 00083 int idx; 00084 00085 FfmpegSchroEncoderParams* p_schro_params = avccontext->priv_data; 00086 00087 for (idx = 0; idx < num_formats; ++idx) { 00088 if (ffmpeg_schro_pixel_format_map[idx].ff_pix_fmt == 00089 avccontext->pix_fmt) { 00090 p_schro_params->format->chroma_format = 00091 ffmpeg_schro_pixel_format_map[idx].schro_pix_fmt; 00092 return 0; 00093 } 00094 } 00095 00096 av_log(avccontext, AV_LOG_ERROR, 00097 "This codec currently only supports planar YUV 4:2:0, 4:2:2" 00098 " and 4:4:4 formats.\n"); 00099 00100 return -1; 00101 } 00102 00103 static int libschroedinger_encode_init(AVCodecContext *avccontext) 00104 { 00105 FfmpegSchroEncoderParams* p_schro_params = avccontext->priv_data; 00106 SchroVideoFormatEnum preset; 00107 00108 /* Initialize the libraries that libschroedinger depends on. */ 00109 schro_init(); 00110 00111 /* Create an encoder object. */ 00112 p_schro_params->encoder = schro_encoder_new(); 00113 00114 if (!p_schro_params->encoder) { 00115 av_log(avccontext, AV_LOG_ERROR, 00116 "Unrecoverable Error: schro_encoder_new failed. "); 00117 return -1; 00118 } 00119 00120 /* Initialize the format. */ 00121 preset = ff_get_schro_video_format_preset(avccontext); 00122 p_schro_params->format = 00123 schro_encoder_get_video_format(p_schro_params->encoder); 00124 schro_video_format_set_std_video_format(p_schro_params->format, preset); 00125 p_schro_params->format->width = avccontext->width; 00126 p_schro_params->format->height = avccontext->height; 00127 00128 if (SetSchroChromaFormat(avccontext) == -1) 00129 return -1; 00130 00131 if (avccontext->color_primaries == AVCOL_PRI_BT709) { 00132 p_schro_params->format->colour_primaries = SCHRO_COLOUR_PRIMARY_HDTV; 00133 } else if (avccontext->color_primaries == AVCOL_PRI_BT470BG) { 00134 p_schro_params->format->colour_primaries = SCHRO_COLOUR_PRIMARY_SDTV_625; 00135 } else if (avccontext->color_primaries == AVCOL_PRI_SMPTE170M) { 00136 p_schro_params->format->colour_primaries = SCHRO_COLOUR_PRIMARY_SDTV_525; 00137 } 00138 00139 if (avccontext->colorspace == AVCOL_SPC_BT709) { 00140 p_schro_params->format->colour_matrix = SCHRO_COLOUR_MATRIX_HDTV; 00141 } else if (avccontext->colorspace == AVCOL_SPC_BT470BG) { 00142 p_schro_params->format->colour_matrix = SCHRO_COLOUR_MATRIX_SDTV; 00143 } 00144 00145 if (avccontext->color_trc == AVCOL_TRC_BT709) { 00146 p_schro_params->format->transfer_function = SCHRO_TRANSFER_CHAR_TV_GAMMA; 00147 } 00148 00149 if (ff_get_schro_frame_format(p_schro_params->format->chroma_format, 00150 &p_schro_params->frame_format) == -1) { 00151 av_log(avccontext, AV_LOG_ERROR, 00152 "This codec currently supports only planar YUV 4:2:0, 4:2:2" 00153 " and 4:4:4 formats.\n"); 00154 return -1; 00155 } 00156 00157 p_schro_params->format->frame_rate_numerator = avccontext->time_base.den; 00158 p_schro_params->format->frame_rate_denominator = avccontext->time_base.num; 00159 00160 p_schro_params->frame_size = avpicture_get_size(avccontext->pix_fmt, 00161 avccontext->width, 00162 avccontext->height); 00163 00164 avccontext->coded_frame = &p_schro_params->picture; 00165 00166 if (!avccontext->gop_size) { 00167 schro_encoder_setting_set_double(p_schro_params->encoder, 00168 "gop_structure", 00169 SCHRO_ENCODER_GOP_INTRA_ONLY); 00170 00171 if (avccontext->coder_type == FF_CODER_TYPE_VLC) 00172 schro_encoder_setting_set_double(p_schro_params->encoder, 00173 "enable_noarith", 1); 00174 } else { 00175 schro_encoder_setting_set_double(p_schro_params->encoder, 00176 "au_distance", avccontext->gop_size); 00177 avccontext->has_b_frames = 1; 00178 } 00179 00180 /* FIXME - Need to handle SCHRO_ENCODER_RATE_CONTROL_LOW_DELAY. */ 00181 if (avccontext->flags & CODEC_FLAG_QSCALE) { 00182 if (!avccontext->global_quality) { 00183 /* lossless coding */ 00184 schro_encoder_setting_set_double(p_schro_params->encoder, 00185 "rate_control", 00186 SCHRO_ENCODER_RATE_CONTROL_LOSSLESS); 00187 } else { 00188 int quality; 00189 schro_encoder_setting_set_double(p_schro_params->encoder, 00190 "rate_control", 00191 SCHRO_ENCODER_RATE_CONTROL_CONSTANT_QUALITY); 00192 00193 quality = avccontext->global_quality / FF_QP2LAMBDA; 00194 if (quality > 10) 00195 quality = 10; 00196 schro_encoder_setting_set_double(p_schro_params->encoder, 00197 "quality", quality); 00198 } 00199 } else { 00200 schro_encoder_setting_set_double(p_schro_params->encoder, 00201 "rate_control", 00202 SCHRO_ENCODER_RATE_CONTROL_CONSTANT_BITRATE); 00203 00204 schro_encoder_setting_set_double(p_schro_params->encoder, 00205 "bitrate", 00206 avccontext->bit_rate); 00207 00208 } 00209 00210 if (avccontext->flags & CODEC_FLAG_INTERLACED_ME) 00211 /* All material can be coded as interlaced or progressive 00212 irrespective of the type of source material. */ 00213 schro_encoder_setting_set_double(p_schro_params->encoder, 00214 "interlaced_coding", 1); 00215 00216 schro_encoder_setting_set_double(p_schro_params->encoder, "open_gop", 00217 !(avccontext->flags & CODEC_FLAG_CLOSED_GOP)); 00218 00219 /* FIXME: Signal range hardcoded to 8-bit data until both libschroedinger 00220 * and libdirac support other bit-depth data. */ 00221 schro_video_format_set_std_signal_range(p_schro_params->format, 00222 SCHRO_SIGNAL_RANGE_8BIT_VIDEO); 00223 00224 /* Set the encoder format. */ 00225 schro_encoder_set_video_format(p_schro_params->encoder, 00226 p_schro_params->format); 00227 00228 /* Set the debug level. */ 00229 schro_debug_set_level(avccontext->debug); 00230 00231 schro_encoder_start(p_schro_params->encoder); 00232 00233 /* Initialize the encoded frame queue. */ 00234 ff_dirac_schro_queue_init(&p_schro_params->enc_frame_queue); 00235 return 0; 00236 } 00237 00238 static SchroFrame *libschroedinger_frame_from_data(AVCodecContext *avccontext, 00239 void *in_data) 00240 { 00241 FfmpegSchroEncoderParams* p_schro_params = avccontext->priv_data; 00242 SchroFrame *in_frame; 00243 /* Input line size may differ from what the codec supports. Especially 00244 * when transcoding from one format to another. So use avpicture_layout 00245 * to copy the frame. */ 00246 in_frame = ff_create_schro_frame(avccontext, p_schro_params->frame_format); 00247 00248 if (in_frame) 00249 avpicture_layout((AVPicture *)in_data, avccontext->pix_fmt, 00250 avccontext->width, avccontext->height, 00251 in_frame->components[0].data, 00252 p_schro_params->frame_size); 00253 00254 return in_frame; 00255 } 00256 00257 static void SchroedingerFreeFrame(void *data) 00258 { 00259 FfmpegDiracSchroEncodedFrame *enc_frame = data; 00260 00261 av_freep(&(enc_frame->p_encbuf)); 00262 av_free(enc_frame); 00263 } 00264 00265 static int libschroedinger_encode_frame(AVCodecContext *avccontext, 00266 unsigned char *frame, 00267 int buf_size, void *data) 00268 { 00269 int enc_size = 0; 00270 FfmpegSchroEncoderParams* p_schro_params = avccontext->priv_data; 00271 SchroEncoder *encoder = p_schro_params->encoder; 00272 struct FfmpegDiracSchroEncodedFrame* p_frame_output = NULL; 00273 int go = 1; 00274 SchroBuffer *enc_buf; 00275 int presentation_frame; 00276 int parse_code; 00277 int last_frame_in_sequence = 0; 00278 00279 if (!data) { 00280 /* Push end of sequence if not already signalled. */ 00281 if (!p_schro_params->eos_signalled) { 00282 schro_encoder_end_of_stream(encoder); 00283 p_schro_params->eos_signalled = 1; 00284 } 00285 } else { 00286 /* Allocate frame data to schro input buffer. */ 00287 SchroFrame *in_frame = libschroedinger_frame_from_data(avccontext, 00288 data); 00289 /* Load next frame. */ 00290 schro_encoder_push_frame(encoder, in_frame); 00291 } 00292 00293 if (p_schro_params->eos_pulled) 00294 go = 0; 00295 00296 /* Now check to see if we have any output from the encoder. */ 00297 while (go) { 00298 SchroStateEnum state; 00299 state = schro_encoder_wait(encoder); 00300 switch (state) { 00301 case SCHRO_STATE_HAVE_BUFFER: 00302 case SCHRO_STATE_END_OF_STREAM: 00303 enc_buf = schro_encoder_pull(encoder, &presentation_frame); 00304 assert(enc_buf->length > 0); 00305 assert(enc_buf->length <= buf_size); 00306 parse_code = enc_buf->data[4]; 00307 00308 /* All non-frame data is prepended to actual frame data to 00309 * be able to set the pts correctly. So we don't write data 00310 * to the frame output queue until we actually have a frame 00311 */ 00312 p_schro_params->enc_buf = av_realloc(p_schro_params->enc_buf, 00313 p_schro_params->enc_buf_size + enc_buf->length); 00314 00315 memcpy(p_schro_params->enc_buf + p_schro_params->enc_buf_size, 00316 enc_buf->data, enc_buf->length); 00317 p_schro_params->enc_buf_size += enc_buf->length; 00318 00319 00320 if (state == SCHRO_STATE_END_OF_STREAM) { 00321 p_schro_params->eos_pulled = 1; 00322 go = 0; 00323 } 00324 00325 if (!SCHRO_PARSE_CODE_IS_PICTURE(parse_code)) { 00326 schro_buffer_unref(enc_buf); 00327 break; 00328 } 00329 00330 /* Create output frame. */ 00331 p_frame_output = av_mallocz(sizeof(FfmpegDiracSchroEncodedFrame)); 00332 /* Set output data. */ 00333 p_frame_output->size = p_schro_params->enc_buf_size; 00334 p_frame_output->p_encbuf = p_schro_params->enc_buf; 00335 if (SCHRO_PARSE_CODE_IS_INTRA(parse_code) && 00336 SCHRO_PARSE_CODE_IS_REFERENCE(parse_code)) 00337 p_frame_output->key_frame = 1; 00338 00339 /* Parse the coded frame number from the bitstream. Bytes 14 00340 * through 17 represesent the frame number. */ 00341 p_frame_output->frame_num = AV_RB32(enc_buf->data + 13); 00342 00343 ff_dirac_schro_queue_push_back(&p_schro_params->enc_frame_queue, 00344 p_frame_output); 00345 p_schro_params->enc_buf_size = 0; 00346 p_schro_params->enc_buf = NULL; 00347 00348 schro_buffer_unref(enc_buf); 00349 00350 break; 00351 00352 case SCHRO_STATE_NEED_FRAME: 00353 go = 0; 00354 break; 00355 00356 case SCHRO_STATE_AGAIN: 00357 break; 00358 00359 default: 00360 av_log(avccontext, AV_LOG_ERROR, "Unknown Schro Encoder state\n"); 00361 return -1; 00362 } 00363 } 00364 00365 /* Copy 'next' frame in queue. */ 00366 00367 if (p_schro_params->enc_frame_queue.size == 1 && 00368 p_schro_params->eos_pulled) 00369 last_frame_in_sequence = 1; 00370 00371 p_frame_output = ff_dirac_schro_queue_pop(&p_schro_params->enc_frame_queue); 00372 00373 if (!p_frame_output) 00374 return 0; 00375 00376 memcpy(frame, p_frame_output->p_encbuf, p_frame_output->size); 00377 avccontext->coded_frame->key_frame = p_frame_output->key_frame; 00378 /* Use the frame number of the encoded frame as the pts. It is OK to 00379 * do so since Dirac is a constant frame rate codec. It expects input 00380 * to be of constant frame rate. */ 00381 avccontext->coded_frame->pts = p_frame_output->frame_num; 00382 enc_size = p_frame_output->size; 00383 00384 /* Append the end of sequence information to the last frame in the 00385 * sequence. */ 00386 if (last_frame_in_sequence && p_schro_params->enc_buf_size > 0) { 00387 memcpy(frame + enc_size, p_schro_params->enc_buf, 00388 p_schro_params->enc_buf_size); 00389 enc_size += p_schro_params->enc_buf_size; 00390 av_freep(&p_schro_params->enc_buf); 00391 p_schro_params->enc_buf_size = 0; 00392 } 00393 00394 /* free frame */ 00395 SchroedingerFreeFrame(p_frame_output); 00396 00397 return enc_size; 00398 } 00399 00400 00401 static int libschroedinger_encode_close(AVCodecContext *avccontext) 00402 { 00403 00404 FfmpegSchroEncoderParams* p_schro_params = avccontext->priv_data; 00405 00406 /* Close the encoder. */ 00407 schro_encoder_free(p_schro_params->encoder); 00408 00409 /* Free data in the output frame queue. */ 00410 ff_dirac_schro_queue_free(&p_schro_params->enc_frame_queue, 00411 SchroedingerFreeFrame); 00412 00413 00414 /* Free the encoder buffer. */ 00415 if (p_schro_params->enc_buf_size) 00416 av_freep(&p_schro_params->enc_buf); 00417 00418 /* Free the video format structure. */ 00419 av_freep(&p_schro_params->format); 00420 00421 return 0; 00422 } 00423 00424 00425 AVCodec ff_libschroedinger_encoder = { 00426 "libschroedinger", 00427 AVMEDIA_TYPE_VIDEO, 00428 CODEC_ID_DIRAC, 00429 sizeof(FfmpegSchroEncoderParams), 00430 libschroedinger_encode_init, 00431 libschroedinger_encode_frame, 00432 libschroedinger_encode_close, 00433 .capabilities = CODEC_CAP_DELAY, 00434 .pix_fmts = (const enum PixelFormat[]){PIX_FMT_YUV420P, PIX_FMT_YUV422P, PIX_FMT_YUV444P, PIX_FMT_NONE}, 00435 .long_name = NULL_IF_CONFIG_SMALL("libschroedinger Dirac 2.2"), 00436 };