X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=libavcodec%2Fdsputil.c;h=3e7bfc35e3a7cd0c49326e32c5537fc7cf589794;hb=feb993e5794b3dacb51085a9b77013495eb6dd1c;hp=1514a4a3b060bc1217f40c60d48716c48c0736b3;hpb=31304587da246672a240216d95298bb0ba9f9c64;p=ffmpeg diff --git a/libavcodec/dsputil.c b/libavcodec/dsputil.c index 1514a4a3b06..3e7bfc35e3a 100644 --- a/libavcodec/dsputil.c +++ b/libavcodec/dsputil.c @@ -1,6 +1,6 @@ /* * DSP utils - * Copyright (c) 2000, 2001 Fabrice Bellard. + * Copyright (c) 2000, 2001 Fabrice Bellard * Copyright (c) 2002-2004 Michael Niedermayer * * gmc & q-pel & 32/64 bit based MC by Michael Niedermayer @@ -23,15 +23,16 @@ */ /** - * @file dsputil.c + * @file libavcodec/dsputil.c * DSP utils */ #include "avcodec.h" #include "dsputil.h" -#include "mpegvideo.h" #include "simple_idct.h" #include "faandct.h" +#include "faanidct.h" +#include "mathops.h" #include "h263.h" #include "snow.h" @@ -41,17 +42,24 @@ void ff_spatial_dwt(int *buffer, int width, int height, int stride, int type, in /* vorbis.c */ void vorbis_inverse_coupling(float *mag, float *ang, int blocksize); +/* ac3dec.c */ +void ff_ac3_downmix_c(float (*samples)[256], float (*matrix)[2], int out_ch, int in_ch, int len); + /* flacenc.c */ void ff_flac_compute_autocorr(const int32_t *data, int len, int lag, double *autoc); /* pngdec.c */ void ff_add_png_paeth_prediction(uint8_t *dst, uint8_t *src, uint8_t *top, int w, int bpp); +/* eaidct.c */ +void ff_ea_idct_put_c(uint8_t *dest, int linesize, DCTELEM *block); + uint8_t ff_cropTbl[256 + 2 * MAX_NEG_CROP] = {0, }; uint32_t ff_squareTbl[512] = {0, }; -static const unsigned long pb_7f = 0x7f7f7f7f7f7f7f7fUL; -static const unsigned long pb_80 = 0x8080808080808080UL; +// 0x7f7f7f7f or 0x7f7f7f7f7f7f7f7f or whatever, depending on the cpu's native arithmetic size +#define pb_7f (~0UL/255 * 0x7f) +#define pb_80 (~0UL/255 * 0x80) const uint8_t ff_zigzag_direct[64] = { 0, 1, 8, 16, 9, 2, 3, 10, @@ -150,6 +158,32 @@ static const uint8_t simple_mmx_permutation[64]={ 0x32, 0x3A, 0x36, 0x3B, 0x33, 0x3E, 0x37, 0x3F, }; +static const uint8_t idct_sse2_row_perm[8] = {0, 4, 1, 5, 2, 6, 3, 7}; + +void ff_init_scantable(uint8_t *permutation, ScanTable *st, const uint8_t *src_scantable){ + int i; + int end; + + st->scantable= src_scantable; + + for(i=0; i<64; i++){ + int j; + j = src_scantable[i]; + st->permutated[i] = permutation[j]; +#if ARCH_PPC + st->inverse[j] = i; +#endif + } + + end=-1; + for(i=0; i<64; i++){ + int j; + j = st->permutated[i]; + if(j>end) end=j; + st->raster_end[i]= end; + } +} + static int pix_sum_c(uint8_t * pix, int line_size) { int s, i, j; @@ -307,7 +341,7 @@ static int sse16_c(void *v, uint8_t *pix1, uint8_t *pix2, int line_size, int h) } -#ifdef CONFIG_SNOW_ENCODER //dwt is in snow.c +#if CONFIG_SNOW_ENCODER //dwt is in snow.c static inline int w_c(void *v, uint8_t * pix1, uint8_t * pix2, int line_size, int w, int h, int type){ int s, i, j; const int dec_count= w==8 ? 3 : 4; @@ -402,6 +436,106 @@ int w97_32_c(void *v, uint8_t * pix1, uint8_t * pix2, int line_size, int h){ } #endif +/* draw the edges of width 'w' of an image of size width, height */ +//FIXME check that this is ok for mpeg4 interlaced +static void draw_edges_c(uint8_t *buf, int wrap, int width, int height, int w) +{ + uint8_t *ptr, *last_line; + int i; + + last_line = buf + (height - 1) * wrap; + for(i=0;i= h){ + src+= (h-1-src_y)*linesize; + src_y=h-1; + }else if(src_y<=-block_h){ + src+= (1-block_h-src_y)*linesize; + src_y=1-block_h; + } + if(src_x>= w){ + src+= (w-1-src_x); + src_x=w-1; + }else if(src_x<=-block_w){ + src+= (1-block_w-src_x); + src_x=1-block_w; + } + + start_y= FFMAX(0, -src_y); + start_x= FFMAX(0, -src_x); + end_y= FFMIN(block_h, h-src_y); + end_x= FFMIN(block_w, w-src_x); + + // copy existing part + for(y=start_y; y> 2 ) + 2 )){ + if( FFABS( p2 - p0 ) < beta) + { + const int p3 = pix[-4*xstride]; + /* p0', p1', p2' */ + pix[-1*xstride] = ( p2 + 2*p1 + 2*p0 + 2*q0 + q1 + 4 ) >> 3; + pix[-2*xstride] = ( p2 + p1 + p0 + q0 + 2 ) >> 2; + pix[-3*xstride] = ( 2*p3 + 3*p2 + p1 + p0 + q0 + 4 ) >> 3; + } else { + /* p0' */ + pix[-1*xstride] = ( 2*p1 + p0 + q1 + 2 ) >> 2; + } + if( FFABS( q2 - q0 ) < beta) + { + const int q3 = pix[3*xstride]; + /* q0', q1', q2' */ + pix[0*xstride] = ( p1 + 2*p0 + 2*q0 + 2*q1 + q2 + 4 ) >> 3; + pix[1*xstride] = ( p0 + q0 + q1 + q2 + 2 ) >> 2; + pix[2*xstride] = ( 2*q3 + 3*q2 + q1 + q0 + p0 + 4 ) >> 3; + } else { + /* q0' */ + pix[0*xstride] = ( 2*q1 + q0 + p1 + 2 ) >> 2; + } + }else{ + /* p0', q0' */ + pix[-1*xstride] = ( 2*p1 + p0 + q1 + 2 ) >> 2; + pix[ 0*xstride] = ( 2*q1 + q0 + p1 + 2 ) >> 2; + } + } + pix += ystride; + } +} +static void h264_v_loop_filter_luma_intra_c(uint8_t *pix, int stride, int alpha, int beta) +{ + h264_loop_filter_luma_intra_c(pix, stride, 1, alpha, beta); +} +static void h264_h_loop_filter_luma_intra_c(uint8_t *pix, int stride, int alpha, int beta) +{ + h264_loop_filter_luma_intra_c(pix, 1, stride, alpha, beta); +} + static inline void h264_loop_filter_chroma_c(uint8_t *pix, int xstride, int ystride, int alpha, int beta, int8_t *tc0) { int i, d; @@ -3213,9 +3425,9 @@ static int zero_cmp(void *s, uint8_t *a, uint8_t *b, int stride, int h){ void ff_set_cmp(DSPContext* c, me_cmp_func *cmp, int type){ int i; - memset(cmp, 0, sizeof(void*)*5); + memset(cmp, 0, sizeof(void*)*6); - for(i=0; i<5; i++){ + for(i=0; i<6; i++){ switch(type&0xFF){ case FF_CMP_SAD: cmp[i]= c->sad[i]; @@ -3256,7 +3468,7 @@ void ff_set_cmp(DSPContext* c, me_cmp_func *cmp, int type){ case FF_CMP_NSSE: cmp[i]= c->nsse[i]; break; -#ifdef CONFIG_SNOW_ENCODER +#if CONFIG_SNOW_ENCODER case FF_CMP_W53: cmp[i]= c->w53[i]; break; @@ -3270,6 +3482,11 @@ void ff_set_cmp(DSPContext* c, me_cmp_func *cmp, int type){ } } +static void clear_block_c(DCTELEM *block) +{ + memset(block, 0, sizeof(DCTELEM)*64); +} + /** * memset(blocks, 0, sizeof(DCTELEM)*6*64) */ @@ -3302,7 +3519,7 @@ static void add_bytes_l2_c(uint8_t *dst, uint8_t *src1, uint8_t *src2, int w){ static void diff_bytes_c(uint8_t *dst, uint8_t *src1, uint8_t *src2, int w){ long i; -#ifndef HAVE_FAST_UNALIGNED +#if !HAVE_FAST_UNALIGNED if((long)src2 & (sizeof(long)-1)){ for(i=0; i+7dsp.sum_abs_dctelem(temp); } -#ifdef CONFIG_GPL +#if CONFIG_GPL #define DCT8_1D {\ const int s07 = SRC(0) + SRC(7);\ const int s16 = SRC(1) + SRC(6);\ @@ -3571,7 +3805,7 @@ static int rd8x8_c(/*MpegEncContext*/ void *c, uint8_t *src1, uint8_t *src2, int DECLARE_ALIGNED_8 (uint64_t, aligned_bak[stride]); DCTELEM * const temp= (DCTELEM*)aligned_temp; uint8_t * const bak= (uint8_t*)aligned_bak; - int i, last, run, bits, level, distoration, start_i; + int i, last, run, bits, level, distortion, start_i; const int esc_length= s->ac_esc_length; uint8_t * length; uint8_t * last_length; @@ -3638,9 +3872,9 @@ static int rd8x8_c(/*MpegEncContext*/ void *c, uint8_t *src1, uint8_t *src2, int s->dsp.idct_add(bak, stride, temp); - distoration= s->dsp.sse[1](NULL, bak, src1, stride, 8); + distortion= s->dsp.sse[1](NULL, bak, src1, stride, 8); - return distoration + ((bits*s->qscale*s->qscale*109 + 64)>>7); + return distortion + ((bits*s->qscale*s->qscale*109 + 64)>>7); } static int bit8x8_c(/*MpegEncContext*/ void *c, uint8_t *src1, uint8_t *src2, int stride, int h){ @@ -3703,20 +3937,23 @@ static int bit8x8_c(/*MpegEncContext*/ void *c, uint8_t *src1, uint8_t *src2, in return bits; } -static int vsad_intra16_c(/*MpegEncContext*/ void *c, uint8_t *s, uint8_t *dummy, int stride, int h){ - int score=0; - int x,y; - - for(y=1; y>31; + // is this faster on some gcc/cpu combinations? +// if(tmp > 0x43c0ffff) tmp = 0xFFFF; +// else tmp = 0; + } + return tmp - 0x8000; +} + +void ff_float_to_int16_c(int16_t *dst, const float *src, long len){ int i; - for(i=0; i>31; - // is this faster on some gcc/cpu combinations? -// if(tmp > 0x43c0ffff) tmp = 0xFFFF; -// else tmp = 0; + for(i=0; i> shift; + + return res; +} + #define W0 2048 #define W1 2841 /* 2048*sqrt (2)*cos (1*pi/16) */ #define W2 2676 /* 2048*sqrt (2)*cos (2*pi/16) */ @@ -3971,9 +4271,9 @@ int ff_check_alignment(void){ static int did_fail=0; DECLARE_ALIGNED_16(int, aligned); - if((long)&aligned & 15){ + if((intptr_t)&aligned & 15){ if(!did_fail){ -#if defined(HAVE_MMX) || defined(HAVE_ALTIVEC) +#if HAVE_MMX || HAVE_ALTIVEC av_log(NULL, AV_LOG_ERROR, "Compiler did not align stack variables. Libavcodec has been miscompiled\n" "and may be very slow or crash. This is not a bug in libavcodec,\n" @@ -3993,7 +4293,7 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) ff_check_alignment(); -#ifdef CONFIG_ENCODERS +#if CONFIG_ENCODERS if(avctx->dct_algo==FF_DCT_FASTINT) { c->fdct = fdct_ifast; c->fdct248 = fdct_ifast248; @@ -4009,7 +4309,7 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) #endif //CONFIG_ENCODERS if(avctx->lowres==1){ - if(avctx->idct_algo==FF_IDCT_INT || avctx->idct_algo==FF_IDCT_AUTO || !ENABLE_H264_DECODER){ + if(avctx->idct_algo==FF_IDCT_INT || avctx->idct_algo==FF_IDCT_AUTO || !CONFIG_H264_DECODER){ c->idct_put= ff_jref_idct4_put; c->idct_add= ff_jref_idct4_add; }else{ @@ -4034,7 +4334,7 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) c->idct_add= ff_jref_idct_add; c->idct = j_rev_dct; c->idct_permutation_type= FF_LIBMPEG2_IDCT_PERM; - }else if((ENABLE_VP3_DECODER || ENABLE_VP5_DECODER || ENABLE_VP6_DECODER || ENABLE_THEORA_DECODER ) && + }else if((CONFIG_VP3_DECODER || CONFIG_VP5_DECODER || CONFIG_VP6_DECODER || CONFIG_THEORA_DECODER ) && avctx->idct_algo==FF_IDCT_VP3){ c->idct_put= ff_vp3_idct_put_c; c->idct_add= ff_vp3_idct_add_c; @@ -4045,6 +4345,14 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) c->idct_add= ff_wmv2_idct_add_c; c->idct = ff_wmv2_idct_c; c->idct_permutation_type= FF_NO_IDCT_PERM; + }else if(avctx->idct_algo==FF_IDCT_FAAN){ + c->idct_put= ff_faanidct_put; + c->idct_add= ff_faanidct_add; + c->idct = ff_faanidct; + c->idct_permutation_type= FF_NO_IDCT_PERM; + }else if(CONFIG_EATGQ_DECODER && avctx->idct_algo==FF_IDCT_EA) { + c->idct_put= ff_ea_idct_put_c; + c->idct_permutation_type= FF_NO_IDCT_PERM; }else{ //accurate/default c->idct_put= ff_simple_idct_put; c->idct_add= ff_simple_idct_add; @@ -4053,11 +4361,15 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) } } - if (ENABLE_H264_DECODER) { + if (CONFIG_H264_DECODER) { c->h264_idct_add= ff_h264_idct_add_c; c->h264_idct8_add= ff_h264_idct8_add_c; c->h264_idct_dc_add= ff_h264_idct_dc_add_c; c->h264_idct8_dc_add= ff_h264_idct8_dc_add_c; + c->h264_idct_add16 = ff_h264_idct_add16_c; + c->h264_idct8_add4 = ff_h264_idct8_add4_c; + c->h264_idct_add8 = ff_h264_idct_add8_c; + c->h264_idct_add16intra= ff_h264_idct_add16intra_c; } c->get_pixels = get_pixels_c; @@ -4070,6 +4382,7 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) c->sum_abs_dctelem = sum_abs_dctelem_c; c->gmc1 = gmc1_c; c->gmc = ff_gmc_c; + c->clear_block = clear_block_c; c->clear_blocks = clear_blocks_c; c->pix_sum = pix_sum_c; c->pix_norm1 = pix_norm1_c; @@ -4196,17 +4509,26 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) c->biweight_h264_pixels_tab[8]= biweight_h264_pixels2x4_c; c->biweight_h264_pixels_tab[9]= biweight_h264_pixels2x2_c; -#ifdef CONFIG_CAVS_DECODER + c->draw_edges = draw_edges_c; + +#if CONFIG_CAVS_DECODER ff_cavsdsp_init(c,avctx); #endif -#if defined(CONFIG_VC1_DECODER) || defined(CONFIG_WMV3_DECODER) +#if CONFIG_VC1_DECODER || CONFIG_WMV3_DECODER ff_vc1dsp_init(c,avctx); #endif -#if defined(CONFIG_WMV2_DECODER) || defined(CONFIG_VC1_DECODER) || defined(CONFIG_WMV3_DECODER) +#if CONFIG_WMV2_DECODER || CONFIG_VC1_DECODER || CONFIG_WMV3_DECODER ff_intrax8dsp_init(c,avctx); #endif -#if defined(CONFIG_H264_ENCODER) - ff_h264dspenc_init(c,avctx); +#if CONFIG_RV30_DECODER + ff_rv30dsp_init(c,avctx); +#endif +#if CONFIG_RV40_DECODER + ff_rv40dsp_init(c,avctx); + c->put_rv40_qpel_pixels_tab[0][15] = put_rv40_qpel16_mc33_c; + c->avg_rv40_qpel_pixels_tab[0][15] = avg_rv40_qpel16_mc33_c; + c->put_rv40_qpel_pixels_tab[1][15] = put_rv40_qpel8_mc33_c; + c->avg_rv40_qpel_pixels_tab[1][15] = avg_rv40_qpel8_mc33_c; #endif c->put_mspel_pixels_tab[0]= put_mspel8_mc00_c; @@ -4224,9 +4546,10 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) SET_CMP_FUNC(hadamard8_diff) c->hadamard8_diff[4]= hadamard8_intra16_c; + c->hadamard8_diff[5]= hadamard8_intra8x8_c; SET_CMP_FUNC(dct_sad) SET_CMP_FUNC(dct_max) -#ifdef CONFIG_GPL +#if CONFIG_GPL SET_CMP_FUNC(dct264_sad) #endif c->sad[0]= pix_abs16_c; @@ -4239,11 +4562,13 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) SET_CMP_FUNC(bit) c->vsad[0]= vsad16_c; c->vsad[4]= vsad_intra16_c; + c->vsad[5]= vsad_intra8_c; c->vsse[0]= vsse16_c; c->vsse[4]= vsse_intra16_c; + c->vsse[5]= vsse_intra8_c; c->nsse[0]= nsse16_c; c->nsse[1]= nsse8_c; -#ifdef CONFIG_SNOW_ENCODER +#if CONFIG_SNOW_ENCODER c->w53[0]= w53_16_c; c->w53[1]= w53_8_c; c->w97[0]= w97_16_c; @@ -4255,46 +4580,66 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) c->add_bytes= add_bytes_c; c->add_bytes_l2= add_bytes_l2_c; c->diff_bytes= diff_bytes_c; + c->add_hfyu_median_prediction= add_hfyu_median_prediction_c; c->sub_hfyu_median_prediction= sub_hfyu_median_prediction_c; c->bswap_buf= bswap_buf; -#ifdef CONFIG_PNG_DECODER +#if CONFIG_PNG_DECODER c->add_png_paeth_prediction= ff_add_png_paeth_prediction; #endif c->h264_v_loop_filter_luma= h264_v_loop_filter_luma_c; c->h264_h_loop_filter_luma= h264_h_loop_filter_luma_c; + c->h264_v_loop_filter_luma_intra= h264_v_loop_filter_luma_intra_c; + c->h264_h_loop_filter_luma_intra= h264_h_loop_filter_luma_intra_c; c->h264_v_loop_filter_chroma= h264_v_loop_filter_chroma_c; c->h264_h_loop_filter_chroma= h264_h_loop_filter_chroma_c; c->h264_v_loop_filter_chroma_intra= h264_v_loop_filter_chroma_intra_c; c->h264_h_loop_filter_chroma_intra= h264_h_loop_filter_chroma_intra_c; c->h264_loop_filter_strength= NULL; - if (ENABLE_ANY_H263) { + if (CONFIG_ANY_H263) { c->h263_h_loop_filter= h263_h_loop_filter_c; c->h263_v_loop_filter= h263_v_loop_filter_c; } + if (CONFIG_VP3_DECODER || CONFIG_THEORA_DECODER) { + c->vp3_h_loop_filter= ff_vp3_h_loop_filter_c; + c->vp3_v_loop_filter= ff_vp3_v_loop_filter_c; + } + if (CONFIG_VP6_DECODER) { + c->vp6_filter_diag4= ff_vp6_filter_diag4_c; + } + c->h261_loop_filter= h261_loop_filter_c; c->try_8x8basis= try_8x8basis_c; c->add_8x8basis= add_8x8basis_c; -#ifdef CONFIG_SNOW_DECODER +#if CONFIG_SNOW_DECODER c->vertical_compose97i = ff_snow_vertical_compose97i; c->horizontal_compose97i = ff_snow_horizontal_compose97i; c->inner_add_yblock = ff_snow_inner_add_yblock; #endif -#ifdef CONFIG_VORBIS_DECODER +#if CONFIG_VORBIS_DECODER c->vorbis_inverse_coupling = vorbis_inverse_coupling; #endif -#ifdef CONFIG_FLAC_ENCODER +#if CONFIG_AC3_DECODER + c->ac3_downmix = ff_ac3_downmix_c; +#endif +#if CONFIG_FLAC_ENCODER c->flac_compute_autocorr = ff_flac_compute_autocorr; #endif c->vector_fmul = vector_fmul_c; c->vector_fmul_reverse = vector_fmul_reverse_c; c->vector_fmul_add_add = ff_vector_fmul_add_add_c; + c->vector_fmul_window = ff_vector_fmul_window_c; + c->int32_to_float_fmul_scalar = int32_to_float_fmul_scalar_c; c->float_to_int16 = ff_float_to_int16_c; + c->float_to_int16_interleave = ff_float_to_int16_interleave_c; + c->add_int16 = add_int16_c; + c->sub_int16 = sub_int16_c; + c->scalarproduct_int16 = scalarproduct_int16_c; c->shrink[0]= ff_img_copy_plane; c->shrink[1]= ff_shrink22; @@ -4306,15 +4651,15 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) memset(c->put_2tap_qpel_pixels_tab, 0, sizeof(c->put_2tap_qpel_pixels_tab)); memset(c->avg_2tap_qpel_pixels_tab, 0, sizeof(c->avg_2tap_qpel_pixels_tab)); - if (ENABLE_MMX) dsputil_init_mmx (c, avctx); - if (ENABLE_ARMV4L) dsputil_init_armv4l(c, avctx); - if (ENABLE_MLIB) dsputil_init_mlib (c, avctx); - if (ENABLE_VIS) dsputil_init_vis (c, avctx); - if (ENABLE_ALPHA) dsputil_init_alpha (c, avctx); - if (ENABLE_POWERPC) dsputil_init_ppc (c, avctx); - if (ENABLE_MMI) dsputil_init_mmi (c, avctx); - if (ENABLE_SH4) dsputil_init_sh4 (c, avctx); - if (ENABLE_BFIN) dsputil_init_bfin (c, avctx); + if (HAVE_MMX) dsputil_init_mmx (c, avctx); + if (ARCH_ARM) dsputil_init_arm (c, avctx); + if (CONFIG_MLIB) dsputil_init_mlib (c, avctx); + if (HAVE_VIS) dsputil_init_vis (c, avctx); + if (ARCH_ALPHA) dsputil_init_alpha (c, avctx); + if (ARCH_PPC) dsputil_init_ppc (c, avctx); + if (HAVE_MMI) dsputil_init_mmi (c, avctx); + if (ARCH_SH4) dsputil_init_sh4 (c, avctx); + if (ARCH_BFIN) dsputil_init_bfin (c, avctx); for(i=0; i<64; i++){ if(!c->put_2tap_qpel_pixels_tab[0][i]) @@ -4344,6 +4689,10 @@ void dsputil_init(DSPContext* c, AVCodecContext *avctx) for(i=0; i<64; i++) c->idct_permutation[i]= (i&0x24) | ((i&3)<<3) | ((i>>3)&3); break; + case FF_SSE2_IDCT_PERM: + for(i=0; i<64; i++) + c->idct_permutation[i]= (i&0x38) | idct_sse2_row_perm[i&7]; + break; default: av_log(avctx, AV_LOG_ERROR, "Internal error, IDCT permutation not set\n"); }