Ignore:
Timestamp:
Mar 31, 2011 5:29:54 PM (14 years ago)
Author:
nanang
Message:

Re #1219:

  • Initial version of H264 implementation (codec & packetization).
  • Added vid_codec_util.h/c for video codec utilities (e.g: fmtp parser).
  • Updated video RTP packetizations to be configurable and have internal state (to be more resilient to packet lost, etc).
  • Fixed wrong SPF calculation in PJMEDIA_SPF2.
  • Updated vid_codec_test.c to also have RTP packetization test.
  • Updated sdp_neg.c to verify H.264 capability match.
File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/branches/projects/2.0-dev/pjmedia/src/pjmedia-codec/ffmpeg_codecs.c

    r3469 r3493  
    1919#include <pjmedia-codec/ffmpeg_codecs.h> 
    2020#include <pjmedia-codec/h263_packetizer.h> 
     21#include <pjmedia-codec/h264_packetizer.h> 
    2122#include <pjmedia/errno.h> 
     23#include <pjmedia/vid_codec_util.h> 
    2224#include <pj/assert.h> 
    2325#include <pj/list.h> 
     
    3941#include <libavcodec/avcodec.h> 
    4042#include <libavformat/avformat.h> 
    41 #include <libswscale/swscale.h> 
    42  
    43  
    44 #define PJMEDIA_FORMAT_FFMPEG_UNKNOWN  PJMEDIA_FORMAT_PACK('f','f','0','0'); 
    4543 
    4644 
     
    8078                                       pj_size_t   payload_len, 
    8179                                       pj_uint8_t *buf, 
    82                                        pj_size_t  *buf_len); 
     80                                       pj_size_t   buf_len, 
     81                                       unsigned   *pos); 
    8382static pj_status_t  ffmpeg_codec_encode( pjmedia_vid_codec *codec,  
    8483                                         const pjmedia_frame *input, 
     
    131130typedef struct ffmpeg_codec_desc ffmpeg_codec_desc; 
    132131 
    133 /* ITU resolution ID */ 
    134 typedef enum itu_res_id { 
    135     ITU_RES_SQCIF, 
    136     ITU_RES_QCIF, 
    137     ITU_RES_CIF, 
    138     ITU_RES_4CIF, 
    139     ITU_RES_16CIF, 
    140     ITU_RES_CUSTOM, 
    141 } itu_res_id; 
    142  
    143 /* ITU resolution definition */ 
    144 struct itu_res { 
    145     itu_res_id          id; 
    146     pj_str_t            name;     
    147     pjmedia_rect_size   size; 
    148 } itu_res_def [] = 
    149 { 
    150     {ITU_RES_16CIF,     {"16CIF",5},    {1408,1142}}, 
    151     {ITU_RES_4CIF,      {"4CIF",4},     {704,576}}, 
    152     {ITU_RES_CIF,       {"CIF",3},      {352,288}}, 
    153     {ITU_RES_QCIF,      {"QCIF",4},     {176,144}}, 
    154     {ITU_RES_SQCIF,     {"SQCIF",5},    {88,72}}, 
    155     {ITU_RES_CUSTOM,    {"CUSTOM",6},   {0,0}}, 
    156 }; 
    157132 
    158133/* FFMPEG codecs private data. */ 
    159 typedef struct ffmpeg_private { 
     134typedef struct ffmpeg_private 
     135{ 
    160136    const ffmpeg_codec_desc         *desc; 
    161137    pjmedia_vid_codec_param          param;     /**< Codec param            */ 
     
    180156     */ 
    181157    enum PixelFormat                 expected_dec_fmt; 
    182                                                 /**< expected output format of  
     158                                                /**< Expected output format of  
    183159                                                     ffmpeg decoder         */ 
     160 
     161    void                            *data;      /**< Codec specific data    */               
    184162} ffmpeg_private; 
    185163 
    186164 
    187 typedef pj_status_t (*func_packetize)   (pj_uint8_t *buf, 
    188                                          pj_size_t buf_len, 
    189                                          unsigned *pos, 
    190                                          int max_payload_len, 
    191                                          const pj_uint8_t **payload, 
    192                                          pj_size_t *payload_len); 
    193  
    194 typedef pj_status_t (*func_unpacketize) (const pj_uint8_t *payload, 
    195                                          pj_size_t   payload_len, 
    196                                          pj_uint8_t *bits, 
    197                                          pj_size_t  *bits_len); 
    198  
    199 typedef pj_status_t (*func_parse_fmtp)  (ffmpeg_private *ff); 
     165/* Shortcuts for packetize & unpacketize function declaration, 
     166 * as it has long params and is reused many times! 
     167 */ 
     168#define FUNC_PACKETIZE(name) \ 
     169    pj_status_t(name)(ffmpeg_private *ff, pj_uint8_t *bits, \ 
     170                      pj_size_t bits_len, unsigned *bits_pos, \ 
     171                      const pj_uint8_t **payload, pj_size_t *payload_len) 
     172 
     173#define FUNC_UNPACKETIZE(name) \ 
     174    pj_status_t(name)(ffmpeg_private *ff, const pj_uint8_t *payload, \ 
     175                      pj_size_t payload_len, pj_uint8_t *bits, \ 
     176                      pj_size_t bits_len, unsigned *bits_pos) 
     177 
     178typedef FUNC_PACKETIZE(*func_packetize); 
     179typedef FUNC_UNPACKETIZE(*func_unpacketize); 
     180typedef pj_status_t (*func_preopen)     (ffmpeg_private *ff); 
     181typedef pj_status_t (*func_postopen)    (ffmpeg_private *ff); 
     182 
    200183 
    201184/* FFMPEG codec info */ 
    202 struct ffmpeg_codec_desc { 
     185struct ffmpeg_codec_desc 
     186{ 
    203187    /* Predefined info */ 
    204188    pjmedia_vid_codec_info       info; 
     
    208192    func_packetize               packetize; 
    209193    func_unpacketize             unpacketize; 
    210     func_parse_fmtp              parse_fmtp; 
     194    func_preopen                 preopen; 
     195    func_preopen                 postopen; 
    211196    pjmedia_codec_fmtp           dec_fmtp; 
    212197 
     
    217202}; 
    218203 
    219 /* H263 packetizer */ 
    220 static pj_status_t h263_packetize(pj_uint8_t *buf, 
    221                                   pj_size_t buf_len, 
    222                                   unsigned *pos, 
    223                                   int max_payload_len, 
    224                                   const pj_uint8_t **payload, 
    225                                   pj_size_t *payload_len) 
    226 { 
    227     return pjmedia_h263_packetize(buf, buf_len, pos, max_payload_len,  
    228                                   payload, payload_len); 
    229 } 
    230  
    231 /* H263 unpacketizer */ 
    232 static pj_status_t h263_unpacketize(const pj_uint8_t *payload, 
    233                                     pj_size_t   payload_len, 
    234                                     pj_uint8_t *bits, 
    235                                     pj_size_t  *bits_len) 
    236 { 
    237     return pjmedia_h263_unpacketize(payload, payload_len, bits, bits_len); 
    238 } 
    239  
    240 /* H263 fmtp parser */ 
    241 static pj_status_t h263_parse_fmtp(ffmpeg_private *ff); 
     204 
     205/* Codec specific functions */ 
     206static pj_status_t h264_preopen(ffmpeg_private *ff); 
     207static pj_status_t h264_postopen(ffmpeg_private *ff); 
     208static pj_status_t h263_preopen(ffmpeg_private *ff); 
     209static FUNC_PACKETIZE(h264_packetize); 
     210static FUNC_UNPACKETIZE(h264_unpacketize); 
     211static FUNC_PACKETIZE(h263_packetize); 
     212static FUNC_UNPACKETIZE(h263_unpacketize); 
    242213 
    243214 
     
    245216ffmpeg_codec_desc codec_desc[] = 
    246217{ 
     218    { 
     219        {PJMEDIA_FORMAT_H264,   {"H264",4},         PJMEDIA_RTP_PT_H264}, 
     220        0,      500000,    1000000, 
     221        &h264_packetize, &h264_unpacketize, &h264_preopen, &h264_postopen, 
     222        /* Leading space for better compatibility (strange indeed!) */ 
     223        {2, { {{" profile-level-id",17},    {"42e01e",6}},  
     224              {{" packetization-mode",19},  {"1",1}}, } }, 
     225    }, 
    247226    { 
    248227        {PJMEDIA_FORMAT_H263P,  {"H263-1998",9},    PJMEDIA_RTP_PT_H263P}, 
    249228        PJMEDIA_FORMAT_H263,    1000000,    2000000, 
    250         &h263_packetize, &h263_unpacketize, &h263_parse_fmtp, 
    251         {2, { {{"CIF",3}, {"2",1}}, {{"QCIF",4}, {"1",1}}, } }, 
     229        &h263_packetize, &h263_unpacketize, &h263_preopen, NULL, 
     230        {2, { {{"CIF",3},   {"1",1}},  
     231              {{"QCIF",4},  {"1",1}}, } }, 
    252232    }, 
    253233    { 
    254234        {PJMEDIA_FORMAT_H263,   {"H263",4},         PJMEDIA_RTP_PT_H263}, 
    255     }, 
    256     { 
    257         {PJMEDIA_FORMAT_H264,   {"H264",4},         PJMEDIA_RTP_PT_H264}, 
    258235    }, 
    259236    { 
     
    272249}; 
    273250 
    274 /* Parse fmtp value for custom resolution, e.g: "CUSTOM=800,600,2" */ 
    275 static pj_status_t parse_fmtp_itu_custom_res(const pj_str_t *fmtp_val, 
    276                                              pjmedia_rect_size *size, 
    277                                              unsigned *mpi) 
    278 { 
    279     const char *p, *p_end; 
    280     pj_str_t token; 
    281     unsigned long val[3] = {0}; 
    282     unsigned i = 0; 
    283  
    284     p = token.ptr = fmtp_val->ptr; 
    285     p_end = p + fmtp_val->slen; 
    286  
    287     while (p<=p_end && i<PJ_ARRAY_SIZE(val)) { 
    288         if (*p==',' || p==p_end) { 
    289             token.slen = (char*)p - token.ptr; 
    290             val[i++] = pj_strtoul(&token); 
    291             token.ptr = (char*)p+1; 
     251 
     252typedef struct h264_data 
     253{ 
     254    pjmedia_vid_codec_h264_fmtp  fmtp; 
     255    pjmedia_h264_packetizer     *pktz; 
     256} h264_data; 
     257 
     258 
     259static pj_status_t h264_preopen(ffmpeg_private *ff) 
     260{ 
     261    h264_data *data; 
     262    pjmedia_h264_packetizer_cfg pktz_cfg; 
     263    pj_status_t status; 
     264 
     265    data = PJ_POOL_ZALLOC_T(ff->pool, h264_data); 
     266    ff->data = data; 
     267 
     268    /* Create packetizer */ 
     269    pktz_cfg.mtu = ff->param.enc_mtu; 
     270    pktz_cfg.mode = PJMEDIA_H264_PACKETIZER_MODE_NON_INTERLEAVED; 
     271    status = pjmedia_h264_packetizer_create(ff->pool, &pktz_cfg, &data->pktz); 
     272    if (status != PJ_SUCCESS) 
     273        return status; 
     274 
     275    if (ff->param.dir & PJMEDIA_DIR_ENCODING) { 
     276        AVCodecContext *ctx = ff->enc_ctx; 
     277 
     278        status = pjmedia_vid_codec_parse_h264_fmtp(&ff->param.enc_fmtp, 
     279                                                   &data->fmtp); 
     280        if (status != PJ_SUCCESS) 
     281            return status; 
     282 
     283        ctx->profile  = data->fmtp.profile_idc; 
     284        if (data->fmtp.profile_iop) { 
     285#if defined(FF_PROFILE_H264_CONSTRAINED) 
     286            ctx->profile |= FF_PROFILE_H264_CONSTRAINED; 
     287#endif 
    292288        } 
    293         ++p; 
    294     } 
    295  
    296     if (!val[0] || !val[1]) 
    297         return PJ_ETOOSMALL; 
    298  
    299     if (val[2]<1 || val[2]>32) 
    300         return PJ_EINVAL; 
    301  
    302     size->w = val[0]; 
    303     size->h = val[1]; 
    304     *mpi = val[2]; 
    305     return PJ_SUCCESS; 
    306 } 
    307  
    308 #define CALC_ITU_CUSTOM_RES_SCORE(size, mpi) ((size)->w * (size)->h / mpi) 
    309  
    310 /* ITU codec capabilities */ 
    311 typedef struct itu_cap 
    312 { 
    313     /* Lowest MPI for each non-custom resolution */ 
    314     unsigned            lowest_mpi[PJ_ARRAY_SIZE(itu_res_def)]; 
    315     /* For custom resolution, we use maximum processing score */ 
    316     unsigned            custom_res_max_score; 
    317 } itu_cap; 
    318  
    319  
    320 static pj_status_t load_itu_cap(const pjmedia_codec_fmtp *fmtp, 
    321                                 itu_cap *cap) 
    322 { 
    323     unsigned i, j; 
    324     unsigned min_mpi = 0; 
    325  
    326     /* Get Minimum Picture Interval (MPI) for each resolution. If a resolution 
    327      * has no MPI setting in fmtp, the MPI setting is derived from the higher 
    328      * resolution. 
    329      */ 
    330     for (i=0; i<PJ_ARRAY_SIZE(itu_res_def); ++i) { 
    331  
    332         /* Init lowest MPI */ 
    333         cap->lowest_mpi[i] = min_mpi? min_mpi:1; 
    334  
    335         for (j=0; j<fmtp->cnt; ++j) { 
    336             if (pj_stricmp(&fmtp->param[j].name, &itu_res_def[i].name)==0) { 
    337                 pjmedia_rect_size size; 
    338                 unsigned mpi; 
    339                 unsigned score; 
    340  
    341                 if (i != ITU_RES_CUSTOM) { 
    342                     size = itu_res_def[i].size; 
    343                     mpi = pj_strtoul(&fmtp->param[j].val); 
    344                     if (min_mpi) 
    345                         min_mpi = PJ_MIN(mpi, min_mpi); 
    346                     else 
    347                         min_mpi = mpi; 
    348  
    349                     /* Update the lowest MPI for this resolution */ 
    350                     cap->lowest_mpi[i] = min_mpi; 
    351  
    352                     /* Also update the processing score for the custom  
    353                      * resolution. 
    354                      */ 
    355                     score = CALC_ITU_CUSTOM_RES_SCORE(&size, mpi); 
    356                     cap->custom_res_max_score =  
    357                                     PJ_MAX(score, cap->custom_res_max_score); 
    358                 } else { 
    359                      
    360  
    361                     if (parse_fmtp_itu_custom_res(&fmtp->param[j].val,  
    362                                                   &size, &mpi) == PJ_SUCCESS) 
    363                     { 
    364                         score = CALC_ITU_CUSTOM_RES_SCORE(&size, mpi); 
    365                         cap->custom_res_max_score =  
    366                                     PJ_MAX(score, cap->custom_res_max_score); 
    367                     } 
    368                 } 
    369             } 
    370         } 
    371     } 
    372  
    373     return PJ_SUCCESS; 
    374 } 
    375  
    376 /* H263 fmtp parser */ 
    377 static pj_status_t h263_parse_fmtp(ffmpeg_private *ff) 
    378 { 
    379     pjmedia_dir dir; 
     289        ctx->level    = data->fmtp.level; 
     290        PJ_TODO(set_h264_constrain_bits_properly_in_ffmpeg); 
     291 
     292        /* Libx264 rejects the "broken" ffmpeg defaults, so just change some */ 
     293        ctx->me_range = 16; 
     294        ctx->max_qdiff = 4; 
     295        ctx->qmin = 10; 
     296        ctx->qmax = 51; 
     297        ctx->qcompress = 0.6f; 
     298 
     299        ctx->flags |= CODEC_FLAG_LOW_DELAY; 
     300    } 
     301 
     302    return PJ_SUCCESS; 
     303} 
     304 
     305static pj_status_t h264_postopen(ffmpeg_private *ff) 
     306{ 
     307    h264_data *data = (h264_data*)ff->data; 
     308    PJ_UNUSED_ARG(data); 
     309 
     310    // Where to apply the "sprop-parameter-sets" fmtp from remote SDP? 
     311    // Through decoder decode() or decoder context extradata? 
     312    PJ_TODO(apply_h264_fmtp_sprop_parameter_sets_from_remote_sdp); 
     313 
     314    return PJ_SUCCESS; 
     315} 
     316 
     317 
     318static FUNC_PACKETIZE(h264_packetize) 
     319{ 
     320    h264_data *data = (h264_data*)ff->data; 
     321    return pjmedia_h264_packetize(data->pktz, bits, bits_len, bits_pos, 
     322                                  payload, payload_len); 
     323} 
     324 
     325static FUNC_UNPACKETIZE(h264_unpacketize) 
     326{ 
     327    h264_data *data = (h264_data*)ff->data; 
     328    return pjmedia_h264_unpacketize(data->pktz, payload, payload_len, 
     329                                    bits, bits_len, bits_pos); 
     330} 
     331 
     332 
     333typedef struct h263_data 
     334{ 
     335    pjmedia_h263_packetizer     *pktz; 
     336} h263_data; 
     337 
     338/* H263 pre-open */ 
     339static pj_status_t h263_preopen(ffmpeg_private *ff) 
     340{ 
     341    h263_data *data; 
     342    pjmedia_h263_packetizer_cfg pktz_cfg; 
    380343    pj_status_t status; 
    381344 
    382     dir = ff->param.dir; 
    383  
    384     if (ff->param.dir & PJMEDIA_DIR_ENCODING) { 
    385         pjmedia_vid_codec_param param_ref; 
    386         pjmedia_codec_fmtp *fmtp_rem, *fmtp_ref; 
    387         itu_cap local_cap; 
    388         pjmedia_rect_size size = {0}; 
    389         unsigned mpi = 0; 
    390         pj_bool_t got_good_res = PJ_FALSE; 
    391         pj_bool_t has_prefered_res = PJ_FALSE; 
    392         unsigned i, j; 
    393  
    394         fmtp_rem = &ff->param.enc_fmtp; 
    395         dir &= ~PJMEDIA_DIR_ENCODING; 
    396  
    397         /* Get default fmtp setting as the reference for local capabilities */ 
    398         status = pjmedia_vid_codec_mgr_get_default_param( 
    399                         ffmpeg_factory.mgr, &ff->desc->info, &param_ref); 
    400         fmtp_ref = (status==PJ_SUCCESS)? &param_ref.enc_fmtp : fmtp_rem; 
    401  
    402         /* Load default local capabilities */ 
    403         status = load_itu_cap(fmtp_ref, &local_cap); 
    404         pj_assert(status == PJ_SUCCESS); 
    405  
    406         /* Negotiate resolution and MPI */ 
    407         for (i=0; i<fmtp_rem->cnt && !got_good_res; ++i) 
    408         { 
    409             for (j=0; j<PJ_ARRAY_SIZE(itu_res_def) && !got_good_res; ++j) 
    410             { 
    411                 if (pj_stricmp(&fmtp_rem->param[i].name, &itu_res_def[j].name)) 
    412                     continue; 
    413  
    414                 has_prefered_res = PJ_TRUE; 
    415                 if (j == ITU_RES_CUSTOM) { 
    416                     unsigned score; 
    417  
    418                     if (parse_fmtp_itu_custom_res(&fmtp_rem->param[i].val,  
    419                                                   &size, &mpi) != PJ_SUCCESS) 
    420                     { 
    421                         /* Invalid custom resolution format, skip this  
    422                          * custom resolution 
    423                          */ 
    424                         break; 
    425                     } 
    426  
    427                     score = CALC_ITU_CUSTOM_RES_SCORE(&size, mpi); 
    428                     if (score <= local_cap.custom_res_max_score) 
    429                         got_good_res = PJ_TRUE; 
    430                 } else { 
    431                     mpi = pj_strtoul(&fmtp_rem->param[i].val); 
    432                     if (mpi>=1 && mpi<=32 && mpi>=local_cap.lowest_mpi[j]) { 
    433                         got_good_res = PJ_TRUE; 
    434                         size = itu_res_def[j].size; 
    435                     } 
    436                 } 
    437             } 
    438         } 
    439  
    440         if (has_prefered_res) { 
    441             if (got_good_res) { 
    442                 pjmedia_video_format_detail *vfd; 
    443  
    444                 /* Apply this size & MPI */ 
    445                 vfd = pjmedia_format_get_video_format_detail(&ff->param.enc_fmt, 
    446                                                              PJ_TRUE); 
    447                 vfd->size = size; 
    448                 vfd->fps.num = 30000; 
    449                 vfd->fps.denum = 1001 * mpi; 
    450                 got_good_res = PJ_TRUE; 
    451  
    452                 PJ_TODO(NOTIFY_APP_ABOUT_THIS_NEW_ENCODING_FORMAT); 
    453             } else { 
    454                 return PJMEDIA_EBADFMT; 
    455             } 
    456         } 
    457     } 
    458  
    459     return PJ_SUCCESS; 
    460 } 
    461  
     345    data = PJ_POOL_ZALLOC_T(ff->pool, h263_data); 
     346    ff->data = data; 
     347 
     348    /* Create packetizer */ 
     349    pktz_cfg.mtu = ff->param.enc_mtu; 
     350    pktz_cfg.mode = PJMEDIA_H263_PACKETIZER_MODE_RFC4629; 
     351    status = pjmedia_h263_packetizer_create(ff->pool, &pktz_cfg, &data->pktz); 
     352    if (status != PJ_SUCCESS) 
     353        return status; 
     354 
     355    /* Apply fmtp settings to codec param */ 
     356    status = pjmedia_vid_codec_h263_apply_fmtp(&ff->param); 
     357 
     358    return status; 
     359} 
     360 
     361static FUNC_PACKETIZE(h263_packetize) 
     362{ 
     363    h263_data *data = (h263_data*)ff->data; 
     364    return pjmedia_h263_packetize(data->pktz, bits, bits_len, bits_pos, 
     365                                  payload, payload_len); 
     366} 
     367 
     368static FUNC_UNPACKETIZE(h263_unpacketize) 
     369{ 
     370    h263_data *data = (h263_data*)ff->data; 
     371    return pjmedia_h263_unpacketize(data->pktz, payload, payload_len, 
     372                                    bits, bits_len, bits_pos); 
     373} 
    462374 
    463375 
     
    810722    attr->enc_fmt.det.vid.max_bps = desc->max_bps; 
    811723 
     724    /* MTU */ 
     725    attr->enc_mtu = PJMEDIA_MAX_MTU; 
     726 
    812727    return PJ_SUCCESS; 
    813728} 
     
    934849 
    935850static enum PixelFormat dec_get_format(struct AVCodecContext *s,  
    936                                           const enum PixelFormat * fmt) 
     851                                       const enum PixelFormat * fmt) 
    937852{ 
    938853    ffmpeg_private *ff = (ffmpeg_private*)s->opaque; 
     
    954869{ 
    955870    enum PixelFormat pix_fmt; 
     871    pjmedia_video_format_detail *vfd; 
     872    pj_bool_t enc_opened = PJ_FALSE, dec_opened = PJ_FALSE; 
    956873    pj_status_t status; 
    957     pjmedia_video_format_detail *vfd; 
    958  
     874 
     875    /* Get decoded pixel format */ 
    959876    status = pjmedia_format_id_to_PixelFormat(ff->param.dec_fmt.id, 
    960877                                              &pix_fmt); 
    961878    if (status != PJ_SUCCESS) 
    962879        return status; 
    963  
     880    ff->expected_dec_fmt = pix_fmt; 
     881 
     882    /* Get video format detail for shortcut access to encoded format */ 
    964883    vfd = pjmedia_format_get_video_format_detail(&ff->param.enc_fmt,  
    965884                                                 PJ_TRUE); 
    966     ff->expected_dec_fmt = pix_fmt; 
    967  
    968     while (((ff->param.dir & PJMEDIA_DIR_ENCODING) && ff->enc_ctx == NULL) || 
    969            ((ff->param.dir & PJMEDIA_DIR_DECODING) && ff->dec_ctx == NULL)) 
    970     { 
    971         pjmedia_dir dir; 
    972         AVCodecContext *ctx = NULL; 
    973         AVCodec *codec = NULL; 
     885 
     886    /* Allocate ffmpeg codec context */ 
     887    if (ff->param.dir & PJMEDIA_DIR_ENCODING) { 
     888        ff->enc_ctx = avcodec_alloc_context(); 
     889        if (ff->enc_ctx == NULL) 
     890            goto on_error; 
     891    } 
     892    if (ff->param.dir & PJMEDIA_DIR_DECODING) { 
     893        ff->dec_ctx = avcodec_alloc_context(); 
     894        if (ff->dec_ctx == NULL) 
     895            goto on_error; 
     896    } 
     897 
     898    /* Let the codec apply specific settings before the codec opened */ 
     899    if (ff->desc->preopen) { 
     900        status = (*ff->desc->preopen)(ff); 
     901        if (status != PJ_SUCCESS) 
     902            goto on_error; 
     903    } 
     904 
     905    if (ff->param.dir & PJMEDIA_DIR_ENCODING) { 
     906        AVCodecContext *ctx = ff->enc_ctx; 
    974907        int err; 
    975908 
    976         /* Set which direction to open */ 
    977         if (ff->param.dir==PJMEDIA_DIR_ENCODING_DECODING && ff->enc!=ff->dec) { 
    978             dir = ff->enc_ctx? PJMEDIA_DIR_DECODING : PJMEDIA_DIR_ENCODING; 
    979         } else { 
    980             dir = ff->param.dir; 
    981         } 
    982  
    983         /* Init ffmpeg codec context */ 
    984         ctx = avcodec_alloc_context(); 
    985  
    986         /* Common attributes */ 
     909        /* Init common settings */ 
    987910        ctx->pix_fmt = pix_fmt; 
     911        ctx->width = vfd->size.w; 
     912        ctx->height = vfd->size.h; 
     913        ctx->time_base.num = vfd->fps.denum; 
     914        ctx->time_base.den = vfd->fps.num; 
     915        if (vfd->avg_bps) { 
     916            ctx->bit_rate = vfd->avg_bps; 
     917            if (vfd->max_bps > vfd->avg_bps) 
     918                ctx->bit_rate_tolerance = vfd->max_bps - vfd->avg_bps; 
     919        } 
     920        ctx->strict_std_compliance = FF_COMPLIANCE_STRICT; 
    988921        ctx->workaround_bugs = FF_BUG_AUTODETECT; 
    989922        ctx->opaque = ff; 
    990923 
    991         if (dir & PJMEDIA_DIR_ENCODING) { 
    992             codec = ff->enc; 
    993  
    994             /* Encoding only attributes */ 
    995             ctx->width = vfd->size.w; 
    996             ctx->height = vfd->size.h; 
    997             ctx->time_base.num = vfd->fps.denum; 
    998             ctx->time_base.den = vfd->fps.num; 
    999             if (vfd->avg_bps) { 
    1000                 ctx->bit_rate = vfd->avg_bps; 
    1001                 if (vfd->max_bps > vfd->avg_bps) 
    1002                     ctx->bit_rate_tolerance = vfd->max_bps - vfd->avg_bps; 
    1003             } 
    1004  
    1005             /* Libx264 experimental setting (it rejects ffmpeg defaults) */ 
    1006             if (ff->param.enc_fmt.id == PJMEDIA_FORMAT_H264) { 
    1007                 ctx->me_range = 16; 
    1008                 ctx->max_qdiff = 4; 
    1009                 ctx->qmin = 10; 
    1010                 ctx->qmax = 51; 
    1011                 ctx->qcompress = 0.6f; 
    1012             } 
    1013  
    1014             /* For encoder, should be better to be strict to the standards */ 
    1015             ctx->strict_std_compliance = FF_COMPLIANCE_STRICT; 
    1016         } 
    1017  
    1018         if (dir & PJMEDIA_DIR_DECODING) { 
    1019             codec = ff->dec; 
    1020  
    1021             /* Decoding only attributes */ 
    1022  
    1023             /* Width/height may be overriden by ffmpeg after first decoding. */ 
    1024             ctx->width = ctx->coded_width = ff->param.dec_fmt.det.vid.size.w; 
    1025             ctx->height = ctx->coded_height = ff->param.dec_fmt.det.vid.size.h; 
    1026  
    1027             /* For decoder, be more flexible */ 
    1028             if (ff->param.dir!=PJMEDIA_DIR_ENCODING_DECODING ||  
    1029                 ff->enc!=ff->dec) 
    1030             { 
    1031                 ctx->strict_std_compliance = FF_COMPLIANCE_EXPERIMENTAL; 
    1032             } 
    1033  
    1034             ctx->get_format = &dec_get_format; 
    1035         } 
    1036  
    1037         /* avcodec_open() should be protected */ 
     924        /* Open ffmpeg codec */ 
    1038925        pj_mutex_lock(ff_mutex); 
    1039         err = avcodec_open(ctx, codec); 
     926        err = avcodec_open(ctx, ff->enc); 
    1040927        pj_mutex_unlock(ff_mutex); 
    1041928        if (err < 0) { 
    1042929            print_ffmpeg_err(err); 
    1043             return PJMEDIA_CODEC_EFAILED; 
     930            status = PJMEDIA_CODEC_EFAILED; 
     931            goto on_error; 
    1044932        } 
    1045  
    1046         if (dir & PJMEDIA_DIR_ENCODING) 
    1047             ff->enc_ctx = ctx; 
    1048         if (dir & PJMEDIA_DIR_DECODING) 
    1049             ff->dec_ctx = ctx; 
    1050     } 
    1051      
    1052     return PJ_SUCCESS; 
     933        enc_opened = PJ_TRUE; 
     934    } 
     935 
     936    if (ff->param.dir & PJMEDIA_DIR_DECODING) { 
     937        AVCodecContext *ctx = ff->dec_ctx; 
     938        int err; 
     939 
     940        /* Init common settings */ 
     941        /* Width/height may be overriden by ffmpeg after first decoding. */ 
     942        ctx->width  = ctx->coded_width  = ff->param.dec_fmt.det.vid.size.w; 
     943        ctx->height = ctx->coded_height = ff->param.dec_fmt.det.vid.size.h; 
     944        ctx->strict_std_compliance = FF_COMPLIANCE_EXPERIMENTAL; 
     945        ctx->workaround_bugs = FF_BUG_AUTODETECT; 
     946        ctx->opaque = ff; 
     947        ctx->get_format = &dec_get_format; 
     948 
     949        /* Open ffmpeg codec */ 
     950        pj_mutex_lock(ff_mutex); 
     951        err = avcodec_open(ctx, ff->dec); 
     952        pj_mutex_unlock(ff_mutex); 
     953        if (err < 0) { 
     954            print_ffmpeg_err(err); 
     955            status = PJMEDIA_CODEC_EFAILED; 
     956            goto on_error; 
     957        } 
     958        dec_opened = PJ_TRUE; 
     959    } 
     960 
     961    /* Let the codec apply specific settings after the codec opened */ 
     962    if (ff->desc->postopen) { 
     963        status = (*ff->desc->postopen)(ff); 
     964        if (status != PJ_SUCCESS) 
     965            goto on_error; 
     966    } 
     967 
     968    return PJ_SUCCESS; 
     969 
     970on_error: 
     971    if (ff->enc_ctx) { 
     972        if (enc_opened) 
     973            avcodec_close(ff->enc_ctx); 
     974        av_free(ff->enc_ctx); 
     975        ff->enc_ctx = NULL; 
     976    } 
     977    if (ff->dec_ctx) { 
     978        if (dec_opened) 
     979            avcodec_close(ff->dec_ctx); 
     980        av_free(ff->dec_ctx); 
     981        ff->dec_ctx = NULL; 
     982    } 
     983    return status; 
    1053984} 
    1054985 
     
    1067998 
    1068999    pj_memcpy(&ff->param, attr, sizeof(*attr)); 
    1069  
    1070     /* Apply SDP fmtp attribute */ 
    1071     if (ff->desc->parse_fmtp) { 
    1072         status = (*ff->desc->parse_fmtp)(ff); 
    1073         if (status != PJ_SUCCESS) 
    1074             goto on_error; 
    1075     } 
    10761000 
    10771001    /* Open the codec */ 
     
    11791103 
    11801104static pj_status_t  ffmpeg_packetize ( pjmedia_vid_codec *codec, 
    1181                                        pj_uint8_t *buf, 
    1182                                        pj_size_t buf_len, 
    1183                                        unsigned *pos, 
     1105                                       pj_uint8_t *bits, 
     1106                                       pj_size_t bits_len, 
     1107                                       unsigned *bits_pos, 
    11841108                                       const pj_uint8_t **payload, 
    11851109                                       pj_size_t *payload_len) 
     
    11881112 
    11891113    if (ff->desc->packetize) { 
    1190         return (*ff->desc->packetize)(buf, buf_len, pos, 
    1191                                       ff->param.enc_mtu, payload, 
    1192                                       payload_len); 
     1114        return (*ff->desc->packetize)(ff, bits, bits_len, bits_pos, 
     1115                                      payload, payload_len); 
    11931116    } 
    11941117 
     
    11991122                                       const pj_uint8_t *payload, 
    12001123                                       pj_size_t   payload_len, 
    1201                                        pj_uint8_t *buf, 
    1202                                        pj_size_t  *buf_len) 
     1124                                       pj_uint8_t *bits, 
     1125                                       pj_size_t   bits_len, 
     1126                                       unsigned   *bits_pos) 
    12031127{ 
    12041128    ffmpeg_private *ff = (ffmpeg_private*)codec->codec_data; 
    12051129 
    12061130    if (ff->desc->unpacketize) { 
    1207         return (*ff->desc->unpacketize)(payload, payload_len, 
    1208                                         buf, buf_len); 
     1131        return (*ff->desc->unpacketize)(ff, payload, payload_len, 
     1132                                        bits, bits_len, bits_pos); 
    12091133    } 
    12101134     
     
    12271151    int out_buf_len = output_buf_len; 
    12281152    int err; 
    1229  
     1153    AVRational src_timebase; 
    12301154    /* For some reasons (e.g: SSE/MMX usage), the avcodec_encode_video() must 
    12311155     * have stack aligned to 16 bytes. Let's try to be safe by preparing the 
     
    12341158    PJ_ALIGN_DATA(pj_uint32_t i[4], 16); 
    12351159 
     1160    if ((long)i & 0xF) { 
     1161        PJ_LOG(2,(THIS_FILE, "Stack alignment fails")); 
     1162    } 
     1163 
    12361164    /* Check if encoder has been opened */ 
    12371165    PJ_ASSERT_RETURN(ff->enc_ctx, PJ_EINVALIDOP); 
    12381166 
    12391167    avcodec_get_frame_defaults(&avframe); 
    1240     avframe.pts = input->timestamp.u64; 
     1168    src_timebase.num = 1; 
     1169    src_timebase.den = ff->desc->info.clock_rate; 
     1170    avframe.pts = av_rescale_q(input->timestamp.u64, src_timebase, 
     1171                               ff->enc_ctx->time_base); 
    12411172     
    12421173    for (i[0] = 0; i[0] < ff->enc_vfi->plane_cnt; ++i[0]) { 
     
    13041235 
    13051236#if LIBAVCODEC_VERSION_MAJOR >= 52 && LIBAVCODEC_VERSION_MINOR >= 72 
    1306     avpacket.flags = AV_PKT_FLAG_KEY; 
     1237    //avpacket.flags = AV_PKT_FLAG_KEY; 
    13071238#else 
    13081239    avpacket.flags = 0; 
Note: See TracChangeset for help on using the changeset viewer.