vp9_decodframe.c 64.2 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 "vp9/decoder/vp9_onyxd_int.h"
Ronald S. Bultje's avatar
Ronald S. Bultje committed
13
#include "vp9/common/vp9_common.h"
14 15 16
#include "vp9/common/vp9_header.h"
#include "vp9/common/vp9_reconintra.h"
#include "vp9/common/vp9_reconinter.h"
Yaowu Xu's avatar
Yaowu Xu committed
17
#include "vp9/common/vp9_entropy.h"
18
#include "vp9/decoder/vp9_decodframe.h"
19
#include "vp9/decoder/vp9_detokenize.h"
20 21 22 23
#include "vp9/common/vp9_invtrans.h"
#include "vp9/common/vp9_alloccommon.h"
#include "vp9/common/vp9_entropymode.h"
#include "vp9/common/vp9_quant_common.h"
Johann's avatar
Johann committed
24
#include "vpx_scale/vpx_scale.h"
25
#include "vp9/common/vp9_setupintrarecon.h"
Scott LaVarnway's avatar
Scott LaVarnway committed
26

27
#include "vp9/decoder/vp9_decodemv.h"
28 29
#include "vp9/common/vp9_extend.h"
#include "vp9/common/vp9_modecont.h"
John Koleszar's avatar
John Koleszar committed
30
#include "vpx_mem/vpx_mem.h"
31
#include "vp9/decoder/vp9_dboolhuff.h"
John Koleszar's avatar
John Koleszar committed
32

33
#include "vp9/common/vp9_seg_common.h"
34
#include "vp9/common/vp9_tile_common.h"
35
#include "vp9_rtcd.h"
36

John Koleszar's avatar
John Koleszar committed
37 38 39
#include <assert.h>
#include <stdio.h>

40 41
#define COEFCOUNT_TESTING

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

47 48 49 50 51 52 53 54 55
static int read_le16(const uint8_t *p) {
  return (p[1] << 8) | p[0];
}

static int read_le32(const uint8_t *p) {
  return (p[3] << 24) | (p[2] << 16) | (p[1] << 8) | p[0];
}

// len == 0 is not allowed
56 57
static int read_is_valid(const uint8_t *start, size_t len,
                         const uint8_t *end) {
58 59 60
  return start + len > start && start + len <= end;
}

61 62 63 64 65 66 67
static TXFM_MODE read_txfm_mode(vp9_reader *r) {
  TXFM_MODE mode = vp9_read_literal(r, 2);
  if (mode == ALLOW_32X32)
    mode += vp9_read_bit(r);
  return mode;
}

John Koleszar's avatar
John Koleszar committed
68 69 70 71 72 73 74 75 76 77 78 79
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;
80 81
}

John Koleszar's avatar
John Koleszar committed
82 83 84
static int inv_remap_prob(int v, int m) {
  const int n = 256;
  const int modulus = MODULUS_PARAM;
85

John Koleszar's avatar
John Koleszar committed
86 87
  v = merge_index(v, n - 1, modulus);
  if ((m << 1) <= n) {
88
    return vp9_inv_recenter_nonneg(v + 1, m);
John Koleszar's avatar
John Koleszar committed
89
  } else {
90
    return n - 1 - vp9_inv_recenter_nonneg(v + 1, n - 1 - m);
John Koleszar's avatar
John Koleszar committed
91
  }
92
}
93

94
static vp9_prob read_prob_diff_update(vp9_reader *const bc, int oldp) {
95
  int delp = vp9_decode_term_subexp(bc, SUBEXP_PARAM, 255);
96
  return (vp9_prob)inv_remap_prob(delp, oldp);
97
}
98

99
void vp9_init_de_quantizer(VP9D_COMP *pbi) {
John Koleszar's avatar
John Koleszar committed
100
  int i;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
101
  int q;
102
  VP9_COMMON *const pc = &pbi->common;
John Koleszar's avatar
John Koleszar committed
103

Dmitry Kovalev's avatar
Dmitry Kovalev committed
104
  for (q = 0; q < QINDEX_RANGE; q++) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
105 106
    pc->y_dequant[q][0] = (int16_t)vp9_dc_quant(q, pc->y1dc_delta_q);
    pc->uv_dequant[q][0] = (int16_t)vp9_dc_uv_quant(q, pc->uvdc_delta_q);
John Koleszar's avatar
John Koleszar committed
107 108 109

    /* all the ac values =; */
    for (i = 1; i < 16; i++) {
110
      const int rc = vp9_default_zig_zag1d_4x4[i];
John Koleszar's avatar
John Koleszar committed
111

Dmitry Kovalev's avatar
Dmitry Kovalev committed
112 113
      pc->y_dequant[q][rc] = (int16_t)vp9_ac_yquant(q);
      pc->uv_dequant[q][rc] = (int16_t)vp9_ac_uv_quant(q, pc->uvac_delta_q);
John Koleszar's avatar
John Koleszar committed
114
    }
John Koleszar's avatar
John Koleszar committed
115
  }
John Koleszar's avatar
John Koleszar committed
116 117
}

