decodframe.c 45.3 KB
Newer Older
John Koleszar's avatar
John Koleszar committed
1
/*
2
 *  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
John Koleszar's avatar
John Koleszar committed
3
 *
4
 *  Use of this source code is governed by a BSD-style license
5 6
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
7
 *  in the file PATENTS.  All contributing project authors may
8
 *  be found in the AUTHORS file in the root of the source tree.
John Koleszar's avatar
John Koleszar committed
9 10 11 12
 */


#include "onyxd_int.h"
John Koleszar's avatar
John Koleszar committed
13 14 15 16 17
#include "vp8/common/header.h"
#include "vp8/common/reconintra.h"
#include "vp8/common/reconintra4x4.h"
#include "vp8/common/recon.h"
#include "vp8/common/reconinter.h"
John Koleszar's avatar
John Koleszar committed
18 19
#include "dequantize.h"
#include "detokenize.h"
John Koleszar's avatar
John Koleszar committed
20 21 22 23
#include "vp8/common/invtrans.h"
#include "vp8/common/alloccommon.h"
#include "vp8/common/entropymode.h"
#include "vp8/common/quant_common.h"
24 25
#include "vpx_scale/vpxscale.h"
#include "vpx_scale/yv12extend.h"
John Koleszar's avatar
John Koleszar committed
26
#include "vp8/common/setupintrarecon.h"
Scott LaVarnway's avatar
Scott LaVarnway committed
27

John Koleszar's avatar
John Koleszar committed
28
#include "decodemv.h"
John Koleszar's avatar
John Koleszar committed
29
#include "vp8/common/extend.h"
Yaowu Xu's avatar
Yaowu Xu committed
30
#include "vp8/common/modecont.h"
John Koleszar's avatar
John Koleszar committed
31
#include "vpx_mem/vpx_mem.h"
John Koleszar's avatar
John Koleszar committed
32
#include "vp8/common/idct.h"
John Koleszar's avatar
John Koleszar committed
33 34 35
#include "dequantize.h"
#include "dboolhuff.h"

36
#include "vp8/common/seg_common.h"
37
#include "vp8/common/entropy.h"
38

John Koleszar's avatar
John Koleszar committed
39 40 41
#include <assert.h>
#include <stdio.h>

42

43 44 45 46
#ifdef DEC_DEBUG
int dec_debug = 0;
#endif

47 48
#define COEFCOUNT_TESTING

John Koleszar's avatar
John Koleszar committed
49 50 51 52 53 54 55 56 57 58 59 60
static int merge_index(int v, int n, int modulus) {
  int max1 = (n - 1 - modulus / 2) / modulus + 1;
  if (v < max1) v = v * modulus + modulus / 2;
  else {
    int w;
    v -= max1;
    w = v;
    v += (v + modulus - modulus / 2) / modulus;
    while (v % modulus == modulus / 2 ||
           w != v - (v + modulus - modulus / 2) / modulus) v++;
  }
  return v;
61 62
}

John Koleszar's avatar
John Koleszar committed
63 64 65
static int inv_remap_prob(int v, int m) {
  const int n = 256;
  const int modulus = MODULUS_PARAM;
66
  int i;
John Koleszar's avatar
John Koleszar committed
67 68 69 70 71 72 73
  v = merge_index(v, n - 1, modulus);
  if ((m << 1) <= n) {
    i = inv_recenter_nonneg(v + 1, m);
  } else {
    i = n - 1 - inv_recenter_nonneg(v + 1, n - 1 - m);
  }
  return i;
74
}
75

John Koleszar's avatar
John Koleszar committed
76 77 78
static vp8_prob read_prob_diff_update(vp8_reader *const bc, int oldp) {
  int delp = vp8_decode_term_subexp(bc, SUBEXP_PARAM, 255);
  return (vp8_prob)inv_remap_prob(delp, oldp);
79
}
80

John Koleszar's avatar
John Koleszar committed
81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97
void vp8cx_init_de_quantizer(VP8D_COMP *pbi) {
  int i;
  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);

    /* all the ac values =; */
    for (i = 1; i < 16; i++) {
      int rc = vp8_default_zig_zag1d[i];

      pc->Y1dequant[Q][rc] = (short)vp8_ac_yquant(Q);
      pc->Y2dequant[Q][rc] = (short)vp8_ac2quant(Q, pc->y2ac_delta_q);
      pc->UVdequant[Q][rc] = (short)vp8_ac_uv_quant(Q, pc->uvac_delta_q);
John Koleszar's avatar
John Koleszar committed
98
    }
John Koleszar's avatar
John Koleszar committed
99
  }
John Koleszar's avatar
John Koleszar committed
100 101
}

John Koleszar's avatar
John Koleszar committed
102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118
void mb_init_dequantizer(VP8D_COMP *pbi, MACROBLOCKD *xd) {
  int i;
  int QIndex;
  VP8_COMMON *const pc = & pbi->common;
  int segment_id = xd->mode_info_context->mbmi.segment_id;

  // Set the Q baseline allowing for any segment level adjustment
  if (segfeature_active(xd, segment_id, SEG_LVL_ALT_Q)) {
    /* Abs Value */
    if (xd->mb_segment_abs_delta == SEGMENT_ABSDATA)
      QIndex = get_segdata(xd, segment_id, SEG_LVL_ALT_Q);

    /* Delta Value */
    else {
      QIndex = pc->base_qindex +
               get_segdata(xd, segment_id, SEG_LVL_ALT_Q);
      QIndex = (QIndex >= 0) ? ((QIndex <= MAXQ) ? QIndex : MAXQ) : 0;    /* Clamp to valid range */
John Koleszar's avatar
John Koleszar committed
119
    }
John Koleszar's avatar
John Koleszar committed
120 121
  } else
    QIndex = pc->base_qindex;
John Koleszar's avatar
John Koleszar committed
122

John Koleszar's avatar
John Koleszar committed
123 124 125 126
  /* Set up the block level dequant pointers */
  for (i = 0; i < 16; i++) {
    xd->block[i].dequant = pc->Y1dequant[QIndex];
  }
John Koleszar's avatar
John Koleszar committed
127

Jingning Han's avatar
Jingning Han committed
128 129 130 131 132
#if CONFIG_HYBRIDTRANSFORM
  xd->q_index = QIndex;
#endif


Hui Su's avatar
Hui Su committed
133
#if CONFIG_LOSSLESS
John Koleszar's avatar
John Koleszar committed
134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156
  if (!QIndex) {
    pbi->common.rtcd.idct.idct1        = vp8_short_inv_walsh4x4_1_x8_c;
    pbi->common.rtcd.idct.idct16       = vp8_short_inv_walsh4x4_x8_c;
    pbi->common.rtcd.idct.idct1_scalar_add  = vp8_dc_only_inv_walsh_add_c;
    pbi->common.rtcd.idct.iwalsh1      = vp8_short_inv_walsh4x4_1_lossless_c;
    pbi->common.rtcd.idct.iwalsh16     = vp8_short_inv_walsh4x4_lossless_c;
    pbi->dequant.idct_add            = vp8_dequant_idct_add_lossless_c;
    pbi->dequant.dc_idct_add         = vp8_dequant_dc_idct_add_lossless_c;
    pbi->dequant.dc_idct_add_y_block = vp8_dequant_dc_idct_add_y_block_lossless_c;
    pbi->dequant.idct_add_y_block    = vp8_dequant_idct_add_y_block_lossless_c;
    pbi->dequant.idct_add_uv_block   = vp8_dequant_idct_add_uv_block_lossless_c;
  } else {
    pbi->common.rtcd.idct.idct1        = vp8_short_idct4x4llm_1_c;
    pbi->common.rtcd.idct.idct16       = vp8_short_idct4x4llm_c;
    pbi->common.rtcd.idct.idct1_scalar_add  = vp8_dc_only_idct_add_c;
    pbi->common.rtcd.idct.iwalsh1      = vp8_short_inv_walsh4x4_1_c;
    pbi->common.rtcd.idct.iwalsh16     = vp8_short_inv_walsh4x4_c;
    pbi->dequant.idct_add            = vp8_dequant_idct_add_c;
    pbi->dequant.dc_idct_add         = vp8_dequant_dc_idct_add_c;
    pbi->dequant.dc_idct_add_y_block = vp8_dequant_dc_idct_add_y_block_c;
    pbi->dequant.idct_add_y_block    = vp8_dequant_idct_add_y_block_c;
    pbi->dequant.idct_add_uv_block   = vp8_dequant_idct_add_uv_block_c;
  }
Hui Su's avatar
Hui Su committed
157 158
#endif

John Koleszar's avatar
John Koleszar committed
159 160 161
  for (i = 16; i < 24; i++) {
    xd->block[i].dequant = pc->UVdequant[QIndex];
  }
John Koleszar's avatar
John Koleszar committed
162

John Koleszar's avatar
John Koleszar committed
163
  xd->block[24].dequant = pc->Y2dequant[QIndex];
John Koleszar's avatar
John Koleszar committed
164 165 166 167 168 169 170 171 172

}

