vp9_decodemv.c 24.7 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 <assert.h>

13
14
#include "vp9/common/vp9_common.h"
#include "vp9/common/vp9_entropy.h"
15
#include "vp9/common/vp9_entropymode.h"
16
#include "vp9/common/vp9_entropymv.h"
17
#include "vp9/common/vp9_findnearmv.h"
18
#include "vp9/common/vp9_mvref_common.h"
19
#include "vp9/common/vp9_pred_common.h"
20
21
22
#include "vp9/common/vp9_reconinter.h"
#include "vp9/common/vp9_seg_common.h"

23
#include "vp9/decoder/vp9_decodemv.h"
24
#include "vp9/decoder/vp9_decodframe.h"
25
#include "vp9/decoder/vp9_onyxd_int.h"
26
#include "vp9/decoder/vp9_dsubexp.h"
27
28
#include "vp9/decoder/vp9_treereader.h"

29
static MB_PREDICTION_MODE read_intra_mode(vp9_reader *r, const vp9_prob *p) {
30
31
32
33
  return (MB_PREDICTION_MODE)treed_read(r, vp9_intra_mode_tree, p);
}

static MB_PREDICTION_MODE read_inter_mode(vp9_reader *r, const vp9_prob *p) {
34
  return (MB_PREDICTION_MODE)treed_read(r, vp9_inter_mode_tree, p);
35
36
}

37
38
static int read_segment_id(vp9_reader *r, const struct segmentation *seg) {
  return treed_read(r, vp9_segment_tree, seg->tree_probs);
Scott LaVarnway's avatar
Scott LaVarnway committed
39
}
40

41
42
43
44
45
46
47
48
49
static TX_SIZE read_selected_tx_size(VP9_COMMON *cm, MACROBLOCKD *xd,
                                     BLOCK_SIZE_TYPE bsize, vp9_reader *r) {
  const uint8_t context = vp9_get_pred_context_tx_size(xd);
  const vp9_prob *tx_probs = get_tx_probs(bsize, context, &cm->fc.tx_probs);
  TX_SIZE tx_size = vp9_read(r, tx_probs[0]);
  if (tx_size != TX_4X4 && bsize >= BLOCK_SIZE_MB16X16) {
    tx_size += vp9_read(r, tx_probs[1]);
    if (tx_size != TX_8X8 && bsize >= BLOCK_SIZE_SB32X32)
      tx_size += vp9_read(r, tx_probs[2]);
50
51
  }

52
  update_tx_counts(bsize, context, tx_size, &cm->counts.tx);
53
  return tx_size;
54
55
}

56
57
58
static TX_SIZE read_tx_size(VP9D_COMP *pbi, TX_MODE tx_mode,
                            BLOCK_SIZE_TYPE bsize, int select_cond,
                            vp9_reader *r) {
59
60
61
  VP9_COMMON *const cm = &pbi->common;
  MACROBLOCKD *const xd = &pbi->mb;

62
  if (tx_mode == TX_MODE_SELECT && bsize >= BLOCK_SIZE_SB8X8 && select_cond)
63
    return read_selected_tx_size(cm, xd, bsize, r);
64
  else if (tx_mode >= ALLOW_32X32 && bsize >= BLOCK_SIZE_SB32X32)
65
    return TX_32X32;
66
  else if (tx_mode >= ALLOW_16X16 && bsize >= BLOCK_SIZE_MB16X16)
67
    return TX_16X16;
68
  else if (tx_mode >= ALLOW_8X8 && bsize >= BLOCK_SIZE_SB8X8)
69
70
71
72
73
    return TX_8X8;
  else
    return TX_4X4;
}

74
static void set_segment_id(VP9_COMMON *cm, BLOCK_SIZE_TYPE bsize,
75
                           int mi_row, int mi_col, int segment_id) {
76
77
78
  const int mi_offset = mi_row * cm->mi_cols + mi_col;
  const int bw = 1 << mi_width_log2(bsize);
  const int bh = 1 << mi_height_log2(bsize);
79
  const int xmis = MIN(cm->mi_cols - mi_col, bw);
80
  const int ymis = MIN(cm->mi_rows - mi_row, bh);
81
82
  int x, y;

Paul Wilkins's avatar
Paul Wilkins committed
83
  assert(segment_id >= 0 && segment_id < MAX_SEGMENTS);
84
85
86
87
88
89
90
91
92

  for (y = 0; y < ymis; y++)
    for (x = 0; x < xmis; x++)
      cm->last_frame_seg_map[mi_offset + y * cm->mi_cols + x] = segment_id;
}