Dmitry Kovalev's avatar
Dmitry Kovalev committed
118 119 120
static int get_qindex(MACROBLOCKD *mb, int segment_id, int base_qindex) {
  // Set the Q baseline allowing for any segment level adjustment
  if (vp9_segfeature_active(mb, segment_id, SEG_LVL_ALT_Q)) {
121 122 123 124
    const int data = vp9_get_segdata(mb, segment_id, SEG_LVL_ALT_Q);
    return mb->mb_segment_abs_delta == SEGMENT_ABSDATA ?
               data :  // Abs value
               clamp(base_qindex + data, 0, MAXQ);  // Delta value
Dmitry Kovalev's avatar
Dmitry Kovalev committed
125 126 127 128 129 130
  } else {
    return base_qindex;
  }
}

static void mb_init_dequantizer(VP9D_COMP *pbi, MACROBLOCKD *mb) {
John Koleszar's avatar
John Koleszar committed
131 132
  int i;

Dmitry Kovalev's avatar
Dmitry Kovalev committed
133
  VP9_COMMON *const pc = &pbi->common;
134 135
  const int segment_id = mb->mode_info_context->mbmi.segment_id;
  const int qindex = get_qindex(mb, segment_id, pc->base_qindex);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
136
  mb->q_index = qindex;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
137

Dmitry Kovalev's avatar
Dmitry Kovalev committed
138
  for (i = 0; i < 16; i++)
Dmitry Kovalev's avatar
Dmitry Kovalev committed
139
    mb->block[i].dequant = pc->y_dequant[qindex];
John Koleszar's avatar
John Koleszar committed
140

Dmitry Kovalev's avatar
Dmitry Kovalev committed
141
  for (i = 16; i < 24; i++)
Dmitry Kovalev's avatar
Dmitry Kovalev committed
142
    mb->block[i].dequant = pc->uv_dequant[qindex];
John Koleszar's avatar
John Koleszar committed
143

Dmitry Kovalev's avatar
Dmitry Kovalev committed
144
  if (mb->lossless) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
145
    assert(qindex == 0);
Yaowu Xu's avatar
Yaowu Xu committed
146 147
    mb->inv_txm4x4_1      = vp9_short_iwalsh4x4_1;
    mb->inv_txm4x4        = vp9_short_iwalsh4x4;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
148 149 150 151
    mb->itxm_add          = vp9_dequant_idct_add_lossless_c;
    mb->itxm_add_y_block  = vp9_dequant_idct_add_y_block_lossless_c;
    mb->itxm_add_uv_block = vp9_dequant_idct_add_uv_block_lossless_c;
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
152 153
    mb->inv_txm4x4_1      = vp9_short_idct4x4_1;
    mb->inv_txm4x4        = vp9_short_idct4x4;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
154 155 156
    mb->itxm_add          = vp9_dequant_idct_add;
    mb->itxm_add_y_block  = vp9_dequant_idct_add_y_block;
    mb->itxm_add_uv_block = vp9_dequant_idct_add_uv_block;
John Koleszar's avatar
John Koleszar committed
157
  }
John Koleszar's avatar
John Koleszar committed
158 159
}

160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185
#if CONFIG_CODE_NONZEROCOUNT
static void propagate_nzcs(VP9_COMMON *cm, MACROBLOCKD *xd) {
  MODE_INFO *m = xd->mode_info_context;
  BLOCK_SIZE_TYPE sb_type = m->mbmi.sb_type;
  const int mis = cm->mode_info_stride;
  int n;
  if (sb_type == BLOCK_SIZE_SB64X64) {
    for (n = 0; n < 16; ++n) {
      int i = n >> 2;
      int j = n & 3;
      if (i == 0 && j == 0) continue;
      vpx_memcpy((m + j + mis * i)->mbmi.nzcs, m->mbmi.nzcs,
                 384 * sizeof(m->mbmi.nzcs[0]));
    }
  } else if (sb_type == BLOCK_SIZE_SB32X32) {
    for (n = 0; n < 4; ++n) {
      int i = n >> 1;
      int j = n & 1;
      if (i == 0 && j == 0) continue;
      vpx_memcpy((m + j + mis * i)->mbmi.nzcs, m->mbmi.nzcs,
                 384 * sizeof(m->mbmi.nzcs[0]));
    }
  }
}
#endif

186 187 188
static void skip_recon_sb(VP9D_COMP *pbi, MACROBLOCKD *xd,
                          int mb_row, int mb_col,
                          BLOCK_SIZE_TYPE bsize) {
189 190
  MODE_INFO *m = xd->mode_info_context;
  BLOCK_SIZE_TYPE sb_type = m->mbmi.sb_type;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
191

John Koleszar's avatar
John Koleszar committed
192
  if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
193 194
    vp9_build_intra_predictors_sbuv_s(xd, bsize);
    vp9_build_intra_predictors_sby_s(xd, bsize);
John Koleszar's avatar
John Koleszar committed
195
  } else {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
196
    if (sb_type == BLOCK_SIZE_SB64X64) {
197
      vp9_build_inter64x64_predictors_sb(xd, mb_row, mb_col);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
198
    } else if (sb_type == BLOCK_SIZE_SB32X32) {
199
      vp9_build_inter32x32_predictors_sb(xd, mb_row, mb_col);
200
    } else {
201 202 203 204 205
      vp9_build_inter16x16_predictors_mb(xd,
                                         xd->dst.y_buffer,
                                         xd->dst.u_buffer,
                                         xd->dst.v_buffer,
                                         xd->dst.y_stride,
206 207
                                         xd->dst.uv_stride,
                                         mb_row, mb_col);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
208
    }
John Koleszar's avatar
John Koleszar committed
209
  }