#if CONFIG_RUNTIME_CPU_DETECT
#define RTCD_VTABLE(x) (&(pbi)->common.rtcd.x)
#else
#define RTCD_VTABLE(x) NULL
#endif

173 174 175
/* skip_recon_mb() is Modified: Instead of writing the result to predictor buffer and then copying it
 *  to dst buffer, we can write the result directly to dst buffer. This eliminates unnecessary copy.
 */
John Koleszar's avatar
John Koleszar committed
176 177 178 179 180 181
static void skip_recon_mb(VP8D_COMP *pbi, MACROBLOCKD *xd) {
  if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
    RECON_INVOKE(&pbi->common.rtcd.recon, build_intra_predictors_mbuv_s)(xd);
    RECON_INVOKE(&pbi->common.rtcd.recon,
                 build_intra_predictors_mby_s)(xd);
  } else {
182 183 184
    vp8_build_1st_inter16x16_predictors_mb(xd, xd->dst.y_buffer,
                                           xd->dst.u_buffer, xd->dst.v_buffer,
                                           xd->dst.y_stride, xd->dst.uv_stride);
John Koleszar's avatar
John Koleszar committed
185 186 187 188 189

    if (xd->mode_info_context->mbmi.second_ref_frame) {
      vp8_build_2nd_inter16x16_predictors_mb(xd, xd->dst.y_buffer,
                                             xd->dst.u_buffer, xd->dst.v_buffer,
                                             xd->dst.y_stride, xd->dst.uv_stride);
190
    }
John Koleszar's avatar
John Koleszar committed
191
  }
192
#ifdef DEC_DEBUG
John Koleszar's avatar
John Koleszar committed
193 194 195 196 197 198 199 200
  if (dec_debug) {
    int i, j;
    printf("Generating predictors\n");
    for (i = 0; i < 16; i++) {
      for (j = 0; j < 16; j++) printf("%3d ", xd->dst.y_buffer[i * xd->dst.y_stride + j]);
      printf("\n");
    }
  }
201
#endif
202

John Koleszar's avatar
John Koleszar committed
203 204
}

