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

Dmitry Kovalev's avatar
Dmitry Kovalev committed
11
12
13
14
#include <limits.h>
#include <math.h>
#include <stdio.h>

Jim Bankoski's avatar
Jim Bankoski committed
15
#include "./vp9_rtcd.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
16
17
18
19
#include "./vpx_config.h"

#include "vpx_ports/vpx_timer.h"

20
#include "vp9/common/vp9_common.h"
Yaowu Xu's avatar
Yaowu Xu committed
21
#include "vp9/common/vp9_entropy.h"
22
#include "vp9/common/vp9_entropymode.h"
23
#include "vp9/common/vp9_idct.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
24
25
26
#include "vp9/common/vp9_mvref_common.h"
#include "vp9/common/vp9_pred_common.h"
#include "vp9/common/vp9_quant_common.h"
27
#include "vp9/common/vp9_reconintra.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
28
#include "vp9/common/vp9_reconinter.h"
29
#include "vp9/common/vp9_seg_common.h"
30
#include "vp9/common/vp9_tile_common.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
31
32
33
#include "vp9/encoder/vp9_encodeframe.h"
#include "vp9/encoder/vp9_encodemb.h"
#include "vp9/encoder/vp9_encodemv.h"
34
#include "vp9/encoder/vp9_extend.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
35
36
37
#include "vp9/encoder/vp9_onyx_int.h"
#include "vp9/encoder/vp9_rdopt.h"
#include "vp9/encoder/vp9_segmentation.h"
38
#include "vp9/common/vp9_systemdependent.h"
39
#include "vp9/encoder/vp9_tokenize.h"
40
41
#include "vp9/encoder/vp9_vaq.h"

Paul Wilkins's avatar
Paul Wilkins committed
42

Yaowu Xu's avatar
Yaowu Xu committed
43
#define DBG_PRNT_SEGMAP 0
44

45

46
// #define ENC_DEBUG
47
#ifdef ENC_DEBUG
John Koleszar's avatar
John Koleszar committed
48
int enc_debug = 0;
49
50
#endif

51
static INLINE uint8_t *get_sb_index(MACROBLOCK *x, BLOCK_SIZE subsize) {
52
53
54
55
56
  switch (subsize) {
    case BLOCK_64X64:
    case BLOCK_64X32:
    case BLOCK_32X64:
    case BLOCK_32X32:
57
      return &x->sb_index;
58
59
60
    case BLOCK_32X16:
    case BLOCK_16X32:
    case BLOCK_16X16:
61
      return &x->mb_index;
62
63
64
    case BLOCK_16X8:
    case BLOCK_8X16:
    case BLOCK_8X8:
65
      return &x->b_index;
66
67
68
    case BLOCK_8X4:
    case BLOCK_4X8:
    case BLOCK_4X4:
69
      return &x->ab_index;
70
71
72
73
74
75
    default:
      assert(0);
      return NULL;
  }
}

Jim Bankoski's avatar
Jim Bankoski committed
76
static void encode_superblock(VP9_COMP *cpi, TOKENEXTRA **t, int output_enabled,
77
                              int mi_row, int mi_col, BLOCK_SIZE bsize);
78

79
static void adjust_act_zbin(VP9_COMP *cpi, MACROBLOCK *x);
80

81
82
83
/* activity_avg must be positive, or flat regions could get a zero weight
 *  (infinite lambda), which confounds analysis.
 * This also avoids the need for divide by zero checks in
84
 *  vp9_activity_masking().
85
 */
86
#define ACTIVITY_AVG_MIN (64)
87

88
89
90
/* Motion vector component magnitude threshold for defining fast motion. */
#define FAST_MOTION_MV_THRESH (24)

91
92
93
94
95
/* This is used as a reference when computing the source variance for the
 *  purposes of activity masking.
 * Eventually this should be replaced by custom no-reference routines,
 *  which will be faster.
 */
96
97
98
99
100
101
102
103
104
105
106
static const uint8_t VP9_VAR_OFFS[64] = {
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128,
  128, 128, 128, 128, 128, 128, 128, 128
};

107
static unsigned int get_sby_perpixel_variance(VP9_COMP *cpi, MACROBLOCK *x,
108
                                              BLOCK_SIZE bs) {
109
110
111
112
  unsigned int var, sse;
  var = cpi->fn_ptr[bs].vf(x->plane[0].src.buf,
                           x->plane[0].src.stride,
                           VP9_VAR_OFFS, 0, &sse);
113
114
115
116
  return (var + (1 << (num_pels_log2_lookup[bs] - 1))) >>
      num_pels_log2_lookup[bs];
}

117
// Original activity measure from Tim T's code.
118
static unsigned int tt_activity_measure(MACROBLOCK *x) {
John Koleszar's avatar
John Koleszar committed
119
120
121
122
123
124
125
126
127
  unsigned int act;
  unsigned int sse;
  /* TODO: This could also be done over smaller areas (8x8), but that would
   *  require extensive changes elsewhere, as lambda is assumed to be fixed
   *  over an entire MB in most of the code.
   * Another option is to compute four 8x8 variances, and pick a single
   *  lambda using a non-linear combination (e.g., the smallest, or second
   *  smallest, etc.).
   */
John Koleszar's avatar
John Koleszar committed
128
129
  act = vp9_variance16x16(x->plane[0].src.buf, x->plane[0].src.stride,
                          VP9_VAR_OFFS, 0, &sse);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
130
  act <<= 4;
John Koleszar's avatar
John Koleszar committed
131
132
133
134
135
136

  /* If the region is flat, lower the activity some more. */
  if (act < 8 << 12)
    act = act < 5 << 12 ? act : 5 << 12;

  return act;
137
138
}

