vp9_tokenize.c 29.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
13
14
15
 */


#include <math.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
16
17
#include "vp9/encoder/vp9_onyx_int.h"
#include "vp9/encoder/vp9_tokenize.h"
John Koleszar's avatar
John Koleszar committed
18
19
#include "vpx_mem/vpx_mem.h"

20
21
22
#include "vp9/common/vp9_pred_common.h"
#include "vp9/common/vp9_seg_common.h"
#include "vp9/common/vp9_entropy.h"
23

John Koleszar's avatar
John Koleszar committed
24
/* Global event counters used for accumulating statistics across several
25
   compressions, then generating vp9_context.c = initial stats. */
John Koleszar's avatar
John Koleszar committed
26
27

#ifdef ENTROPY_STATS
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
vp9_coeff_accum context_counters_4x4[BLOCK_TYPES_4X4];
vp9_coeff_accum hybrid_context_counters_4x4[BLOCK_TYPES_4X4];
vp9_coeff_accum context_counters_8x8[BLOCK_TYPES_8X8];
vp9_coeff_accum hybrid_context_counters_8x8[BLOCK_TYPES_8X8];
vp9_coeff_accum context_counters_16x16[BLOCK_TYPES_16X16];
vp9_coeff_accum hybrid_context_counters_16x16[BLOCK_TYPES_16X16];
#if CONFIG_TX32X32
vp9_coeff_accum context_counters_32x32[BLOCK_TYPES_32X32];
#endif

extern vp9_coeff_stats tree_update_hist_4x4[BLOCK_TYPES_4X4];
extern vp9_coeff_stats hybrid_tree_update_hist_4x4[BLOCK_TYPES_4X4];
extern vp9_coeff_stats tree_update_hist_8x8[BLOCK_TYPES_8X8];
extern vp9_coeff_stats hybrid_tree_update_hist_8x8[BLOCK_TYPES_8X8];
extern vp9_coeff_stats tree_update_hist_16x16[BLOCK_TYPES_16X16];
extern vp9_coeff_stats hybrid_tree_update_hist_16x16[BLOCK_TYPES_16X16];
#if CONFIG_TX32X32
extern vp9_coeff_stats tree_update_hist_32x32[BLOCK_TYPES_32X32];
#endif
47
48
#endif  /* ENTROPY_STATS */

John Koleszar's avatar
John Koleszar committed
49
static TOKENVALUE dct_value_tokens[DCT_MAX_VALUE * 2];
50
const TOKENVALUE *vp9_dct_value_tokens_ptr;
John Koleszar's avatar
John Koleszar committed
51
static int dct_value_cost[DCT_MAX_VALUE * 2];
52
const int *vp9_dct_value_cost_ptr;
53