Yaowu Xu's avatar
Yaowu Xu committed
205
extern const int vp8_i8x8_block[4];
206
static void decode_macroblock(VP8D_COMP *pbi, MACROBLOCKD *xd,
John Koleszar's avatar
John Koleszar committed
207 208 209 210 211 212
                              unsigned int mb_idx) {
  int eobtotal = 0;
  MB_PREDICTION_MODE mode;
  int i;
  int tx_type;

Jingning Han's avatar
Jingning Han committed
213
#if CONFIG_HYBRIDTRANSFORM
Jingning Han's avatar
Jingning Han committed
214 215
  int QIndex;
  int active_ht;
Jingning Han's avatar
Jingning Han committed
216 217
#endif

Jingning Han's avatar
Jingning Han committed
218 219 220 221
  // re-initialize macroblock dequantizer before detokenization
  if (xd->segmentation_enabled)
    mb_init_dequantizer(pbi, xd);

John Koleszar's avatar
John Koleszar committed
222
  if (pbi->common.frame_type == KEY_FRAME) {
Daniel Kang's avatar
Daniel Kang committed
223 224 225 226 227 228 229 230
#if CONFIG_TX16X16
    if (xd->mode_info_context->mbmi.mode <= TM_PRED ||
        xd->mode_info_context->mbmi.mode == NEWMV ||
        xd->mode_info_context->mbmi.mode == ZEROMV ||
        xd->mode_info_context->mbmi.mode == NEARMV ||
        xd->mode_info_context->mbmi.mode == NEARESTMV)
      xd->mode_info_context->mbmi.txfm_size = TX_16X16;
    else if (pbi->common.txfm_mode == ALLOW_8X8 &&
John Koleszar's avatar
John Koleszar committed
231 232
        xd->mode_info_context->mbmi.mode != I8X8_PRED &&
        xd->mode_info_context->mbmi.mode != B_PRED)
Daniel Kang's avatar
Daniel Kang committed
233 234 235 236 237
#else
      if (pbi->common.txfm_mode == ALLOW_8X8 &&
          xd->mode_info_context->mbmi.mode != I8X8_PRED &&
          xd->mode_info_context->mbmi.mode != B_PRED)
#endif
John Koleszar's avatar
John Koleszar committed
238
      xd->mode_info_context->mbmi.txfm_size = TX_8X8;
239
    else
John Koleszar's avatar
John Koleszar committed
240 241
      xd->mode_info_context->mbmi.txfm_size = TX_4X4;
  } else {
Daniel Kang's avatar
Daniel Kang committed
242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261
#if CONFIG_TX16X16
    if (xd->mode_info_context->mbmi.mode <= TM_PRED ||
        xd->mode_info_context->mbmi.mode == NEWMV ||
        xd->mode_info_context->mbmi.mode == ZEROMV ||
        xd->mode_info_context->mbmi.mode == NEARMV ||
        xd->mode_info_context->mbmi.mode == NEARESTMV) {
      xd->mode_info_context->mbmi.txfm_size = TX_16X16;
    } else if (pbi->common.txfm_mode == ALLOW_8X8 &&
        xd->mode_info_context->mbmi.mode != I8X8_PRED &&
        xd->mode_info_context->mbmi.mode != B_PRED &&
        xd->mode_info_context->mbmi.mode != SPLITMV) {
#else
    if (pbi->common.txfm_mode == ALLOW_8X8 &&
        xd->mode_info_context->mbmi.mode != I8X8_PRED &&
        xd->mode_info_context->mbmi.mode != B_PRED &&
        xd->mode_info_context->mbmi.mode != SPLITMV) {
#endif
      xd->mode_info_context->mbmi.txfm_size = TX_8X8;
    }
    else {
John Koleszar's avatar
John Koleszar committed
262
      xd->mode_info_context->mbmi.txfm_size = TX_4X4;
263
    }
John Koleszar's avatar
John Koleszar committed
264
  }
265

266
#if CONFIG_HYBRIDTRANSFORM8X8
267 268 269 270 271
  if (xd->mode_info_context->mbmi.mode == I8X8_PRED) {
    xd->mode_info_context->mbmi.txfm_size = TX_8X8;
  }
#endif

John Koleszar's avatar
John Koleszar committed
272 273 274 275 276 277 278 279
  tx_type = xd->mode_info_context->mbmi.txfm_size;

  if (xd->mode_info_context->mbmi.mb_skip_coeff) {
    vp8_reset_mb_tokens_context(xd);
  } else if (!vp8dx_bool_error(xd->current_bc)) {
    for (i = 0; i < 25; i++) {
      xd->block[i].eob = 0;
      xd->eobs[i] = 0;
280
    }
Daniel Kang's avatar
Daniel Kang committed
281 282 283 284 285
#if CONFIG_TX16X16
    if (tx_type == TX_16X16)
      eobtotal = vp8_decode_mb_tokens_16x16(pbi, xd);
    else
#endif
John Koleszar's avatar
John Koleszar committed
286 287 288 289
    if (tx_type == TX_8X8)
      eobtotal = vp8_decode_mb_tokens_8x8(pbi, xd);
    else
      eobtotal = vp8_decode_mb_tokens(pbi, xd);
290
#ifdef DEC_DEBUG
John Koleszar's avatar
John Koleszar committed
291 292 293 294 295 296 297
    if (dec_debug) {
      printf("\nTokens (%d)\n", eobtotal);
      for (i = 0; i < 400; i++) {
        printf("%3d ", xd->qcoeff[i]);
        if (i % 16 == 15) printf("\n");
      }
      printf("\n");
298
    }
John Koleszar's avatar
John Koleszar committed
299 300
#endif
  }
301

John Koleszar's avatar
John Koleszar committed
302
  mode = xd->mode_info_context->mbmi.mode;
303 304 305 306 307
#if CONFIG_SWITCHABLE_INTERP
  if (pbi->common.frame_type != KEY_FRAME)
    vp8_setup_interp_filters(xd, xd->mode_info_context->mbmi.interp_filter,
                             &pbi->common);
#endif
Gaute Strokkenes's avatar
Gaute Strokkenes committed
308

John Koleszar's avatar
John Koleszar committed
309 310 311 312 313 314 315 316
  if (eobtotal == 0 && mode != B_PRED && mode != SPLITMV
      && mode != I8X8_PRED
      && !vp8dx_bool_error(xd->current_bc)
     ) {
    /* Special case:  Force the loopfilter to skip when eobtotal and
     * mb_skip_coeff are zero.
     * */
    xd->mode_info_context->mbmi.mb_skip_coeff = 1;
Scott LaVarnway's avatar
Scott LaVarnway committed
317

John Koleszar's avatar
John Koleszar committed
318 319 320
    skip_recon_mb(pbi, xd);
    return;
  }
Yaowu Xu's avatar
Yaowu Xu committed
321

322
#ifdef DEC_DEBUG
John Koleszar's avatar
John Koleszar committed
323 324 325 326 327 328 329 330
  if (dec_debug) {
    int i, j;
    printf("Generating predictors\n");
    for (i = 0; i < 16; i++) {
      for (j = 0; j < 16; j++) printf("%3d ", xd->dst.y_buffer[i * xd->dst.y_stride + j]);
      printf("\n");
    }
  }
331 332
#endif

Jingning Han's avatar
Jingning Han committed
333 334 335
  // moved to be performed before detokenization
//  if (xd->segmentation_enabled)
//    mb_init_dequantizer(pbi, xd);
336

Jingning Han's avatar
Jingning Han committed
337 338
#if CONFIG_HYBRIDTRANSFORM
  // parse transform types for intra 4x4 mode
Jingning Han's avatar
Jingning Han committed
339 340
  QIndex = xd->q_index;
  active_ht = (QIndex < ACTIVE_HT);
Jingning Han's avatar
Jingning Han committed
341 342 343 344
  if (mode == B_PRED) {
    for (i = 0; i < 16; i++) {
      BLOCKD *b = &xd->block[i];
      int b_mode = xd->mode_info_context->bmi[i].as_mode.first;
345 346
      if(active_ht)
        txfm_map(b, b_mode);
Jingning Han's avatar
Jingning Han committed
347 348 349 350
    } // loop over 4x4 blocks
  }
#endif

John Koleszar's avatar
John Koleszar committed
351 352 353 354 355 356 357 358
  /* do prediction */
  if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
    if (mode != I8X8_PRED) {
      RECON_INVOKE(&pbi->common.rtcd.recon, build_intra_predictors_mbuv)(xd);
      if (mode != B_PRED) {
        RECON_INVOKE(&pbi->common.rtcd.recon,
                     build_intra_predictors_mby)(xd);
      }
Adrian Grange's avatar
Adrian Grange committed
359
#if 0
John Koleszar's avatar
John Koleszar committed
360 361 362 363 364
      // Intra-modes requiring recon data from top-right
      // MB have been temporarily disabled.
      else {
        vp8_intra_prediction_down_copy(xd);
      }
Adrian Grange's avatar
Adrian Grange committed
365
#endif
John Koleszar's avatar
John Koleszar committed
366
    }
John Koleszar's avatar
John Koleszar committed
367 368 369 370 371 372 373 374 375 376 377 378 379
  } else {
    vp8_build_inter_predictors_mb(xd);
  }

  /* dequantization and idct */
  if (mode == I8X8_PRED) {
    for (i = 0; i < 4; i++) {
      int ib = vp8_i8x8_block[i];
      const int iblock[4] = {0, 1, 4, 5};
      int j;
      int i8x8mode;
      BLOCKD *b;

380
#if CONFIG_HYBRIDTRANSFORM8X8
381 382 383 384 385 386 387 388 389 390 391 392
      int idx = (ib & 0x02) ? (ib + 2) : ib;

      short *q  = xd->block[idx].qcoeff;
      short *dq = xd->block[0].dequant;
      unsigned char *pre = xd->block[ib].predictor;
      unsigned char *dst = *(xd->block[ib].base_dst) + xd->block[ib].dst;
      int stride = xd->dst.y_stride;

      tx_type = TX_4X4;
      xd->mode_info_context->mbmi.txfm_size = TX_4X4;
#endif

John Koleszar's avatar
John Koleszar committed
393 394 395 396 397
      b = &xd->block[ib];
      i8x8mode = b->bmi.as_mode.first;
      RECON_INVOKE(RTCD_VTABLE(recon), intra8x8_predict)
      (b, i8x8mode, b->predictor);

398 399 400 401
#if CONFIG_HYBRIDTRANSFORM8X8
      txfm_map(b, pred_mode_conv(i8x8mode));
      vp8_ht_dequant_idct_add_8x8_c(b->bmi.as_mode.tx_type,
                                    q, dq, pre, dst, 16, stride);
402 403
      q += 64;
#else
John Koleszar's avatar
John Koleszar committed
404 405 406 407 408 409 410 411 412 413 414
      for (j = 0; j < 4; j++) {
        b = &xd->block[ib + iblock[j]];
        if (xd->eobs[ib + iblock[j]] > 1) {
          DEQUANT_INVOKE(&pbi->dequant, idct_add)
          (b->qcoeff, b->dequant,  b->predictor,
           *(b->base_dst) + b->dst, 16, b->dst_stride);
        } else {
          IDCT_INVOKE(RTCD_VTABLE(idct), idct1_scalar_add)
          (b->qcoeff[0] * b->dequant[0], b->predictor,
           *(b->base_dst) + b->dst, 16, b->dst_stride);
          ((int *)b->qcoeff)[0] = 0;
Yaowu Xu's avatar
Yaowu Xu committed
415
        }
John Koleszar's avatar
John Koleszar committed
416
      }
417
#endif
John Koleszar's avatar
John Koleszar committed
418 419 420 421 422 423 424 425 426 427 428 429 430

      b = &xd->block[16 + i];
      RECON_INVOKE(RTCD_VTABLE(recon), intra_uv4x4_predict)
      (b, i8x8mode, b->predictor);
      DEQUANT_INVOKE(&pbi->dequant, idct_add)
      (b->qcoeff, b->dequant,  b->predictor,
       *(b->base_dst) + b->dst, 8, b->dst_stride);
      b = &xd->block[20 + i];
      RECON_INVOKE(RTCD_VTABLE(recon), intra_uv4x4_predict)
      (b, i8x8mode, b->predictor);
      DEQUANT_INVOKE(&pbi->dequant, idct_add)
      (b->qcoeff, b->dequant,  b->predictor,
       *(b->base_dst) + b->dst, 8, b->dst_stride);
Yaowu Xu's avatar
Yaowu Xu committed
431
    }
John Koleszar's avatar
John Koleszar committed
432 433 434 435
  } else if (mode == B_PRED) {
    for (i = 0; i < 16; i++) {
      BLOCKD *b = &xd->block[i];
      int b_mode = xd->mode_info_context->bmi[i].as_mode.first;
436
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
437
      int b_mode2 = xd->mode_info_context->bmi[i].as_mode.second;
438

John Koleszar's avatar
John Koleszar committed
439
      if (b_mode2 == (B_PREDICTION_MODE)(B_DC_PRED - 1)) {
440
#endif
John Koleszar's avatar
John Koleszar committed
441 442
        RECON_INVOKE(RTCD_VTABLE(recon), intra4x4_predict)
        (b, b_mode, b->predictor);
443
#if CONFIG_COMP_INTRA_PRED
John Koleszar's avatar
John Koleszar committed
444 445 446 447
      } else {
        RECON_INVOKE(RTCD_VTABLE(recon), comp_intra4x4_predict)
        (b, b_mode, b_mode2, b->predictor);
      }
448
#endif
John Koleszar's avatar
John Koleszar committed
449

Jingning Han's avatar
Jingning Han committed
450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470
#if CONFIG_HYBRIDTRANSFORM
      if(active_ht)
        vp8_ht_dequant_idct_add_c( (TX_TYPE)b->bmi.as_mode.tx_type, b->qcoeff,
                                   b->dequant, b->predictor,
                                   *(b->base_dst) + b->dst, 16, b->dst_stride);
      else
        vp8_dequant_idct_add_c(b->qcoeff, b->dequant, b->predictor,
                               *(b->base_dst) + b->dst, 16, b->dst_stride);
#else
      if (xd->eobs[i] > 1)
      {
          DEQUANT_INVOKE(&pbi->dequant, idct_add)
              (b->qcoeff, b->dequant,  b->predictor,
              *(b->base_dst) + b->dst, 16, b->dst_stride);
      }
      else
      {
          IDCT_INVOKE(RTCD_VTABLE(idct), idct1_scalar_add)
              (b->qcoeff[0] * b->dequant[0], b->predictor,
              *(b->base_dst) + b->dst, 16, b->dst_stride);
          ((int *)b->qcoeff)[0] = 0;
John Koleszar's avatar
John Koleszar committed
471
      }
Jingning Han's avatar
Jingning Han committed
472
#endif
John Koleszar's avatar
John Koleszar committed
473
    }
John Koleszar's avatar
John Koleszar committed
474 475 476 477 478 479 480
  } else if (mode == SPLITMV) {
    DEQUANT_INVOKE(&pbi->dequant, idct_add_y_block)
    (xd->qcoeff, xd->block[0].dequant,
     xd->predictor, xd->dst.y_buffer,
     xd->dst.y_stride, xd->eobs);
  } else {
    BLOCKD *b = &xd->block[24];
Daniel Kang's avatar
Daniel Kang committed
481 482 483 484 485 486 487 488 489

#if CONFIG_TX16X16
    if (tx_type == TX_16X16) {
      vp8_dequant_idct_add_16x16_c(xd->qcoeff, xd->block[0].dequant,
                                   xd->predictor, xd->dst.y_buffer,
                                   16, xd->dst.y_stride);
    }
    else
#endif
John Koleszar's avatar
John Koleszar committed
490 491
    if (tx_type == TX_8X8) {
      DEQUANT_INVOKE(&pbi->dequant, block_2x2)(b);
492
#ifdef DEC_DEBUG
John Koleszar's avatar
John Koleszar committed
493 494 495 496 497
      if (dec_debug) {
        int j;
        printf("DQcoeff Haar\n");
        for (j = 0; j < 16; j++) {
          printf("%d ", b->dqcoeff[j]);
Yaowu Xu's avatar
Yaowu Xu committed
498
        }
John Koleszar's avatar
John Koleszar committed
499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535
        printf("\n");
      }
#endif
      IDCT_INVOKE(RTCD_VTABLE(idct), ihaar2)(&b->dqcoeff[0], b->diff, 8);
      ((int *)b->qcoeff)[0] = 0;// 2nd order block are set to 0 after inverse transform
      ((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;
      DEQUANT_INVOKE(&pbi->dequant, dc_idct_add_y_block_8x8)
      (xd->qcoeff, xd->block[0].dequant,
       xd->predictor, xd->dst.y_buffer,
       xd->dst.y_stride, xd->eobs, xd->block[24].diff, xd);
    } else {
      DEQUANT_INVOKE(&pbi->dequant, block)(b);
      if (xd->eobs[24] > 1) {
        IDCT_INVOKE(RTCD_VTABLE(idct), iwalsh16)(&b->dqcoeff[0], b->diff);
        ((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 {
        IDCT_INVOKE(RTCD_VTABLE(idct), iwalsh1)(&b->dqcoeff[0], b->diff);
        ((int *)b->qcoeff)[0] = 0;
      }

      DEQUANT_INVOKE(&pbi->dequant, dc_idct_add_y_block)
      (xd->qcoeff, xd->block[0].dequant,
       xd->predictor, xd->dst.y_buffer,
       xd->dst.y_stride, xd->eobs, xd->block[24].diff);
536
    }
John Koleszar's avatar
John Koleszar committed
537 538
  }

Daniel Kang's avatar
Daniel Kang committed
539 540 541 542 543
  if (tx_type == TX_8X8
#if CONFIG_TX16X16
      || tx_type == TX_16X16
#endif
      )
John Koleszar's avatar
John Koleszar committed
544 545 546 547 548 549 550 551 552
    DEQUANT_INVOKE(&pbi->dequant, idct_add_uv_block_8x8) //
    (xd->qcoeff + 16 * 16, xd->block[16].dequant,
     xd->predictor + 16 * 16, xd->dst.u_buffer, xd->dst.v_buffer,
     xd->dst.uv_stride, xd->eobs + 16, xd); //
  else if (xd->mode_info_context->mbmi.mode != I8X8_PRED)
    DEQUANT_INVOKE(&pbi->dequant, idct_add_uv_block)
    (xd->qcoeff + 16 * 16, xd->block[16].dequant,
     xd->predictor + 16 * 16, xd->dst.u_buffer, xd->dst.v_buffer,
     xd->dst.uv_stride, xd->eobs + 16);
Yaowu Xu's avatar
Yaowu Xu committed
553
}
John Koleszar's avatar
John Koleszar committed
554

555

John Koleszar's avatar
John Koleszar committed
556 557
static int get_delta_q(vp8_reader *bc, int prev, int *q_update) {
  int ret_val = 0;
John Koleszar's avatar
John Koleszar committed
558

John Koleszar's avatar
John Koleszar committed
559 560
  if (vp8_read_bit(bc)) {
    ret_val = vp8_read_literal(bc, 4);
John Koleszar's avatar
John Koleszar committed
561

John Koleszar's avatar
John Koleszar committed
562 563 564
    if (vp8_read_bit(bc))
      ret_val = -ret_val;
  }
John Koleszar's avatar
John Koleszar committed
565

John Koleszar's avatar
John Koleszar committed
566 567 568
  /* Trigger a quantizer update if the delta-q value has changed */
  if (ret_val != prev)
    *q_update = 1;
John Koleszar's avatar
John Koleszar committed
569

John Koleszar's avatar
John Koleszar committed
570
  return ret_val;
John Koleszar's avatar
John Koleszar committed
571 572 573 574 575 576 577
}

#ifdef PACKET_TESTING
#include <stdio.h>
FILE *vpxlog = 0;
#endif

Adrian Grange's avatar
Adrian Grange committed
578
/* Decode a row of Superblocks (2x2 region of MBs) */
579
static void
John Koleszar's avatar
John Koleszar committed
580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 606 607 608 609 610 611 612
decode_sb_row(VP8D_COMP *pbi, VP8_COMMON *pc, int mbrow, MACROBLOCKD *xd) {
  int i;
  int sb_col;
  int mb_row, mb_col;
  int recon_yoffset, recon_uvoffset;
  int ref_fb_idx = pc->lst_fb_idx;
  int dst_fb_idx = pc->new_fb_idx;
  int recon_y_stride = pc->yv12_fb[ref_fb_idx].y_stride;
  int recon_uv_stride = pc->yv12_fb[ref_fb_idx].uv_stride;
  int row_delta[4] = { 0, +1,  0, -1};
  int col_delta[4] = { +1, -1, +1, +1};
  int sb_cols = (pc->mb_cols + 1) >> 1;
  ENTROPY_CONTEXT_PLANES left_context[2];

  // For a SB there are 2 left contexts, each pertaining to a MB row within
  vpx_memset(left_context, 0, sizeof(left_context));

  mb_row = mbrow;
  mb_col = 0;

  for (sb_col = 0; sb_col < sb_cols; sb_col++) {
    // Process the 4 MBs within the SB in the order:
    // top-left, top-right, bottom-left, bottom-right
    for (i = 0; i < 4; i++) {
      int dy = row_delta[i];
      int dx = col_delta[i];
      int offset_extended = dy * xd->mode_info_stride + dx;

      if ((mb_row >= pc->mb_rows) || (mb_col >= pc->mb_cols)) {
        // MB lies outside frame, skip on to next
        mb_row += dy;
        mb_col += dx;
        xd->mode_info_context += offset_extended;
613
        xd->prev_mode_info_context += offset_extended;
John Koleszar's avatar
John Koleszar committed
614 615
        continue;
      }
Yaowu Xu's avatar
Yaowu Xu committed
616

Adrian Grange's avatar
Adrian Grange committed
617
#ifdef DEC_DEBUG
John Koleszar's avatar
John Koleszar committed
618
      dec_debug = (pc->current_video_frame == 0 && mb_row == 0 && mb_col == 0);
Adrian Grange's avatar
Adrian Grange committed
619
#endif
John Koleszar's avatar
John Koleszar committed
620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645 646 647 648
      // Copy in the appropriate left context for this MB row
      vpx_memcpy(&pc->left_context,
                 &left_context[i >> 1],
                 sizeof(ENTROPY_CONTEXT_PLANES));

      // Set above context pointer
      xd->above_context = pc->above_context + mb_col;

      /* Distance of Mb to the various image edges.
       * These are specified to 8th pel as they are always compared to
       * values that are in 1/8th pel units
       */
      xd->mb_to_top_edge = -((mb_row * 16)) << 3;
      xd->mb_to_bottom_edge = ((pc->mb_rows - 1 - mb_row) * 16) << 3;

      xd->mb_to_left_edge = -((mb_col * 16) << 3);
      xd->mb_to_right_edge = ((pc->mb_cols - 1 - mb_col) * 16) << 3;

      xd->up_available = (mb_row != 0);
      xd->left_available = (mb_col != 0);


      recon_yoffset = (mb_row * recon_y_stride * 16) + (mb_col * 16);
      recon_uvoffset = (mb_row * recon_uv_stride * 8) + (mb_col * 8);

      xd->dst.y_buffer = pc->yv12_fb[dst_fb_idx].y_buffer + recon_yoffset;
      xd->dst.u_buffer = pc->yv12_fb[dst_fb_idx].u_buffer + recon_uvoffset;
      xd->dst.v_buffer = pc->yv12_fb[dst_fb_idx].v_buffer + recon_uvoffset;

649 650 651 652 653
      if(pbi->interleaved_decoding)
        vpx_decode_mb_mode_mv(pbi, xd, mb_row, mb_col);

      update_blockd_bmi(xd);

John Koleszar's avatar
John Koleszar committed
654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702
      /* Select the appropriate reference frame for this MB */
      if (xd->mode_info_context->mbmi.ref_frame == LAST_FRAME)
        ref_fb_idx = pc->lst_fb_idx;
      else if (xd->mode_info_context->mbmi.ref_frame == GOLDEN_FRAME)
        ref_fb_idx = pc->gld_fb_idx;
      else
        ref_fb_idx = pc->alt_fb_idx;

      xd->pre.y_buffer = pc->yv12_fb[ref_fb_idx].y_buffer + recon_yoffset;
      xd->pre.u_buffer = pc->yv12_fb[ref_fb_idx].u_buffer + recon_uvoffset;
      xd->pre.v_buffer = pc->yv12_fb[ref_fb_idx].v_buffer + recon_uvoffset;

      if (xd->mode_info_context->mbmi.second_ref_frame) {
        int second_ref_fb_idx;

        /* Select the appropriate reference frame for this MB */
        if (xd->mode_info_context->mbmi.second_ref_frame == LAST_FRAME)
          second_ref_fb_idx = pc->lst_fb_idx;
        else if (xd->mode_info_context->mbmi.second_ref_frame ==
                 GOLDEN_FRAME)
          second_ref_fb_idx = pc->gld_fb_idx;
        else
          second_ref_fb_idx = pc->alt_fb_idx;

        xd->second_pre.y_buffer =
          pc->yv12_fb[second_ref_fb_idx].y_buffer + recon_yoffset;
        xd->second_pre.u_buffer =
          pc->yv12_fb[second_ref_fb_idx].u_buffer + recon_uvoffset;
        xd->second_pre.v_buffer =
          pc->yv12_fb[second_ref_fb_idx].v_buffer + recon_uvoffset;
      }

      if (xd->mode_info_context->mbmi.ref_frame != INTRA_FRAME) {
        /* propagate errors from reference frames */
        xd->corrupted |= pc->yv12_fb[ref_fb_idx].corrupted;
      }

      decode_macroblock(pbi, xd, mb_row * pc->mb_cols + mb_col);

      /* check if the boolean decoder has suffered an error */
      xd->corrupted |= vp8dx_bool_error(xd->current_bc);

      // Store the modified left context for the MB row locally
      vpx_memcpy(&left_context[i >> 1],
                 &pc->left_context,
                 sizeof(ENTROPY_CONTEXT_PLANES));

      // skip to next MB
      xd->mode_info_context += offset_extended;
703
      xd->prev_mode_info_context += offset_extended;
John Koleszar's avatar
John Koleszar committed
704 705
      mb_row += dy;
      mb_col += dx;
John Koleszar's avatar
John Koleszar committed
706
    }
John Koleszar's avatar
John Koleszar committed
707
  }
John Koleszar's avatar
John Koleszar committed
708

John Koleszar's avatar
John Koleszar committed
709 710
  /* skip prediction column */
  xd->mode_info_context += 1 - (pc->mb_cols & 0x1) + xd->mode_info_stride;
711
  xd->prev_mode_info_context += 1 - (pc->mb_cols & 0x1) + xd->mode_info_stride;
John Koleszar's avatar
John Koleszar committed
712 713
}

John Koleszar's avatar
John Koleszar committed
714 715 716 717
static unsigned int read_partition_size(const unsigned char *cx_size) {
  const unsigned int size =
    cx_size[0] + (cx_size[1] << 8) + (cx_size[2] << 16);
  return size;
John Koleszar's avatar
John Koleszar committed
718 719
}

720 721
static int read_is_valid(const unsigned char *start,
                         size_t               len,
John Koleszar's avatar
John Koleszar committed
722 723
                         const unsigned char *end) {
  return (start + len > start && start + len <= end);
724 725 726
}


John Koleszar's avatar
John Koleszar committed
727
static void setup_token_decoder(VP8D_COMP *pbi,
John Koleszar's avatar
John Koleszar committed
728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758
                                const unsigned char *cx_data) {
  VP8_COMMON          *pc = &pbi->common;
  const unsigned char *user_data_end = pbi->Source + pbi->source_sz;
  vp8_reader          *bool_decoder;
  const unsigned char *partition;

  ptrdiff_t            partition_size;
  ptrdiff_t            bytes_left;

  // Dummy read for now
  vp8_read_literal(&pbi->bc, 2);

  // Set up pointers to token partition
  partition = cx_data;
  bool_decoder = &pbi->bc2;
  bytes_left = user_data_end - partition;
  partition_size = bytes_left;

  /* Validate the calculated partition length. If the buffer
   * described by the partition can't be fully read, then restrict
   * it to the portion that can be (for EC mode) or throw an error.
   */
  if (!read_is_valid(partition, partition_size, user_data_end)) {
    vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
                       "Truncated packet or corrupt partition "
                       "%d length", 1);
  }

  if (vp8dx_start_decode(bool_decoder, partition, partition_size))
    vpx_internal_error(&pc->error, VPX_CODEC_MEM_ERROR,
                       "Failed to allocate bool decoder %d", 1);
John Koleszar's avatar
John Koleszar committed
759 760
}

John Koleszar's avatar
John Koleszar committed
761 762 763
static void init_frame(VP8D_COMP *pbi) {
  VP8_COMMON *const pc = & pbi->common;
  MACROBLOCKD *const xd  = & pbi->mb;
John Koleszar's avatar
John Koleszar committed
764

John Koleszar's avatar
John Koleszar committed
765 766 767 768 769
  if (pc->frame_type == KEY_FRAME) {
    /* Various keyframe initializations */
    vpx_memcpy(pc->fc.mvc, vp8_default_mv_context, sizeof(vp8_default_mv_context));
    vpx_memcpy(pc->fc.mvc_hp, vp8_default_mv_context_hp,
               sizeof(vp8_default_mv_context_hp));
John Koleszar's avatar
John Koleszar committed
770

John Koleszar's avatar
John Koleszar committed
771
    vp8_init_mbmode_probs(pc);
John Koleszar's avatar
John Koleszar committed
772

John Koleszar's avatar
John Koleszar committed
773 774
    vp8_default_coef_probs(pc);
    vp8_kf_default_bmode_probs(pc->kf_bmode_prob);
John Koleszar's avatar
John Koleszar committed
775

John Koleszar's avatar
John Koleszar committed
776 777 778
    // Reset the segment feature data to the default stats:
    // Features disabled, 0, with delta coding (Default state).
    clearall_segfeatures(xd);
Paul Wilkins's avatar
Paul Wilkins committed
779

John Koleszar's avatar
John Koleszar committed
780
    xd->mb_segment_abs_delta = SEGMENT_DELTADATA;
John Koleszar's avatar
John Koleszar committed
781

John Koleszar's avatar
John Koleszar committed
782 783 784
    /* reset the mode ref deltasa for loop filter */
    vpx_memset(xd->ref_lf_deltas, 0, sizeof(xd->ref_lf_deltas));
    vpx_memset(xd->mode_lf_deltas, 0, sizeof(xd->mode_lf_deltas));
John Koleszar's avatar
John Koleszar committed
785

John Koleszar's avatar
John Koleszar committed
786 787 788 789 790
    /* All buffers are implicitly updated on key frames. */
    pc->refresh_golden_frame = 1;
    pc->refresh_alt_ref_frame = 1;
    pc->copy_buffer_to_gf = 0;
    pc->copy_buffer_to_arf = 0;
John Koleszar's avatar
John Koleszar committed
791

John Koleszar's avatar
John Koleszar committed
792 793 794 795 796
    /* Note that Golden and Altref modes cannot be used on a key frame so
     * ref_frame_sign_bias[] is undefined and meaningless
     */
    pc->ref_frame_sign_bias[GOLDEN_FRAME] = 0;
    pc->ref_frame_sign_bias[ALTREF_FRAME] = 0;
797

John Koleszar's avatar
John Koleszar committed
798 799 800
    vp8_init_mode_contexts(&pbi->common);
    vpx_memcpy(&pc->lfc, &pc->fc, sizeof(pc->fc));
    vpx_memcpy(&pc->lfc_a, &pc->fc, sizeof(pc->fc));
Yaowu Xu's avatar
Yaowu Xu committed
801

John Koleszar's avatar
John Koleszar committed
802 803 804 805
    vpx_memcpy(pbi->common.fc.vp8_mode_contexts,
               pbi->common.fc.mode_context,
               sizeof(pbi->common.fc.mode_context));
  } else {
806

John Koleszar's avatar
John Koleszar committed
807 808 809 810 811
    if (!pc->use_bilinear_mc_filter)
      pc->mcomp_filter_type = EIGHTTAP;
    else
      pc->mcomp_filter_type = BILINEAR;

812
    /* To enable choice of different interpolation filters */
813
    vp8_setup_interp_filters(xd, pc->mcomp_filter_type, pc);
John Koleszar's avatar
John Koleszar committed
814
  }
John Koleszar's avatar
John Koleszar committed
815

John Koleszar's avatar
John Koleszar committed
816 817
  xd->left_context = &pc->left_context;
  xd->mode_info_context = pc->mi;
818
  xd->prev_mode_info_context = pc->prev_mi;
John Koleszar's avatar
John Koleszar committed
819 820 821 822
  xd->frame_type = pc->frame_type;
  xd->mode_info_context->mbmi.mode = DC_PRED;
  xd->mode_info_stride = pc->mode_info_stride;
  xd->corrupted = 0; /* init without corruption */
823

John Koleszar's avatar
John Koleszar committed
824 825 826
  xd->fullpixel_mask = 0xffffffff;
  if (pc->full_pixel)
    xd->fullpixel_mask = 0xfffffff8;
827

John Koleszar's avatar
John Koleszar committed
828 829
}

John Koleszar's avatar
John Koleszar committed
830 831 832 833 834 835 836 837 838 839 840 841 842 843
static void read_coef_probs2(VP8D_COMP *pbi) {
  const vp8_prob grpupd = 192;
  int i, j, k, l;
  vp8_reader *const bc = & pbi->bc;
  VP8_COMMON *const pc = & pbi->common;
  for (l = 0; l < ENTROPY_NODES; l++) {
    if (vp8_read(bc, grpupd)) {
      // printf("Decoding %d\n", l);
      for (i = 0; i < BLOCK_TYPES; i++)
        for (j = !i; j < COEF_BANDS; j++)
          for (k = 0; k < PREV_COEF_CONTEXTS; k++) {
            if (k >= 3 && ((i == 0 && j == 1) ||
                           (i > 0 && j == 0)))
              continue;
844
            {
John Koleszar's avatar
John Koleszar committed
845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862
              vp8_prob *const p = pc->fc.coef_probs [i][j][k] + l;
              int u = vp8_read(bc, COEF_UPDATE_PROB);
              if (u) *p = read_prob_diff_update(bc, *p);
            }
          }
    }
  }
  if (pbi->common.txfm_mode == ALLOW_8X8) {
    for (l = 0; l < ENTROPY_NODES; l++) {
      if (vp8_read(bc, grpupd)) {
        for (i = 0; i < BLOCK_TYPES_8X8; i++)
          for (j = !i; j < COEF_BANDS; j++)
            for (k = 0; k < PREV_COEF_CONTEXTS; k++) {
              if (k >= 3 && ((i == 0 && j == 1) ||
                             (i > 0 && j == 0)))
                continue;
              {
                vp8_prob *const p = pc->fc.coef_probs_8x8 [i][j][k] + l;
863

John Koleszar's avatar
John Koleszar committed
864 865 866
                int u = vp8_read(bc, COEF_UPDATE_PROB_8X8);
                if (u) *p = read_prob_diff_update(bc, *p);
              }
867
            }
John Koleszar's avatar
John Koleszar committed
868
      }
869
    }
John Koleszar's avatar
John Koleszar committed
870
  }
871 872
}

John Koleszar's avatar
John Koleszar committed
873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888
static void read_coef_probs(VP8D_COMP *pbi) {
  int i, j, k, l;
  vp8_reader *const bc = & pbi->bc;
  VP8_COMMON *const pc = & pbi->common;

  {
    if (vp8_read_bit(bc)) {
      /* read coef probability tree */
      for (i = 0; i < BLOCK_TYPES; i++)
        for (j = !i; j < COEF_BANDS; j++)
          for (k = 0; k < PREV_COEF_CONTEXTS; k++) {
            if (k >= 3 && ((i == 0 && j == 1) ||
                           (i > 0 && j == 0)))
              continue;
            for (l = 0; l < ENTROPY_NODES; l++) {
              vp8_prob *const p = pc->fc.coef_probs [i][j][k] + l;
889

John Koleszar's avatar
John Koleszar committed
890 891 892 893 894
              if (vp8_read(bc, COEF_UPDATE_PROB)) {
                *p = read_prob_diff_update(bc, *p);
              }
            }
          }
Daniel Kang's avatar
Daniel Kang committed
895
        }
John Koleszar's avatar
John Koleszar committed
896
  }
897

John Koleszar's avatar
John Koleszar committed
898 899 900 901 902 903 904 905 906
  if (pbi->common.txfm_mode == ALLOW_8X8 && vp8_read_bit(bc)) {
    // read coef probability tree
    for (i = 0; i < BLOCK_TYPES_8X8; i++)
      for (j = !i; j < COEF_BANDS; j++)
        for (k = 0; k < PREV_COEF_CONTEXTS; k++) {
          if (k >= 3 && ((i == 0 && j == 1) ||
                         (i > 0 && j == 0)))
            continue;
          for (l = 0; l < ENTROPY_NODES; l++) {
907

John Koleszar's avatar
John Koleszar committed
908
            vp8_prob *const p = pc->fc.coef_probs_8x8 [i][j][k] + l;
909

John Koleszar's avatar
John Koleszar committed
910 911 912 913 914 915
            if (vp8_read(bc, COEF_UPDATE_PROB_8X8)) {
              *p = read_prob_diff_update(bc, *p);
            }
          }
        }
  }
Daniel Kang's avatar
Daniel Kang committed
916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935 936 937

#if CONFIG_TX16X16
  // 16x16
  if (vp8_read_bit(bc)) {
    // read coef probability tree
    for (i = 0; i < BLOCK_TYPES_16X16; ++i)
      for (j = !i; j < COEF_BANDS; ++j)
        for (k = 0; k < PREV_COEF_CONTEXTS; ++k) {
          if (k >= 3 && ((i == 0 && j == 1) ||
                         (i > 0 && j == 0)))
            continue;
          for (l = 0; l < ENTROPY_NODES; ++l) {

            vp8_prob *const p = pc->fc.coef_probs_16x16[i][j][k] + l;

            if (vp8_read(bc, COEF_UPDATE_PROB_16X16)) {
              *p = read_prob_diff_update(bc, *p);
            }
          }
        }
  }
#endif
938 939
}

John Koleszar's avatar
John Koleszar committed
940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963 964 965 966 967 968 969 970 971 972 973 974
int vp8_decode_frame(VP8D_COMP *pbi) {
  vp8_reader *const bc = & pbi->bc;
  VP8_COMMON *const pc = & pbi->common;
  MACROBLOCKD *const xd  = & pbi->mb;
  const unsigned char *data = (const unsigned char *)pbi->Source;
  const unsigned char *data_end = data + pbi->source_sz;
  ptrdiff_t first_partition_length_in_bytes = 0;

  int mb_row;
  int i, j;
  int corrupt_tokens = 0;

  /* start with no corruption of current frame */
  xd->corrupted = 0;
  pc->yv12_fb[pc->new_fb_idx].corrupted = 0;

  if (data_end - data < 3) {
    vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
                       "Truncated packet");
  } else {
    pc->last_frame_type = pc->frame_type;
    pc->frame_type = (FRAME_TYPE)(data[0] & 1);
    pc->version = (data[0] >> 1) & 7;
    pc->show_frame = (data[0] >> 4) & 1;
    first_partition_length_in_bytes =
      (data[0] | (data[1] << 8) | (data[2] << 16)) >> 5;

    if ((data + first_partition_length_in_bytes > data_end
         || data + first_partition_length_in_bytes < data))
      vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
                         "Truncated packet or corrupt partition 0 length");

    data += 3;

    vp8_setup_version(pc);
Yaowu Xu's avatar
Yaowu Xu committed
975

John Koleszar's avatar
John Koleszar committed
976 977 978 979 980 981 982 983 984 985 986 987 988 989 990 991 992 993 994 995 996 997 998 999 1000 1001 1002 1003 1004 1005 1006 1007
    if (pc->frame_type == KEY_FRAME) {
      const int Width = pc->Width;
      const int Height = pc->Height;

      /* vet via sync code */
      /* When error concealment is enabled we should only check the sync
       * code if we have enough bits available
       */
      if (data + 3 < data_end) {
        if (data[0] != 0x9d || data[1] != 0x01 || data[2] != 0x2a)
          vpx_internal_error(&pc->error, VPX_CODEC_UNSUP_BITSTREAM,
                             "Invalid frame sync code");
      }

      /* If error concealment is enabled we should only parse the new size
       * if we have enough data. Otherwise we will end up with the wrong
       * size.
       */
      if (data + 6 < data_end) {
        pc->Width = (data[3] | (data[4] << 8)) & 0x3fff;
        pc->horiz_scale = data[4] >> 6;
        pc->Height = (data[5] | (data[6] << 8)) & 0x3fff;
        pc->vert_scale = data[6] >> 6;
      }
      data += 7;

      if (Width != pc->Width  ||  Height != pc->Height) {
        if (pc->Width <= 0) {
          pc->Width = Width;
          vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
                             "Invalid frame width");
        }
John Koleszar's avatar
John Koleszar committed
1008

John Koleszar's avatar
John Koleszar committed
1009 1010 1011 1012 1013
        if (pc->Height <= 0) {
          pc->Height = Height;
          vpx_internal_error(&pc->error, VPX_CODEC_CORRUPT_FRAME,
                             "Invalid frame height");
        }
1014

John Koleszar's avatar
John Koleszar committed
1015 1016 1017 1018
        if (vp8_alloc_frame_buffers(pc, pc->Width, pc->Height))
          vpx_internal_error(&pc->error, VPX_CODEC_MEM_ERROR,
                             "Failed to allocate frame buffers");
      }
1019
    }
John Koleszar's avatar
John Koleszar committed
1020
  }
John Koleszar's avatar
John Koleszar committed
1021

John Koleszar's avatar
John Koleszar committed
1022 1023 1024 1025
  if ((!pbi->decoded_key_frame && pc->frame_type != KEY_FRAME) ||
      pc->Width == 0 || pc->Height == 0) {
    return -1;
  }
1026

John Koleszar's avatar
John Koleszar committed
1027
  init_frame(pbi);
John Koleszar's avatar
John Koleszar committed
1028

John Koleszar's avatar
John Koleszar committed
1029 1030 1031 1032 1033 1034 1035
  if (vp8dx_start_decode(bc, data, data_end - data))
    vpx_internal_error(&pc->error, VPX_CODEC_MEM_ERROR,
                       "Failed to allocate bool decoder 0");
  if (pc->frame_type == KEY_FRAME) {
    pc->clr_type    = (YUV_TYPE)vp8_read_bit(bc);
    pc->clamp_type  = (CLAMP_TYPE)vp8_read_bit(bc);
  }
John Koleszar's avatar
John Koleszar committed
1036

John Koleszar's avatar
John Koleszar committed
1037 1038
  /* Is segmentation enabled */
  xd->segmentation_enabled = (unsigned char)vp8_read_bit(bc);
John Koleszar's avatar
John Koleszar committed
1039

John Koleszar's avatar
John Koleszar committed
1040 1041 1042 1043
  if (xd->segmentation_enabled) {
    // Read whether or not the segmentation map is being explicitly
    // updated this frame.
    xd->update_mb_segmentation_map = (unsigned char)vp8_read_bit(bc);
John Koleszar's avatar
John Koleszar committed
1044

John Koleszar's avatar
John Koleszar committed
1045 1046 1047
    // If so what method will be used.
    if (xd->update_mb_segmentation_map)
      pc->temporal_update = (unsigned char)vp8_read_bit(bc);
1048

John Koleszar's avatar
John Koleszar committed
1049 1050
    // Is the segment data being updated
    xd->update_mb_segmentation_data = (unsigned char)vp8_read_bit(bc);
Paul Wilkins's avatar
Paul Wilkins committed
1051

John Koleszar's avatar
John Koleszar committed
1052 1053
    if (xd->update_mb_segmentation_data) {
      int data;
Paul Wilkins's avatar
Paul Wilkins committed
1054

John Koleszar's avatar
John Koleszar committed
1055
      xd->mb_segment_abs_delta = (unsigned char)vp8_read_bit(bc);
John Koleszar's avatar
John Koleszar committed
1056

John Koleszar's avatar
John Koleszar committed
1057
      clearall_segfeatures(xd);
1058

John Koleszar's avatar
John Koleszar committed
1059 1060 1061 1062
      // For each segmentation...
      for (i = 0; i < MAX_MB_SEGMENTS; i++) {
        // For each of the segments features...
        for (j = 0; j < SEG_LVL_MAX; j++) {
John Koleszar's avatar
John Koleszar committed
1063

John Koleszar's avatar
John Koleszar committed
1064 1065 1066 1067
#if CONFIG_FEATUREUPDATES
          // feature updated?
          if (vp8_read_bit(bc)) {
            int active = 1;
Paul Wilkins's avatar
Paul Wilkins committed
1068

John Koleszar's avatar
John Koleszar committed
1069 1070
            if (segfeature_active(xd, i, j))
              active = vp8_read_bit(bc);
Jim Bankoski's avatar
Jim Bankoski committed
1071

John Koleszar's avatar
John Koleszar committed
1072 1073 1074 1075
            // Is the feature enabled
            if (active) {
              // Update the feature data and mask
              enable_segfeature(xd, i, j);
Jim Bankoski's avatar
Jim Bankoski committed
1076

John Koleszar's avatar
John Koleszar committed
1077 1078
              data = (signed char)vp8_read_literal(
                       bc, seg_feature_data_bits(j));
John Koleszar's avatar
John Koleszar committed
1079

John Koleszar's avatar
John Koleszar committed
1080 1081
              // Is the segment data signed..
              if (is_segfeature_signed(j)) {
John Koleszar's avatar
John Koleszar committed
1082
                if (vp8_read_bit(bc))
John Koleszar's avatar
John Koleszar committed
1083 1084 1085 1086
                  data = - data;
              }
            } else
              data = 0;
1087

John Koleszar's avatar
John Koleszar committed
1088 1089 1090 1091 1092 1093 1094 1095 1096 1097 1098 1099 1100 1101 1102 1103
            set_segdata(xd, i, j, data);
          }

#else
          // Is the feature enabled
          if (vp8_read_bit(bc)) {
            // Update the feature data and mask
            enable_segfeature(xd, i, j);

            data = (signed char)vp8_read_literal(
                     bc, seg_feature_data_bits(j));

            // Is the segment data signed..
            if (is_segfeature_signed(j)) {
              if (vp8_read_bit(bc))
                data = - data;
1104
            }
John Koleszar's avatar
John Koleszar committed
1105 1106