139
// Stub for alternative experimental activity measures.
140
141
static unsigned int alt_activity_measure(MACROBLOCK *x, int use_dc_pred) {
  return vp9_encode_intra(x, use_dc_pred);
142
143
144
145
}

// Measure the activity of the current macroblock
// What we measure here is TBD so abstracted to this function
146
#define ALT_ACT_MEASURE 1
147
static unsigned int mb_activity_measure(MACROBLOCK *x, int mb_row, int mb_col) {
John Koleszar's avatar
John Koleszar committed
148
  unsigned int mb_activity;
149

John Koleszar's avatar
John Koleszar committed
150
151
  if (ALT_ACT_MEASURE) {
    int use_dc_pred = (mb_col || mb_row) && (!mb_col || !mb_row);
152

John Koleszar's avatar
John Koleszar committed
153
    // Or use and alternative.
154
    mb_activity = alt_activity_measure(x, use_dc_pred);
John Koleszar's avatar
John Koleszar committed
155
156
  } else {
    // Original activity measure from Tim T's code.
157
    mb_activity = tt_activity_measure(x);
John Koleszar's avatar
John Koleszar committed
158
  }
159

160
161
  if (mb_activity < ACTIVITY_AVG_MIN)
    mb_activity = ACTIVITY_AVG_MIN;
162

John Koleszar's avatar
John Koleszar committed
163
  return mb_activity;
164
165
166
}

// Calculate an "average" mb activity value for the frame
167
#define ACT_MEDIAN 0
168
static void calc_av_activity(VP9_COMP *cpi, int64_t activity_sum) {
169
#if ACT_MEDIAN
John Koleszar's avatar
John Koleszar committed
170
171
172
173
174
175
176
177
  // Find median: Simple n^2 algorithm for experimentation
  {
    unsigned int median;
    unsigned int i, j;
    unsigned int *sortlist;
    unsigned int tmp;

    // Create a list to sort to
178
179
    CHECK_MEM_ERROR(&cpi->common, sortlist, vpx_calloc(sizeof(unsigned int),
                    cpi->common.MBs));
John Koleszar's avatar
John Koleszar committed
180
181
182

    // Copy map to sort list
    vpx_memcpy(sortlist, cpi->mb_activity_map,
Jim Bankoski's avatar
Jim Bankoski committed
183
        sizeof(unsigned int) * cpi->common.MBs);
John Koleszar's avatar
John Koleszar committed
184
185
186
187
188
189
190
191
192

    // Ripple each value down to its correct position
    for (i = 1; i < cpi->common.MBs; i ++) {
      for (j = i; j > 0; j --) {
        if (sortlist[j] < sortlist[j - 1]) {
          // Swap values
          tmp = sortlist[j - 1];
          sortlist[j - 1] = sortlist[j];
          sortlist[j] = tmp;
193
194
195
        } else {
          break;
        }
John Koleszar's avatar
John Koleszar committed
196
197
      }
    }
198

John Koleszar's avatar
John Koleszar committed
199
200
    // Even number MBs so estimate median as mean of two either side.
    median = (1 + sortlist[cpi->common.MBs >> 1] +
Jim Bankoski's avatar
Jim Bankoski committed
201
        sortlist[(cpi->common.MBs >> 1) + 1]) >> 1;
202

John Koleszar's avatar
John Koleszar committed
203
    cpi->activity_avg = median;
204

John Koleszar's avatar
John Koleszar committed
205
206
    vpx_free(sortlist);
  }
207
#else
John Koleszar's avatar
John Koleszar committed
208
  // Simple mean for now
Jim Bankoski's avatar
Jim Bankoski committed
209
  cpi->activity_avg = (unsigned int) (activity_sum / cpi->common.MBs);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
210
#endif  // ACT_MEDIAN
211

212
213
  if (cpi->activity_avg < ACTIVITY_AVG_MIN)
    cpi->activity_avg = ACTIVITY_AVG_MIN;
214

John Koleszar's avatar
John Koleszar committed
215
216
217
  // Experimental code: return fixed value normalized for several clips
  if (ALT_ACT_MEASURE)
    cpi->activity_avg = 100000;
218
219
}

220
#define USE_ACT_INDEX   0
221
#define OUTPUT_NORM_ACT_STATS   0
222
223

#if USE_ACT_INDEX
224
// Calculate an activity index for each mb
225
226
static void calc_activity_index(VP9_COMP *cpi, MACROBLOCK *x) {
  VP9_COMMON *const cm = &cpi->common;
John Koleszar's avatar
John Koleszar committed
227
  int mb_row, mb_col;
228

John Koleszar's avatar
John Koleszar committed
229
230
231
  int64_t act;
  int64_t a;
  int64_t b;
232
233

#if OUTPUT_NORM_ACT_STATS
John Koleszar's avatar
John Koleszar committed
234
235
  FILE *f = fopen("norm_act.stt", "a");
  fprintf(f, "\n%12d\n", cpi->activity_avg);
236
237
#endif

John Koleszar's avatar
John Koleszar committed
238
239
  // Reset pointers to start of activity map
  x->mb_activity_ptr = cpi->mb_activity_map;
240

John Koleszar's avatar
John Koleszar committed
241
242
243
244
245
246
  // Calculate normalized mb activity number.
  for (mb_row = 0; mb_row < cm->mb_rows; mb_row++) {
    // for each macroblock col in image
    for (mb_col = 0; mb_col < cm->mb_cols; mb_col++) {
      // Read activity from the map
      act = *(x->mb_activity_ptr);
247

John Koleszar's avatar
John Koleszar committed
248
249
250
      // Calculate a normalized activity number
      a = act + 4 * cpi->activity_avg;
      b = 4 * act + cpi->activity_avg;
251

John Koleszar's avatar
John Koleszar committed
252
      if (b >= a)
Jim Bankoski's avatar
Jim Bankoski committed
253
      *(x->activity_ptr) = (int)((b + (a >> 1)) / a) - 1;
John Koleszar's avatar
John Koleszar committed
254
      else
Jim Bankoski's avatar
Jim Bankoski committed
255
      *(x->activity_ptr) = 1 - (int)((a + (b >> 1)) / b);
256
257

#if OUTPUT_NORM_ACT_STATS
John Koleszar's avatar
John Koleszar committed
258
      fprintf(f, " %6d", *(x->mb_activity_ptr));
259
#endif
John Koleszar's avatar
John Koleszar committed
260
261
262
      // Increment activity map pointers
      x->mb_activity_ptr++;
    }
263
264

#if OUTPUT_NORM_ACT_STATS
John Koleszar's avatar
John Koleszar committed
265
    fprintf(f, "\n");
266
#endif
John Koleszar's avatar
John Koleszar committed
267
  }
268
269

#if OUTPUT_NORM_ACT_STATS
John Koleszar's avatar
John Koleszar committed
270
  fclose(f);
271
272
#endif
}
Dmitry Kovalev's avatar
Dmitry Kovalev committed
273
#endif  // USE_ACT_INDEX
274
275
276