John Koleszar's avatar
John Koleszar committed
54
static void fill_value_tokens() {
John Koleszar's avatar
John Koleszar committed
55

John Koleszar's avatar
John Koleszar committed
56
  TOKENVALUE *const t = dct_value_tokens + DCT_MAX_VALUE;
57
  vp9_extra_bit_struct *const e = vp9_extra_bits;
John Koleszar's avatar
John Koleszar committed
58

John Koleszar's avatar
John Koleszar committed
59
60
  int i = -DCT_MAX_VALUE;
  int sign = 1;
John Koleszar's avatar
John Koleszar committed
61

John Koleszar's avatar
John Koleszar committed
62
63
64
  do {
    if (!i)
      sign = 0;
John Koleszar's avatar
John Koleszar committed
65

John Koleszar's avatar
John Koleszar committed
66
67
68
    {
      const int a = sign ? -i : i;
      int eb = sign;
John Koleszar's avatar
John Koleszar committed
69

John Koleszar's avatar
John Koleszar committed
70
71
      if (a > 4) {
        int j = 4;
John Koleszar's avatar
John Koleszar committed
72

John Koleszar's avatar
John Koleszar committed
73
        while (++j < 11  &&  e[j].base_val <= a) {}
John Koleszar's avatar
John Koleszar committed
74

John Koleszar's avatar
John Koleszar committed
75
76
77
78
        t[i].Token = --j;
        eb |= (a - e[j].base_val) << 1;
      } else
        t[i].Token = a;
John Koleszar's avatar
John Koleszar committed
79

John Koleszar's avatar
John Koleszar committed
80
81
      t[i].Extra = eb;
    }
John Koleszar's avatar
John Koleszar committed
82

John Koleszar's avatar
John Koleszar committed
83
84
85
    // initialize the cost for extra bits for all possible coefficient value.
    {
      int cost = 0;
86
      vp9_extra_bit_struct *p = vp9_extra_bits + t[i].Token;
John Koleszar's avatar
John Koleszar committed
87

John Koleszar's avatar
John Koleszar committed
88
89
90
      if (p->base_val) {
        const int extra = t[i].Extra;
        const int Length = p->Len;
John Koleszar's avatar
John Koleszar committed
91

John Koleszar's avatar
John Koleszar committed
92
        if (Length)
93
          cost += treed_cost(p->tree, p->prob, extra >> 1, Length);
John Koleszar's avatar
John Koleszar committed
94

95
        cost += vp9_cost_bit(vp9_prob_half, extra & 1); /* sign */
John Koleszar's avatar
John Koleszar committed
96
97
        dct_value_cost[i + DCT_MAX_VALUE] = cost;
      }
John Koleszar's avatar
John Koleszar committed
98
99
100

    }

John Koleszar's avatar
John Koleszar committed
101
102
  } while (++i < DCT_MAX_VALUE);

103
104
  vp9_dct_value_tokens_ptr = dct_value_tokens + DCT_MAX_VALUE;
  vp9_dct_value_cost_ptr   = dct_value_cost + DCT_MAX_VALUE;
John Koleszar's avatar
John Koleszar committed
105
}
106
static void tokenize_b(VP9_COMP *cpi,
107
                       MACROBLOCKD *xd,
Yaowu Xu's avatar
Yaowu Xu committed
108
                       const int ib,
109
110
111
112
                       TOKENEXTRA **tp,
                       PLANE_TYPE type,
                       TX_SIZE tx_size,
                       int dry_run) {
Daniel Kang's avatar
Daniel Kang committed
113
  int pt; /* near block/prev token context index */
114
  int c = (type == PLANE_TYPE_Y_NO_DC) ? 1 : 0;
Yaowu Xu's avatar
Yaowu Xu committed
115
  const BLOCKD * const b = xd->block + ib;
116
  int eob = b->eob;     /* one beyond last nonzero coeff */
Daniel Kang's avatar
Daniel Kang committed
117
118
  TOKENEXTRA *t = *tp;        /* store tokens starting here */
  const short *qcoeff_ptr = b->qcoeff;
119
  int seg_eob;
Yaowu Xu's avatar
Yaowu Xu committed
120
  const int segment_id = xd->mode_info_context->mbmi.segment_id;
121
  const int *bands, *scan;
122
123
  vp9_coeff_count *counts;
  vp9_coeff_probs *probs;
124
125
  const TX_TYPE tx_type = (type == PLANE_TYPE_Y_WITH_DC) ?
                          get_tx_type(xd, b) : DCT_DCT;
Daniel Kang's avatar
Daniel Kang committed
126

Yaowu Xu's avatar
Yaowu Xu committed
127
128
129
130
131
132
  ENTROPY_CONTEXT *const a = (ENTROPY_CONTEXT *)xd->above_context +
      vp9_block2above[tx_size][ib];
  ENTROPY_CONTEXT *const l = (ENTROPY_CONTEXT *)xd->left_context +
      vp9_block2left[tx_size][ib];
  ENTROPY_CONTEXT a_ec = *a, l_ec = *l;

133
134
135
136
  switch (tx_size) {
    default:
    case TX_4X4:
      seg_eob = 16;
137
138
      bands = vp9_coef_bands;
      scan = vp9_default_zig_zag1d;
139
      if (tx_type != DCT_DCT) {
140
141
        counts = cpi->hybrid_coef_counts_4x4;
        probs = cpi->common.fc.hybrid_coef_probs_4x4;
142
        if (tx_type == ADST_DCT) {
143
          scan = vp9_row_scan;
144
        } else if (tx_type == DCT_ADST) {
145
          scan = vp9_col_scan;
146
147
        }
      } else {
148
149
        counts = cpi->coef_counts_4x4;
        probs = cpi->common.fc.coef_probs_4x4;
150
151
152
153
154
      }
      break;
    case TX_8X8:
      if (type == PLANE_TYPE_Y2) {
        seg_eob = 4;
155
156
        bands = vp9_coef_bands;
        scan = vp9_default_zig_zag1d;
157
      } else {
Yaowu Xu's avatar
Yaowu Xu committed
158
159
160
161
#if CONFIG_CNVCONTEXT
        a_ec = (a[0] + a[1]) != 0;
        l_ec = (l[0] + l[1]) != 0;
#endif
162
        seg_eob = 64;
163
164
        bands = vp9_coef_bands_8x8;
        scan = vp9_default_zig_zag1d_8x8;
165
166
167
168
169
170
171
172
173
174
      }
      if (tx_type != DCT_DCT) {
        counts = cpi->hybrid_coef_counts_8x8;
        probs = cpi->common.fc.hybrid_coef_probs_8x8;
      } else {
        counts = cpi->coef_counts_8x8;
        probs = cpi->common.fc.coef_probs_8x8;
      }
      break;
    case TX_16X16:
Yaowu Xu's avatar
Yaowu Xu committed
175
#if CONFIG_CNVCONTEXT
Yaowu Xu's avatar
Yaowu Xu committed
176
177
178
179
      if (type != PLANE_TYPE_UV) {
        a_ec = (a[0] + a[1] + a[2] + a[3]) != 0;
        l_ec = (l[0] + l[1] + l[2] + l[3]) != 0;
      }
Yaowu Xu's avatar
Yaowu Xu committed
180
#endif
181
      seg_eob = 256;
182
183
      bands = vp9_coef_bands_16x16;
      scan = vp9_default_zig_zag1d_16x16;
184
185
186
187
188
189
190
      if (tx_type != DCT_DCT) {
        counts = cpi->hybrid_coef_counts_16x16;
        probs = cpi->common.fc.hybrid_coef_probs_16x16;
      } else {
        counts = cpi->coef_counts_16x16;
        probs = cpi->common.fc.coef_probs_16x16;
      }
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
#if CONFIG_SUPERBLOCKS && CONFIG_TX32X32
      if (type == PLANE_TYPE_UV) {
        int uv_idx = (((int) (b - xd->block)) - 16) >> 2;
        qcoeff_ptr = xd->sb_coeff_data.qcoeff + 1024 + 256 * uv_idx;
      }
#endif
      break;
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
    case TX_32X32:
      seg_eob = 1024;
      bands = vp9_coef_bands_32x32;
      scan = vp9_default_zig_zag1d_32x32;
      counts = cpi->coef_counts_32x32;
      probs = cpi->common.fc.coef_probs_32x32;
      qcoeff_ptr = xd->sb_coeff_data.qcoeff;
206
      break;
207
#endif
John Koleszar's avatar
John Koleszar committed
208
209
  }

Yaowu Xu's avatar
Yaowu Xu committed
210
211
  VP9_COMBINEENTROPYCONTEXTS(pt, a_ec, l_ec);

212
213
  if (vp9_segfeature_active(xd, segment_id, SEG_LVL_EOB))
    seg_eob = vp9_get_segdata(xd, segment_id, SEG_LVL_EOB);
John Koleszar's avatar
John Koleszar committed
214

215
  do {
216
    const int band = bands[c];
217
218
219
    int token;

    if (c < eob) {
220
      const int rc = scan[c];
221
      const int v = qcoeff_ptr[rc];
222
223
      assert(-DCT_MAX_VALUE <= v  &&  v < DCT_MAX_VALUE);

224
225
      t->Extra = vp9_dct_value_tokens_ptr[v].Extra;
      token    = vp9_dct_value_tokens_ptr[v].Token;
226
227
228
    } else {
      token = DCT_EOB_TOKEN;
    }
John Koleszar's avatar
John Koleszar committed
229
230

    t->Token = token;
231
232
233
    t->context_tree = probs[type][band][pt];
    t->skip_eob_node = (pt == 0) && ((band > 0 && type != PLANE_TYPE_Y_NO_DC) ||
                                     (band > 1 && type == PLANE_TYPE_Y_NO_DC));
234
    assert(vp9_coef_encodings[t->Token].Len - t->skip_eob_node > 0);
235
    if (!dry_run) {
236
      ++counts[type][band][pt][token];
237
    }
238
    pt = vp9_prev_token_class[token];
239
    ++t;
240
241
242
  } while (c < eob && ++c < seg_eob);

  *tp = t;
Yaowu Xu's avatar
Yaowu Xu committed
243
244
245
246
247
248
249
250
  a_ec = l_ec = (c > !type); /* 0 <-> all coeff data is zero */
  a[0] = a_ec;
  l[0] = l_ec;

  if (tx_size == TX_8X8 && type != PLANE_TYPE_Y2) {
    a[1] = a_ec;
    l[1] = l_ec;
  } else if (tx_size == TX_16X16) {
Yaowu Xu's avatar
Yaowu Xu committed
251
252
253
254
255
256
257
258
259
    if (type != PLANE_TYPE_UV) {
      a[1] = a[2] = a[3] = a_ec;
      l[1] = l[2] = l[3] = l_ec;
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
    } else {
      a[1] = a_ec;
      l[1] = l_ec;
#endif
    }
Yaowu Xu's avatar
Yaowu Xu committed
260
  }
John Koleszar's avatar
John Koleszar committed
261
262
}