210 211 212 213
#if CONFIG_CODE_NONZEROCOUNT
  vpx_memset(m->mbmi.nzcs, 0, 384 * sizeof(m->mbmi.nzcs[0]));
  propagate_nzcs(&pbi->common, xd);
#endif
John Koleszar's avatar
John Koleszar committed
214 215
}

216 217
static void decode_16x16(VP9D_COMP *pbi, MACROBLOCKD *xd,
                         BOOL_DECODER* const bc) {
218
  const TX_TYPE tx_type = get_tx_type_16x16(xd, 0);
219

220
  if (tx_type != DCT_DCT) {
221
    vp9_dequant_iht_add_16x16_c(tx_type, xd->plane[0].qcoeff,
222 223 224
                                xd->block[0].dequant, xd->dst.y_buffer,
                                xd->dst.y_buffer, xd->dst.y_stride,
                                xd->dst.y_stride, xd->plane[0].eobs[0]);
225
  } else {
226
    vp9_dequant_idct_add_16x16(xd->plane[0].qcoeff, xd->block[0].dequant,
227 228 229
                               xd->dst.y_buffer, xd->dst.y_buffer,
                               xd->dst.y_stride, xd->dst.y_stride,
                               xd->plane[0].eobs[0]);
230
  }
231 232

  vp9_dequant_idct_add_8x8(xd->plane[1].qcoeff, xd->block[16].dequant,
233 234 235
                           xd->dst.u_buffer, xd->dst.u_buffer,
                           xd->dst.uv_stride, xd->dst.uv_stride,
                           xd->plane[1].eobs[0]);
236

Dmitry Kovalev's avatar
Dmitry Kovalev committed
237
  vp9_dequant_idct_add_8x8(xd->plane[2].qcoeff, xd->block[20].dequant,
238 239 240
                           xd->dst.v_buffer, xd->dst.v_buffer,
                           xd->dst.uv_stride, xd->dst.uv_stride,
                           xd->plane[2].eobs[0]);
241 242 243 244
}

static void decode_8x8(VP9D_COMP *pbi, MACROBLOCKD *xd,
                       BOOL_DECODER* const bc) {
245 246
  const MB_PREDICTION_MODE mode = xd->mode_info_context->mbmi.mode;
  // luma
247
  // if the first one is DCT_DCT assume all the rest are as well
248
  TX_TYPE tx_type = get_tx_type_8x8(xd, 0);
249
  if (tx_type != DCT_DCT || mode == I8X8_PRED) {
250 251 252 253
    int i;
    for (i = 0; i < 4; i++) {
      int ib = vp9_i8x8_block[i];
      int idx = (ib & 0x02) ? (ib + 2) : ib;
254
      int16_t *q  = BLOCK_OFFSET(xd->plane[0].qcoeff, idx, 16);
255 256
      int16_t *dq = xd->block[0].dequant;
      uint8_t *dst = *(xd->block[ib].base_dst) + xd->block[ib].dst;
257
      int stride = xd->dst.y_stride;
258
      if (mode == I8X8_PRED) {
259
        BLOCKD *b = &xd->block[ib];
260
        int i8x8mode = b->bmi.as_mode.first;
261
        vp9_intra8x8_predict(xd, b, i8x8mode, dst, stride);
262
      }
263
      tx_type = get_tx_type_8x8(xd, ib);
264
      if (tx_type != DCT_DCT) {
265
        vp9_dequant_iht_add_8x8_c(tx_type, q, dq, dst, dst, stride, stride,
266
                                  xd->plane[0].eobs[idx]);
267
      } else {
268
        vp9_dequant_idct_add_8x8_c(q, dq, dst, dst, stride, stride,
John Koleszar's avatar
John Koleszar committed
269
                                   xd->plane[0].eobs[idx]);
270 271
      }
    }
272
  } else {
273
    vp9_dequant_idct_add_y_block_8x8(xd->plane[0].qcoeff,
274
                                     xd->block[0].dequant,
275 276
                                     xd->dst.y_buffer,
                                     xd->dst.y_stride,
277 278
                                     xd->dst.y_buffer,
                                     xd->dst.y_stride,
279
                                     xd);
280 281
  }

282 283
  // chroma
  if (mode == I8X8_PRED) {
284 285 286 287 288
    int i;
    for (i = 0; i < 4; i++) {
      int ib = vp9_i8x8_block[i];
      BLOCKD *b = &xd->block[ib];
      int i8x8mode = b->bmi.as_mode.first;
289

290
      b = &xd->block[16 + i];
291 292
      vp9_intra_uv4x4_predict(xd, b, i8x8mode, *(b->base_dst) + b->dst,
                              b->dst_stride);
293
      xd->itxm_add(BLOCK_OFFSET(xd->plane[1].qcoeff, i, 16),
294 295
                   b->dequant, *(b->base_dst) + b->dst,
                   *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
296
                   xd->plane[1].eobs[i]);
297

298
      b = &xd->block[20 + i];
299 300
      vp9_intra_uv4x4_predict(xd, b, i8x8mode, *(b->base_dst) + b->dst,
                              b->dst_stride);
301
      xd->itxm_add(BLOCK_OFFSET(xd->plane[2].qcoeff, i, 16),
302 303
                   b->dequant, *(b->base_dst) + b->dst,
                   *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
304
                   xd->plane[2].eobs[i]);
305
    }
306
  } else if (mode == SPLITMV) {
307
    xd->itxm_add_uv_block(xd->plane[1].qcoeff, xd->block[16].dequant,
308
         xd->dst.u_buffer, xd->dst.uv_stride, xd->dst.u_buffer,
John Koleszar's avatar
John Koleszar committed
309
         xd->dst.uv_stride, xd->plane[1].eobs);
310
    xd->itxm_add_uv_block(xd->plane[2].qcoeff, xd->block[16].dequant,
311
         xd->dst.v_buffer, xd->dst.uv_stride, xd->dst.v_buffer,
John Koleszar's avatar
John Koleszar committed
312
         xd->dst.uv_stride, xd->plane[2].eobs);
313
  } else {
314
    vp9_dequant_idct_add_8x8(xd->plane[1].qcoeff, xd->block[16].dequant,
315 316 317
                             xd->dst.u_buffer, xd->dst.u_buffer,
                             xd->dst.uv_stride, xd->dst.uv_stride,
                             xd->plane[1].eobs[0]);
318 319

    vp9_dequant_idct_add_8x8(xd->plane[2].qcoeff, xd->block[16].dequant,
320 321 322
                             xd->dst.v_buffer, xd->dst.v_buffer,
                             xd->dst.uv_stride, xd->dst.uv_stride,
                             xd->plane[2].eobs[0]);
323 324 325 326 327 328
  }
}