// Loop through all MBs. Note activity of each, average activity and
// calculate a normalized activity for each
277
static void build_activity_map(VP9_COMP *cpi) {
Jim Bankoski's avatar
Jim Bankoski committed
278
  MACROBLOCK * const x = &cpi->mb;
John Koleszar's avatar
John Koleszar committed
279
  MACROBLOCKD *xd = &x->e_mbd;
Jim Bankoski's avatar
Jim Bankoski committed
280
  VP9_COMMON * const cm = &cpi->common;
281

282
#if ALT_ACT_MEASURE
283
  YV12_BUFFER_CONFIG *new_yv12 = get_frame_new_buffer(cm);
John Koleszar's avatar
John Koleszar committed
284
285
  int recon_yoffset;
  int recon_y_stride = new_yv12->y_stride;
286
287
#endif

John Koleszar's avatar
John Koleszar committed
288
289
290
  int mb_row, mb_col;
  unsigned int mb_activity;
  int64_t activity_sum = 0;
291

292
293
  x->mb_activity_ptr = cpi->mb_activity_map;

John Koleszar's avatar
John Koleszar committed
294
295
  // for each macroblock row in image
  for (mb_row = 0; mb_row < cm->mb_rows; mb_row++) {
296
#if ALT_ACT_MEASURE
John Koleszar's avatar
John Koleszar committed
297
298
299
    // reset above block coeffs
    xd->up_available = (mb_row != 0);
    recon_yoffset = (mb_row * recon_y_stride * 16);
300
#endif
John Koleszar's avatar
John Koleszar committed
301
302
    // for each macroblock col in image
    for (mb_col = 0; mb_col < cm->mb_cols; mb_col++) {
303
#if ALT_ACT_MEASURE
304
      xd->plane[0].dst.buf = new_yv12->y_buffer + recon_yoffset;
John Koleszar's avatar
John Koleszar committed
305
306
      xd->left_available = (mb_col != 0);
      recon_yoffset += 16;
307
#endif
308

John Koleszar's avatar
John Koleszar committed
309
      // measure activity
310
      mb_activity = mb_activity_measure(x, mb_row, mb_col);
311

John Koleszar's avatar
John Koleszar committed
312
313
      // Keep frame sum
      activity_sum += mb_activity;
314

John Koleszar's avatar
John Koleszar committed
315
316
      // Store MB level activity details.
      *x->mb_activity_ptr = mb_activity;
317

John Koleszar's avatar
John Koleszar committed
318
319
      // Increment activity map pointer
      x->mb_activity_ptr++;
320

John Koleszar's avatar
John Koleszar committed
321
      // adjust to the next column of source macroblocks
John Koleszar's avatar
John Koleszar committed
322
      x->plane[0].src.buf += 16;
John Koleszar's avatar
John Koleszar committed
323
    }
324

John Koleszar's avatar
John Koleszar committed
325
    // adjust to the next row of mbs
John Koleszar's avatar
John Koleszar committed
326
    x->plane[0].src.buf += 16 * x->plane[0].src.stride - 16 * cm->mb_cols;
John Koleszar's avatar
John Koleszar committed
327
  }
328

John Koleszar's avatar
John Koleszar committed
329
330
  // Calculate an "average" MB activity
  calc_av_activity(cpi, activity_sum);
331

332
#if USE_ACT_INDEX
John Koleszar's avatar
John Koleszar committed
333
334
  // Calculate an activity index number of each mb
  calc_activity_index(cpi, x);
335
#endif
336
337
}

338
// Macroblock activity masking
339
void vp9_activity_masking(VP9_COMP *cpi, MACROBLOCK *x) {
340
#if USE_ACT_INDEX
John Koleszar's avatar
John Koleszar committed
341
342
343
  x->rdmult += *(x->mb_activity_ptr) * (x->rdmult >> 2);
  x->errorperbit = x->rdmult * 100 / (110 * x->rddiv);
  x->errorperbit += (x->errorperbit == 0);
344
#else
John Koleszar's avatar
John Koleszar committed
345
346
347
  int64_t a;
  int64_t b;
  int64_t act = *(x->mb_activity_ptr);
348

John Koleszar's avatar
John Koleszar committed
349
350
351
  // Apply the masking to the RD multiplier.
  a = act + (2 * cpi->activity_avg);
  b = (2 * act) + cpi->activity_avg;
352

Jim Bankoski's avatar
Jim Bankoski committed
353
  x->rdmult = (unsigned int) (((int64_t) x->rdmult * b + (a >> 1)) / a);
John Koleszar's avatar
John Koleszar committed
354
355
  x->errorperbit = x->rdmult * 100 / (110 * x->rddiv);
  x->errorperbit += (x->errorperbit == 0);
356
#endif
357

John Koleszar's avatar
John Koleszar committed
358
359
  // Activity based Zbin adjustment
  adjust_act_zbin(cpi, x);
360
}
John Koleszar's avatar
John Koleszar committed
361