263
int vp9_mby_is_skippable_4x4(MACROBLOCKD *xd, int has_2nd_order) {
John Koleszar's avatar
John Koleszar committed
264
265
  int skip = 1;
  int i = 0;
266

267
  if (has_2nd_order) {
John Koleszar's avatar
John Koleszar committed
268
    for (i = 0; i < 16; i++)
Paul Wilkins's avatar
Paul Wilkins committed
269
270
      skip &= (xd->block[i].eob < 2);
    skip &= (!xd->block[24].eob);
John Koleszar's avatar
John Koleszar committed
271
272
  } else {
    for (i = 0; i < 16; i++)
Paul Wilkins's avatar
Paul Wilkins committed
273
      skip &= (!xd->block[i].eob);
John Koleszar's avatar
John Koleszar committed
274
275
  }
  return skip;
276
}
277

278
int vp9_mbuv_is_skippable_4x4(MACROBLOCKD *xd) {
John Koleszar's avatar
John Koleszar committed
279
280
  int skip = 1;
  int i;
281

John Koleszar's avatar
John Koleszar committed
282
  for (i = 16; i < 24; i++)
Paul Wilkins's avatar
Paul Wilkins committed
283
    skip &= (!xd->block[i].eob);
John Koleszar's avatar
John Koleszar committed
284
  return skip;
285
286
}

287
288
static int mb_is_skippable_4x4(MACROBLOCKD *xd, int has_2nd_order) {
  return (vp9_mby_is_skippable_4x4(xd, has_2nd_order) &
289
          vp9_mbuv_is_skippable_4x4(xd));
290
}
Yaowu Xu's avatar
Yaowu Xu committed
291

292
int vp9_mby_is_skippable_8x8(MACROBLOCKD *xd, int has_2nd_order) {
John Koleszar's avatar
John Koleszar committed
293
294
  int skip = 1;
  int i = 0;
295

296
  if (has_2nd_order) {
Deb Mukherjee's avatar
Deb Mukherjee committed
297
298
299
300
301
302
303
    for (i = 0; i < 16; i += 4)
      skip &= (xd->block[i].eob < 2);
    skip &= (!xd->block[24].eob);
  } else {
    for (i = 0; i < 16; i += 4)
      skip &= (!xd->block[i].eob);
  }
John Koleszar's avatar
John Koleszar committed
304
  return skip;
305
}
306

307
int vp9_mbuv_is_skippable_8x8(MACROBLOCKD *xd) {
Paul Wilkins's avatar
Paul Wilkins committed
308
  return (!xd->block[16].eob) & (!xd->block[20].eob);
309
}
310

311
312
static int mb_is_skippable_8x8(MACROBLOCKD *xd, int has_2nd_order) {
  return (vp9_mby_is_skippable_8x8(xd, has_2nd_order) &
313
          vp9_mbuv_is_skippable_8x8(xd));
Deb Mukherjee's avatar
Deb Mukherjee committed
314
315
}

316
317
static int mb_is_skippable_8x8_4x4uv(MACROBLOCKD *xd, int has_2nd_order) {
  return (vp9_mby_is_skippable_8x8(xd, has_2nd_order) &
318
          vp9_mbuv_is_skippable_4x4(xd));
319
}
Yaowu Xu's avatar
Yaowu Xu committed
320

321
int vp9_mby_is_skippable_16x16(MACROBLOCKD *xd) {
Daniel Kang's avatar
Daniel Kang committed
322
  int skip = 1;
Paul Wilkins's avatar
Paul Wilkins committed
323
  skip &= !xd->block[0].eob;
Daniel Kang's avatar
Daniel Kang committed
324
325
326
  return skip;
}

327
328
static int mb_is_skippable_16x16(MACROBLOCKD *xd) {
  return (vp9_mby_is_skippable_16x16(xd) & vp9_mbuv_is_skippable_8x8(xd));
Daniel Kang's avatar
Daniel Kang committed
329
}
330

331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
int vp9_sby_is_skippable_32x32(MACROBLOCKD *xd) {
  int skip = 1;
  skip &= !xd->block[0].eob;
  return skip;
}

int vp9_sbuv_is_skippable_16x16(MACROBLOCKD *xd) {
  return (!xd->block[16].eob) & (!xd->block[20].eob);
}

static int sb_is_skippable_32x32(MACROBLOCKD *xd) {
  return vp9_sby_is_skippable_32x32(xd) &&
         vp9_sbuv_is_skippable_16x16(xd);
}

void vp9_tokenize_sb(VP9_COMP *cpi,
                     MACROBLOCKD *xd,
                     TOKENEXTRA **t,
                     int dry_run) {
  VP9_COMMON * const cm = &cpi->common;
  MB_MODE_INFO * const mbmi = &xd->mode_info_context->mbmi;
  TOKENEXTRA *t_backup = *t;
  ENTROPY_CONTEXT *A[2] = { (ENTROPY_CONTEXT *) (xd->above_context + 0),
                            (ENTROPY_CONTEXT *) (xd->above_context + 1), };
  ENTROPY_CONTEXT *L[2] = { (ENTROPY_CONTEXT *) (xd->left_context + 0),
                            (ENTROPY_CONTEXT *) (xd->left_context + 1), };
  const int mb_skip_context = vp9_get_pred_context(cm, xd, PRED_MBSKIP);
  const int segment_id = mbmi->segment_id;
  const int skip_inc =  !vp9_segfeature_active(xd, segment_id, SEG_LVL_EOB) ||
                        (vp9_get_segdata(xd, segment_id, SEG_LVL_EOB) != 0);
  int b;

  mbmi->mb_skip_coeff = sb_is_skippable_32x32(xd);

  if (mbmi->mb_skip_coeff) {
    if (!dry_run)
      cpi->skip_true_count[mb_skip_context] += skip_inc;
    if (!cm->mb_no_coeff_skip) {
      vp9_stuff_sb(cpi, xd, t, dry_run);
    } else {
      vp9_fix_contexts_sb(xd);
    }
    if (dry_run)
      *t = t_backup;
    return;
  }

  if (!dry_run)
    cpi->skip_false_count[mb_skip_context] += skip_inc;

382
383
  tokenize_b(cpi, xd, 0, t, PLANE_TYPE_Y_WITH_DC,
             TX_32X32, dry_run);
384
385
386
387
  A[0][1] = A[0][2] = A[0][3] = A[0][0];
  L[0][1] = L[0][2] = L[0][3] = L[0][0];

  for (b = 16; b < 24; b += 4) {
388
    tokenize_b(cpi, xd, b, t, PLANE_TYPE_UV,
389
390
391
392
393
394
395
396
397
398
399
400
               TX_16X16, dry_run);
  }
  vpx_memset(&A[0][8], 0, sizeof(A[0][8]));
  vpx_memset(&L[0][8], 0, sizeof(L[0][8]));
  vpx_memcpy(A[1], A[0], sizeof(ENTROPY_CONTEXT_PLANES));
  vpx_memcpy(L[1], L[0], sizeof(ENTROPY_CONTEXT_PLANES));

  if (dry_run)
    *t = t_backup;
}
#endif