static void decode_4x4(VP9D_COMP *pbi, MACROBLOCKD *xd,
                       BOOL_DECODER* const bc) {
  TX_TYPE tx_type;
329
  int i = 0;
330
  const MB_PREDICTION_MODE mode = xd->mode_info_context->mbmi.mode;
331 332 333 334 335
  if (mode == I8X8_PRED) {
    for (i = 0; i < 4; i++) {
      int ib = vp9_i8x8_block[i];
      const int iblock[4] = {0, 1, 4, 5};
      int j;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
336 337
      BLOCKD *b = &xd->block[ib];
      int i8x8mode = b->bmi.as_mode.first;
338 339
      vp9_intra8x8_predict(xd, b, i8x8mode, *(b->base_dst) + b->dst,
                           b->dst_stride);
340 341
      for (j = 0; j < 4; j++) {
        b = &xd->block[ib + iblock[j]];
342
        tx_type = get_tx_type_4x4(xd, ib + iblock[j]);
343
        if (tx_type != DCT_DCT) {
344
          vp9_dequant_iht_add_c(tx_type,
345
              BLOCK_OFFSET(xd->plane[0].qcoeff, ib + iblock[j], 16),
346 347
                                    b->dequant, *(b->base_dst) + b->dst,
                                    *(b->base_dst) + b->dst, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
348 349
                                    b->dst_stride,
                                    xd->plane[0].eobs[ib + iblock[j]]);
350
        } else {
351
          xd->itxm_add(BLOCK_OFFSET(xd->plane[0].qcoeff, ib + iblock[j], 16),
352 353
                       b->dequant, *(b->base_dst) + b->dst,
                       *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
354
                       xd->plane[0].eobs[ib + iblock[j]]);
355 356 357
        }
      }
      b = &xd->block[16 + i];
358 359
      vp9_intra_uv4x4_predict(xd, b, i8x8mode, *(b->base_dst) + b->dst,
                              b->dst_stride);
360
      xd->itxm_add(BLOCK_OFFSET(xd->plane[1].qcoeff, i, 16),
361 362
                   b->dequant, *(b->base_dst) + b->dst,
                   *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
363
                   xd->plane[1].eobs[i]);
364
      b = &xd->block[20 + i];
365 366
      vp9_intra_uv4x4_predict(xd, b, i8x8mode, *(b->base_dst) + b->dst,
                              b->dst_stride);
367
      xd->itxm_add(BLOCK_OFFSET(xd->plane[2].qcoeff, i, 16),
368 369
                   b->dequant, *(b->base_dst) + b->dst,
                   *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
370
                   xd->plane[2].eobs[i]);
371 372 373 374
    }
  } else if (mode == B_PRED) {
    for (i = 0; i < 16; i++) {
      BLOCKD *b = &xd->block[i];
Dmitry Kovalev's avatar
Dmitry Kovalev committed
375
      int b_mode = xd->mode_info_context->bmi[i].as_mode.first;
376 377
#if CONFIG_NEWBINTRAMODES
      xd->mode_info_context->bmi[i].as_mode.context = b->bmi.as_mode.context =
378
          vp9_find_bpred_context(xd, b);
379 380
      if (!xd->mode_info_context->mbmi.mb_skip_coeff)
        vp9_decode_coefs_4x4(pbi, xd, bc, PLANE_TYPE_Y_WITH_DC, i);
381
#endif
382 383
      vp9_intra4x4_predict(xd, b, b_mode, *(b->base_dst) + b->dst,
                           b->dst_stride);
384
      tx_type = get_tx_type_4x4(xd, i);
385
      if (tx_type != DCT_DCT) {
386 387
        vp9_dequant_iht_add_c(tx_type,
                              BLOCK_OFFSET(xd->plane[0].qcoeff, i, 16),
388 389 390
                              b->dequant, *(b->base_dst) + b->dst,
                              *(b->base_dst) + b->dst, b->dst_stride,
                              b->dst_stride, xd->plane[0].eobs[i]);
391
      } else {
392
        xd->itxm_add(BLOCK_OFFSET(xd->plane[0].qcoeff, i, 16),
393 394
                     b->dequant, *(b->base_dst) + b->dst,
                     *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
395
                     xd->plane[0].eobs[i]);
396 397
      }
    }
398 399 400 401
#if CONFIG_NEWBINTRAMODES
    if (!xd->mode_info_context->mbmi.mb_skip_coeff)
      vp9_decode_mb_tokens_4x4_uv(pbi, xd, bc);
#endif
402
    vp9_build_intra_predictors_sbuv_s(xd, BLOCK_SIZE_MB16X16);
403
    xd->itxm_add_uv_block(xd->plane[1].qcoeff, xd->block[16].dequant,
404
         xd->dst.u_buffer, xd->dst.uv_stride, xd->dst.u_buffer,
John Koleszar's avatar
John Koleszar committed
405
         xd->dst.uv_stride, xd->plane[1].eobs);
406
    xd->itxm_add_uv_block(xd->plane[2].qcoeff, xd->block[16].dequant,
407
         xd->dst.v_buffer, xd->dst.uv_stride, xd->dst.v_buffer,
John Koleszar's avatar
John Koleszar committed
408
         xd->dst.uv_stride, xd->plane[2].eobs);
409
  } else if (mode == SPLITMV || get_tx_type_4x4(xd, 0) == DCT_DCT) {
410
    xd->itxm_add_y_block(xd->plane[0].qcoeff,
411
                          xd->block[0].dequant,
412
                          xd->dst.y_buffer, xd->dst.y_stride,
413 414
                          xd->dst.y_buffer,
                          xd->dst.y_stride,
415
                          xd);
416
    xd->itxm_add_uv_block(xd->plane[1].qcoeff, xd->block[16].dequant,
417
         xd->dst.u_buffer, xd->dst.uv_stride, xd->dst.u_buffer,
John Koleszar's avatar
John Koleszar committed
418
         xd->dst.uv_stride, xd->plane[1].eobs);
419
    xd->itxm_add_uv_block(xd->plane[2].qcoeff, xd->block[16].dequant,
420
         xd->dst.v_buffer, xd->dst.uv_stride, xd->dst.v_buffer,
John Koleszar's avatar
John Koleszar committed
421
         xd->dst.uv_stride, xd->plane[2].eobs);
422
  } else {
423 424
    for (i = 0; i < 16; i++) {
      BLOCKD *b = &xd->block[i];
425
      tx_type = get_tx_type_4x4(xd, i);
426
      if (tx_type != DCT_DCT) {
427 428
        vp9_dequant_iht_add_c(tx_type,
                              BLOCK_OFFSET(xd->plane[0].qcoeff, i, 16),
429 430
                              b->dequant, *(b->base_dst) + b->dst,
                              *(b->base_dst) + b->dst, b->dst_stride,
431
                              b->dst_stride, xd->plane[0].eobs[i]);
432
      } else {
433
        xd->itxm_add(BLOCK_OFFSET(xd->plane[0].qcoeff, i, 16),
434 435
                     b->dequant, *(b->base_dst) + b->dst,
                     *(b->base_dst) + b->dst, b->dst_stride, b->dst_stride,
John Koleszar's avatar
John Koleszar committed
436
                     xd->plane[0].eobs[i]);
437 438
      }
    }
439
    xd->itxm_add_uv_block(xd->plane[1].qcoeff, xd->block[16].dequant,
440
                          xd->dst.u_buffer, xd->dst.uv_stride, xd->dst.u_buffer,
John Koleszar's avatar
John Koleszar committed
441
                          xd->dst.uv_stride, xd->plane[1].eobs);
442
    xd->itxm_add_uv_block(xd->plane[2].qcoeff, xd->block[16].dequant,
443
                          xd->dst.v_buffer, xd->dst.uv_stride, xd->dst.v_buffer,
John Koleszar's avatar
John Koleszar committed
444
                          xd->dst.uv_stride, xd->plane[2].eobs);
445 446 447
  }
}