362
363
364
365
366
367
368
369
// Select a segment for the current SB64
static void select_in_frame_q_segment(VP9_COMP *cpi,
                                      int mi_row, int mi_col,
                                      int output_enabled, int projected_rate) {
  VP9_COMMON * const cm = &cpi->common;
  int target_rate = cpi->rc.sb64_target_rate << 8;   // convert to bits << 8

  const int mi_offset = mi_row * cm->mi_cols + mi_col;
370
371
  const int bw = num_8x8_blocks_wide_lookup[BLOCK_64X64];
  const int bh = num_8x8_blocks_high_lookup[BLOCK_64X64];
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
  const int xmis = MIN(cm->mi_cols - mi_col, bw);
  const int ymis = MIN(cm->mi_rows - mi_row, bh);
  int complexity_metric = 64;
  int x, y;

  unsigned char segment;

  if (!output_enabled) {
    segment = 0;
  } else {
    // Rate depends on fraction of a SB64 in frame (xmis * ymis / bw * bh).
    // It is converted to bits * 256 units
    target_rate = (cpi->rc.sb64_target_rate * xmis * ymis * 256) / (bw * bh);

    if (projected_rate < (target_rate / 4)) {
      segment = 2;
    } else if (projected_rate < (target_rate / 2)) {
      segment = 1;
    } else {
      segment = 0;
    }

    complexity_metric =
      clamp((int)((projected_rate * 64) / target_rate), 16, 255);
  }

  // Fill in the entires in the segment map corresponding to this SB64
  for (y = 0; y < ymis; y++) {
    for (x = 0; x < xmis; x++) {
      cpi->segmentation_map[mi_offset + y * cm->mi_cols + x] = segment;
      cpi->complexity_map[mi_offset + y * cm->mi_cols + x] =
        (unsigned char)complexity_metric;
    }
  }
}

Jim Bankoski's avatar
Jim Bankoski committed
408
static void update_state(VP9_COMP *cpi, PICK_MODE_CONTEXT *ctx,
409
                         BLOCK_SIZE bsize, int output_enabled) {
Ronald S. Bultje's avatar
Ronald S. Bultje committed
410
  int i, x_idx, y;
411
412
413
  VP9_COMMON *const cm = &cpi->common;
  MACROBLOCK *const x = &cpi->mb;
  MACROBLOCKD *const xd = &x->e_mbd;
414
415
  struct macroblock_plane *const p = x->plane;
  struct macroblockd_plane *const pd = xd->plane;
John Koleszar's avatar
John Koleszar committed
416
  MODE_INFO *mi = &ctx->mic;
417
418
  MB_MODE_INFO *const mbmi = &xd->mi_8x8[0]->mbmi;
  MODE_INFO *mi_addr = xd->mi_8x8[0];
419

John Koleszar's avatar
John Koleszar committed
420
  int mb_mode_index = ctx->best_mode_index;
421
  const int mis = cm->mode_info_stride;
Jim Bankoski's avatar
Jim Bankoski committed
422
  const int mi_width = num_8x8_blocks_wide_lookup[bsize];
Jim Bankoski's avatar
Jim Bankoski committed
423
  const int mi_height = num_8x8_blocks_high_lookup[bsize];
424
  int max_plane;
Adrian Grange's avatar
Adrian Grange committed
425

426
  assert(mi->mbmi.mode < MB_MODE_COUNT);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
427
428
  assert(mi->mbmi.ref_frame[0] < MAX_REF_FRAMES);
  assert(mi->mbmi.ref_frame[1] < MAX_REF_FRAMES);
429
  assert(mi->mbmi.sb_type == bsize);
430

431
432
433
434
435
  // For in frame adaptive Q copy over the chosen segment id into the
  // mode innfo context for the chosen mode / partition.
  if ((cpi->oxcf.aq_mode == COMPLEXITY_AQ) && output_enabled)
    mi->mbmi.segment_id = xd->mi_8x8[0]->mbmi.segment_id;

436
437
  *mi_addr = *mi;

438
439
  max_plane = is_inter_block(mbmi) ? MAX_MB_PLANE : 1;
  for (i = 0; i < max_plane; ++i) {
440
    p[i].coeff = ctx->coeff_pbuf[i][1];
441
    p[i].qcoeff = ctx->qcoeff_pbuf[i][1];
442
    pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][1];
443
    p[i].eobs = ctx->eobs_pbuf[i][1];
444
445
  }

446
447
  for (i = max_plane; i < MAX_MB_PLANE; ++i) {
    p[i].coeff = ctx->coeff_pbuf[i][2];
448
    p[i].qcoeff = ctx->qcoeff_pbuf[i][2];
449
    pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][2];
450
    p[i].eobs = ctx->eobs_pbuf[i][2];
451
452
  }

John Koleszar's avatar
John Koleszar committed
453
454
  // Restore the coding context of the MB to that that was in place
  // when the mode was picked for it
455
456
  for (y = 0; y < mi_height; y++)
    for (x_idx = 0; x_idx < mi_width; x_idx++)
James Zern's avatar
James Zern committed
457
      if ((xd->mb_to_right_edge >> (3 + MI_SIZE_LOG2)) + mi_width > x_idx
458
        && (xd->mb_to_bottom_edge >> (3 + MI_SIZE_LOG2)) + mi_height > y) {
459
        xd->mi_8x8[x_idx + y * mis] = mi_addr;
460
      }
461