static int read_intra_segment_id(VP9D_COMP *pbi, int mi_row, int mi_col,
                                 vp9_reader *r) {
  MACROBLOCKD *const xd = &pbi->mb;
93
  struct segmentation *const seg = &xd->seg;
94
  const BLOCK_SIZE_TYPE bsize = xd->mode_info_context->mbmi.sb_type;
95
  int segment_id;
96

97
98
99
100
  if (!seg->enabled)
    return 0;  // Default for disabled segmentation

  if (!seg->update_map)
101
    return 0;
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126

  segment_id = read_segment_id(r, seg);
  set_segment_id(&pbi->common, bsize, mi_row, mi_col, segment_id);
  return segment_id;
}

static int read_inter_segment_id(VP9D_COMP *pbi, int mi_row, int mi_col,
                                 vp9_reader *r) {
  VP9_COMMON *const cm = &pbi->common;
  MACROBLOCKD *const xd = &pbi->mb;
  struct segmentation *const seg = &xd->seg;
  const BLOCK_SIZE_TYPE bsize = xd->mode_info_context->mbmi.sb_type;
  int pred_segment_id, segment_id;

  if (!seg->enabled)
    return 0;  // Default for disabled segmentation

  pred_segment_id = vp9_get_segment_id(cm, cm->last_frame_seg_map,
                                       bsize, mi_row, mi_col);
  if (!seg->update_map)
    return pred_segment_id;

  if (seg->temporal_update) {
    const vp9_prob pred_prob = vp9_get_pred_prob_seg_id(xd);
    const int pred_flag = vp9_read(r, pred_prob);
127
    vp9_set_pred_flag_seg_id(cm, bsize, mi_row, mi_col, pred_flag);
128
129
130
131
    segment_id = pred_flag ? pred_segment_id
                           : read_segment_id(r, seg);
  } else {
    segment_id = read_segment_id(r, seg);
132
  }
133
134
  set_segment_id(cm, bsize, mi_row, mi_col, segment_id);
  return segment_id;
135
136
}

137
static uint8_t read_skip_coeff(VP9D_COMP *pbi, int segment_id, vp9_reader *r) {
138
  VP9_COMMON *const cm = &pbi->common;
139
  MACROBLOCKD *const xd = &pbi->mb;
140
  int skip_coeff = vp9_segfeature_active(&xd->seg, segment_id, SEG_LVL_SKIP);
141
  if (!skip_coeff) {
142
    const int ctx = vp9_get_pred_context_mbskip(xd);
143
    skip_coeff = vp9_read(r, vp9_get_pred_prob_mbskip(cm, xd));
144
    cm->counts.mbskip[ctx][skip_coeff]++;
Deb Mukherjee's avatar
Deb Mukherjee committed
145
  }
146
147
  return skip_coeff;
}
John Koleszar's avatar
John Koleszar committed
148

149
150
151
152
153
154
155
static void read_intra_mode_info(VP9D_COMP *pbi, MODE_INFO *m,
                                 int mi_row, int mi_col, vp9_reader *r) {
  VP9_COMMON *const cm = &pbi->common;
  MACROBLOCKD *const xd = &pbi->mb;
  MB_MODE_INFO *const mbmi = &m->mbmi;
  const BLOCK_SIZE_TYPE bsize = mbmi->sb_type;
  const int mis = cm->mode_info_stride;
156

157
158
  mbmi->segment_id = read_intra_segment_id(pbi, mi_row, mi_col, r);
  mbmi->mb_skip_coeff = read_skip_coeff(pbi, mbmi->segment_id, r);
159
  mbmi->txfm_size = read_tx_size(pbi, cm->tx_mode, bsize, 1, r);
160
161
162
  mbmi->ref_frame[0] = INTRA_FRAME;

  if (bsize >= BLOCK_SIZE_SB8X8) {
163
164
165
    const MB_PREDICTION_MODE A = above_block_mode(m, 0, mis);
    const MB_PREDICTION_MODE L = xd->left_available ?
                                  left_block_mode(m, 0) : DC_PRED;
166
    mbmi->mode = read_intra_mode(r, vp9_kf_y_mode_prob[A][L]);
167
  } else {
168
169
170
    // Only 4x4, 4x8, 8x4 blocks
    const int bw = 1 << b_width_log2(bsize);
    const int bh = 1 << b_height_log2(bsize);
171
    int idx, idy;
172
173
174

    for (idy = 0; idy < 2; idy += bh) {
      for (idx = 0; idx < 2; idx += bw) {
175
        const int ib = idy * 2 + idx;
176
177
178
        const MB_PREDICTION_MODE A = above_block_mode(m, ib, mis);
        const MB_PREDICTION_MODE L = (xd->left_available || idx) ?
                                      left_block_mode(m, ib) : DC_PRED;
179
        const MB_PREDICTION_MODE b_mode = read_intra_mode(r,
180
                                              vp9_kf_y_mode_prob[A][L]);
181
        m->bmi[ib].as_mode = b_mode;
182
        if (bh == 2)
183
          m->bmi[ib + 2].as_mode = b_mode;
184
        if (bw == 2)
185
          m->bmi[ib + 1].as_mode = b_mode;
186
187
      }
    }
188

189
    mbmi->mode = m->bmi[3].as_mode;
John Koleszar's avatar
John Koleszar committed
190
  }
Dmitry Kovalev's avatar
Dmitry Kovalev committed
191

192
  mbmi->uv_mode = read_intra_mode(r, vp9_kf_uv_mode_prob[mbmi->mode]);
Scott LaVarnway's avatar
Scott LaVarnway committed
193
}
John Koleszar's avatar
John Koleszar committed
194