448 449 450 451
static INLINE void decode_sby_32x32(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize) - 1, bw = 1 << bwl;
  const int bhl = mb_height_log2(bsize) - 1, bh = 1 << bhl;
  const int y_count = bw * bh;
452 453 454
  int n;

  for (n = 0; n < y_count; n++) {
455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> bwl;
    const int y_offset = (y_idx * 32) * mb->dst.y_stride + (x_idx * 32);
    vp9_dequant_idct_add_32x32(BLOCK_OFFSET(mb->plane[0].qcoeff, n, 1024),
                               mb->block[0].dequant ,
                               mb->dst.y_buffer + y_offset,
                               mb->dst.y_buffer + y_offset,
                               mb->dst.y_stride, mb->dst.y_stride,
                               mb->plane[0].eobs[n * 64]);
  }
}

static INLINE void decode_sbuv_32x32(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize) - 1, bw = (1 << bwl) / 2;
  const int bhl = mb_height_log2(bsize) - 1, bh = (1 << bhl) / 2;
  const int uv_count = bw * bh;
  int n;
  for (n = 0; n < uv_count; n++) {
     const int x_idx = n & (bw - 1);
     const int y_idx = n >> (bwl - 1);
     const int uv_offset = (y_idx * 32) * mb->dst.uv_stride + (x_idx * 32);
     vp9_dequant_idct_add_32x32(BLOCK_OFFSET(mb->plane[1].qcoeff, n, 1024),
                                mb->block[16].dequant,
                                mb->dst.u_buffer + uv_offset,
                                mb->dst.u_buffer + uv_offset,
                                mb->dst.uv_stride, mb->dst.uv_stride,
                                mb->plane[1].eobs[n * 64]);
     vp9_dequant_idct_add_32x32(BLOCK_OFFSET(mb->plane[2].qcoeff, n, 1024),
                                mb->block[20].dequant,
                                mb->dst.v_buffer + uv_offset,
                                mb->dst.v_buffer + uv_offset,
                                mb->dst.uv_stride, mb->dst.uv_stride,
                                mb->plane[2].eobs[n * 64]);
  }
}