462
463
    if ((cpi->oxcf.aq_mode == VARIANCE_AQ) ||
        (cpi->oxcf.aq_mode == COMPLEXITY_AQ)) {
464
465
466
    vp9_mb_init_quantizer(cpi, x);
  }

467
468
  // FIXME(rbultje) I'm pretty sure this should go to the end of this block
  // (i.e. after the output_enabled)
469
470
  if (bsize < BLOCK_32X32) {
    if (bsize < BLOCK_16X16)
471
472
      ctx->tx_rd_diff[ALLOW_16X16] = ctx->tx_rd_diff[ALLOW_8X8];
    ctx->tx_rd_diff[ALLOW_32X32] = ctx->tx_rd_diff[ALLOW_16X16];
Ronald S. Bultje's avatar
Ronald S. Bultje committed
473
  }
Adrian Grange's avatar
Adrian Grange committed
474

475
  if (is_inter_block(mbmi) && mbmi->sb_type < BLOCK_8X8) {
476
477
    mbmi->mv[0].as_int = mi->bmi[3].as_mv[0].as_int;
    mbmi->mv[1].as_int = mi->bmi[3].as_mv[1].as_int;
John Koleszar's avatar
John Koleszar committed
478
479
  }

480
  x->skip = ctx->skip;
481
  vpx_memcpy(x->zcoeff_blk[mbmi->tx_size], ctx->zcoeff_blk,
482
             sizeof(uint8_t) * ctx->num_4x4_blk);
483

Ronald S. Bultje's avatar
Ronald S. Bultje committed
484
485
486
  if (!output_enabled)
    return;

487
  if (!vp9_segfeature_active(&cm->seg, mbmi->segment_id, SEG_LVL_SKIP)) {
488
    for (i = 0; i < TX_MODES; i++)
489
      cpi->rd_tx_select_diff[i] += ctx->tx_rd_diff[i];
490
491
  }

492
  if (frame_is_intra_only(cm)) {
493
#if CONFIG_INTERNAL_STATS
John Koleszar's avatar
John Koleszar committed
494
495
496
497
498
499
500
501
    static const int kf_mode_index[] = {
      THR_DC /*DC_PRED*/,
      THR_V_PRED /*V_PRED*/,
      THR_H_PRED /*H_PRED*/,
      THR_D45_PRED /*D45_PRED*/,
      THR_D135_PRED /*D135_PRED*/,
      THR_D117_PRED /*D117_PRED*/,
      THR_D153_PRED /*D153_PRED*/,
Dmitry Kovalev's avatar
Dmitry Kovalev committed
502
      THR_D207_PRED /*D207_PRED*/,
John Koleszar's avatar
John Koleszar committed
503
504
505
      THR_D63_PRED /*D63_PRED*/,
      THR_TM /*TM_PRED*/,
    };
506
    cpi->mode_chosen_counts[kf_mode_index[mi->mbmi.mode]]++;
507
#endif
John Koleszar's avatar
John Koleszar committed
508
509
510
  } else {
    // Note how often each mode chosen as best
    cpi->mode_chosen_counts[mb_mode_index]++;
511
    if (is_inter_block(mbmi)
512
        && (mbmi->sb_type < BLOCK_8X8 || mbmi->mode == NEWMV)) {
513
      int_mv best_mv[2];
Ronald S. Bultje's avatar
Ronald S. Bultje committed
514
515
      const MV_REFERENCE_FRAME rf1 = mbmi->ref_frame[0];
      const MV_REFERENCE_FRAME rf2 = mbmi->ref_frame[1];
516
517
      best_mv[0].as_int = ctx->best_ref_mv[0].as_int;
      best_mv[1].as_int = ctx->best_ref_mv[1].as_int;
Deb Mukherjee's avatar
Deb Mukherjee committed
518
      if (mbmi->mode == NEWMV) {
519
        best_mv[0].as_int = mbmi->ref_mvs[rf1][0].as_int;
Yaowu Xu's avatar
Yaowu Xu committed
520
        if (rf2 > 0)
521
          best_mv[1].as_int = mbmi->ref_mvs[rf2][0].as_int;
Deb Mukherjee's avatar
Deb Mukherjee committed
522
      }
523
524
525
      mbmi->best_mv[0].as_int = best_mv[0].as_int;
      mbmi->best_mv[1].as_int = best_mv[1].as_int;
      vp9_update_mv_count(cpi, x, best_mv);
526
    }
Jingning Han's avatar
Jingning Han committed
527

528
529
530
    if (cm->mcomp_filter_type == SWITCHABLE && is_inter_mode(mbmi->mode)) {
      const int ctx = vp9_get_pred_context_switchable_interp(xd);
      ++cm->counts.switchable_interp[ctx][mbmi->interp_filter];
531
    }
Adrian Grange's avatar
Adrian Grange committed
532

533
534
535
    cpi->rd_comp_pred_diff[SINGLE_REFERENCE] += ctx->single_pred_diff;
    cpi->rd_comp_pred_diff[COMPOUND_REFERENCE] += ctx->comp_pred_diff;
    cpi->rd_comp_pred_diff[REFERENCE_MODE_SELECT] += ctx->hybrid_pred_diff;
536

537
    for (i = 0; i < SWITCHABLE_FILTER_CONTEXTS; i++)
538
      cpi->rd_filter_diff[i] += ctx->best_filter_diff[i];
John Koleszar's avatar
John Koleszar committed
539
  }
Adrian Grange's avatar
Adrian Grange committed
540
541
}