195
196
static int read_mv_component(vp9_reader *r,
                             const nmv_component *mvcomp, int usehp) {
197

198
  int mag, d, fr, hp;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
199
200
  const int sign = vp9_read(r, mvcomp->sign);
  const int mv_class = treed_read(r, vp9_mv_class_tree, mvcomp->classes);
201
  const int class0 = mv_class == MV_CLASS_0;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
202

203
  // Integer part
204
  if (class0) {
205
    d = treed_read(r, vp9_mv_class0_tree, mvcomp->class0);
206
  } else {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
207
    int i;
208
    const int n = mv_class + CLASS0_BITS - 1;  // number of bits
Dmitry Kovalev's avatar
Dmitry Kovalev committed
209

210
    d = 0;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
211
212
    for (i = 0; i < n; ++i)
      d |= vp9_read(r, mvcomp->bits[i]) << i;
213
214
  }

215
216
  // Fractional part
  fr = treed_read(r, vp9_mv_fp_tree,
217
                  class0 ? mvcomp->class0_fp[d] : mvcomp->fp);
218
219


220
  // High precision part (if hp is not used, the default value of the hp is 1)
221
  hp = usehp ? vp9_read(r, class0 ? mvcomp->class0_hp : mvcomp->hp)
222
             : 1;
223

224
  // Result
225
226
  mag = vp9_get_mv_mag(mv_class, (d << 3) | (fr << 1) | hp) + 1;
  return sign ? -mag : mag;
227
228
}

229
230
231
232
233
234
235
236
237
238
239
240
241
static INLINE void read_mv(vp9_reader *r, MV *mv, const MV *ref,
                           const nmv_context *ctx,
                           nmv_context_counts *counts, int usehp) {
  const MV_JOINT_TYPE j = treed_read(r, vp9_mv_joint_tree, ctx->joints);
  MV diff = {0, 0};

  usehp = usehp && vp9_use_mv_hp(ref);
  if (mv_joint_vertical(j))
    diff.row = read_mv_component(r, &ctx->comps[0], usehp);

  if (mv_joint_horizontal(j))
    diff.col = read_mv_component(r, &ctx->comps[1], usehp);

242
  vp9_inc_mv(&diff, counts);
243
244
245
246
247

  mv->row = ref->row + diff.row;
  mv->col = ref->col + diff.col;
}

248
static void update_mv(vp9_reader *r, vp9_prob *p, vp9_prob upd_p) {
249
  if (vp9_read(r, upd_p))
250
    *p = (vp9_read_literal(r, 7) << 1) | 1;
251
252
}

Dmitry Kovalev's avatar
Dmitry Kovalev committed
253
static void read_mv_probs(vp9_reader *r, nmv_context *mvc, int usehp) {
254
  int i, j, k;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
255
256

  for (j = 0; j < MV_JOINTS - 1; ++j)
Dmitry Kovalev's avatar
Dmitry Kovalev committed
257
    update_mv(r, &mvc->joints[j], VP9_NMV_UPDATE_PROB);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
258

259
  for (i = 0; i < 2; ++i) {
260
261
262
    nmv_component *const comp = &mvc->comps[i];

    update_mv(r, &comp->sign, VP9_NMV_UPDATE_PROB);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
263
    for (j = 0; j < MV_CLASSES - 1; ++j)
264
      update_mv(r, &comp->classes[j], VP9_NMV_UPDATE_PROB);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
265
266

    for (j = 0; j < CLASS0_SIZE - 1; ++j)
267
      update_mv(r, &comp->class0[j], VP9_NMV_UPDATE_PROB);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
268
269

    for (j = 0; j < MV_OFFSET_BITS; ++j)
270
      update_mv(r, &comp->bits[j], VP9_NMV_UPDATE_PROB);
271
272
273
  }

  for (i = 0; i < 2; ++i) {
274
275
    nmv_component *const comp = &mvc->comps[i];

276
    for (j = 0; j < CLASS0_SIZE; ++j)
277
      for (k = 0; k < 3; ++k)
278
        update_mv(r, &comp->class0_fp[j][k], VP9_NMV_UPDATE_PROB);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
279
280

    for (j = 0; j < 3; ++j)
281
      update_mv(r, &comp->fp[j], VP9_NMV_UPDATE_PROB);
282
283
284
285
  }

  if (usehp) {
    for (i = 0; i < 2; ++i) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
286
287
      update_mv(r, &mvc->comps[i].class0_hp, VP9_NMV_UPDATE_PROB);
      update_mv(r, &mvc->comps[i].hp, VP9_NMV_UPDATE_PROB);
288
289
290
291
    }
  }
}