401
void vp9_tokenize_mb(VP9_COMP *cpi,
Paul Wilkins's avatar
Paul Wilkins committed
402
                     MACROBLOCKD *xd,
403
404
                     TOKENEXTRA **t,
                     int dry_run) {
405
  PLANE_TYPE plane_type;
406
  int has_2nd_order;
John Koleszar's avatar
John Koleszar committed
407
  int b;
408
  int tx_size = xd->mode_info_context->mbmi.txfm_size;
Paul Wilkins's avatar
Paul Wilkins committed
409
  int mb_skip_context = vp9_get_pred_context(&cpi->common, xd, PRED_MBSKIP);
410
  TOKENEXTRA *t_backup = *t;
Paul Wilkins's avatar
Paul Wilkins committed
411

John Koleszar's avatar
John Koleszar committed
412
413
414
415
  // If the MB is going to be skipped because of a segment level flag
  // exclude this from the skip count stats used to calculate the
  // transmitted skip probability;
  int skip_inc;
Paul Wilkins's avatar
Paul Wilkins committed
416
  int segment_id = xd->mode_info_context->mbmi.segment_id;
417

418
419
  if (!vp9_segfeature_active(xd, segment_id, SEG_LVL_EOB) ||
      (vp9_get_segdata(xd, segment_id, SEG_LVL_EOB) != 0)) {
John Koleszar's avatar
John Koleszar committed
420
421
422
    skip_inc = 1;
  } else
    skip_inc = 0;
423

424
  has_2nd_order = get_2nd_order_usage(xd);
John Koleszar's avatar
John Koleszar committed
425

426
  switch (tx_size) {
Daniel Kang's avatar
Daniel Kang committed
427
    case TX_16X16:
Daniel Kang's avatar
Daniel Kang committed
428
      xd->mode_info_context->mbmi.mb_skip_coeff = mb_is_skippable_16x16(xd);
Daniel Kang's avatar
Daniel Kang committed
429
430
      break;
    case TX_8X8:
431
432
      if (xd->mode_info_context->mbmi.mode == I8X8_PRED ||
          xd->mode_info_context->mbmi.mode == SPLITMV)
433
434
        xd->mode_info_context->mbmi.mb_skip_coeff =
            mb_is_skippable_8x8_4x4uv(xd, 0);
Deb Mukherjee's avatar
Deb Mukherjee committed
435
      else
436
437
        xd->mode_info_context->mbmi.mb_skip_coeff =
            mb_is_skippable_8x8(xd, has_2nd_order);
Daniel Kang's avatar
Daniel Kang committed
438
      break;
Deb Mukherjee's avatar
Deb Mukherjee committed
439

Daniel Kang's avatar
Daniel Kang committed
440
    default:
441
442
      xd->mode_info_context->mbmi.mb_skip_coeff =
          mb_is_skippable_4x4(xd, has_2nd_order);
Daniel Kang's avatar
Daniel Kang committed
443
444
      break;
  }
445

Paul Wilkins's avatar
Paul Wilkins committed
446
  if (xd->mode_info_context->mbmi.mb_skip_coeff) {
447
448
    if (!dry_run)
      cpi->skip_true_count[mb_skip_context] += skip_inc;
John Koleszar's avatar
John Koleszar committed
449
    if (!cpi->common.mb_no_coeff_skip) {
450
      vp9_stuff_mb(cpi, xd, t, dry_run);
John Koleszar's avatar
John Koleszar committed
451
    } else {
Yaowu Xu's avatar
Yaowu Xu committed
452
      vp9_reset_mb_tokens_context(xd);
John Koleszar's avatar
John Koleszar committed
453
    }
Yaowu Xu's avatar
Yaowu Xu committed
454

455
456
    if (dry_run)
      *t = t_backup;
John Koleszar's avatar
John Koleszar committed
457
458
459
    return;
  }

460
461
  if (!dry_run)
    cpi->skip_false_count[mb_skip_context] += skip_inc;
462

463
  if (has_2nd_order) {
Yaowu Xu's avatar
Yaowu Xu committed
464
    tokenize_b(cpi, xd, 24, t, PLANE_TYPE_Y2, tx_size, dry_run);
465
    plane_type = PLANE_TYPE_Y_NO_DC;
Yaowu Xu's avatar
Yaowu Xu committed
466
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
467
468
    xd->above_context->y2 = 0;
    xd->left_context->y2 = 0;
469
    plane_type = PLANE_TYPE_Y_WITH_DC;
Yaowu Xu's avatar
Yaowu Xu committed
470
  }
John Koleszar's avatar
John Koleszar committed
471

472
  if (tx_size == TX_16X16) {
Yaowu Xu's avatar
Yaowu Xu committed
473
    tokenize_b(cpi, xd, 0, t, PLANE_TYPE_Y_WITH_DC, TX_16X16, dry_run);
Daniel Kang's avatar
Daniel Kang committed
474
    for (b = 16; b < 24; b += 4) {
Yaowu Xu's avatar
Yaowu Xu committed
475
      tokenize_b(cpi, xd, b, t, PLANE_TYPE_UV, TX_8X8, dry_run);
Daniel Kang's avatar
Daniel Kang committed
476
    }
477
  } else if (tx_size == TX_8X8) {
John Koleszar's avatar
John Koleszar committed
478
    for (b = 0; b < 16; b += 4) {
Yaowu Xu's avatar
Yaowu Xu committed
479
      tokenize_b(cpi, xd, b, t, plane_type, TX_8X8, dry_run);
John Koleszar's avatar
John Koleszar committed
480
    }
481
482
    if (xd->mode_info_context->mbmi.mode == I8X8_PRED ||
        xd->mode_info_context->mbmi.mode == SPLITMV) {
483
      for (b = 16; b < 24; b++) {
Yaowu Xu's avatar
Yaowu Xu committed
484
        tokenize_b(cpi, xd, b, t, PLANE_TYPE_UV, TX_4X4, dry_run);
485
      }
486
    } else {
Deb Mukherjee's avatar
Deb Mukherjee committed
487
      for (b = 16; b < 24; b += 4) {
Yaowu Xu's avatar
Yaowu Xu committed
488
        tokenize_b(cpi, xd, b, t, PLANE_TYPE_UV, TX_8X8, dry_run);
Deb Mukherjee's avatar
Deb Mukherjee committed
489
      }
490
    }
Jingning Han's avatar
Jingning Han committed
491
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
492
493
494
495
    for (b = 0; b < 24; b++) {
      if (b >= 16)
        plane_type = PLANE_TYPE_UV;
      tokenize_b(cpi, xd, b, t, plane_type, TX_4X4, dry_run);
496
    }
Jingning Han's avatar
Jingning Han committed
497
  }
498
499
  if (dry_run)
    *t = t_backup;
John Koleszar's avatar
John Koleszar committed
500
}
501

