Mercurial > libavcodec.hg
diff mpegvideo.c @ 1421:340c90faa1dc libavcodec
mpeg2 encoding
author | michaelni |
---|---|
date | Mon, 25 Aug 2003 22:47:32 +0000 |
parents | 8edad1e372d1 |
children | efeed6e29f9b |
line wrap: on
line diff
--- a/mpegvideo.c Mon Aug 25 12:50:15 2003 +0000 +++ b/mpegvideo.c Mon Aug 25 22:47:32 2003 +0000 @@ -34,8 +34,8 @@ #include "fastmemcpy.h" #endif -//#undef NDEBUG -//#include <assert.h> +#undef NDEBUG +#include <assert.h> #ifdef CONFIG_ENCODERS static void encode_picture(MpegEncContext *s, int picture_number); @@ -191,7 +191,7 @@ #endif #ifdef HAVE_MMX - MPV_common_init_mmx(s); + MPV_common_init_mmx(s); //FIXME dont pass mpegenccontext to these, rather use dspcontext #endif #ifdef ARCH_ALPHA MPV_common_init_axp(s); @@ -279,7 +279,7 @@ } CHECKED_ALLOCZ(pic->mbskip_table , mb_array_size * sizeof(uint8_t)+2) //the +2 is for the slice end check - CHECKED_ALLOCZ(pic->qscale_table , mb_array_size * sizeof(uint8_t)) + CHECKED_ALLOCZ(pic->qscale_table , mb_array_size * sizeof(uint8_t)+3) //+3 for mpeg2 SIMD >>1 CHECKED_ALLOCZ(pic->mb_type_base , big_mb_num * sizeof(int)) pic->mb_type= pic->mb_type_base + s->mb_stride+1; if(s->out_format == FMT_H264){ @@ -424,7 +424,7 @@ CHECKED_ALLOCZ(s->error_status_table, mb_array_size*sizeof(uint8_t)) - if (s->out_format == FMT_H263 || s->encoding) { + if (s->out_format == FMT_H263 || s->encoding || 1) { int size; /* MV prediction */ @@ -581,7 +581,7 @@ s->data_partitioning= avctx->flags & CODEC_FLAG_PART; s->quarter_sample= (avctx->flags & CODEC_FLAG_QPEL)!=0; s->mpeg_quant= avctx->mpeg_quant; - + if (s->gop_size <= 1) { s->intra_only = 1; s->gop_size = 12; @@ -618,20 +618,20 @@ return -1; } - if(s->max_b_frames && s->codec_id != CODEC_ID_MPEG4 && s->codec_id != CODEC_ID_MPEG1VIDEO){ + if(s->max_b_frames && s->codec_id != CODEC_ID_MPEG4 && s->codec_id != CODEC_ID_MPEG1VIDEO && s->codec_id != CODEC_ID_MPEG2VIDEO){ fprintf(stderr, "b frames not supporetd by codec\n"); return -1; } - +/* if(s->mpeg_quant && s->codec_id != CODEC_ID_MPEG4){ //FIXME mpeg2 uses that too fprintf(stderr, "mpeg2 style quantization not supporetd by codec\n"); return -1; } - + */ if(s->codec_id==CODEC_ID_MJPEG){ s->intra_quant_bias= 1<<(QUANT_BIAS_SHIFT-1); //(a + x/2)/x s->inter_quant_bias= 0; - }else if(s->mpeg_quant || s->codec_id==CODEC_ID_MPEG1VIDEO){ + }else if(s->mpeg_quant || s->codec_id==CODEC_ID_MPEG1VIDEO || s->codec_id==CODEC_ID_MPEG2VIDEO){ s->intra_quant_bias= 3<<(QUANT_BIAS_SHIFT-3); //(a + x*3/8)/x s->inter_quant_bias= 0; }else{ @@ -652,6 +652,13 @@ s->low_delay= 0; //s->max_b_frames ? 0 : 1; avctx->delay= s->low_delay ? 0 : (s->max_b_frames + 1); break; + case CODEC_ID_MPEG2VIDEO: + s->out_format = FMT_MPEG1; + s->low_delay= 0; //s->max_b_frames ? 0 : 1; + avctx->delay= s->low_delay ? 0 : (s->max_b_frames + 1); + s->rtp_mode= 1; // mpeg2 must have slices + if(s->rtp_payload_size == 0) s->rtp_payload_size= 256*256*256; + break; case CODEC_ID_LJPEG: case CODEC_ID_MJPEG: s->out_format = FMT_MJPEG; @@ -820,7 +827,7 @@ s->inter_matrix[j] = ff_mpeg1_default_non_intra_matrix[i]; }else #endif - { /* mpeg1 */ + { /* mpeg1/2 */ s->intra_matrix[j] = ff_mpeg1_default_intra_matrix[i]; s->inter_matrix[j] = ff_mpeg1_default_non_intra_matrix[i]; } @@ -1002,6 +1009,7 @@ if( alloc_picture(s, (Picture*)pic, 0) < 0) return -1; + assert(pic->data[0]); s->current_picture_ptr= &s->picture[i]; } @@ -1048,12 +1056,11 @@ /* set dequantizer, we cant do it during init as it might change for mpeg4 and we cant do it in the header decode as init isnt called for mpeg4 there yet */ - if(s->out_format == FMT_H263){ - if(s->mpeg_quant) - s->dct_unquantize = s->dct_unquantize_mpeg2; - else - s->dct_unquantize = s->dct_unquantize_h263; - }else + if(s->mpeg_quant || s->codec_id == CODEC_ID_MPEG2VIDEO) + s->dct_unquantize = s->dct_unquantize_mpeg2; + else if(s->out_format == FMT_H263) + s->dct_unquantize = s->dct_unquantize_h263; + else s->dct_unquantize = s->dct_unquantize_mpeg1; #ifdef HAVE_XVMC @@ -1074,7 +1081,7 @@ XVMC_field_end(s); }else #endif - if(s->codec_id!=CODEC_ID_SVQ1 && s->codec_id != CODEC_ID_MPEG1VIDEO){ + if(s->codec_id!=CODEC_ID_SVQ1 && s->out_format != FMT_MPEG1){ if (s->pict_type != B_TYPE && !s->intra_only && !(s->flags&CODEC_FLAG_EMU_EDGE)) { draw_edges(s->current_picture.data[0], s->linesize , s->h_edge_pos , s->v_edge_pos , EDGE_WIDTH ); draw_edges(s->current_picture.data[1], s->uvlinesize, s->h_edge_pos>>1, s->v_edge_pos>>1, EDGE_WIDTH/2); @@ -2345,7 +2352,8 @@ } } break; - + default: + printf("X"); } } @@ -2523,7 +2531,7 @@ if(s->hurry_up>1) return; /* add dct residue */ - if(s->encoding || !( s->mpeg2 || s->h263_msmpeg4 || s->codec_id==CODEC_ID_MPEG1VIDEO + if(s->encoding || !( s->h263_msmpeg4 || s->codec_id==CODEC_ID_MPEG1VIDEO || s->codec_id==CODEC_ID_MPEG2VIDEO || (s->codec_id==CODEC_ID_MPEG4 && !s->mpeg_quant))){ add_dequant_dct(s, block[0], 0, dest_y, dct_linesize); add_dequant_dct(s, block[1], 1, dest_y + 8, dct_linesize); @@ -2552,7 +2560,7 @@ #endif } else { /* dct only in intra block */ - if(s->encoding || !(s->mpeg2 || s->codec_id==CODEC_ID_MPEG1VIDEO)){ + if(s->encoding || !(s->codec_id==CODEC_ID_MPEG1VIDEO || s->codec_id==CODEC_ID_MPEG2VIDEO)){ put_dct(s, block[0], 0, dest_y, dct_linesize); put_dct(s, block[1], 1, dest_y + 8, dct_linesize); put_dct(s, block[2], 2, dest_y + dct_offset, dct_linesize); @@ -2997,7 +3005,9 @@ for(i=0;i<6;i++) { if(!skip_dct[i]){ int overflow; +START_TIMER; s->block_last_index[i] = s->dct_quantize(s, s->block[i], i, s->qscale, &overflow); +STOP_TIMER("dct_quant"); // FIXME we could decide to change to quantizer instead of clipping // JS: I don't think that would be a good idea it could lower quality instead // of improve it. Just INTRADC clipping deserves changes in quantizer @@ -3023,6 +3033,7 @@ /* huffman encode */ switch(s->codec_id){ //FIXME funct ptr could be slightly faster case CODEC_ID_MPEG1VIDEO: + case CODEC_ID_MPEG2VIDEO: mpeg1_encode_mb(s, s->block, motion_x, motion_y); break; #ifdef CONFIG_RISKY case CODEC_ID_MPEG4: @@ -3316,7 +3327,8 @@ #ifdef CONFIG_RISKY /* we need to initialize some time vars before we can encode b-frames */ // RAL: Condition added for MPEG1VIDEO - if (s->codec_id == CODEC_ID_MPEG1VIDEO || (s->h263_pred && !s->h263_msmpeg4)) + //FIXME figure out why mpeg1/2 need this !!! + if (s->codec_id == CODEC_ID_MPEG1VIDEO || s->codec_id == CODEC_ID_MPEG2VIDEO || (s->h263_pred && !s->h263_msmpeg4)) ff_set_mpeg4_time(s, s->picture_number); #endif @@ -3562,15 +3574,14 @@ /* write gob / video packet header */ #ifdef CONFIG_RISKY - if(s->rtp_mode){ + if(s->rtp_mode && mb_y + mb_x>0){ int current_packet_size, is_gob_start; current_packet_size= pbBufPtr(&s->pb) - s->ptr_lastgob; is_gob_start=0; if(s->codec_id==CODEC_ID_MPEG4){ - if(current_packet_size >= s->rtp_payload_size - && s->mb_y + s->mb_x>0){ + if(current_packet_size >= s->rtp_payload_size){ if(s->partitioned_frame){ ff_mpeg4_merge_partitions(s); @@ -3588,14 +3599,21 @@ } }else if(s->codec_id==CODEC_ID_MPEG1VIDEO){ if( current_packet_size >= s->rtp_payload_size - && s->mb_y + s->mb_x>0 && s->mb_skip_run==0){ + && s->mb_skip_run==0){ + ff_mpeg1_encode_slice_header(s); + ff_mpeg1_clean_buffers(s); + is_gob_start=1; + } + }else if(s->codec_id==CODEC_ID_MPEG2VIDEO){ + if( ( current_packet_size >= s->rtp_payload_size || mb_x==0) + && s->mb_skip_run==0){ ff_mpeg1_encode_slice_header(s); ff_mpeg1_clean_buffers(s); is_gob_start=1; } }else{ if(current_packet_size >= s->rtp_payload_size - && s->mb_x==0 && s->mb_y>0 && s->mb_y%s->gob_index==0){ + && s->mb_x==0 && s->mb_y%s->gob_index==0){ h263_encode_gob_header(s, mb_y); is_gob_start=1; @@ -4000,7 +4018,7 @@ start_i = 1; last_non_zero = 0; qmat = s->q_intra_matrix[qscale]; - if(s->mpeg_quant || s->codec_id== CODEC_ID_MPEG1VIDEO) + if(s->mpeg_quant) bias= 1<<(QMAT_SHIFT-1); length = s->intra_ac_vlc_length; last_length= s->intra_ac_vlc_last_length; @@ -4529,6 +4547,16 @@ #ifdef CONFIG_RISKY +AVCodec mpeg2video_encoder = { + "mpeg2video", + CODEC_TYPE_VIDEO, + CODEC_ID_MPEG2VIDEO, + sizeof(MpegEncContext), + MPV_encode_init, + MPV_encode_picture, + MPV_encode_end, +}; + AVCodec h263_encoder = { "h263", CODEC_TYPE_VIDEO,