292
// Read the referncence frame
Ronald S. Bultje's avatar
Ronald S. Bultje committed
293
294
static void read_ref_frame(VP9D_COMP *pbi, vp9_reader *r,
                           int segment_id, MV_REFERENCE_FRAME ref_frame[2]) {
295
  VP9_COMMON *const cm = &pbi->common;
John Koleszar's avatar
John Koleszar committed
296
  MACROBLOCKD *const xd = &pbi->mb;
297
  FRAME_CONTEXT *const fc = &cm->fc;
298
  FRAME_COUNTS *const counts = &cm->counts;
299

300
301
  if (vp9_segfeature_active(&xd->seg, segment_id, SEG_LVL_REF_FRAME)) {
    ref_frame[0] = vp9_get_segdata(&xd->seg, segment_id, SEG_LVL_REF_FRAME);
302
303
    ref_frame[1] = NONE;
  } else {
304
    const int comp_ctx = vp9_get_pred_context_comp_inter_inter(cm, xd);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
305
    int is_comp;
John Koleszar's avatar
John Koleszar committed
306

Ronald S. Bultje's avatar
Ronald S. Bultje committed
307
    if (cm->comp_pred_mode == HYBRID_PREDICTION) {
308
      is_comp = vp9_read(r, fc->comp_inter_prob[comp_ctx]);
309
      counts->comp_inter[comp_ctx][is_comp]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
310
311
312
    } else {
      is_comp = cm->comp_pred_mode == COMP_PREDICTION_ONLY;
    }
John Koleszar's avatar
John Koleszar committed
313

Ronald S. Bultje's avatar
Ronald S. Bultje committed
314
315
    // FIXME(rbultje) I'm pretty sure this breaks segmentation ref frame coding
    if (is_comp) {
316
      const int fix_ref_idx = cm->ref_frame_sign_bias[cm->comp_fixed_ref];
317
      const int ref_ctx = vp9_get_pred_context_comp_ref_p(cm, xd);
318
      const int b = vp9_read(r, fc->comp_ref_prob[ref_ctx]);
319
      counts->comp_ref[ref_ctx][b]++;
320
      ref_frame[fix_ref_idx] = cm->comp_fixed_ref;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
321
      ref_frame[!fix_ref_idx] = cm->comp_var_ref[b];
Dmitry Kovalev's avatar
Dmitry Kovalev committed
322
    } else {
323
      const int ref1_ctx = vp9_get_pred_context_single_ref_p1(xd);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
324
      ref_frame[1] = NONE;
325
      if (vp9_read(r, fc->single_ref_prob[ref1_ctx][0])) {
326
        const int ref2_ctx = vp9_get_pred_context_single_ref_p2(xd);
327
328
        const int b = vp9_read(r, fc->single_ref_prob[ref2_ctx][1]);
        ref_frame[0] = b ? ALTREF_FRAME : GOLDEN_FRAME;
329
330
        counts->single_ref[ref1_ctx][0][1]++;
        counts->single_ref[ref2_ctx][1][b]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
331
332
      } else {
        ref_frame[0] = LAST_FRAME;
333
        counts->single_ref[ref1_ctx][0][0]++;
John Koleszar's avatar
John Koleszar committed
334
      }
335
    }
John Koleszar's avatar
John Koleszar committed
336
  }
337
}
John Koleszar's avatar
John Koleszar committed
338

339
static void read_switchable_interp_probs(FRAME_CONTEXT *fc, vp9_reader *r) {
340
  int i, j;
341
342
343
  for (j = 0; j < VP9_SWITCHABLE_FILTERS + 1; ++j)
    for (i = 0; i < VP9_SWITCHABLE_FILTERS - 1; ++i)
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
344
        vp9_diff_update_prob(r, &fc->switchable_interp_prob[j][i]);
345
346
}

347
static void read_inter_mode_probs(FRAME_CONTEXT *fc, vp9_reader *r) {
348
349
  int i, j;
  for (i = 0; i < INTER_MODE_CONTEXTS; ++i)
350
351
    for (j = 0; j < VP9_INTER_MODES - 1; ++j)
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
352
        vp9_diff_update_prob(r, &fc->inter_mode_probs[i][j]);
353
}
John Koleszar's avatar
John Koleszar committed
354