John Koleszar's avatar
John Koleszar committed
502
503

#ifdef ENTROPY_STATS
John Koleszar's avatar
John Koleszar committed
504
505
506
void init_context_counters(void) {
  FILE *f = fopen("context.bin", "rb");
  if (!f) {
507
508
509
    vpx_memset(context_counters_4x4, 0, sizeof(context_counters_4x4));
    vpx_memset(hybrid_context_counters_4x4, 0,
               sizeof(hybrid_context_counters_4x4));
John Koleszar's avatar
John Koleszar committed
510
    vpx_memset(context_counters_8x8, 0, sizeof(context_counters_8x8));
511
512
    vpx_memset(hybrid_context_counters_8x8, 0,
               sizeof(hybrid_context_counters_8x8));
Daniel Kang's avatar
Daniel Kang committed
513
    vpx_memset(context_counters_16x16, 0, sizeof(context_counters_16x16));
514
515
516
517
518
    vpx_memset(hybrid_context_counters_16x16, 0,
               sizeof(hybrid_context_counters_16x16));
#if CONFIG_TX32X32
    vpx_memset(context_counters_32x32, 0, sizeof(context_counters_32x32));
#endif
John Koleszar's avatar
John Koleszar committed
519
  } else {
520
521
522
    fread(context_counters_4x4, sizeof(context_counters_4x4), 1, f);
    fread(hybrid_context_counters_4x4,
          sizeof(hybrid_context_counters_4x4), 1, f);
John Koleszar's avatar
John Koleszar committed
523
    fread(context_counters_8x8, sizeof(context_counters_8x8), 1, f);
524
525
    fread(hybrid_context_counters_8x8,
          sizeof(hybrid_context_counters_8x8), 1, f);
Daniel Kang's avatar
Daniel Kang committed
526
    fread(context_counters_16x16, sizeof(context_counters_16x16), 1, f);
527
528
529
530
531
    fread(hybrid_context_counters_16x16,
          sizeof(hybrid_context_counters_16x16), 1, f);
#if CONFIG_TX32X32
    fread(context_counters_32x32, sizeof(context_counters_32x32), 1, f);
#endif
John Koleszar's avatar
John Koleszar committed
532
533
534
535
536
    fclose(f);
  }

  f = fopen("treeupdate.bin", "rb");
  if (!f) {
537
538
539
    vpx_memset(tree_update_hist_4x4, 0, sizeof(tree_update_hist_4x4));
    vpx_memset(hybrid_tree_update_hist_4x4, 0,
               sizeof(hybrid_tree_update_hist_4x4));
John Koleszar's avatar
John Koleszar committed
540
    vpx_memset(tree_update_hist_8x8, 0, sizeof(tree_update_hist_8x8));
541
542
    vpx_memset(hybrid_tree_update_hist_8x8, 0,
               sizeof(hybrid_tree_update_hist_8x8));
Daniel Kang's avatar
Daniel Kang committed
543
    vpx_memset(tree_update_hist_16x16, 0, sizeof(tree_update_hist_16x16));
544
545
546
547
548
    vpx_memset(hybrid_tree_update_hist_16x16, 0,
               sizeof(hybrid_tree_update_hist_16x16));
#if CONFIG_TX32X32
    vpx_memset(tree_update_hist_32x32, 0, sizeof(tree_update_hist_32x32));
#endif
John Koleszar's avatar
John Koleszar committed
549
  } else {
550
551
552
    fread(tree_update_hist_4x4, sizeof(tree_update_hist_4x4), 1, f);
    fread(hybrid_tree_update_hist_4x4,
          sizeof(hybrid_tree_update_hist_4x4), 1, f);
John Koleszar's avatar
John Koleszar committed
553
    fread(tree_update_hist_8x8, sizeof(tree_update_hist_8x8), 1, f);
554
555
    fread(hybrid_tree_update_hist_8x8,
          sizeof(hybrid_tree_update_hist_8x8), 1, f);
Daniel Kang's avatar
Daniel Kang committed
556
    fread(tree_update_hist_16x16, sizeof(tree_update_hist_16x16), 1, f);
557
558
559
560
561
    fread(hybrid_tree_update_hist_16x16,
          sizeof(hybrid_tree_update_hist_16x16), 1, f);
#if CONFIG_TX32X32
    fread(tree_update_hist_32x32, sizeof(tree_update_hist_32x32), 1, f);
#endif
John Koleszar's avatar
John Koleszar committed
562
563
    fclose(f);
  }
John Koleszar's avatar
John Koleszar committed
564
565
}

566
567
static void print_counter(FILE *f, vp9_coeff_accum *context_counters,
                          int block_types, const char *header) {
John Koleszar's avatar
John Koleszar committed
568
  int type, band, pt, t;
John Koleszar's avatar
John Koleszar committed
569

570
  fprintf(f, "static const vp9_coeff_count %s = {\n", header);
John Koleszar's avatar
John Koleszar committed
571

572
#define Comma(X) (X ? "," : "")
John Koleszar's avatar
John Koleszar committed
573
574
575
576
577
578
579
580
581
582
583
584
  type = 0;
  do {
    fprintf(f, "%s\n  { /* block Type %d */", Comma(type), type);
    band = 0;
    do {
      fprintf(f, "%s\n    { /* Coeff Band %d */", Comma(band), band);
      pt = 0;
      do {
        fprintf(f, "%s\n      {", Comma(pt));

        t = 0;
        do {
585
          const INT64 x = context_counters[type][band][pt][t];
John Koleszar's avatar
John Koleszar committed
586
          const int y = (int) x;
587

John Koleszar's avatar
John Koleszar committed
588
589
590
591
592
593
594
595
          assert(x == (INT64) y);  /* no overflow handling yet */
          fprintf(f, "%s %d", Comma(t), y);
        } while (++t < MAX_ENTROPY_TOKENS);
        fprintf(f, "}");
      } while (++pt < PREV_COEF_CONTEXTS);
      fprintf(f, "\n    }");
    } while (++band < COEF_BANDS);
    fprintf(f, "\n  }");
596
  } while (++type < block_types);
Daniel Kang's avatar
Daniel Kang committed
597
  fprintf(f, "\n};\n");
598
}
599