Jim Bankoski's avatar
Jim Bankoski committed
542
void vp9_setup_src_planes(MACROBLOCK *x, const YV12_BUFFER_CONFIG *src,
543
544
545
546
547
                          int mi_row, int mi_col) {
  uint8_t *const buffers[4] = {src->y_buffer, src->u_buffer, src->v_buffer,
                               src->alpha_buffer};
  const int strides[4] = {src->y_stride, src->uv_stride, src->uv_stride,
                          src->alpha_stride};
548
549
  int i;

550
551
552
  // Set current frame pointer.
  x->e_mbd.cur_buf = src;

553
554
  for (i = 0; i < MAX_MB_PLANE; i++)
    setup_pred_plane(&x->plane[i].src, buffers[i], strides[i], mi_row, mi_col,
Jim Bankoski's avatar
Jim Bankoski committed
555
                     NULL, x->e_mbd.plane[i].subsampling_x,
556
                     x->e_mbd.plane[i].subsampling_y);
John Koleszar's avatar
John Koleszar committed
557
558
}

James Zern's avatar
James Zern committed
559
560
static void set_offsets(VP9_COMP *cpi, const TileInfo *const tile,
                        int mi_row, int mi_col, BLOCK_SIZE bsize) {
561
562
563
  MACROBLOCK *const x = &cpi->mb;
  VP9_COMMON *const cm = &cpi->common;
  MACROBLOCKD *const xd = &x->e_mbd;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
564
565
  MB_MODE_INFO *mbmi;
  const int dst_fb_idx = cm->new_fb_idx;
566
  const int idx_str = xd->mode_info_stride * mi_row + mi_col;
Jim Bankoski's avatar
Jim Bankoski committed
567
568
  const int mi_width = num_8x8_blocks_wide_lookup[bsize];
  const int mi_height = num_8x8_blocks_high_lookup[bsize];
Jingning Han's avatar
Jingning Han committed
569
570
  const int mb_row = mi_row >> 1;
  const int mb_col = mi_col >> 1;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
571
  const int idx_map = mb_row * cm->mb_cols + mb_col;
572
  const struct segmentation *const seg = &cm->seg;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
573

574
  set_skip_context(xd, cpi->above_context, cpi->left_context, mi_row, mi_col);
575

Ronald S. Bultje's avatar
Ronald S. Bultje committed
576
577
578
579
  // Activity map pointer
  x->mb_activity_ptr = &cpi->mb_activity_map[idx_map];
  x->active_ptr = cpi->active_map + idx_map;

580
581
582
  xd->mi_8x8 = cm->mi_grid_visible + idx_str;
  xd->prev_mi_8x8 = cm->prev_mi_grid_visible + idx_str;

583
584
  // Special case: if prev_mi is NULL, the previous mode info context
  // cannot be used.
585
586
  xd->last_mi = cm->prev_mi ? xd->prev_mi_8x8[0] : NULL;

587
  xd->mi_8x8[0] = cm->mi + idx_str;
588

589
  mbmi = &xd->mi_8x8[0]->mbmi;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
590
591

  // Set up destination pointers
592
  setup_dst_planes(xd, &cm->yv12_fb[dst_fb_idx], mi_row, mi_col);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
593

Yaowu Xu's avatar
Yaowu Xu committed
594
595
  // Set up limit values for MV components
  // mv beyond the range do not produce new/different prediction block
596
597
  x->mv_row_min = -(((mi_row + mi_height) * MI_SIZE) + VP9_INTERP_EXTEND);
  x->mv_col_min = -(((mi_col + mi_width) * MI_SIZE) + VP9_INTERP_EXTEND);
Yaowu Xu's avatar
Yaowu Xu committed
598
599
  x->mv_row_max = (cm->mi_rows - mi_row) * MI_SIZE + VP9_INTERP_EXTEND;
  x->mv_col_max = (cm->mi_cols - mi_col) * MI_SIZE + VP9_INTERP_EXTEND;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
600
601

  // Set up distance of MB to edge of frame in 1/8th pel units
Jim Bankoski's avatar
Jim Bankoski committed
602
  assert(!(mi_col & (mi_width - 1)) && !(mi_row & (mi_height - 1)));
James Zern's avatar
James Zern committed
603
604
  set_mi_row_col(xd, tile, mi_row, mi_height, mi_col, mi_width,
                 cm->mi_rows, cm->mi_cols);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
605
606

  /* set up source buffers */
607
  vp9_setup_src_planes(x, cpi->Source, mi_row, mi_col);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
608
609
610
611
612
613

  /* R/D setup */
  x->rddiv = cpi->RDDIV;
  x->rdmult = cpi->RDMULT;

  /* segment ID */
614
  if (seg->enabled) {
615
    if (cpi->oxcf.aq_mode != VARIANCE_AQ) {
616
617
618
619
      uint8_t *map = seg->update_map ? cpi->segmentation_map
          : cm->last_frame_seg_map;
      mbmi->segment_id = vp9_get_segment_id(cm, map, bsize, mi_row, mi_col);
    }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
620
621
    vp9_mb_init_quantizer(cpi, x);

622
623
624
    if (seg->enabled && cpi->seg0_cnt > 0
        && !vp9_segfeature_active(seg, 0, SEG_LVL_REF_FRAME)
        && vp9_segfeature_active(seg, 1, SEG_LVL_REF_FRAME)) {
Ronald S. Bultje's avatar
Ronald S. Bultje committed
625
626
627
628
      cpi->seg0_progress = (cpi->seg0_idx << 16) / cpi->seg0_cnt;
    } else {
      const int y = mb_row & ~3;
      const int x = mb_col & ~3;
Jim Bankoski's avatar
Jim Bankoski committed
629
      const int p16 = ((mb_row & 1) << 1) + (mb_col & 1);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
630
      const int p32 = ((mb_row & 2) << 2) + ((mb_col & 2) << 1);
James Zern's avatar
James Zern committed
631
632
      const int tile_progress = tile->mi_col_start * cm->mb_rows >> 1;
      const int mb_cols = (tile->mi_col_end - tile->mi_col_start) >> 1;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
633

Jim Bankoski's avatar
Jim Bankoski committed
634
635
      cpi->seg0_progress = ((y * mb_cols + x * 4 + p32 + p16 + tile_progress)
          << 16) / cm->MBs;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
636
    }
637
638

    x->encode_breakout = cpi->segment_encode_breakout[mbmi->segment_id];
Ronald S. Bultje's avatar
Ronald S. Bultje committed
639
640
  } else {
    mbmi->segment_id = 0;
641
    x->encode_breakout = cpi->oxcf.encode_breakout;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
642
643
644
  }
}

