Originally committed as revision 759 to svn://svn.ffmpeg.org/ffmpeg/trunktags/v0.5
| @@ -5,8 +5,8 @@ | |||||
| #define LIBAVCODEC_VERSION_INT 0x000406 | #define LIBAVCODEC_VERSION_INT 0x000406 | ||||
| #define LIBAVCODEC_VERSION "0.4.6" | #define LIBAVCODEC_VERSION "0.4.6" | ||||
| #define LIBAVCODEC_BUILD 4615 | |||||
| #define LIBAVCODEC_BUILD_STR "4615" | |||||
| #define LIBAVCODEC_BUILD 4616 | |||||
| #define LIBAVCODEC_BUILD_STR "4616" | |||||
| enum CodecID { | enum CodecID { | ||||
| CODEC_ID_NONE, | CODEC_ID_NONE, | ||||
| @@ -100,12 +100,14 @@ static const int Motion_Est_QTab[] = { ME_ZERO, ME_PHODS, ME_LOG, | |||||
| #define CODEC_FLAG_PASS1 0x0200 /* use internal 2pass ratecontrol in first pass mode */ | #define CODEC_FLAG_PASS1 0x0200 /* use internal 2pass ratecontrol in first pass mode */ | ||||
| #define CODEC_FLAG_PASS2 0x0400 /* use internal 2pass ratecontrol in second pass mode */ | #define CODEC_FLAG_PASS2 0x0400 /* use internal 2pass ratecontrol in second pass mode */ | ||||
| #define CODEC_FLAG_EXTERN_HUFF 0x1000 /* use external huffman table (for mjpeg) */ | #define CODEC_FLAG_EXTERN_HUFF 0x1000 /* use external huffman table (for mjpeg) */ | ||||
| #define CODEC_FLAG_GRAY 0x2000 /* only decode/encode grayscale */ | |||||
| #define CODEC_FLAG_GRAY 0x2000 /* only decode/encode grayscale */ | |||||
| #define CODEC_FLAG_EMU_EDGE 0x4000/* dont draw edges */ | |||||
| #define CODEC_FLAG_DR1 0x8000 /* dr1 */ | |||||
| /* codec capabilities */ | /* codec capabilities */ | ||||
| /* decoder can use draw_horiz_band callback */ | /* decoder can use draw_horiz_band callback */ | ||||
| #define CODEC_CAP_DRAW_HORIZ_BAND 0x0001 | #define CODEC_CAP_DRAW_HORIZ_BAND 0x0001 | ||||
| #define CODEC_CAP_DR1 0x0002 /* direct rendering method 1 */ | |||||
| #define FRAME_RATE_BASE 10000 | #define FRAME_RATE_BASE 10000 | ||||
| @@ -248,8 +250,16 @@ typedef struct AVCodecContext { | |||||
| #define MBC 128 | #define MBC 128 | ||||
| #define MBR 96 | #define MBR 96 | ||||
| #endif | #endif | ||||
| int *quant_store; /* field for communicating with external postprocessing */ | |||||
| #define QP_TYPE int //FIXME note xxx this might be changed to int8_t | |||||
| QP_TYPE *quant_store; /* field for communicating with external postprocessing */ | |||||
| unsigned qstride; | unsigned qstride; | ||||
| uint8_t *dr_buffer[3]; | |||||
| int dr_stride; | |||||
| void *dr_opaque_frame; | |||||
| void (*get_buffer_callback)(struct AVCodecContext *c, int width, int height, int pict_type); | |||||
| //FIXME this should be reordered after kabis API is finished ... | //FIXME this should be reordered after kabis API is finished ... | ||||
| /* | /* | ||||
| Note: Below are located reserved fields for further usage | Note: Below are located reserved fields for further usage | ||||
| @@ -267,13 +277,12 @@ typedef struct AVCodecContext { | |||||
| flt_res6,flt_res7,flt_res8,flt_res9,flt_res10,flt_res11; | flt_res6,flt_res7,flt_res8,flt_res9,flt_res10,flt_res11; | ||||
| void | void | ||||
| *ptr_res0,*ptr_res1,*ptr_res2,*ptr_res3,*ptr_res4,*ptr_res5, | *ptr_res0,*ptr_res1,*ptr_res2,*ptr_res3,*ptr_res4,*ptr_res5, | ||||
| *ptr_res6,*ptr_res7,*ptr_res8,*ptr_res9,*ptr_res10,*ptr_res11; | |||||
| *ptr_res6; | |||||
| unsigned long int | unsigned long int | ||||
| ul_res0,ul_res1,ul_res2,ul_res3,ul_res4,ul_res5, | ul_res0,ul_res1,ul_res2,ul_res3,ul_res4,ul_res5, | ||||
| ul_res6,ul_res7,ul_res8,ul_res9,ul_res10,ul_res11,ul_res12; | ul_res6,ul_res7,ul_res8,ul_res9,ul_res10,ul_res11,ul_res12; | ||||
| unsigned int | unsigned int | ||||
| ui_res0,ui_res1,ui_res2,ui_res3,ui_res4,ui_res5, | |||||
| ui_res6; | |||||
| ui_res0,ui_res1,ui_res2,ui_res3,ui_res4,ui_res5; | |||||
| unsigned short int | unsigned short int | ||||
| us_res0,us_res1,us_res2,us_res3,us_res4,us_res5, | us_res0,us_res1,us_res2,us_res3,us_res4,us_res5, | ||||
| us_res6,us_res7,us_res8,us_res9,us_res10,us_res11,us_res12; | us_res6,us_res7,us_res8,us_res9,us_res10,us_res11,us_res12; | ||||
| @@ -89,7 +89,7 @@ static int h263_decode_init(AVCodecContext *avctx) | |||||
| } | } | ||||
| s->codec_id= avctx->codec->id; | s->codec_id= avctx->codec->id; | ||||
| avctx->mbskip_table= s->mbskip_table; | avctx->mbskip_table= s->mbskip_table; | ||||
| /* for h263, we allocate the images after having read the header */ | /* for h263, we allocate the images after having read the header */ | ||||
| if (avctx->codec->id != CODEC_ID_H263 && avctx->codec->id != CODEC_ID_MPEG4) | if (avctx->codec->id != CODEC_ID_H263 && avctx->codec->id != CODEC_ID_MPEG4) | ||||
| if (MPV_common_init(s) < 0) | if (MPV_common_init(s) < 0) | ||||
| @@ -155,21 +155,22 @@ uint64_t time= rdtsc(); | |||||
| ret = h263_decode_picture_header(s); | ret = h263_decode_picture_header(s); | ||||
| } | } | ||||
| /* After H263 & mpeg4 header decode we have the height, width,*/ | /* After H263 & mpeg4 header decode we have the height, width,*/ | ||||
| /* and other parameters. So then we could init the picture */ | /* and other parameters. So then we could init the picture */ | ||||
| /* FIXME: By the way H263 decoder is evolving it should have */ | /* FIXME: By the way H263 decoder is evolving it should have */ | ||||
| /* an H263EncContext */ | /* an H263EncContext */ | ||||
| if (s->width != avctx->width || s->height != avctx->height) { | |||||
| /* H.263 could change picture size any time */ | |||||
| MPV_common_end(s); | |||||
| s->context_initialized=0; | |||||
| } | |||||
| if (!s->context_initialized) { | if (!s->context_initialized) { | ||||
| avctx->width = s->width; | avctx->width = s->width; | ||||
| avctx->height = s->height; | avctx->height = s->height; | ||||
| avctx->aspect_ratio_info= s->aspect_ratio_info; | avctx->aspect_ratio_info= s->aspect_ratio_info; | ||||
| if (MPV_common_init(s) < 0) | if (MPV_common_init(s) < 0) | ||||
| return -1; | return -1; | ||||
| } else if (s->width != avctx->width || s->height != avctx->height) { | |||||
| /* H.263 could change picture size any time */ | |||||
| MPV_common_end(s); | |||||
| if (MPV_common_init(s) < 0) | |||||
| return -1; | |||||
| } | } | ||||
| if(ret==FRAME_SKIPED) return buf_size; | if(ret==FRAME_SKIPED) return buf_size; | ||||
| @@ -190,7 +191,7 @@ uint64_t time= rdtsc(); | |||||
| s->next_p_frame_damaged=0; | s->next_p_frame_damaged=0; | ||||
| } | } | ||||
| MPV_frame_start(s); | |||||
| MPV_frame_start(s, avctx); | |||||
| #ifdef DEBUG | #ifdef DEBUG | ||||
| printf("qscale=%d\n", s->qscale); | printf("qscale=%d\n", s->qscale); | ||||
| @@ -459,7 +460,7 @@ AVCodec mpeg4_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec h263_decoder = { | AVCodec h263_decoder = { | ||||
| @@ -471,7 +472,7 @@ AVCodec h263_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec msmpeg4v1_decoder = { | AVCodec msmpeg4v1_decoder = { | ||||
| @@ -483,7 +484,7 @@ AVCodec msmpeg4v1_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec msmpeg4v2_decoder = { | AVCodec msmpeg4v2_decoder = { | ||||
| @@ -495,7 +496,7 @@ AVCodec msmpeg4v2_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec msmpeg4v3_decoder = { | AVCodec msmpeg4v3_decoder = { | ||||
| @@ -507,7 +508,7 @@ AVCodec msmpeg4v3_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec wmv1_decoder = { | AVCodec wmv1_decoder = { | ||||
| @@ -519,7 +520,7 @@ AVCodec wmv1_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec wmv2_decoder = { | AVCodec wmv2_decoder = { | ||||
| @@ -531,7 +532,7 @@ AVCodec wmv2_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| AVCodec h263i_decoder = { | AVCodec h263i_decoder = { | ||||
| @@ -543,6 +544,6 @@ AVCodec h263i_decoder = { | |||||
| NULL, | NULL, | ||||
| h263_decode_end, | h263_decode_end, | ||||
| h263_decode_frame, | h263_decode_frame, | ||||
| CODEC_CAP_DRAW_HORIZ_BAND, | |||||
| CODEC_CAP_DRAW_HORIZ_BAND | CODEC_CAP_DR1, | |||||
| }; | }; | ||||
| @@ -144,9 +144,10 @@ int MPV_common_init(MpegEncContext *s) | |||||
| s->mb_width = (s->width + 15) / 16; | s->mb_width = (s->width + 15) / 16; | ||||
| s->mb_height = (s->height + 15) / 16; | s->mb_height = (s->height + 15) / 16; | ||||
| s->mb_num = s->mb_width * s->mb_height; | s->mb_num = s->mb_width * s->mb_height; | ||||
| s->linesize = s->mb_width * 16 + 2 * EDGE_WIDTH; | |||||
| if(!(s->flags&CODEC_FLAG_DR1)){ | |||||
| s->linesize = s->mb_width * 16 + 2 * EDGE_WIDTH; | |||||
| for(i=0;i<3;i++) { | |||||
| for(i=0;i<3;i++) { | |||||
| int w, h, shift, pict_start; | int w, h, shift, pict_start; | ||||
| w = s->linesize; | w = s->linesize; | ||||
| @@ -173,8 +174,11 @@ int MPV_common_init(MpegEncContext *s) | |||||
| s->aux_picture[i] = pict + pict_start; | s->aux_picture[i] = pict + pict_start; | ||||
| if(i>0) memset(s->aux_picture_base[i], 128, c_size); | if(i>0) memset(s->aux_picture_base[i], 128, c_size); | ||||
| } | } | ||||
| } | |||||
| } | } | ||||
| CHECKED_ALLOCZ(s->edge_emu_buffer, (s->width+32)*2*17); | |||||
| if (s->encoding) { | if (s->encoding) { | ||||
| int j; | int j; | ||||
| int mv_table_size= (s->mb_width+2)*(s->mb_height+2); | int mv_table_size= (s->mb_width+2)*(s->mb_height+2); | ||||
| @@ -267,7 +271,7 @@ int MPV_common_init(MpegEncContext *s) | |||||
| } | } | ||||
| /* default structure is frame */ | /* default structure is frame */ | ||||
| s->picture_structure = PICT_FRAME; | s->picture_structure = PICT_FRAME; | ||||
| /* init macroblock skip table */ | /* init macroblock skip table */ | ||||
| CHECKED_ALLOCZ(s->mbskip_table, s->mb_num); | CHECKED_ALLOCZ(s->mbskip_table, s->mb_num); | ||||
| @@ -315,11 +319,22 @@ void MPV_common_end(MpegEncContext *s) | |||||
| av_freep(&s->bitstream_buffer); | av_freep(&s->bitstream_buffer); | ||||
| av_freep(&s->tex_pb_buffer); | av_freep(&s->tex_pb_buffer); | ||||
| av_freep(&s->pb2_buffer); | av_freep(&s->pb2_buffer); | ||||
| av_freep(&s->edge_emu_buffer); | |||||
| for(i=0;i<3;i++) { | for(i=0;i<3;i++) { | ||||
| int j; | int j; | ||||
| av_freep(&s->last_picture_base[i]); | |||||
| av_freep(&s->next_picture_base[i]); | |||||
| av_freep(&s->aux_picture_base[i]); | |||||
| if(!(s->flags&CODEC_FLAG_DR1)){ | |||||
| av_freep(&s->last_picture_base[i]); | |||||
| av_freep(&s->next_picture_base[i]); | |||||
| av_freep(&s->aux_picture_base[i]); | |||||
| } | |||||
| s->last_picture_base[i]= | |||||
| s->next_picture_base[i]= | |||||
| s->aux_picture_base [i] = NULL; | |||||
| s->last_picture[i]= | |||||
| s->next_picture[i]= | |||||
| s->aux_picture [i] = NULL; | |||||
| for(j=0; j<REORDER_BUFFER_SIZE; j++){ | for(j=0; j<REORDER_BUFFER_SIZE; j++){ | ||||
| av_freep(&s->picture_buffer[j][i]); | av_freep(&s->picture_buffer[j][i]); | ||||
| } | } | ||||
| @@ -595,7 +610,7 @@ static void draw_edges_c(UINT8 *buf, int wrap, int width, int height, int w) | |||||
| } | } | ||||
| /* generic function for encode/decode called before a frame is coded/decoded */ | /* generic function for encode/decode called before a frame is coded/decoded */ | ||||
| void MPV_frame_start(MpegEncContext *s) | |||||
| void MPV_frame_start(MpegEncContext *s, AVCodecContext *avctx) | |||||
| { | { | ||||
| int i; | int i; | ||||
| UINT8 *tmp; | UINT8 *tmp; | ||||
| @@ -603,17 +618,39 @@ void MPV_frame_start(MpegEncContext *s) | |||||
| s->mb_skiped = 0; | s->mb_skiped = 0; | ||||
| s->decoding_error=0; | s->decoding_error=0; | ||||
| if(avctx->flags&CODEC_FLAG_DR1){ | |||||
| int i; | |||||
| avctx->get_buffer_callback(avctx, s->width, s->height, s->pict_type); | |||||
| s->linesize= avctx->dr_stride; | |||||
| } | |||||
| if (s->pict_type == B_TYPE) { | if (s->pict_type == B_TYPE) { | ||||
| for(i=0;i<3;i++) { | for(i=0;i<3;i++) { | ||||
| if(avctx->flags&CODEC_FLAG_DR1) | |||||
| s->aux_picture[i]= avctx->dr_buffer[i]; | |||||
| s->current_picture[i] = s->aux_picture[i]; | s->current_picture[i] = s->aux_picture[i]; | ||||
| } | } | ||||
| } else { | } else { | ||||
| for(i=0;i<3;i++) { | for(i=0;i<3;i++) { | ||||
| /* swap next and last */ | /* swap next and last */ | ||||
| tmp = s->last_picture[i]; | |||||
| if(avctx->flags&CODEC_FLAG_DR1) | |||||
| tmp= avctx->dr_buffer[i]; | |||||
| else | |||||
| tmp = s->last_picture[i]; | |||||
| s->last_picture[i] = s->next_picture[i]; | s->last_picture[i] = s->next_picture[i]; | ||||
| s->next_picture[i] = tmp; | s->next_picture[i] = tmp; | ||||
| s->current_picture[i] = tmp; | s->current_picture[i] = tmp; | ||||
| s->last_dr_opaque= s->next_dr_opaque; | |||||
| s->next_dr_opaque= avctx->dr_opaque_frame; | |||||
| if(s->has_b_frames && s->last_dr_opaque) | |||||
| avctx->dr_opaque_frame= s->last_dr_opaque; | |||||
| else | |||||
| avctx->dr_opaque_frame= s->next_dr_opaque; | |||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| @@ -624,7 +661,7 @@ void MPV_frame_end(MpegEncContext *s) | |||||
| // if((s->picture_number%100)==0 && s->encoding) printf("sads:%d //\n", sads); | // if((s->picture_number%100)==0 && s->encoding) printf("sads:%d //\n", sads); | ||||
| /* draw edge for correct motion prediction if outside */ | /* draw edge for correct motion prediction if outside */ | ||||
| if (s->pict_type != B_TYPE && !s->intra_only) { | |||||
| if (s->pict_type != B_TYPE && !s->intra_only && !(s->flags&CODEC_FLAG_EMU_EDGE)) { | |||||
| if(s->avctx==NULL || s->avctx->codec->id!=CODEC_ID_MPEG4 || s->divx_version>=500){ | if(s->avctx==NULL || s->avctx->codec->id!=CODEC_ID_MPEG4 || s->divx_version>=500){ | ||||
| draw_edges(s->current_picture[0], s->linesize, s->mb_width*16, s->mb_height*16, EDGE_WIDTH); | draw_edges(s->current_picture[0], s->linesize, s->mb_width*16, s->mb_height*16, EDGE_WIDTH); | ||||
| draw_edges(s->current_picture[1], s->linesize/2, s->mb_width*8, s->mb_height*8, EDGE_WIDTH/2); | draw_edges(s->current_picture[1], s->linesize/2, s->mb_width*8, s->mb_height*8, EDGE_WIDTH/2); | ||||
| @@ -776,7 +813,7 @@ int MPV_encode_picture(AVCodecContext *avctx, | |||||
| s->picture_in_gop_number= s->coded_order[0].picture_in_gop_number; | s->picture_in_gop_number= s->coded_order[0].picture_in_gop_number; | ||||
| s->picture_number= s->coded_order[0].picture_number; | s->picture_number= s->coded_order[0].picture_number; | ||||
| MPV_frame_start(s); | |||||
| MPV_frame_start(s, avctx); | |||||
| encode_picture(s, s->picture_number); | encode_picture(s, s->picture_number); | ||||
| avctx->key_frame = (s->pict_type == I_TYPE); | avctx->key_frame = (s->pict_type == I_TYPE); | ||||
| @@ -879,6 +916,60 @@ static inline void gmc1_motion(MpegEncContext *s, | |||||
| return; | return; | ||||
| } | } | ||||
| static void emulated_edge_mc(UINT8 *buf, UINT8 *src, int linesize, int block_w, int block_h, | |||||
| int src_x, int src_y, int w, int h){ | |||||
| int x, y; | |||||
| int start_y, start_x, end_y, end_x; | |||||
| if(src_y>= h){ | |||||
| src+= (h-1-src_y)*linesize; | |||||
| src_y=h-1; | |||||
| } | |||||
| if(src_x>= w){ | |||||
| src+= (w-1-src_x); | |||||
| src_x=w-1; | |||||
| } | |||||
| start_y= MAX(0, -src_y); | |||||
| start_x= MAX(0, -src_x); | |||||
| end_y= MIN(block_h, h-src_y); | |||||
| end_x= MIN(block_w, w-src_x); | |||||
| // copy existing part | |||||
| for(y=start_y; y<end_y; y++){ | |||||
| for(x=start_x; x<end_x; x++){ | |||||
| buf[x + y*linesize]= src[x + y*linesize]; | |||||
| } | |||||
| } | |||||
| //top | |||||
| for(y=0; y<start_y; y++){ | |||||
| for(x=start_x; x<end_x; x++){ | |||||
| buf[x + y*linesize]= buf[x + start_y*linesize]; | |||||
| } | |||||
| } | |||||
| //bottom | |||||
| for(y=end_y; y<block_h; y++){ | |||||
| for(x=start_x; x<end_x; x++){ | |||||
| buf[x + y*linesize]= buf[x + (end_y-1)*linesize]; | |||||
| } | |||||
| } | |||||
| for(y=0; y<block_h; y++){ | |||||
| //left | |||||
| for(x=0; x<start_x; x++){ | |||||
| buf[x + y*linesize]= buf[start_x + y*linesize]; | |||||
| } | |||||
| //right | |||||
| for(x=end_x; x<block_w; x++){ | |||||
| buf[x + y*linesize]= buf[end_x - 1 + y*linesize]; | |||||
| } | |||||
| } | |||||
| } | |||||
| /* apply one mpeg motion vector to the three components */ | /* apply one mpeg motion vector to the three components */ | ||||
| static inline void mpeg_motion(MpegEncContext *s, | static inline void mpeg_motion(MpegEncContext *s, | ||||
| UINT8 *dest_y, UINT8 *dest_cb, UINT8 *dest_cr, | UINT8 *dest_y, UINT8 *dest_cb, UINT8 *dest_cr, | ||||
| @@ -889,6 +980,8 @@ static inline void mpeg_motion(MpegEncContext *s, | |||||
| { | { | ||||
| UINT8 *ptr; | UINT8 *ptr; | ||||
| int dxy, offset, mx, my, src_x, src_y, height, linesize; | int dxy, offset, mx, my, src_x, src_y, height, linesize; | ||||
| int emu=0; | |||||
| if(s->quarter_sample) | if(s->quarter_sample) | ||||
| { | { | ||||
| motion_x>>=1; | motion_x>>=1; | ||||
| @@ -909,6 +1002,15 @@ if(s->quarter_sample) | |||||
| linesize = s->linesize << field_based; | linesize = s->linesize << field_based; | ||||
| ptr = ref_picture[0] + (src_y * linesize) + (src_x) + src_offset; | ptr = ref_picture[0] + (src_y * linesize) + (src_x) + src_offset; | ||||
| dest_y += dest_offset; | dest_y += dest_offset; | ||||
| if(s->flags&CODEC_FLAG_EMU_EDGE){ | |||||
| if(src_x<0 || src_y<0 || src_x + (motion_x&1) + 16 > s->width | |||||
| || src_y + (motion_y&1) + h > height){ | |||||
| emulated_edge_mc(s->edge_emu_buffer, ptr, linesize, 17, h+1, src_x, src_y, s->width, height); | |||||
| ptr= s->edge_emu_buffer; | |||||
| emu=1; | |||||
| } | |||||
| } | |||||
| pix_op[dxy](dest_y, ptr, linesize, h); | pix_op[dxy](dest_y, ptr, linesize, h); | ||||
| pix_op[dxy](dest_y + 8, ptr + 8, linesize, h); | pix_op[dxy](dest_y + 8, ptr + 8, linesize, h); | ||||
| @@ -941,8 +1043,17 @@ if(s->quarter_sample) | |||||
| offset = (src_y * (linesize >> 1)) + src_x + (src_offset >> 1); | offset = (src_y * (linesize >> 1)) + src_x + (src_offset >> 1); | ||||
| ptr = ref_picture[1] + offset; | ptr = ref_picture[1] + offset; | ||||
| if(emu){ | |||||
| emulated_edge_mc(s->edge_emu_buffer, ptr, linesize>>1, 9, (h>>1)+1, src_x, src_y, s->width>>1, height>>1); | |||||
| ptr= s->edge_emu_buffer; | |||||
| } | |||||
| pix_op[dxy](dest_cb + (dest_offset >> 1), ptr, linesize >> 1, h >> 1); | pix_op[dxy](dest_cb + (dest_offset >> 1), ptr, linesize >> 1, h >> 1); | ||||
| ptr = ref_picture[2] + offset; | ptr = ref_picture[2] + offset; | ||||
| if(emu){ | |||||
| emulated_edge_mc(s->edge_emu_buffer, ptr, linesize>>1, 9, (h>>1)+1, src_x, src_y, s->width>>1, height>>1); | |||||
| ptr= s->edge_emu_buffer; | |||||
| } | |||||
| pix_op[dxy](dest_cr + (dest_offset >> 1), ptr, linesize >> 1, h >> 1); | pix_op[dxy](dest_cr + (dest_offset >> 1), ptr, linesize >> 1, h >> 1); | ||||
| } | } | ||||
| @@ -143,6 +143,8 @@ typedef struct MpegEncContext { | |||||
| UINT8 *aux_picture[3]; /* aux picture (for B frames only) */ | UINT8 *aux_picture[3]; /* aux picture (for B frames only) */ | ||||
| UINT8 *aux_picture_base[3]; /* real start of the picture */ | UINT8 *aux_picture_base[3]; /* real start of the picture */ | ||||
| UINT8 *current_picture[3]; /* buffer to store the decompressed current picture */ | UINT8 *current_picture[3]; /* buffer to store the decompressed current picture */ | ||||
| void *last_dr_opaque; | |||||
| void *next_dr_opaque; | |||||
| int num_available_buffers; /* is 0 at the start & after seeking, after the first I frame its 1 after next I/P 2 */ | int num_available_buffers; /* is 0 at the start & after seeking, after the first I frame its 1 after next I/P 2 */ | ||||
| int last_dc[3]; /* last DC values for MPEG1 */ | int last_dc[3]; /* last DC values for MPEG1 */ | ||||
| INT16 *dc_val[3]; /* used for mpeg4 DC prediction, all 3 arrays must be continuous */ | INT16 *dc_val[3]; /* used for mpeg4 DC prediction, all 3 arrays must be continuous */ | ||||
| @@ -159,6 +161,7 @@ typedef struct MpegEncContext { | |||||
| UINT8 *cbp_table; /* used to store cbp, ac_pred for partitioned decoding */ | UINT8 *cbp_table; /* used to store cbp, ac_pred for partitioned decoding */ | ||||
| UINT8 *pred_dir_table; /* used to store pred_dir for partitioned decoding */ | UINT8 *pred_dir_table; /* used to store pred_dir for partitioned decoding */ | ||||
| INT8 *qscale_table; /* used to store qscale for partitioned decoding (& postprocessing FIXME export) */ | INT8 *qscale_table; /* used to store qscale for partitioned decoding (& postprocessing FIXME export) */ | ||||
| UINT8 *edge_emu_buffer; | |||||
| int input_qscale; /* qscale prior to reordering of frames */ | int input_qscale; /* qscale prior to reordering of frames */ | ||||
| int input_pict_type; /* pict_type prior to reordering of frames */ | int input_pict_type; /* pict_type prior to reordering of frames */ | ||||
| @@ -447,7 +450,7 @@ typedef struct MpegEncContext { | |||||
| int MPV_common_init(MpegEncContext *s); | int MPV_common_init(MpegEncContext *s); | ||||
| void MPV_common_end(MpegEncContext *s); | void MPV_common_end(MpegEncContext *s); | ||||
| void MPV_decode_mb(MpegEncContext *s, DCTELEM block[6][64]); | void MPV_decode_mb(MpegEncContext *s, DCTELEM block[6][64]); | ||||
| void MPV_frame_start(MpegEncContext *s); | |||||
| void MPV_frame_start(MpegEncContext *s, AVCodecContext *avctx); | |||||
| void MPV_frame_end(MpegEncContext *s); | void MPV_frame_end(MpegEncContext *s); | ||||
| #ifdef HAVE_MMX | #ifdef HAVE_MMX | ||||
| void MPV_common_init_mmx(MpegEncContext *s); | void MPV_common_init_mmx(MpegEncContext *s); | ||||
| @@ -419,7 +419,7 @@ static int rv10_decode_frame(AVCodecContext *avctx, | |||||
| } | } | ||||
| if (s->mb_x == 0 && s->mb_y == 0) { | if (s->mb_x == 0 && s->mb_y == 0) { | ||||
| MPV_frame_start(s); | |||||
| MPV_frame_start(s, avctx); | |||||
| } | } | ||||
| #ifdef DEBUG | #ifdef DEBUG | ||||