static INLINE void decode_sby_16x16(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize), bw = 1 << bwl;
  const int bhl = mb_height_log2(bsize), bh = 1 << bhl;
  const int y_count = bw * bh;
  int n;

  for (n = 0; n < y_count; n++) {
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> bwl;
500
    const int y_offset = (y_idx * 16) * mb->dst.y_stride + (x_idx * 16);
501
    const TX_TYPE tx_type = get_tx_type_16x16(mb,
502
                                (y_idx * (4 * bw) + x_idx) * 4);
503
    if (tx_type == DCT_DCT) {
504
      vp9_dequant_idct_add_16x16(BLOCK_OFFSET(mb->plane[0].qcoeff, n, 256),
505 506 507 508
                                 mb->block[0].dequant ,
                                 mb->dst.y_buffer + y_offset,
                                 mb->dst.y_buffer + y_offset,
                                 mb->dst.y_stride, mb->dst.y_stride,
John Koleszar's avatar
John Koleszar committed
509
                                 mb->plane[0].eobs[n * 16]);
510
    } else {
511 512 513 514 515 516 517
      vp9_dequant_iht_add_16x16_c(tx_type,
                                  BLOCK_OFFSET(mb->plane[0].qcoeff, n, 256),
                                  mb->block[0].dequant,
                                  mb->dst.y_buffer + y_offset,
                                  mb->dst.y_buffer + y_offset,
                                  mb->dst.y_stride, mb->dst.y_stride,
                                  mb->plane[0].eobs[n * 16]);
518 519
    }
  }
520 521 522 523 524 525 526 527 528
}

static INLINE void decode_sbuv_16x16(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize), bw = (1 << bwl) / 2;
  const int bhl = mb_height_log2(bsize), bh = (1 << bhl) / 2;
  const int uv_count = bw * bh;
  int n;

  assert(bsize >= BLOCK_SIZE_SB32X32);
529 530

  for (n = 0; n < uv_count; n++) {
531 532
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> (bwl - 1);
533
    const int uv_offset = (y_idx * 16) * mb->dst.uv_stride + (x_idx * 16);
534
    vp9_dequant_idct_add_16x16(BLOCK_OFFSET(mb->plane[1].qcoeff, n, 256),
535 536 537 538
                               mb->block[16].dequant,
                               mb->dst.u_buffer + uv_offset,
                               mb->dst.u_buffer + uv_offset,
                               mb->dst.uv_stride, mb->dst.uv_stride,
John Koleszar's avatar
John Koleszar committed
539
                               mb->plane[1].eobs[n * 16]);
540
    vp9_dequant_idct_add_16x16(BLOCK_OFFSET(mb->plane[2].qcoeff, n, 256),
541 542 543 544
                               mb->block[20].dequant,
                               mb->dst.v_buffer + uv_offset,
                               mb->dst.v_buffer + uv_offset,
                               mb->dst.uv_stride, mb->dst.uv_stride,
John Koleszar's avatar
John Koleszar committed
545
                               mb->plane[2].eobs[n * 16]);
546 547 548
  }
}

549 550 551 552
static INLINE void decode_sby_8x8(MACROBLOCKD *xd, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize)  + 1, bw = 1 << bwl;
  const int bhl = mb_height_log2(bsize) + 1, bh = 1 << bhl;
  const int y_count = bw * bh;