600
601
602
static void print_probs(FILE *f, vp9_coeff_accum *context_counters,
                        int block_types, const char *header) {
  int type, band, pt, t;
Daniel Kang's avatar
Daniel Kang committed
603

604
  fprintf(f, "static const vp9_coeff_probs %s = {", header);
605

John Koleszar's avatar
John Koleszar committed
606
  type = 0;
607
#define Newline(x, spaces) (x ? " " : "\n" spaces)
John Koleszar's avatar
John Koleszar committed
608
  do {
609
610
    fprintf(f, "%s%s{ /* block Type %d */",
            Comma(type), Newline(type, "  "), type);
John Koleszar's avatar
John Koleszar committed
611
612
    band = 0;
    do {
613
614
      fprintf(f, "%s%s{ /* Coeff Band %d */",
              Comma(band), Newline(band, "    "), band);
John Koleszar's avatar
John Koleszar committed
615
616
      pt = 0;
      do {
617
        unsigned int branch_ct[ENTROPY_NODES][2];
John Koleszar's avatar
John Koleszar committed
618
        unsigned int coef_counts[MAX_ENTROPY_TOKENS];
619
        vp9_prob coef_probs[ENTROPY_NODES];
620

John Koleszar's avatar
John Koleszar committed
621
        for (t = 0; t < MAX_ENTROPY_TOKENS; ++t)
622
623
624
          coef_counts[t] = context_counters[type][band][pt][t];
        vp9_tree_probs_from_distribution(MAX_ENTROPY_TOKENS,
                                         vp9_coef_encodings, vp9_coef_tree,
625
                                         coef_probs, branch_ct, coef_counts);
John Koleszar's avatar
John Koleszar committed
626
        fprintf(f, "%s\n      {", Comma(pt));
627

John Koleszar's avatar
John Koleszar committed
628
629
        t = 0;
        do {
630
          fprintf(f, "%s %3d", Comma(t), coef_probs[t]);
John Koleszar's avatar
John Koleszar committed
631
        } while (++t < ENTROPY_NODES);
632

633
        fprintf(f, " }");
John Koleszar's avatar
John Koleszar committed
634
635
636
637
      } while (++pt < PREV_COEF_CONTEXTS);
      fprintf(f, "\n    }");
    } while (++band < COEF_BANDS);
    fprintf(f, "\n  }");
638
  } while (++type < block_types);
John Koleszar's avatar
John Koleszar committed
639
  fprintf(f, "\n};\n");
640
}
641

642
643
void print_context_counters() {
  FILE *f = fopen("vp9_context.c", "w");
644

645
646
  fprintf(f, "#include \"vp9_entropy.h\"\n");
  fprintf(f, "\n/* *** GENERATED FILE: DO NOT EDIT *** */\n\n");
John Koleszar's avatar
John Koleszar committed
647

648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
  /* print counts */
  print_counter(f, context_counters_4x4, BLOCK_TYPES_4X4,
                "vp9_default_coef_counts_4x4[BLOCK_TYPES_4X4]");
  print_counter(f, hybrid_context_counters_4x4, BLOCK_TYPES_4X4,
                "vp9_default_hybrid_coef_counts_4x4[BLOCK_TYPES_4X4]");
  print_counter(f, context_counters_8x8, BLOCK_TYPES_8X8,
                "vp9_default_coef_counts_8x8[BLOCK_TYPES_8X8]");
  print_counter(f, hybrid_context_counters_8x8, BLOCK_TYPES_8X8,
                "vp9_default_hybrid_coef_counts_8x8[BLOCK_TYPES_8X8]");
  print_counter(f, context_counters_16x16, BLOCK_TYPES_16X16,
                "vp9_default_coef_counts_16x16[BLOCK_TYPES_16X16]");
  print_counter(f, hybrid_context_counters_16x16, BLOCK_TYPES_16X16,
                "vp9_default_hybrid_coef_counts_16x16[BLOCK_TYPES_16X16]");
#if CONFIG_TX32X32
  print_counter(f, context_counters_32x32, BLOCK_TYPES_32X32,
                "vp9_default_coef_counts_32x32[BLOCK_TYPES_32X32]");
#endif
Daniel Kang's avatar
Daniel Kang committed
665

666
667
  /* print coefficient probabilities */
  print_probs(f, context_counters_4x4, BLOCK_TYPES_4X4,
668
              "default_coef_probs_4x4[BLOCK_TYPES_4X4]");
669
  print_probs(f, hybrid_context_counters_4x4, BLOCK_TYPES_4X4,
670
              "default_hybrid_coef_probs_4x4[BLOCK_TYPES_4X4]");
671
  print_probs(f, context_counters_8x8, BLOCK_TYPES_8X8,
672
              "default_coef_probs_8x8[BLOCK_TYPES_8X8]");
673
  print_probs(f, hybrid_context_counters_8x8, BLOCK_TYPES_8X8,
674
              "default_hybrid_coef_probs_8x8[BLOCK_TYPES_8X8]");
675
  print_probs(f, context_counters_16x16, BLOCK_TYPES_16X16,
676
              "default_coef_probs_16x16[BLOCK_TYPES_16X16]");
677
  print_probs(f, hybrid_context_counters_16x16, BLOCK_TYPES_16X16,
678
              "default_hybrid_coef_probs_16x16[BLOCK_TYPES_16X16]");
679
680
#if CONFIG_TX32X32
  print_probs(f, context_counters_32x32, BLOCK_TYPES_32X32,
681
              "default_coef_probs_32x32[BLOCK_TYPES_32X32]");
682
#endif
Daniel Kang's avatar
Daniel Kang committed
683

John Koleszar's avatar
John Koleszar committed
684
685
686
  fclose(f);

  f = fopen("context.bin", "wb");
687
688
689
  fwrite(context_counters_4x4, sizeof(context_counters_4x4), 1, f);
  fwrite(hybrid_context_counters_4x4,
         sizeof(hybrid_context_counters_4x4), 1, f);
John Koleszar's avatar
John Koleszar committed
690
  fwrite(context_counters_8x8, sizeof(context_counters_8x8), 1, f);
691
692
  fwrite(hybrid_context_counters_8x8,
         sizeof(hybrid_context_counters_8x8), 1, f);
Daniel Kang's avatar
Daniel Kang committed
693
  fwrite(context_counters_16x16, sizeof(context_counters_16x16), 1, f);
694
695
696
697
698
  fwrite(hybrid_context_counters_16x16,
         sizeof(hybrid_context_counters_16x16), 1, f);
#if CONFIG_TX32X32
  fwrite(context_counters_32x32, sizeof(context_counters_32x32), 1, f);
#endif
John Koleszar's avatar
John Koleszar committed
699
  fclose(f);
John Koleszar's avatar
John Koleszar committed
700
701
702
}
#endif