355
356
357
static INLINE COMPPREDMODE_TYPE read_comp_pred_mode(vp9_reader *r) {
  COMPPREDMODE_TYPE mode = vp9_read_bit(r);
  if (mode)
358
    mode += vp9_read_bit(r);
359
360
361
  return mode;
}

Dmitry Kovalev's avatar
Dmitry Kovalev committed
362
363
364
365
366
367
368
369
370
371
static INLINE void assign_and_clamp_mv(int_mv *dst, const int_mv *src,
                                       int mb_to_left_edge,
                                       int mb_to_right_edge,
                                       int mb_to_top_edge,
                                       int mb_to_bottom_edge) {
  dst->as_int = src->as_int;
  clamp_mv(dst, mb_to_left_edge, mb_to_right_edge, mb_to_top_edge,
           mb_to_bottom_edge);
}

372
static INLINE INTERPOLATIONFILTERTYPE read_switchable_filter_type(
373
    VP9D_COMP *pbi, vp9_reader *r) {
374
375
  VP9_COMMON *const cm = &pbi->common;
  MACROBLOCKD *const xd = &pbi->mb;
376
  const vp9_prob *probs = vp9_get_pred_probs_switchable_interp(cm, xd);
377
  const int index = treed_read(r, vp9_switchable_interp_tree, probs);
378
  const int ctx = vp9_get_pred_context_switchable_interp(xd);
379
  ++cm->counts.switchable_interp[ctx][index];
380
381
382
  return vp9_switchable_interp[index];
}

383
static void read_intra_block_modes(VP9D_COMP *pbi, MODE_INFO *mi,
384
                                   vp9_reader *r) {
385
  VP9_COMMON *const cm = &pbi->common;
386
  MB_MODE_INFO *const mbmi = &mi->mbmi;
387
  const BLOCK_SIZE_TYPE bsize = mi->mbmi.sb_type;
388
  const int bwl = b_width_log2(bsize), bhl = b_height_log2(bsize);
389
390

  if (bsize >= BLOCK_SIZE_SB8X8) {
391
392
    const int size_group = MIN(3, MIN(bwl, bhl));
    mbmi->mode = read_intra_mode(r, cm->fc.y_mode_prob[size_group]);
393
    cm->counts.y_mode[size_group][mbmi->mode]++;
394
  } else {
395
396
     // Only 4x4, 4x8, 8x4 blocks
     const int bw = 1 << bwl, bh = 1 << bhl;
397
     int idx, idy;
398

399
400
     for (idy = 0; idy < 2; idy += bh) {
       for (idx = 0; idx < 2; idx += bw) {
401
402
         const int ib = idy * 2 + idx;
         const int b_mode = read_intra_mode(r, cm->fc.y_mode_prob[0]);
403
         mi->bmi[ib].as_mode = b_mode;
404
         cm->counts.y_mode[0][b_mode]++;
405
406

         if (bh == 2)
407
           mi->bmi[ib + 2].as_mode = b_mode;
408
         if (bw == 2)
409
           mi->bmi[ib + 1].as_mode = b_mode;
410
411
      }
    }
412
    mbmi->mode = mi->bmi[3].as_mode;
413
414
415
  }

  mbmi->uv_mode = read_intra_mode(r, cm->fc.uv_mode_prob[mbmi->mode]);
416
  cm->counts.uv_mode[mbmi->mode][mbmi->uv_mode]++;
417
418
419
420
421
422
423
424
}

static MV_REFERENCE_FRAME read_reference_frame(VP9D_COMP *pbi, int segment_id,
                                               vp9_reader *r) {
  VP9_COMMON *const cm = &pbi->common;
  MACROBLOCKD *const xd = &pbi->mb;

  MV_REFERENCE_FRAME ref;
425
  if (!vp9_segfeature_active(&xd->seg, segment_id, SEG_LVL_REF_FRAME)) {
426
    const int ctx = vp9_get_pred_context_intra_inter(xd);
427
    ref = (MV_REFERENCE_FRAME)
428
              vp9_read(r, vp9_get_pred_prob_intra_inter(cm, xd));
429
    cm->counts.intra_inter[ctx][ref != INTRA_FRAME]++;
430
  } else {
431
432
    ref = (MV_REFERENCE_FRAME) vp9_get_segdata(&xd->seg, segment_id,
                                   SEG_LVL_REF_FRAME) != INTRA_FRAME;
433
434
435
436
  }
  return ref;
}