James Zern's avatar
James Zern committed
645
646
static void pick_sb_modes(VP9_COMP *cpi, const TileInfo *const tile,
                          int mi_row, int mi_col,
647
                          int *totalrate, int64_t *totaldist,
648
                          BLOCK_SIZE bsize, PICK_MODE_CONTEXT *ctx,
649
                          int64_t best_rd) {
650
651
652
  VP9_COMMON *const cm = &cpi->common;
  MACROBLOCK *const x = &cpi->mb;
  MACROBLOCKD *const xd = &x->e_mbd;
653
654
655
  struct macroblock_plane *const p = x->plane;
  struct macroblockd_plane *const pd = xd->plane;
  int i;
656
  int orig_rdmult = x->rdmult;
657
658
659
660
  double rdmult_ratio;

  vp9_clear_system_state();  // __asm emms;
  rdmult_ratio = 1.0;  // avoid uninitialized warnings
Ronald S. Bultje's avatar
Ronald S. Bultje committed
661

662
  // Use the lower precision, but faster, 32x32 fdct for mode selection.
663
  x->use_lp32x32fdct = 1;
664

665
  if (bsize < BLOCK_8X8) {
666
667
    // When ab_index = 0 all sub-blocks are handled, so for ab_index != 0
    // there is nothing to be done.
668
    if (x->ab_index != 0) {
669
670
      *totalrate = 0;
      *totaldist = 0;
671
      return;
672
    }
673
  }
674

James Zern's avatar
James Zern committed
675
  set_offsets(cpi, tile, mi_row, mi_col, bsize);
676
  xd->mi_8x8[0]->mbmi.sb_type = bsize;
677

678
  for (i = 0; i < MAX_MB_PLANE; ++i) {
679
    p[i].coeff = ctx->coeff_pbuf[i][0];
680
    p[i].qcoeff = ctx->qcoeff_pbuf[i][0];
681
    pd[i].dqcoeff = ctx->dqcoeff_pbuf[i][0];
682
    p[i].eobs = ctx->eobs_pbuf[i][0];
683
  }
684
  ctx->is_coded = 0;
685
  x->skip_recode = 0;
686

687
  // Set to zero to make sure we do not use the previous encoded frame stats
688
  xd->mi_8x8[0]->mbmi.skip_coeff = 0;
689

690
  x->source_variance = get_sby_perpixel_variance(cpi, x, bsize);
691

692
  if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
693
694
695
696
697
698
699
    int energy;
    if (bsize <= BLOCK_16X16) {
      energy = x->mb_energy;
    } else {
      energy = vp9_block_energy(cpi, x, bsize);
    }

700
    xd->mi_8x8[0]->mbmi.segment_id = vp9_vaq_segment_id(energy);
701
702
703
704
    rdmult_ratio = vp9_vaq_rdmult_ratio(energy);
    vp9_mb_init_quantizer(cpi, x);
  }

Ronald S. Bultje's avatar
Ronald S. Bultje committed
705
  if (cpi->oxcf.tuning == VP8_TUNE_SSIM)
706
    vp9_activity_masking(cpi, x);
Ronald S. Bultje's avatar
Ronald S. Bultje committed
707

708
  if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
709
710
    vp9_clear_system_state();  // __asm emms;
    x->rdmult = round(x->rdmult * rdmult_ratio);
711
712
713
714
715
716
717
718
  } else if (cpi->oxcf.aq_mode == COMPLEXITY_AQ) {
    const int mi_offset = mi_row * cm->mi_cols + mi_col;
    unsigned char complexity = cpi->complexity_map[mi_offset];
    const int is_edge = (mi_row == 0) || (mi_row == (cm->mi_rows - 1)) ||
                        (mi_col == 0) || (mi_col == (cm->mi_cols - 1));

    if (!is_edge && (complexity > 128))
      x->rdmult = x->rdmult  + ((x->rdmult * (complexity - 128)) / 256);
719
  }
720

721
722
  // Find best coding mode & reconstruct the MB so it is available
  // as a predictor for MBs that follow in the SB
723
  if (frame_is_intra_only(cm)) {
724
725
    vp9_rd_pick_intra_mode_sb(cpi, x, totalrate, totaldist, bsize, ctx,
                              best_rd);
726
727
  } else {
    if (bsize >= BLOCK_8X8)
James Zern's avatar
James Zern committed
728
729
      vp9_rd_pick_inter_mode_sb(cpi, x, tile, mi_row, mi_col,
                                totalrate, totaldist, bsize, ctx, best_rd);
730
    else
James Zern's avatar
James Zern committed
731
      vp9_rd_pick_inter_mode_sub8x8(cpi, x, tile, mi_row, mi_col, totalrate,
732
733
                                    totaldist, bsize, ctx, best_rd);
  }
734

735
  if (cpi->oxcf.aq_mode == VARIANCE_AQ) {
736
737
738
739
740
741
    x->rdmult = orig_rdmult;
    if (*totalrate != INT_MAX) {
      vp9_clear_system_state();  // __asm emms;
      *totalrate = round(*totalrate * rdmult_ratio);
    }
  }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
742
}
Adrian Grange's avatar
Adrian Grange committed
743