553 554 555 556
  int n;

  // luma
  for (n = 0; n < y_count; n++) {
557 558
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> bwl;
559 560
    const int y_offset = (y_idx * 8) * xd->dst.y_stride + (x_idx * 8);
    const TX_TYPE tx_type = get_tx_type_8x8(xd,
561
                                            (y_idx * (2 * bw) + x_idx) * 2);
562
    if (tx_type == DCT_DCT) {
563 564 565 566 567
      vp9_dequant_idct_add_8x8_c(BLOCK_OFFSET(xd->plane[0].qcoeff, n, 64),
                                 xd->block[0].dequant,
                                 xd->dst.y_buffer + y_offset,
                                 xd->dst.y_buffer + y_offset,
                                 xd->dst.y_stride, xd->dst.y_stride,
John Koleszar's avatar
John Koleszar committed
568
                                 xd->plane[0].eobs[n * 4]);
569
    } else {
570 571 572 573 574 575 576
      vp9_dequant_iht_add_8x8_c(tx_type,
                                BLOCK_OFFSET(xd->plane[0].qcoeff, n, 64),
                                xd->block[0].dequant,
                                xd->dst.y_buffer + y_offset,
                                xd->dst.y_buffer + y_offset,
                                xd->dst.y_stride, xd->dst.y_stride,
                                xd->plane[0].eobs[n * 4]);
577 578
    }
  }
579 580 581 582 583 584 585
}

static INLINE void decode_sbuv_8x8(MACROBLOCKD *xd, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize)  + 1, bw = 1 << (bwl - 1);
  const int bhl = mb_height_log2(bsize) + 1, bh = 1 << (bhl - 1);
  const int uv_count = bw * bh;
  int n;
586 587 588

  // chroma
  for (n = 0; n < uv_count; n++) {
589 590
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> (bwl - 1);
591 592 593 594 595 596
    const int uv_offset = (y_idx * 8) * xd->dst.uv_stride + (x_idx * 8);
    vp9_dequant_idct_add_8x8_c(BLOCK_OFFSET(xd->plane[1].qcoeff, n, 64),
                               xd->block[16].dequant,
                               xd->dst.u_buffer + uv_offset,
                               xd->dst.u_buffer + uv_offset,
                               xd->dst.uv_stride, xd->dst.uv_stride,
John Koleszar's avatar
John Koleszar committed
597
                               xd->plane[1].eobs[n * 4]);
598 599 600 601 602
    vp9_dequant_idct_add_8x8_c(BLOCK_OFFSET(xd->plane[2].qcoeff, n, 64),
                               xd->block[20].dequant,
                               xd->dst.v_buffer + uv_offset,
                               xd->dst.v_buffer + uv_offset,
                               xd->dst.uv_stride, xd->dst.uv_stride,
John Koleszar's avatar
John Koleszar committed
603
                               xd->plane[2].eobs[n * 4]);
604 605 606
  }
}

607 608 609 610
static INLINE void decode_sby_4x4(MACROBLOCKD *xd, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize)  + 2, bw = 1 << bwl;
  const int bhl = mb_height_log2(bsize) + 2, bh = 1 << bhl;
  const int y_count = bw * bh;
611 612 613
  int n;

  for (n = 0; n < y_count; n++) {
614 615
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> bwl;
616
    const int y_offset = (y_idx * 4) * xd->dst.y_stride + (x_idx * 4);
617
    const TX_TYPE tx_type = get_tx_type_4x4(xd, n);
618
    if (tx_type == DCT_DCT) {
619 620 621 622 623
      xd->itxm_add(BLOCK_OFFSET(xd->plane[0].qcoeff, n, 16),
                   xd->block[0].dequant,
                   xd->dst.y_buffer + y_offset,
                   xd->dst.y_buffer + y_offset,
                   xd->dst.y_stride, xd->dst.y_stride,
John Koleszar's avatar
John Koleszar committed
624
                   xd->plane[0].eobs[n]);
625
    } else {
626 627 628 629 630 631 632 633
      vp9_dequant_iht_add_c(tx_type,
                            BLOCK_OFFSET(xd->plane[0].qcoeff, n, 16),
                            xd->block[0].dequant,
                            xd->dst.y_buffer + y_offset,
                            xd->dst.y_buffer + y_offset,
                            xd->dst.y_stride,
                            xd->dst.y_stride,
                            xd->plane[0].eobs[n]);
634 635
    }
  }
636 637 638 639 640 641 642
}

static INLINE void decode_sbuv_4x4(MACROBLOCKD *xd, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize)  + 2, bw = 1 << (bwl - 1);
  const int bhl = mb_height_log2(bsize) + 2, bh = 1 << (bhl - 1);
  const int uv_count = bw * bh;
  int n;