437
438
static void read_inter_mode_info(VP9D_COMP *pbi, MODE_INFO *mi,
                                 int mi_row, int mi_col, vp9_reader *r) {
439
  VP9_COMMON *const cm = &pbi->common;
440
  MACROBLOCKD *const xd = &pbi->mb;
441
  nmv_context *const nmvc = &cm->fc.nmvc;
442
  MB_MODE_INFO *const mbmi = &mi->mbmi;
John Koleszar's avatar
John Koleszar committed
443

444
445
  int_mv *const mv0 = &mbmi->mv[0];
  int_mv *const mv1 = &mbmi->mv[1];
446
447
448
  const BLOCK_SIZE_TYPE bsize = mi->mbmi.sb_type;
  const int bw = 1 << b_width_log2(bsize);
  const int bh = 1 << b_height_log2(bsize);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
449

450
  int idx, idy;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
451

452
  mbmi->segment_id = read_inter_segment_id(pbi, mi_row, mi_col, r);
453
  mbmi->mb_skip_coeff = read_skip_coeff(pbi, mbmi->segment_id, r);
454
  mbmi->ref_frame[0] = read_reference_frame(pbi, mbmi->segment_id, r);
455
  mbmi->ref_frame[1] = NONE;
456
  mbmi->txfm_size = read_tx_size(pbi, cm->tx_mode, bsize,
457
     (!mbmi->mb_skip_coeff || mbmi->ref_frame[0] == INTRA_FRAME), r);
458

Ronald S. Bultje's avatar
Ronald S. Bultje committed
459
  if (mbmi->ref_frame[0] != INTRA_FRAME) {
John Koleszar's avatar
John Koleszar committed
460
461
    int_mv nearest, nearby, best_mv;
    int_mv nearest_second, nearby_second, best_mv_second;
462
    vp9_prob *mv_ref_p;
463
    MV_REFERENCE_FRAME ref0, ref1;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
464
465

    read_ref_frame(pbi, r, mbmi->segment_id, mbmi->ref_frame);
466
467
    ref0 = mbmi->ref_frame[0];
    ref1 = mbmi->ref_frame[1];
468

469
470
    vp9_find_mv_refs(cm, xd, mi, xd->prev_mode_info_context,
                     ref0, mbmi->ref_mvs[ref0], cm->ref_frame_sign_bias);
471

472
    mv_ref_p = cm->fc.inter_mode_probs[mbmi->mb_mode_context[ref0]];
473

474
    if (vp9_segfeature_active(&xd->seg, mbmi->segment_id, SEG_LVL_SKIP)) {
475
476
477
478
479
480
481
482
483
484
485
486
      mbmi->mode = ZEROMV;
    } else if (bsize >= BLOCK_SIZE_SB8X8) {
      mbmi->mode = read_inter_mode(r, mv_ref_p);
      vp9_accum_mv_refs(cm, mbmi->mode, mbmi->mb_mode_context[ref0]);
    }
    mbmi->uv_mode = DC_PRED;

    // nearest, nearby
    if (bsize < BLOCK_SIZE_SB8X8 || mbmi->mode != ZEROMV) {
      vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref0], &nearest, &nearby);
      best_mv.as_int = mbmi->ref_mvs[ref0][0].as_int;
    }
487

488
489
490
    mbmi->interp_filter = cm->mcomp_filter_type == SWITCHABLE
                              ? read_switchable_filter_type(pbi, r)
                              : cm->mcomp_filter_type;
491

492
    if (ref1 > INTRA_FRAME) {
Ronald S. Bultje's avatar
Ronald S. Bultje committed
493
      vp9_find_mv_refs(cm, xd, mi, xd->prev_mode_info_context,
494
                       ref1, mbmi->ref_mvs[ref1], cm->ref_frame_sign_bias);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
495
496

      if (bsize < BLOCK_SIZE_SB8X8 || mbmi->mode != ZEROMV) {
497
498
499
        vp9_find_best_ref_mvs(xd, mbmi->ref_mvs[ref1],
                              &nearest_second, &nearby_second);
        best_mv_second.as_int = mbmi->ref_mvs[ref1][0].as_int;
500
      }
John Koleszar's avatar
John Koleszar committed
501
    }
502

503