744
745
746
747
static void update_stats(VP9_COMP *cpi) {
  VP9_COMMON *const cm = &cpi->common;
  MACROBLOCK *const x = &cpi->mb;
  MACROBLOCKD *const xd = &x->e_mbd;
748
  MODE_INFO *mi = xd->mi_8x8[0];
749
  MB_MODE_INFO *const mbmi = &mi->mbmi;
Adrian Grange's avatar
Adrian Grange committed
750

751
  if (!frame_is_intra_only(cm)) {
752
    const int seg_ref_active = vp9_segfeature_active(&cm->seg, mbmi->segment_id,
753
                                                     SEG_LVL_REF_FRAME);
754
755

    if (!seg_ref_active)
756
      cm->counts.intra_inter[vp9_get_intra_inter_context(xd)]
Dmitry Kovalev's avatar
Dmitry Kovalev committed
757
                            [is_inter_block(mbmi)]++;
Adrian Grange's avatar
Adrian Grange committed
758

759
760
761
    // If the segment reference feature is enabled we have only a single
    // reference frame allowed for the segment so exclude it from
    // the reference frame counts used to work out probabilities.
Dmitry Kovalev's avatar
Dmitry Kovalev committed
762
    if (is_inter_block(mbmi) && !seg_ref_active) {
763
      if (cm->reference_mode == REFERENCE_MODE_SELECT)
764
        cm->counts.comp_inter[vp9_get_reference_mode_context(cm, xd)]
Dmitry Kovalev's avatar
Dmitry Kovalev committed
765
                             [has_second_ref(mbmi)]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
766

Dmitry Kovalev's avatar
Dmitry Kovalev committed
767
      if (has_second_ref(mbmi)) {
768
        cm->counts.comp_ref[vp9_get_pred_context_comp_ref_p(cm, xd)]
Dmitry Kovalev's avatar
Dmitry Kovalev committed
769
                           [mbmi->ref_frame[0] == GOLDEN_FRAME]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
770
      } else {
771
        cm->counts.single_ref[vp9_get_pred_context_single_ref_p1(xd)][0]
Dmitry Kovalev's avatar
Dmitry Kovalev committed
772
                             [mbmi->ref_frame[0] != LAST_FRAME]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
773
        if (mbmi->ref_frame[0] != LAST_FRAME)
774
          cm->counts.single_ref[vp9_get_pred_context_single_ref_p2(xd)][1]
Dmitry Kovalev's avatar
Dmitry Kovalev committed
775
                               [mbmi->ref_frame[0] != GOLDEN_FRAME]++;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
776
      }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
777
    }
Ronald S. Bultje's avatar
Ronald S. Bultje committed
778
779
  }
}
John Koleszar's avatar
John Koleszar committed
780

781
static BLOCK_SIZE *get_sb_partitioning(MACROBLOCK *x, BLOCK_SIZE bsize) {
782
  switch (bsize) {
783
    case BLOCK_64X64:
784
      return &x->sb64_partitioning;
785
    case BLOCK_32X32:
786
      return &x->sb_partitioning[x->sb_index];
787
    case BLOCK_16X16:
788
      return &x->mb_partitioning[x->sb_index][x->mb_index];
789
    case BLOCK_8X8:
790
      return &x->b_partitioning[x->sb_index][x->mb_index][x->b_index];
791
792
    default:
      assert(0);
793
      return NULL;
794
795
796
797
798
799
  }
}

static void restore_context(VP9_COMP *cpi, int mi_row, int mi_col,
                            ENTROPY_CONTEXT a[16 * MAX_MB_PLANE],
                            ENTROPY_CONTEXT l[16 * MAX_MB_PLANE],
Jim Bankoski's avatar
Jim Bankoski committed
800
                            PARTITION_CONTEXT sa[8], PARTITION_CONTEXT sl[8],
801
                            BLOCK_SIZE bsize) {
Jim Bankoski's avatar
Jim Bankoski committed
802
803
  MACROBLOCK *const x = &cpi->mb;
  MACROBLOCKD *const xd = &x->e_mbd;
804
  int p;
Jim Bankoski's avatar
Jim Bankoski committed
805
806
  const int num_4x4_blocks_wide = num_4x4_blocks_wide_lookup[bsize];
  const int num_4x4_blocks_high = num_4x4_blocks_high_lookup[bsize];
Jim Bankoski's avatar
Jim Bankoski committed
807
808
  int mi_width = num_8x8_blocks_wide_lookup[bsize];
  int mi_height = num_8x8_blocks_high_lookup[bsize];
809
  for (p = 0; p < MAX_MB_PLANE; p++) {
Jim Bankoski's avatar
Jim Bankoski committed
810
    vpx_memcpy(
811
        cpi->above_context[p] + ((mi_col * 2) >> xd->plane[p].subsampling_x),
Jim Bankoski's avatar
Jim Bankoski committed
812
813
814
        a + num_4x4_blocks_wide * p,
        (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_wide) >>
        xd->plane[p].subsampling_x);
Jim Bankoski's avatar
Jim Bankoski committed
815
    vpx_memcpy(
816
        cpi->left_context[p]
Jim Bankoski's avatar
Jim Bankoski committed
817
818
819
820
821
            + ((mi_row & MI_MASK) * 2 >> xd->plane[p].subsampling_y),
        l + num_4x4_blocks_high * p,
        (sizeof(ENTROPY_CONTEXT) * num_4x4_blocks_high) >>
        xd->plane[p].subsampling_y);
  }
822
823
824
825
  vpx_memcpy(cpi->above_seg_context + mi_col, sa,
             sizeof(*cpi->above_seg_context) * mi_width);
  vpx_memcpy(cpi->left_seg_context + (mi_row & MI_MASK), sl,
             sizeof(cpi->left_seg_context[0]) * mi_height);
826
}
Jim Bankoski's avatar
Jim Bankoski committed
827
static void save_context(VP9_COMP<