643 644

  for (n = 0; n < uv_count; n++) {
645 646
    const int x_idx = n & (bw - 1);
    const int y_idx = n >> (bwl - 1);
647 648 649 650 651
    const int uv_offset = (y_idx * 4) * xd->dst.uv_stride + (x_idx * 4);
    xd->itxm_add(BLOCK_OFFSET(xd->plane[1].qcoeff, n, 16),
        xd->block[16].dequant,
        xd->dst.u_buffer + uv_offset,
        xd->dst.u_buffer + uv_offset,
John Koleszar's avatar
John Koleszar committed
652
        xd->dst.uv_stride, xd->dst.uv_stride, xd->plane[1].eobs[n]);
653 654 655 656
    xd->itxm_add(BLOCK_OFFSET(xd->plane[2].qcoeff, n, 16),
        xd->block[20].dequant,
        xd->dst.v_buffer + uv_offset,
        xd->dst.v_buffer + uv_offset,
John Koleszar's avatar
John Koleszar committed
657
        xd->dst.uv_stride, xd->dst.uv_stride, xd->plane[2].eobs[n]);
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
// TODO(jingning): combine luma and chroma dequantization and inverse
// transform into a single function looping over planes.
static void decode_sb_32x32(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  decode_sby_32x32(mb, bsize);
  if (bsize == BLOCK_SIZE_SB64X64)
    decode_sbuv_32x32(mb, bsize);
  else
    decode_sbuv_16x16(mb, bsize);
}

static void decode_sb_16x16(MACROBLOCKD *mb, BLOCK_SIZE_TYPE bsize) {
  decode_sby_16x16(mb, bsize);
  if (bsize >= BLOCK_SIZE_SB32X32)
    decode_sbuv_16x16(mb, bsize);
  else
    decode_sbuv_8x8(mb, bsize);
}

static void decode_sb(VP9D_COMP *pbi, MACROBLOCKD *xd, int mb_row, int mb_col,
                      BOOL_DECODER* const bc, BLOCK_SIZE_TYPE bsize) {
  const int bwl = mb_width_log2(bsize), bhl = mb_height_log2(bsize);
  const int bw = 1 << bwl, bh = 1 << bhl;
683
  int n, eobtotal;
684
  VP9_COMMON *const pc = &pbi->common;
685
  MODE_INFO *mi = xd->mode_info_context;
686
  const int mis = pc->mode_info_stride;
687

688
  assert(mi->mbmi.sb_type == bsize);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
689 690

  if (pbi->common.frame_type != KEY_FRAME)
691
    vp9_setup_interp_filters(xd, mi->mbmi.interp_filter, pc);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
692 693 694 695 696

  // re-initialize macroblock dequantizer before detokenization
  if (xd->segmentation_enabled)
    mb_init_dequantizer(pbi, xd);

697
  if (mi->mbmi.mb_skip_coeff) {
698
    vp9_reset_sb_tokens_context(xd, bsize);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
699

700 701
    // Special case:  Force the loopfilter to skip when eobtotal and
    // mb_skip_coeff are zero.
702
    skip_recon_sb(pbi, xd, mb_row, mb_col, bsize);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
703 704 705
    return;
  }

706
  // TODO(jingning): need to combine inter predictor functions and
707 708
  // make them block size independent.
  // generate prediction
709 710 711
  if (xd->mode_info_context->mbmi.ref_frame == INTRA_FRAME) {
    vp9_build_intra_predictors_sby_s(xd, bsize);
    vp9_build_intra_predictors_sbuv_s(xd, bsize);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
712
  } else {
713 714
    if (bsize == BLOCK_SIZE_SB64X64) {
      vp9_build_inter64x64_predictors_sb(xd, mb_row, mb_col);
715
    } else {
716
      assert(bsize == BLOCK_SIZE_SB32X32);
717 718
      vp9_build_inter32x32_predictors_sb(xd, mb_row, mb_col);
    }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
719 720
  }

721
  // dequantization and idct
722
  eobtotal = vp9_decode_tokens(pbi, xd, bc, bsize);
723
  if (eobtotal == 0) {  // skip loopfilter
724 725
    for (n = 0; n < bw * bh; n++) {
      const int x_idx = n & (bw - 1), y_idx = n >> bwl;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
726

727 728 729 730 731 732
      if (mb_col + x_idx < pc->mb_cols && mb_row + y_idx < pc->mb_rows)
        mi[y_idx * mis + x_idx].mbmi.mb_skip_coeff = mi->mbmi.mb_skip_coeff;
    }
  } else {
    switch (xd->mode_info_context->mbmi.txfm_size) {
      case TX_32X32:
733
        decode_sb_32x32(xd, bsize);
734
        break;
735
      case TX_16X16:
736
        decode_sb_16x16(xd, bsize);
737
        break;
738
      case TX_8X8:
739 740
        decode_sby_8x8(xd, bsize);
        decode_sbuv_8x8(xd, bsize);
741
        break;
742
      case TX_4X4:
743 744
        decode_sby_4x4(xd, bsize);
        decode_sbuv_4x4(xd, bsize);
745 746
        break;
      default: assert(0);
747
    }
748
  }
749 750 751
#if CONFIG_CODE_NONZEROCOUNT
  propagate_nzcs(&pbi->common, xd);
#endif
752 753
}

754 755
// TODO(jingning): Need to merge SB and MB decoding. The MB decoding currently
// couples special handles on I8x8, B_PRED, and splitmv modes.
756 757 758
static void decode_mb(VP9D_COMP *pbi, MACROBLOCKD *xd,
                     int mb_row, int mb_col,
                     BOOL_DECODER* const bc) {
John Koleszar's avatar
John Koleszar committed
759
  int eobtotal = 0;
760 761
  const MB_PREDICTION_MODE mode = xd->mode_info_context->mbmi.mode;
  const int tx_size = xd->mode_info_context->mbmi.txfm_size;
762

Ronald S. Bultje's avatar
Ronald S. Bultje committed
763
  assert(!xd->mode_info_context->mbmi.sb_type);
John Koleszar's avatar
John Koleszar committed
764