Ronald S. Bultje's avatar
Ronald S. Bultje committed
504
505
506
507
    if (mbmi->sb_type < BLOCK_SIZE_SB8X8) {
      for (idy = 0; idy < 2; idy += bh) {
        for (idx = 0; idx < 2; idx += bw) {
          int_mv blockmv, secondmv;
508
          const int j = idy * 2 + idx;
509
          const int blockmode = read_inter_mode(r, mv_ref_p);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
510

511
          vp9_accum_mv_refs(cm, blockmode, mbmi->mb_mode_context[ref0]);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
512
513
          if (blockmode == NEARESTMV || blockmode == NEARMV) {
            vp9_append_sub8x8_mvs_for_idx(cm, xd, &nearest, &nearby, j, 0);
514
            if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
515
516
517
              vp9_append_sub8x8_mvs_for_idx(cm, xd,  &nearest_second,
                                            &nearby_second, j, 1);
          }
518

Ronald S. Bultje's avatar
Ronald S. Bultje committed
519
520
          switch (blockmode) {
            case NEWMV:
521
              read_mv(r, &blockmv.as_mv, &best_mv.as_mv, nmvc,
522
                      &cm->counts.mv, xd->allow_high_precision_mv);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
523

524
              if (ref1 > 0)
525
                read_mv(r, &secondmv.as_mv, &best_mv_second.as_mv, nmvc,
526
                        &cm->counts.mv, xd->allow_high_precision_mv);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
527
528
529
              break;
            case NEARESTMV:
              blockmv.as_int = nearest.as_int;
530
              if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
531
532
533
534
                secondmv.as_int = nearest_second.as_int;
              break;
            case NEARMV:
              blockmv.as_int = nearby.as_int;
535
              if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
536
537
538
539
                secondmv.as_int = nearby_second.as_int;
              break;
            case ZEROMV:
              blockmv.as_int = 0;
540
              if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
541
542
543
                secondmv.as_int = 0;
              break;
            default:
544
              assert(!"Invalid inter mode value");
John Koleszar's avatar
John Koleszar committed
545
          }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
546
          mi->bmi[j].as_mv[0].as_int = blockmv.as_int;
547
          if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
548
549
            mi->bmi[j].as_mv[1].as_int = secondmv.as_int;

550
          if (bh == 2)
551
            mi->bmi[j + 2] = mi->bmi[j];
552
          if (bw == 2)
553
            mi->bmi[j + 1] = mi->bmi[j];
Ronald S. Bultje's avatar
Ronald S. Bultje committed
554
          mi->mbmi.mode = blockmode;
555
        }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
556
      }
John Koleszar's avatar
John Koleszar committed
557

Ronald S. Bultje's avatar
Ronald S. Bultje committed
558
559
560
      mv0->as_int = mi->bmi[3].as_mv[0].as_int;
      mv1->as_int = mi->bmi[3].as_mv[1].as_int;
    } else {
561
562
563
564
565
      const int mb_to_top_edge = xd->mb_to_top_edge - LEFT_TOP_MARGIN;
      const int mb_to_bottom_edge = xd->mb_to_bottom_edge + RIGHT_BOTTOM_MARGIN;
      const int mb_to_left_edge = xd->mb_to_left_edge - LEFT_TOP_MARGIN;
      const int mb_to_right_edge = xd->mb_to_right_edge + RIGHT_BOTTOM_MARGIN;

Ronald S. Bultje's avatar
Ronald S. Bultje committed
566
567
568
569
570
571
572
      switch (mbmi->mode) {
        case NEARMV:
          // Clip "next_nearest" so that it does not extend to far out of image
          assign_and_clamp_mv(mv0, &nearby, mb_to_left_edge,
                                            mb_to_right_edge,
                                            mb_to_top_edge,
                                            mb_to_bottom_edge);
573
          if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
574
575
576
577
578
579
580
581
582
583
584
585
            assign_and_clamp_mv(mv1, &nearby_second, mb_to_left_edge,
                                                     mb_to_right_edge,
                                                     mb_to_top_edge,
                                                     mb_to_bottom_edge);
          break;

        case NEARESTMV:
          // Clip "next_nearest" so that it does not extend to far out of image
          assign_and_clamp_mv(mv0, &nearest, mb_to_left_edge,
                                             mb_to_right_edge,
                                             mb_to_top_edge,
                                             mb_to_bottom_edge);
586
          if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
587
588
589
590
591
592
593
594
            assign_and_clamp_mv(mv1, &nearest_second, mb_to_left_edge,
                                                      mb_to_right_edge,
                                                      mb_to_top_edge,
                                                      mb_to_bottom_edge);
          break;

        case ZEROMV:
          mv0->as_int = 0;
595
          if (ref1 > 0)
Ronald S. Bultje's avatar
Ronald S. Bultje committed
596
597
598
599
            mv1->as_int = 0;
          break;

        case NEWMV:
600
          read_mv(r, &mv0->as_mv, &best_mv.as_mv, nmvc, &cm->counts.mv,
601
                  xd->allow_high_precision_mv);
602
          if (ref1 > 0)
603
            read_mv(r, &mv1->as_mv, &best_mv_second.as_mv, nmvc,
604
                    &cm->counts.mv, xd->allow_high_precision_mv);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
605
606
          break;
        default:
607
          assert(!"Invalid inter mode value");
Ronald S. Bultje's avatar
Ronald S. Bultje committed
608
      }
Scott LaVarnway's avatar
Scott LaVarnway committed
609
    }
John Koleszar's avatar
John Koleszar committed
610
  } else {
611
    mv0->as_int = 0;  // required for left and above block mv
612
    read_intra_block_modes(pbi, mi, r);
John Koleszar's avatar
John Koleszar committed
613
  }
