1385 lines · 45.5 KB · C
RawDownload
/* *  Copyright (c) 2010 The WebM project authors. All Rights Reserved. * *  Use of this source code is governed by a BSD-style license *  that can be found in the LICENSE file in the root of the source *  tree. An additional intellectual property rights grant can be found *  in the file PATENTS.  All contributing project authors may *  be found in the AUTHORS file in the root of the source tree. */  #include "vpx_config.h"#include "vpx_rtcd.h"#include "onyxd_int.h"#include "vp8/common/header.h"#include "vp8/common/reconintra4x4.h"#include "vp8/common/reconinter.h"#include "detokenize.h"#include "vp8/common/invtrans.h"#include "vp8/common/alloccommon.h"#include "vp8/common/entropymode.h"#include "vp8/common/quant_common.h"#include "vpx_scale/vpxscale.h"#include "vp8/common/setupintrarecon.h" #include "decodemv.h"#include "vp8/common/extend.h"#if CONFIG_ERROR_CONCEALMENT#include "error_concealment.h"#endif#include "vpx_mem/vpx_mem.h"#include "vp8/common/threading.h"#include "decoderthreading.h"#include "dboolhuff.h" #include <assert.h>#include <stdio.h> void vp8cx_init_de_quantizer(VP8D_COMP *pbi){    int Q;    VP8_COMMON *const pc = & pbi->common;     for (Q = 0; Q < QINDEX_RANGE; Q++)    {        pc->Y1dequant[Q][0] = (short)vp8_dc_quant(Q, pc->y1dc_delta_q);        pc->Y2dequant[Q][0] = (short)vp8_dc2quant(Q, pc->y2dc_delta_q);        pc->UVdequant[Q][0] = (short)vp8_dc_uv_quant(Q, pc->uvdc_delta_q);         pc->Y1dequant[Q][1] = (short)vp8_ac_yquant(Q);        pc->Y2dequant[Q][1] = (short)vp8_ac2quant(Q, pc->y2ac_delta_q);        pc->UVdequant[Q][1] = (short)vp8_ac_uv_quant(Q, pc->uvac_delta_q);    }} void vp8_mb_init_dequantizer(VP8D_COMP *pbi, MACROBLOCKD *xd){    int i;    int QIndex;    MB_MODE_INFO *mbmi = &xd->mode_info_context->mbmi;    VP8_COMMON *const pc = & pbi->common;     /* Decide whether to use the default or alternate baseline Q value. */    if (xd->segmentation_enabled)    {        /* Abs Value */        if (xd->mb_segement_abs_delta == SEGMENT_ABSDATA)            QIndex = xd->segment_feature_data[MB_LVL_ALT_Q][mbmi->segment_id];         /* Delta Value */        else        {            QIndex = pc->base_qindex + xd->segment_feature_data[MB_LVL_ALT_Q][mbmi->segment_id];            QIndex = (QIndex >= 0) ? ((QIndex <= MAXQ) ? QIndex : MAXQ) : 0;    /* Clamp to valid range */        }    }    else        QIndex = pc->base_qindex;     /* Set up the macroblock dequant constants */    xd->dequant_y1_dc[0] = 1;    xd->dequant_y1[0] = pc->Y1dequant[QIndex][0];    xd->dequant_y2[0] = pc->Y2dequant[QIndex][0];    xd->dequant_uv[0] = pc->UVdequant[QIndex][0];     for (i = 1; i < 16; i++)    {        xd->dequant_y1_dc[i] =        xd->dequant_y1[i] = pc->Y1dequant[QIndex][1];        xd->dequant_y2[i] = pc->Y2dequant[QIndex][1];        xd->dequant_uv[i] = pc->UVdequant[QIndex][1];    }} static void decode_macroblock(VP8D_COMP *pbi, MACROBLOCKD *xd,                              unsigned int mb_idx){    MB_PREDICTION_MODE mode;    int i;#if CONFIG_ERROR_CONCEALMENT    int corruption_detected = 0;#endif     if (xd->mode_info_context->mbmi.mb_skip_coeff)    {        vp8_reset_mb_tokens_context(xd);    }    else if (!vp8dx_bool_error(xd->current_bc))    {        int eobtotal;        eobtotal = vp8_decode_mb_tokens(pbi, xd);         /* Special case:  Force the loopfilter to skip when eobtotal is zero */        xd->mode_info_context->mbmi.mb_skip_coeff = (eobtotal==0);    }     mode = xd->mode_info_context->mbmi.mode;     if (xd->segmentation_enabled)        vp8_mb_init_dequantizer(pbi, xd);  #if CONFIG_ERROR_CONCEALMENT     if(pbi->ec_active)    {        int throw_residual;        /* When we have independent partitions we can apply residual even         * though other partitions within the frame are corrupt.         */        throw_residual = (!pbi->independent_partitions &&                          pbi->frame_corrupt_residual);        throw_residual = (throw_residual || vp8dx_bool_error(xd->current_bc));         if ((mb_idx >= pbi->mvs_corrupt_from_mb || throw_residual))        {            /* MB with corrupt residuals or corrupt mode/motion vectors.             * Better to use the predictor as reconstruction.             */            pbi->frame_corrupt_residual = 1;            vpx_memset(xd->qcoeff, 0, sizeof(xd->qcoeff));            vp8_conceal_corrupt_mb(xd);              corruption_detected = 1;             /* force idct to be skipped for B_PRED and use the             * prediction only for reconstruction             * */            vpx_memset(xd->eobs, 0, 25);        }    }#endif     /* do prediction */    if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME)    {        vp8_build_intra_predictors_mbuv_s(xd,                                          xd->recon_above[1],                                          xd->recon_above[2],                                          xd->recon_left[1],                                          xd->recon_left[2],                                          xd->recon_left_stride[1],                                          xd->dst.u_buffer, xd->dst.v_buffer,                                          xd->dst.uv_stride);         if (mode != B_PRED)        {            vp8_build_intra_predictors_mby_s(xd,                                                 xd->recon_above[0],                                                 xd->recon_left[0],                                                 xd->recon_left_stride[0],                                                 xd->dst.y_buffer,                                                 xd->dst.y_stride);        }        else        {            short *DQC = xd->dequant_y1;            int dst_stride = xd->dst.y_stride;             /* clear out residual eob info */            if(xd->mode_info_context->mbmi.mb_skip_coeff)                vpx_memset(xd->eobs, 0, 25);             intra_prediction_down_copy(xd, xd->recon_above[0] + 16);             for (i = 0; i < 16; i++)            {                BLOCKD *b = &xd->block[i];                unsigned char *dst = xd->dst.y_buffer + b->offset;                B_PREDICTION_MODE b_mode =                    xd->mode_info_context->bmi[i].as_mode;                unsigned char *Above = dst - dst_stride;                unsigned char *yleft = dst - 1;                int left_stride = dst_stride;                unsigned char top_left = Above[-1];                 vp8_intra4x4_predict(Above, yleft, left_stride, b_mode,                                     dst, dst_stride, top_left);                 if (xd->eobs[i])                {                    if (xd->eobs[i] > 1)                    {                    vp8_dequant_idct_add(b->qcoeff, DQC, dst, dst_stride);                    }                    else                    {                        vp8_dc_only_idct_add                            (b->qcoeff[0] * DQC[0],                                dst, dst_stride,                                dst, dst_stride);                        ((int *)b->qcoeff)[0] = 0;                    }                }            }        }    }    else    {        vp8_build_inter_predictors_mb(xd);    }  #if CONFIG_ERROR_CONCEALMENT    if (corruption_detected)    {        return;    }#endif     if(!xd->mode_info_context->mbmi.mb_skip_coeff)    {        /* dequantization and idct */        if (mode != B_PRED)        {            short *DQC = xd->dequant_y1;             if (mode != SPLITMV)            {                BLOCKD *b = &xd->block[24];                 /* do 2nd order transform on the dc block */                if (xd->eobs[24] > 1)                {                    vp8_dequantize_b(b, xd->dequant_y2);                     vp8_short_inv_walsh4x4(&b->dqcoeff[0],                        xd->qcoeff);                    ((int *)b->qcoeff)[0] = 0;                    ((int *)b->qcoeff)[1] = 0;                    ((int *)b->qcoeff)[2] = 0;                    ((int *)b->qcoeff)[3] = 0;                    ((int *)b->qcoeff)[4] = 0;                    ((int *)b->qcoeff)[5] = 0;                    ((int *)b->qcoeff)[6] = 0;                    ((int *)b->qcoeff)[7] = 0;                }                else                {                    b->dqcoeff[0] = b->qcoeff[0] * xd->dequant_y2[0];                    vp8_short_inv_walsh4x4_1(&b->dqcoeff[0],                        xd->qcoeff);                    ((int *)b->qcoeff)[0] = 0;                }                 /* override the dc dequant constant in order to preserve the                 * dc components                 */                DQC = xd->dequant_y1_dc;            }             vp8_dequant_idct_add_y_block                            (xd->qcoeff, DQC,                             xd->dst.y_buffer,                             xd->dst.y_stride, xd->eobs);        }         vp8_dequant_idct_add_uv_block                        (xd->qcoeff+16*16, xd->dequant_uv,                         xd->dst.u_buffer, xd->dst.v_buffer,                         xd->dst.uv_stride, xd->eobs+16);    }} static int get_delta_q(vp8_reader *bc, int prev, int *q_update){    int ret_val = 0;     if (vp8_read_bit(bc))    {        ret_val = vp8_read_literal(bc, 4);         if (vp8_read_bit(bc))            ret_val = -ret_val;    }     /* Trigger a quantizer update if the delta-q value has changed */    if (ret_val != prev)        *q_update = 1;     return ret_val;} #ifdef PACKET_TESTING#include <stdio.h>FILE *vpxlog = 0;#endif static void yv12_extend_frame_top_c(YV12_BUFFER_CONFIG *ybf){    int i;    unsigned char *src_ptr1;    unsigned char *dest_ptr1;     unsigned int Border;    int plane_stride;     /***********/    /* Y Plane */    /***********/    Border = ybf->border;    plane_stride = ybf->y_stride;    src_ptr1 = ybf->y_buffer - Border;    dest_ptr1 = src_ptr1 - (Border * plane_stride);     for (i = 0; i < (int)Border; i++)    {        vpx_memcpy(dest_ptr1, src_ptr1, plane_stride);        dest_ptr1 += plane_stride;    }      /***********/    /* U Plane */    /***********/    plane_stride = ybf->uv_stride;    Border /= 2;    src_ptr1 = ybf->u_buffer - Border;    dest_ptr1 = src_ptr1 - (Border * plane_stride);     for (i = 0; i < (int)(Border); i++)    {        vpx_memcpy(dest_ptr1, src_ptr1, plane_stride);        dest_ptr1 += plane_stride;    }     /***********/    /* V Plane */    /***********/     src_ptr1 = ybf->v_buffer - Border;    dest_ptr1 = src_ptr1 - (Border * plane_stride);     for (i = 0; i < (int)(Border); i++)    {        vpx_memcpy(dest_ptr1, src_ptr1, plane_stride);        dest_ptr1 += plane_stride;    }} static void yv12_extend_frame_bottom_c(YV12_BUFFER_CONFIG *ybf){    int i;    unsigned char *src_ptr1, *src_ptr2;    unsigned char *dest_ptr2;     unsigned int Border;    int plane_stride;    int plane_height;     /***********/    /* Y Plane */    /***********/    Border = ybf->border;    plane_stride = ybf->y_stride;    plane_height = ybf->y_height;     src_ptr1 = ybf->y_buffer - Border;    src_ptr2 = src_ptr1 + (plane_height * plane_stride) - plane_stride;    dest_ptr2 = src_ptr2 + plane_stride;     for (i = 0; i < (int)Border; i++)    {        vpx_memcpy(dest_ptr2, src_ptr2, plane_stride);        dest_ptr2 += plane_stride;    }      /***********/    /* U Plane */    /***********/    plane_stride = ybf->uv_stride;    plane_height = ybf->uv_height;    Border /= 2;     src_ptr1 = ybf->u_buffer - Border;    src_ptr2 = src_ptr1 + (plane_height * plane_stride) - plane_stride;    dest_ptr2 = src_ptr2 + plane_stride;     for (i = 0; i < (int)(Border); i++)    {        vpx_memcpy(dest_ptr2, src_ptr2, plane_stride);        dest_ptr2 += plane_stride;    }     /***********/    /* V Plane */    /***********/     src_ptr1 = ybf->v_buffer - Border;    src_ptr2 = src_ptr1 + (plane_height * plane_stride) - plane_stride;    dest_ptr2 = src_ptr2 + plane_stride;     for (i = 0; i < (int)(Border); i++)    {        vpx_memcpy(dest_ptr2, src_ptr2, plane_stride);        dest_ptr2 += plane_stride;    }} static void yv12_extend_frame_left_right_c(YV12_BUFFER_CONFIG *ybf,                                           unsigned char *y_src,                                           unsigned char *u_src,                                           unsigned char *v_src){    int i;    unsigned char *src_ptr1, *src_ptr2;    unsigned char *dest_ptr1, *dest_ptr2;     unsigned int Border;    int plane_stride;    int plane_height;    int plane_width;     /***********/    /* Y Plane */    /***********/    Border = ybf->border;    plane_stride = ybf->y_stride;    plane_height = 16;    plane_width = ybf->y_width;     /* copy the left and right most columns out */    src_ptr1 = y_src;    src_ptr2 = src_ptr1 + plane_width - 1;    dest_ptr1 = src_ptr1 - Border;    dest_ptr2 = src_ptr2 + 1;     for (i = 0; i < plane_height; i++)    {        vpx_memset(dest_ptr1, src_ptr1[0], Border);        vpx_memset(dest_ptr2, src_ptr2[0], Border);        src_ptr1  += plane_stride;        src_ptr2  += plane_stride;        dest_ptr1 += plane_stride;        dest_ptr2 += plane_stride;    }     /***********/    /* U Plane */    /***********/    plane_stride = ybf->uv_stride;    plane_height = 8;    plane_width = ybf->uv_width;    Border /= 2;     /* copy the left and right most columns out */    src_ptr1 = u_src;    src_ptr2 = src_ptr1 + plane_width - 1;    dest_ptr1 = src_ptr1 - Border;    dest_ptr2 = src_ptr2 + 1;     for (i = 0; i < plane_height; i++)    {        vpx_memset(dest_ptr1, src_ptr1[0], Border);        vpx_memset(dest_ptr2, src_ptr2[0], Border);        src_ptr1  += plane_stride;        src_ptr2  += plane_stride;        dest_ptr1 += plane_stride;        dest_ptr2 += plane_stride;    }     /***********/    /* V Plane */    /***********/     /* copy the left and right most columns out */    src_ptr1 = v_src;    src_ptr2 = src_ptr1 + plane_width - 1;    dest_ptr1 = src_ptr1 - Border;    dest_ptr2 = src_ptr2 + 1;     for (i = 0; i < plane_height; i++)    {        vpx_memset(dest_ptr1, src_ptr1[0], Border);        vpx_memset(dest_ptr2, src_ptr2[0], Border);        src_ptr1  += plane_stride;        src_ptr2  += plane_stride;        dest_ptr1 += plane_stride;

Lines 1–500 of 1385.

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t