703
void vp9_tokenize_initialize() {
John Koleszar's avatar
John Koleszar committed
704
  fill_value_tokens();
John Koleszar's avatar
John Koleszar committed
705
706
}

707
static __inline void stuff_b(VP9_COMP *cpi,
708
                             MACROBLOCKD *xd,
Yaowu Xu's avatar
Yaowu Xu committed
709
                             const int ib,
710
711
712
713
                             TOKENEXTRA **tp,
                             PLANE_TYPE type,
                             TX_SIZE tx_size,
                             int dry_run) {
Yaowu Xu's avatar
Yaowu Xu committed
714
  const BLOCKD * const b = xd->block + ib;
715
  const int *bands;
716
717
  vp9_coeff_count *counts;
  vp9_coeff_probs *probs;
718
719
720
721
  int pt, band;
  TOKENEXTRA *t = *tp;
  const TX_TYPE tx_type = (type == PLANE_TYPE_Y_WITH_DC) ?
                          get_tx_type(xd, b) : DCT_DCT;
Yaowu Xu's avatar
Yaowu Xu committed
722
723
724
725
726
727

  ENTROPY_CONTEXT *const a = (ENTROPY_CONTEXT *)xd->above_context +
      vp9_block2above[tx_size][ib];
  ENTROPY_CONTEXT *const l = (ENTROPY_CONTEXT *)xd->left_context +
      vp9_block2left[tx_size][ib];
  ENTROPY_CONTEXT a_ec = *a, l_ec = *l;
John Koleszar's avatar
John Koleszar committed
728

729
730
731
  switch (tx_size) {
    default:
    case TX_4X4:
732
      bands = vp9_coef_bands;
733
      if (tx_type != DCT_DCT) {
734
735
        counts = cpi->hybrid_coef_counts_4x4;
        probs = cpi->common.fc.hybrid_coef_probs_4x4;
736
      } else {
737
738
        counts = cpi->coef_counts_4x4;
        probs = cpi->common.fc.coef_probs_4x4;
739
740
741
      }
      break;
    case TX_8X8:
Yaowu Xu's avatar
Yaowu Xu committed
742
743
744
745
746
747
#if CONFIG_CNVCONTEXT
      if (type != PLANE_TYPE_Y2) {
        a_ec = (a[0] + a[1]) != 0;
        l_ec = (l[0] + l[1]) != 0;
      }
#endif
748
      bands = vp9_coef_bands_8x8;
749
750
751
752
753
754
755
756
757
      if (tx_type != DCT_DCT) {
        counts = cpi->hybrid_coef_counts_8x8;
        probs = cpi->common.fc.hybrid_coef_probs_8x8;
      } else {
        counts = cpi->coef_counts_8x8;
        probs = cpi->common.fc.coef_probs_8x8;
      }
      break;
    case TX_16X16:
Yaowu Xu's avatar
Yaowu Xu committed
758
#if CONFIG_CNVCONTEXT
Yaowu Xu's avatar
Yaowu Xu committed
759
760
761
762
      if (type != PLANE_TYPE_UV) {
        a_ec = (a[0] + a[1] + a[2] + a[3]) != 0;
        l_ec = (l[0] + l[1] + l[2] + l[3]) != 0;
      }
Yaowu Xu's avatar
Yaowu Xu committed
763
#endif
764
      bands = vp9_coef_bands_16x16;
765
766
767
768
769
770
771
772
      if (tx_type != DCT_DCT) {
        counts = cpi->hybrid_coef_counts_16x16;
        probs = cpi->common.fc.hybrid_coef_probs_16x16;
      } else {
        counts = cpi->coef_counts_16x16;
        probs = cpi->common.fc.coef_probs_16x16;
      }
      break;
773
774
775
776
777
778
779
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
    case TX_32X32:
      bands = vp9_coef_bands_32x32;
      counts = cpi->coef_counts_32x32;
      probs = cpi->common.fc.coef_probs_32x32;
      break;
#endif
780
  }
Yaowu Xu's avatar
Yaowu Xu committed
781
782
783

  VP9_COMBINEENTROPYCONTEXTS(pt, a_ec, l_ec);

784
  band = bands[(type == PLANE_TYPE_Y_NO_DC) ? 1 : 0];
John Koleszar's avatar
John Koleszar committed
785
  t->Token = DCT_EOB_TOKEN;
786
  t->context_tree = probs[type][band][pt];
John Koleszar's avatar
John Koleszar committed
787
788
789
  t->skip_eob_node = 0;
  ++t;
  *tp = t;
790
  *a = *l = 0;
Yaowu Xu's avatar
Yaowu Xu committed
791
792
793
794
  if (tx_size == TX_8X8 && type != PLANE_TYPE_Y2) {
    a[1] = 0;
    l[1] = 0;
  } else if (tx_size == TX_16X16) {
Yaowu Xu's avatar
Yaowu Xu committed
795
796
797
798
799
800
801
802
803
    if (type != PLANE_TYPE_UV) {
      a[1] = a[2] = a[3] = 0;
      l[1] = l[2] = l[3] = 0;
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
    } else {
      a[1] = 0;
      l[1] = 0;
#endif
    }
Yaowu Xu's avatar
Yaowu Xu committed
804
805
  }

806
  if (!dry_run) {
807
    ++counts[type][band][pt][DCT_EOB_TOKEN];
808
  }
809
810
}