Scott LaVarnway's avatar
Scott LaVarnway committed
614
}
John Koleszar's avatar
John Koleszar committed
615

616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
static void read_comp_pred(VP9_COMMON *cm, vp9_reader *r) {
  int i;

  cm->comp_pred_mode = cm->allow_comp_inter_inter ? read_comp_pred_mode(r)
                                                  : SINGLE_PREDICTION_ONLY;

  if (cm->comp_pred_mode == HYBRID_PREDICTION)
    for (i = 0; i < COMP_INTER_CONTEXTS; i++)
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
        vp9_diff_update_prob(r, &cm->fc.comp_inter_prob[i]);

  if (cm->comp_pred_mode != COMP_PREDICTION_ONLY)
    for (i = 0; i < REF_CONTEXTS; i++) {
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
        vp9_diff_update_prob(r, &cm->fc.single_ref_prob[i][0]);
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
        vp9_diff_update_prob(r, &cm->fc.single_ref_prob[i][1]);
    }

  if (cm->comp_pred_mode != SINGLE_PREDICTION_ONLY)
    for (i = 0; i < REF_CONTEXTS; i++)
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
        vp9_diff_update_prob(r, &cm->fc.comp_ref_prob[i]);
}

641
642
void vp9_prepare_read_mode_info(VP9D_COMP* pbi, vp9_reader *r) {
  VP9_COMMON *const cm = &pbi->common;
643
  int k;
644

645
  // TODO(jkoleszar): does this clear more than MBSKIP_CONTEXTS? Maybe remove.
Deb Mukherjee's avatar
Deb Mukherjee committed
646
  // vpx_memset(cm->fc.mbskip_probs, 0, sizeof(cm->fc.mbskip_probs));
647
648
  for (k = 0; k < MBSKIP_CONTEXTS; ++k)
    if (vp9_read(r, VP9_MODE_UPDATE_PROB))
649
      vp9_diff_update_prob(r, &cm->fc.mbskip_probs[k]);
650

651
652
653
654
655
656
657
658
659
660
661
662
663
664
  if (cm->frame_type != KEY_FRAME && !cm->intra_only) {
    nmv_context *const nmvc = &pbi->common.fc.nmvc;
    MACROBLOCKD *const xd = &pbi->mb;
    int i, j;

    read_inter_mode_probs(&cm->fc, r);

    if (cm->mcomp_filter_type == SWITCHABLE)
      read_switchable_interp_probs(&cm->fc, r);

    for (i = 0; i < INTRA_INTER_CONTEXTS; i++)
      if (vp9_read(r, VP9_MODE_UPDATE_PROB))
        vp9_diff_update_prob(r, &cm->fc.intra_inter_prob[i]);

665
    read_comp_pred(cm, r);
666
667
668
669
670
671
672
673
674
675
676
677
678

    for (j = 0; j < BLOCK_SIZE_GROUPS; j++)
      for (i = 0; i < VP9_INTRA_MODES - 1; ++i)
        if (vp9_read(r, VP9_MODE_UPDATE_PROB))
          vp9_diff_update_prob(r, &cm->fc.y_mode_prob[j][i]);

    for (j = 0; j < NUM_PARTITION_CONTEXTS; ++j)
      for (i = 0; i < PARTITION_TYPES - 1; ++i)
        if (vp9_read(r, VP9_MODE_UPDATE_PROB))
          vp9_diff_update_prob(r, &cm->fc.partition_prob[INTER_FRAME][j][i]);

    read_mv_probs(r, nmvc, xd->allow_high_precision_mv);
  }
679
}
680

681
void vp9_read_mode_info(VP9D_COMP* pbi, int mi_row, int mi_col, vp9_reader *r) {
682
  VP9_COMMON *const cm = &pbi->common;
683
  MACROBLOCKD *const xd = &pbi->mb;
684
  MODE_INFO *mi = xd->mode_info_context;
685
  const BLOCK_SIZE_TYPE bsize = mi->mbmi.sb_type;
Jim Bankoski's avatar
Jim Bankoski committed
686
687
688
689
690
  const int bw = 1 << mi_width_log2(bsize);
  const int bh = 1 << mi_height_log2(bsize);
  const int y_mis = MIN(bh, cm->mi_rows - mi_row);
  const int x_mis = MIN(bw, cm->mi_cols - mi_col);
  int x, y;
691

692
693
694
695
  if (cm->frame_type == KEY_FRAME || cm->intra_only)
    read_intra_mode_info(pbi, mi, mi_row, mi_col, r);
  else
    read_inter_mode_info(pbi, mi, mi_row, mi_col, r);
696

Jim Bankoski's avatar
Jim Bankoski committed
697
698
699
  for (y = 0; y < y_mis; y++)
    for (x = !y; x < x_mis; x++)
      mi[y * cm->mode_info_stride + x] = *mi;
700
}