811
812
static void stuff_mb_8x8(VP9_COMP *cpi, MACROBLOCKD *xd,
                         TOKENEXTRA **t, int dry_run) {
813
  PLANE_TYPE plane_type;
John Koleszar's avatar
John Koleszar committed
814
  int b;
815
  int has_2nd_order = get_2nd_order_usage(xd);
John Koleszar's avatar
John Koleszar committed
816

817
  if (has_2nd_order) {
Yaowu Xu's avatar
Yaowu Xu committed
818
    stuff_b(cpi, xd, 24, t, PLANE_TYPE_Y2, TX_8X8, dry_run);
819
820
    plane_type = PLANE_TYPE_Y_NO_DC;
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
821
822
823
824
#if CONFIG_CNVCONTEXT
    xd->above_context->y2 = 0;
    xd->left_context->y2 = 0;
#endif
825
826
    plane_type = PLANE_TYPE_Y_WITH_DC;
  }
John Koleszar's avatar
John Koleszar committed
827

Yaowu Xu's avatar
Yaowu Xu committed
828
829
830
831
  for (b = 0; b < 24; b += 4) {
    if (b >= 16)
      plane_type = PLANE_TYPE_UV;
    stuff_b(cpi, xd, b, t, plane_type, TX_8X8, dry_run);
John Koleszar's avatar
John Koleszar committed
832
  }
Daniel Kang's avatar
Daniel Kang committed
833
834
}

835
836
static void stuff_mb_16x16(VP9_COMP *cpi, MACROBLOCKD *xd,
                           TOKENEXTRA **t, int dry_run) {
837
  int b;
Yaowu Xu's avatar
Yaowu Xu committed
838
  stuff_b(cpi, xd, 0, t, PLANE_TYPE_Y_WITH_DC, TX_16X16, dry_run);
Daniel Kang's avatar
Daniel Kang committed
839
840

  for (b = 16; b < 24; b += 4) {
Yaowu Xu's avatar
Yaowu Xu committed
841
842
    stuff_b(cpi, xd, b, t, PLANE_TYPE_UV, TX_8X8, dry_run);
  }
Yaowu Xu's avatar
Yaowu Xu committed
843
#if CONFIG_CNVCONTEXT
Yaowu Xu's avatar
Yaowu Xu committed
844
845
  xd->above_context->y2 = 0;
  xd->left_context->y2 = 0;
Yaowu Xu's avatar
Yaowu Xu committed
846
#endif
John Koleszar's avatar
John Koleszar committed
847
848
}

849
850
static void stuff_mb_4x4(VP9_COMP *cpi, MACROBLOCKD *xd,
                         TOKENEXTRA **t, int dry_run) {
John Koleszar's avatar
John Koleszar committed
851
  int b;
852
  PLANE_TYPE plane_type;
Yaowu Xu's avatar
Yaowu Xu committed
853
  int has_2nd_order = get_2nd_order_usage(xd);
John Koleszar's avatar
John Koleszar committed
854

855
  if (has_2nd_order) {
Yaowu Xu's avatar
Yaowu Xu committed
856
    stuff_b(cpi, xd, 24, t, PLANE_TYPE_Y2, TX_4X4, dry_run);
857
858
    plane_type = PLANE_TYPE_Y_NO_DC;
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
859
860
    xd->above_context->y2 = 0;
    xd->left_context->y2 = 0;
861
862
    plane_type = PLANE_TYPE_Y_WITH_DC;
  }
John Koleszar's avatar
John Koleszar committed
863

Yaowu Xu's avatar
Yaowu Xu committed
864
865
866
867
868
  for (b = 0; b < 24; b++) {
    if (b >= 16)
      plane_type = PLANE_TYPE_UV;
    stuff_b(cpi, xd, b, t, plane_type, TX_4X4, dry_run);
  }
John Koleszar's avatar
John Koleszar committed
869
}
Deb Mukherjee's avatar
Deb Mukherjee committed
870

871
872
static void stuff_mb_8x8_4x4uv(VP9_COMP *cpi, MACROBLOCKD *xd,
                               TOKENEXTRA **t, int dry_run) {
873
  PLANE_TYPE plane_type;
Deb Mukherjee's avatar
Deb Mukherjee committed
874
875
  int b;

876
877
  int has_2nd_order = get_2nd_order_usage(xd);
  if (has_2nd_order) {
Yaowu Xu's avatar
Yaowu Xu committed
878
    stuff_b(cpi, xd, 24, t, PLANE_TYPE_Y2, TX_8X8, dry_run);
879
880
    plane_type = PLANE_TYPE_Y_NO_DC;
  } else {
Yaowu Xu's avatar
Yaowu Xu committed
881
882
    xd->above_context->y2 = 0;
    xd->left_context->y2 = 0;
883
884
885
    plane_type = PLANE_TYPE_Y_WITH_DC;
  }

Deb Mukherjee's avatar
Deb Mukherjee committed
886
  for (b = 0; b < 16; b += 4) {
Yaowu Xu's avatar
Yaowu Xu committed
887
    stuff_b(cpi, xd, b, t, plane_type, TX_8X8, dry_run);
Deb Mukherjee's avatar
Deb Mukherjee committed
888
889
  }

Yaowu Xu's avatar
Yaowu Xu committed
890
891
892
  for (b = 16; b < 24; b++) {
    stuff_b(cpi, xd, b, t, PLANE_TYPE_UV, TX_4X4, dry_run);
  }
Deb Mukherjee's avatar
Deb Mukherjee committed
893
894
}

895
void vp9_stuff_mb(VP9_COMP *cpi, MACROBLOCKD *xd, TOKENEXTRA **t, int dry_run) {
896
  TX_SIZE tx_size = xd->mode_info_context->mbmi.txfm_size;
897
  TOKENEXTRA * const t_backup = *t;
898
899

  if (tx_size == TX_16X16) {
900
    stuff_mb_16x16(cpi, xd, t, dry_run);
901
  } else if (tx_size == TX_8X8) {
902
903
    if (xd->mode_info_context->mbmi.mode == I8X8_PRED ||
        xd->mode_info_context->mbmi.mode == SPLITMV) {
904
      stuff_mb_8x8_4x4uv(cpi, xd, t, dry_run);
905
    } else {
906
      stuff_mb_8x8(cpi, xd, t, dry_run);
907
908
    }
  } else {
909
    stuff_mb_4x4(cpi, xd, t, dry_run);
910
  }
911
912
913
914

  if (dry_run) {
    *t = t_backup;
  }
915
916
}

917
918
919
920
921
922
923
924
925
#if CONFIG_TX32X32 && CONFIG_SUPERBLOCKS
static void stuff_sb_32x32(VP9_COMP *cpi, MACROBLOCKD *xd,
                               TOKENEXTRA **t, int dry_run) {
  ENTROPY_CONTEXT *A[2] = { (ENTROPY_CONTEXT *) (xd->above_context + 0),
                            (