vp9_encoder.c 93.8 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
 */

Jim Bankoski's avatar
Jim Bankoski committed
11 12 13 14 15 16
#include <math.h>
#include <stdio.h>
#include <limits.h>

#include "./vpx_config.h"
#include "./vpx_scale_rtcd.h"
17 18
#include "vpx/internal/vpx_psnr.h"
#include "vpx_ports/vpx_timer.h"
John Koleszar's avatar
John Koleszar committed
19

Jim Bankoski's avatar
Jim Bankoski committed
20
#include "vp9/common/vp9_alloccommon.h"
21
#include "vp9/common/vp9_filter.h"
22
#include "vp9/common/vp9_idct.h"
Jim Bankoski's avatar
Jim Bankoski committed
23 24 25
#if CONFIG_VP9_POSTPROC
#include "vp9/common/vp9_postproc.h"
#endif
26
#include "vp9/common/vp9_reconinter.h"
27
#include "vp9/common/vp9_systemdependent.h"
Jim Bankoski's avatar
Jim Bankoski committed
28
#include "vp9/common/vp9_tile_common.h"
29

30
#include "vp9/encoder/vp9_aq_complexity.h"
Marco Paniconi's avatar
Marco Paniconi committed
31 32
#include "vp9/encoder/vp9_aq_cyclicrefresh.h"
#include "vp9/encoder/vp9_aq_variance.h"
33
#include "vp9/encoder/vp9_bitstream.h"
34
#include "vp9/encoder/vp9_context_tree.h"
35
#include "vp9/encoder/vp9_encodeframe.h"
36
#include "vp9/encoder/vp9_encodemv.h"
37
#include "vp9/encoder/vp9_firstpass.h"
Jim Bankoski's avatar
Jim Bankoski committed
38
#include "vp9/encoder/vp9_mbgraph.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
39
#include "vp9/encoder/vp9_encoder.h"
Jim Bankoski's avatar
Jim Bankoski committed
40
#include "vp9/encoder/vp9_picklpf.h"
41
#include "vp9/encoder/vp9_ratectrl.h"
42
#include "vp9/encoder/vp9_rd.h"
Jim Bankoski's avatar
Jim Bankoski committed
43
#include "vp9/encoder/vp9_segmentation.h"
Yaowu Xu's avatar
Yaowu Xu committed
44
#include "vp9/encoder/vp9_speed_features.h"
Dmitry Kovalev's avatar
Dmitry Kovalev committed
45 46 47
#if CONFIG_INTERNAL_STATS
#include "vp9/encoder/vp9_ssim.h"
#endif
48
#include "vp9/encoder/vp9_temporal_filter.h"
49
#include "vp9/encoder/vp9_resize.h"
50
#include "vp9/encoder/vp9_svc_layercontext.h"
Paul Wilkins's avatar
Paul Wilkins committed
51

52
void vp9_coef_tree_initialize();
53

54 55
#define SHARP_FILTER_QTHRESH 0          /* Q threshold for 8-tap sharp filter */

Jim Bankoski's avatar
Jim Bankoski committed
56 57 58 59 60 61
#define ALTREF_HIGH_PRECISION_MV 1      // Whether to use high precision mv
                                         //  for altref computation.
#define HIGH_PRECISION_MV_QTHRESH 200   // Q threshold for high precision
                                         // mv. Choose a very high value for
                                         // now so that HIGH_PRECISION is always
                                         // chosen.
62

John Koleszar's avatar
John Koleszar committed
63
// #define OUTPUT_YUV_REC
John Koleszar's avatar
John Koleszar committed
64

65
#ifdef OUTPUT_YUV_DENOISED
66
FILE *yuv_denoised_file = NULL;
67
#endif
68 69 70
#ifdef OUTPUT_YUV_REC
FILE *yuv_rec_file;
#endif
John Koleszar's avatar
John Koleszar committed
71 72 73

#if 0
FILE *framepsnr;
Yaowu Xu's avatar
Yaowu Xu committed
74
FILE *kf_list;
John Koleszar's avatar
John Koleszar committed
75 76 77
FILE *keyfile;
#endif

78
static INLINE void Scale2Ratio(VPX_SCALING mode, int *hr, int *hs) {
79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103
  switch (mode) {
    case NORMAL:
      *hr = 1;
      *hs = 1;
      break;
    case FOURFIVE:
      *hr = 4;
      *hs = 5;
      break;
    case THREEFIVE:
      *hr = 3;
      *hs = 5;
    break;
    case ONETWO:
      *hr = 1;
      *hs = 2;
    break;
    default:
      *hr = 1;
      *hs = 1;
       assert(0);
      break;
  }
}

104
void vp9_set_high_precision_mv(VP9_COMP *cpi, int allow_high_precision_mv) {
105
  MACROBLOCK *const mb = &cpi->mb;
Deb Mukherjee's avatar
Deb Mukherjee committed
106
  cpi->common.allow_high_precision_mv = allow_high_precision_mv;
107
  if (cpi->common.allow_high_precision_mv) {
108 109 110 111 112 113 114
    mb->mvcost = mb->nmvcost_hp;
    mb->mvsadcost = mb->nmvsadcost_hp;
  } else {
    mb->mvcost = mb->nmvcost;
    mb->mvsadcost = mb->nmvsadcost;
  }
}
Paul Wilkins's avatar
Paul Wilkins committed
115

116 117 118 119 120 121 122
static void setup_frame(VP9_COMP *cpi) {
  VP9_COMMON *const cm = &cpi->common;
  // Set up entropy context depending on frame type. The decoder mandates
  // the use of the default context, index 0, for keyframes and inter
  // frames where the error_resilient_mode or intra_only flag is set. For
  // other inter-frames the encoder currently uses only two contexts;
  // context 1 for ALTREF frames and context 0 for the others.
123 124 125 126 127 128 129
  if (frame_is_intra_only(cm) || cm->error_resilient_mode) {
    vp9_setup_past_independence(cm);
  } else {
    if (!cpi->use_svc)
      cm->frame_context_idx = cpi->refresh_alt_ref_frame;
  }

130
  if (cm->frame_type == KEY_FRAME) {
131
    if (!is_spatial_svc(cpi))
132
      cpi->refresh_golden_frame = 1;
133
    cpi->refresh_alt_ref_frame = 1;
134
  } else {
135
    cm->fc = cm->frame_contexts[cm->frame_context_idx];
136 137 138
  }
}

139
void vp9_initialize_enc() {
John Koleszar's avatar
John Koleszar committed
140 141 142
  static int init_done = 0;

  if (!init_done) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
143
    vp9_init_neighbors();
144
    vp9_coef_tree_initialize();
145 146
    vp9_tokenize_initialize();
    vp9_init_me_luts();
147
    vp9_rc_init_minq_luts();
148
    vp9_entropy_mv_init();
149
    vp9_entropy_mode_init();
150
    vp9_temporal_filter_init();
John Koleszar's avatar
John Koleszar committed
151 152
    init_done = 1;
  }
John Koleszar's avatar
John Koleszar committed
153 154
}

155
static void dealloc_compressor_data(VP9_COMP *cpi) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
156
  VP9_COMMON *const cm = &cpi->common;
157
  int i;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
158

John Koleszar's avatar
John Koleszar committed
159 160
  // Delete sementation map
  vpx_free(cpi->segmentation_map);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
161 162 163
  cpi->segmentation_map = NULL;
  vpx_free(cm->last_frame_seg_map);
  cm->last_frame_seg_map = NULL;
John Koleszar's avatar
John Koleszar committed
164
  vpx_free(cpi->coding_context.last_frame_seg_map_copy);
Dmitry Kovalev's avatar
Dmitry Kovalev committed
165
  cpi->coding_context.last_frame_seg_map_copy = NULL;
John Koleszar's avatar
John Koleszar committed
166

167
  vpx_free(cpi->complexity_map);
168 169 170 171 172
  cpi->complexity_map = NULL;

  vp9_cyclic_refresh_free(cpi->cyclic_refresh);
  cpi->cyclic_refresh = NULL;

Adrian Grange's avatar
Adrian Grange committed
173
  vp9_free_ref_frame_buffers(cm);
174
  vp9_free_context_buffers(cm);
John Koleszar's avatar
John Koleszar committed
175

176 177
  vp9_free_frame_buffer(&cpi->last_frame_uf);
  vp9_free_frame_buffer(&cpi->scaled_source);
178
  vp9_free_frame_buffer(&cpi->scaled_last_source);
179
  vp9_free_frame_buffer(&cpi->alt_ref_buffer);
180
  vp9_lookahead_destroy(cpi->lookahead);
John Koleszar's avatar
John Koleszar committed
181

John Koleszar's avatar
John Koleszar committed
182 183
  vpx_free(cpi->tok);
  cpi->tok = 0;
John Koleszar's avatar
John Koleszar committed
184

185
  vp9_free_pc_tree(cpi);
186

187 188 189 190 191 192
  for (i = 0; i < cpi->svc.number_spatial_layers; ++i) {
    LAYER_CONTEXT *const lc = &cpi->svc.layer_context[i];
    vpx_free(lc->rc_twopass_stats_in.buf);
    lc->rc_twopass_stats_in.buf = NULL;
    lc->rc_twopass_stats_in.sz = 0;
  }
193 194 195 196 197

  if (cpi->source_diff_var != NULL) {
    vpx_free(cpi->source_diff_var);
    cpi->source_diff_var = NULL;
  }
198

199 200 201 202 203
  for (i = 0; i < MAX_LAG_BUFFERS; ++i) {
    vp9_free_frame_buffer(&cpi->svc.scaled_frames[i]);
  }
  vpx_memset(&cpi->svc.scaled_frames[0], 0,
             MAX_LAG_BUFFERS * sizeof(cpi->svc.scaled_frames[0]));
John Koleszar's avatar
John Koleszar committed
204 205
}

206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250
static void save_coding_context(VP9_COMP *cpi) {
  CODING_CONTEXT *const cc = &cpi->coding_context;
  VP9_COMMON *cm = &cpi->common;

  // Stores a snapshot of key state variables which can subsequently be
  // restored with a call to vp9_restore_coding_context. These functions are
  // intended for use in a re-code loop in vp9_compress_frame where the
  // quantizer value is adjusted between loop iterations.
  vp9_copy(cc->nmvjointcost,  cpi->mb.nmvjointcost);
  vp9_copy(cc->nmvcosts,  cpi->mb.nmvcosts);
  vp9_copy(cc->nmvcosts_hp,  cpi->mb.nmvcosts_hp);

  vp9_copy(cc->segment_pred_probs, cm->seg.pred_probs);

  vpx_memcpy(cpi->coding_context.last_frame_seg_map_copy,
             cm->last_frame_seg_map, (cm->mi_rows * cm->mi_cols));

  vp9_copy(cc->last_ref_lf_deltas, cm->lf.last_ref_deltas);
  vp9_copy(cc->last_mode_lf_deltas, cm->lf.last_mode_deltas);

  cc->fc = cm->fc;
}

static void restore_coding_context(VP9_COMP *cpi) {
  CODING_CONTEXT *const cc = &cpi->coding_context;
  VP9_COMMON *cm = &cpi->common;

  // Restore key state variables to the snapshot state stored in the
  // previous call to vp9_save_coding_context.
  vp9_copy(cpi->mb.nmvjointcost, cc->nmvjointcost);
  vp9_copy(cpi->mb.nmvcosts, cc->nmvcosts);
  vp9_copy(cpi->mb.nmvcosts_hp, cc->nmvcosts_hp);

  vp9_copy(cm->seg.pred_probs, cc->segment_pred_probs);

  vpx_memcpy(cm->last_frame_seg_map,
             cpi->coding_context.last_frame_seg_map_copy,
             (cm->mi_rows * cm->mi_cols));

  vp9_copy(cm->lf.last_ref_deltas, cc->last_ref_lf_deltas);
  vp9_copy(cm->lf.last_mode_deltas, cc->last_mode_lf_deltas);

  cm->fc = cc->fc;
}

251
static void configure_static_seg_features(VP9_COMP *cpi) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
252
  VP9_COMMON *const cm = &cpi->common;
253
  const RATE_CONTROL *const rc = &cpi->rc;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
254
  struct segmentation *const seg = &cm->seg;
255

256
  int high_q = (int)(rc->avg_q > 48.0);
John Koleszar's avatar
John Koleszar committed
257
  int qi_delta;
258

John Koleszar's avatar
John Koleszar committed
259 260 261
  // Disable and clear down for KF
  if (cm->frame_type == KEY_FRAME) {
    // Clear down the global segmentation map
262
    vpx_memset(cpi->segmentation_map, 0, cm->mi_rows * cm->mi_cols);
263 264
    seg->update_map = 0;
    seg->update_data = 0;
John Koleszar's avatar
John Koleszar committed
265
    cpi->static_mb_pct = 0;
266

John Koleszar's avatar
John Koleszar committed
267
    // Disable segmentation
268
    vp9_disable_segmentation(seg);
Paul Wilkins's avatar
Paul Wilkins committed
269

John Koleszar's avatar
John Koleszar committed
270
    // Clear down the segment features.
271
    vp9_clearall_segfeatures(seg);
272 273
  } else if (cpi->refresh_alt_ref_frame) {
    // If this is an alt ref frame
John Koleszar's avatar
John Koleszar committed
274
    // Clear down the global segmentation map
275
    vpx_memset(cpi->segmentation_map, 0, cm->mi_rows * cm->mi_cols);
276 277
    seg->update_map = 0;
    seg->update_data = 0;
John Koleszar's avatar
John Koleszar committed
278
    cpi->static_mb_pct = 0;
Paul Wilkins's avatar
Paul Wilkins committed
279

John Koleszar's avatar
John Koleszar committed
280
    // Disable segmentation and individual segment features by default
281
    vp9_disable_segmentation(seg);
282
    vp9_clearall_segfeatures(seg);
Paul Wilkins's avatar
Paul Wilkins committed
283

John Koleszar's avatar
John Koleszar committed
284 285
    // Scan frames from current to arf frame.
    // This function re-enables segmentation if appropriate.
286
    vp9_update_mbgraph_stats(cpi);
Paul Wilkins's avatar
Paul Wilkins committed
287

John Koleszar's avatar
John Koleszar committed
288 289
    // If segmentation was enabled set those features needed for the
    // arf itself.
290 291 292
    if (seg->enabled) {
      seg->update_map = 1;
      seg->update_data = 1;
Paul Wilkins's avatar
Paul Wilkins committed
293

294
      qi_delta = vp9_compute_qdelta(rc, rc->avg_q, rc->avg_q * 0.875);
295
      vp9_set_segdata(seg, 1, SEG_LVL_ALT_Q, qi_delta - 2);
296
      vp9_set_segdata(seg, 1, SEG_LVL_ALT_LF, -2);
Paul Wilkins's avatar
Paul Wilkins committed
297

298 299
      vp9_enable_segfeature(seg, 1, SEG_LVL_ALT_Q);
      vp9_enable_segfeature(seg, 1, SEG_LVL_ALT_LF);
300

John Koleszar's avatar
John Koleszar committed
301
      // Where relevant assume segment data is delta data
302
      seg->abs_delta = SEGMENT_DELTADATA;
303
    }
304
  } else if (seg->enabled) {
305 306
    // All other frames if segmentation has been enabled

John Koleszar's avatar
John Koleszar committed
307
    // First normal frame in a valid gf or alt ref group
308
    if (rc->frames_since_golden == 0) {
Paul Wilkins's avatar
Paul Wilkins committed
309
      // Set up segment features for normal frames in an arf group
310
      if (rc->source_alt_ref_active) {
311 312 313
        seg->update_map = 0;
        seg->update_data = 1;
        seg->abs_delta = SEGMENT_DELTADATA;
Paul Wilkins's avatar
Paul Wilkins committed
314

315
        qi_delta = vp9_compute_qdelta(rc, rc->avg_q, rc->avg_q * 1.125);
316
        vp9_set_segdata(seg, 1, SEG_LVL_ALT_Q, qi_delta + 2);
317
        vp9_enable_segfeature(seg, 1, SEG_LVL_ALT_Q);
Paul Wilkins's avatar
Paul Wilkins committed
318

319 320
        vp9_set_segdata(seg, 1, SEG_LVL_ALT_LF, -2);
        vp9_enable_segfeature(seg, 1, SEG_LVL_ALT_LF);
Paul Wilkins's avatar
Paul Wilkins committed
321

John Koleszar's avatar
John Koleszar committed
322 323
        // Segment coding disabled for compred testing
        if (high_q || (cpi->static_mb_pct == 100)) {
324 325 326
          vp9_set_segdata(seg, 1, SEG_LVL_REF_FRAME, ALTREF_FRAME);
          vp9_enable_segfeature(seg, 1, SEG_LVL_REF_FRAME);
          vp9_enable_segfeature(seg, 1, SEG_LVL_SKIP);
John Koleszar's avatar
John Koleszar committed
327
        }
328 329 330 331
      } else {
        // Disable segmentation and clear down features if alt ref
        // is not active for this group

332
        vp9_disable_segmentation(seg);
Paul Wilkins's avatar
Paul Wilkins committed
333

334
        vpx_memset(cpi->segmentation_map, 0, cm->mi_rows * cm->mi_cols);
Paul Wilkins's avatar
Paul Wilkins committed
335

336 337
        seg->update_map = 0;
        seg->update_data = 0;
Paul Wilkins's avatar
Paul Wilkins committed
338

339
        vp9_clearall_segfeatures(seg);
John Koleszar's avatar
John Koleszar committed
340
      }
341
    } else if (rc->is_src_frame_alt_ref) {
342 343 344
      // Special case where we are coding over the top of a previous
      // alt ref frame.
      // Segment coding disabled for compred testing
John Koleszar's avatar
John Koleszar committed
345

Paul Wilkins's avatar
Paul Wilkins committed
346
      // Enable ref frame features for segment 0 as well
347 348
      vp9_enable_segfeature(seg, 0, SEG_LVL_REF_FRAME);
      vp9_enable_segfeature(seg, 1, SEG_LVL_REF_FRAME);
John Koleszar's avatar
John Koleszar committed
349

Paul Wilkins's avatar
Paul Wilkins committed
350
      // All mbs should use ALTREF_FRAME
351 352 353 354
      vp9_clear_segdata(seg, 0, SEG_LVL_REF_FRAME);
      vp9_set_segdata(seg, 0, SEG_LVL_REF_FRAME, ALTREF_FRAME);
      vp9_clear_segdata(seg, 1, SEG_LVL_REF_FRAME);
      vp9_set_segdata(seg, 1, SEG_LVL_REF_FRAME, ALTREF_FRAME);
John Koleszar's avatar
John Koleszar committed
355

Paul Wilkins's avatar
Paul Wilkins committed
356
      // Skip all MBs if high Q (0,0 mv and skip coeffs)
John Koleszar's avatar
John Koleszar committed
357
      if (high_q) {
358 359
        vp9_enable_segfeature(seg, 0, SEG_LVL_SKIP);
        vp9_enable_segfeature(seg, 1, SEG_LVL_SKIP);
John Koleszar's avatar
John Koleszar committed
360
      }
Adrian Grange's avatar
Adrian Grange committed
361
      // Enable data update
362
      seg->update_data = 1;
363 364 365
    } else {
      // All other frames.

John Koleszar's avatar
John Koleszar committed
366
      // No updates.. leave things as they are.
367 368
      seg->update_map = 0;
      seg->update_data = 0;
John Koleszar's avatar
John Koleszar committed
369 370
    }
  }
371 372
}

373
static void update_reference_segmentation_map(VP9_COMP *cpi) {
Ronald S. Bultje's avatar
Ronald S. Bultje committed
374
  VP9_COMMON *const cm = &cpi->common;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
375 376
  MODE_INFO **mi_8x8_ptr = cm->mi_grid_visible;
  uint8_t *cache_ptr = cm->last_frame_seg_map;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
377 378
  int row, col;

379
  for (row = 0; row < cm->mi_rows; row++) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
380 381
    MODE_INFO **mi_8x8 = mi_8x8_ptr;
    uint8_t *cache = cache_ptr;
382 383
    for (col = 0; col < cm->mi_cols; col++, mi_8x8++, cache++)
      cache[0] = mi_8x8[0]->mbmi.segment_id;
384
    mi_8x8_ptr += cm->mi_stride;
385
    cache_ptr += cm->mi_cols;
Ronald S. Bultje's avatar
Ronald S. Bultje committed
386 387 388
  }
}

389

390
static void set_speed_features(VP9_COMP *cpi) {
391
#if CONFIG_INTERNAL_STATS
392
  int i;
393
  for (i = 0; i < MAX_MODES; ++i)
John Koleszar's avatar
John Koleszar committed
394
    cpi->mode_chosen_counts[i] = 0;
395
#endif
John Koleszar's avatar
John Koleszar committed
396

397
  vp9_set_speed_features(cpi);
398

399
  // Set rd thresholds based on mode and speed setting
400 401
  vp9_set_rd_speed_thresholds(cpi);
  vp9_set_rd_speed_thresholds_sub8x8(cpi);
John Koleszar's avatar
John Koleszar committed
402
}
403

404
static void alloc_raw_frame_buffers(VP9_COMP *cpi) {
405
  VP9_COMMON *cm = &cpi->common;
406
  const VP9EncoderConfig *oxcf = &cpi->oxcf;
407

Dmitry Kovalev's avatar
Dmitry Kovalev committed
408
  cpi->lookahead = vp9_lookahead_init(oxcf->width, oxcf->height,
409
                                      cm->subsampling_x, cm->subsampling_y,
Dmitry Kovalev's avatar
Dmitry Kovalev committed
410
                                      oxcf->lag_in_frames);
John Koleszar's avatar
John Koleszar committed
411
  if (!cpi->lookahead)
412
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
John Koleszar's avatar
John Koleszar committed
413
                       "Failed to allocate lag buffers");
John Koleszar's avatar
John Koleszar committed
414

415
  if (vp9_realloc_frame_buffer(&cpi->alt_ref_buffer,
Dmitry Kovalev's avatar
Dmitry Kovalev committed
416
                               oxcf->width, oxcf->height,
417
                               cm->subsampling_x, cm->subsampling_y,
418
                               VP9_ENC_BORDER_IN_PIXELS, NULL, NULL, NULL))
419
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
John Koleszar's avatar
John Koleszar committed
420
                       "Failed to allocate altref buffer");
John Koleszar's avatar
John Koleszar committed
421
}
422

423 424
static void alloc_ref_frame_buffers(VP9_COMP *cpi) {
  VP9_COMMON *const cm = &cpi->common;
Adrian Grange's avatar
Adrian Grange committed
425
  if (vp9_alloc_ref_frame_buffers(cm, cm->width, cm->height))
426
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
John Koleszar's avatar
John Koleszar committed
427
                       "Failed to allocate frame buffers");
John Koleszar's avatar
John Koleszar committed
428 429
}

430
static void alloc_util_frame_buffers(VP9_COMP *cpi) {
431
  VP9_COMMON *const cm = &cpi->common;
432 433 434
  if (vp9_realloc_frame_buffer(&cpi->last_frame_uf,
                               cm->width, cm->height,
                               cm->subsampling_x, cm->subsampling_y,
435
                               VP9_ENC_BORDER_IN_PIXELS, NULL, NULL, NULL))
436
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
437
                       "Failed to allocate last frame buffer");
438

439 440 441
  if (vp9_realloc_frame_buffer(&cpi->scaled_source,
                               cm->width, cm->height,
                               cm->subsampling_x, cm->subsampling_y,
442
                               VP9_ENC_BORDER_IN_PIXELS, NULL, NULL, NULL))
443
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
444
                       "Failed to allocate scaled source buffer");
445

446 447 448 449 450
  if (vp9_realloc_frame_buffer(&cpi->scaled_last_source,
                               cm->width, cm->height,
                               cm->subsampling_x, cm->subsampling_y,
                               VP9_ENC_BORDER_IN_PIXELS, NULL, NULL, NULL))
    vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
451 452
                       "Failed to allocate scaled last source buffer");
}
453

454 455
void vp9_alloc_compressor_data(VP9_COMP *cpi) {
  VP9_COMMON *cm = &cpi->common;
456

457 458 459 460 461 462 463
  vp9_alloc_context_buffers(cm, cm->width, cm->height);

  vpx_free(cpi->tok);

  {
    unsigned int tokens = get_token_alloc(cm->mb_rows, cm->mb_cols);
    CHECK_MEM_ERROR(cm, cpi->tok, vpx_calloc(tokens, sizeof(*cpi->tok)));
464
  }
465

466 467 468 469 470 471
  vp9_setup_pc_tree(&cpi->common, cpi);
}

static void update_frame_size(VP9_COMP *cpi) {
  VP9_COMMON *const cm = &cpi->common;
  MACROBLOCKD *const xd = &cpi->mb.e_mbd;
Adrian Grange's avatar
Adrian Grange committed
472 473 474

  vp9_set_mb_mi(cm, cm->width, cm->height);
  vp9_init_context_buffers(cm);
475
  init_macroblockd(cm, xd);
476

477
  if (is_spatial_svc(cpi)) {
478 479 480 481 482 483 484
    if (vp9_realloc_frame_buffer(&cpi->alt_ref_buffer,
                                 cm->width, cm->height,
                                 cm->subsampling_x, cm->subsampling_y,
                                 VP9_ENC_BORDER_IN_PIXELS, NULL, NULL, NULL))
      vpx_internal_error(&cm->error, VPX_CODEC_MEM_ERROR,
                         "Failed to reallocate alt_ref_buffer");
  }
485 486
}

James Zern's avatar
James Zern committed
487
void vp9_new_framerate(VP9_COMP *cpi, double framerate) {
488 489
  cpi->oxcf.framerate = framerate < 0.1 ? 30 : framerate;
  vp9_rc_update_framerate(cpi);
John Koleszar's avatar
John Koleszar committed
490 491
}

492
int64_t vp9_rescale(int64_t val, int64_t num, int denom) {
John Koleszar's avatar
John Koleszar committed
493 494 495
  int64_t llnum = num;
  int64_t llden = denom;
  int64_t llval = val;
496

Jingning Han's avatar
Jingning Han committed
497
  return (llval * llnum / llden);
498 499
}

Ronald S. Bultje's avatar
Ronald S. Bultje committed
500 501
static void set_tile_limits(VP9_COMP *cpi) {
  VP9_COMMON *const cm = &cpi->common;
502

Dmitry Kovalev's avatar
Dmitry Kovalev committed
503 504
  int min_log2_tile_cols, max_log2_tile_cols;
  vp9_get_tile_n_bits(cm->mi_cols, &min_log2_tile_cols, &max_log2_tile_cols);
505

Dmitry Kovalev's avatar
Dmitry Kovalev committed
506 507 508
  cm->log2_tile_cols = clamp(cpi->oxcf.tile_columns,
                             min_log2_tile_cols, max_log2_tile_cols);
  cm->log2_tile_rows = cpi->oxcf.tile_rows;
509
}
510

511 512 513 514 515 516
static void init_buffer_indices(VP9_COMP *cpi) {
  cpi->lst_fb_idx = 0;
  cpi->gld_fb_idx = 1;
  cpi->alt_fb_idx = 2;
}

517
static void init_config(struct VP9_COMP *cpi, VP9EncoderConfig *oxcf) {
518
  VP9_COMMON *const cm = &cpi->common;
John Koleszar's avatar
John Koleszar committed
519

John Koleszar's avatar
John Koleszar committed
520
  cpi->oxcf = *oxcf;
John Koleszar's avatar
John Koleszar committed
521

522 523
  cm->profile = oxcf->profile;
  cm->bit_depth = oxcf->bit_depth;
524
  cm->color_space = UNKNOWN;
John Koleszar's avatar
John Koleszar committed
525

526 527
  cm->width = oxcf->width;
  cm->height = oxcf->height;
528
  vp9_alloc_compressor_data(cpi);
529

530 531 532 533 534
  // Spatial scalability.
  cpi->svc.number_spatial_layers = oxcf->ss_number_layers;
  // Temporal scalability.
  cpi->svc.number_temporal_layers = oxcf->ts_number_layers;

535
  if ((cpi->svc.number_temporal_layers > 1 &&
536
      cpi->oxcf.rc_mode == VPX_CBR) ||
537
      (cpi->svc.number_spatial_layers > 1 &&
Dmitry Kovalev's avatar
Dmitry Kovalev committed
538
      cpi->oxcf.mode == TWO_PASS_SECOND_BEST)) {
539
    vp9_init_layer_context(cpi);
540 541
  }

John Koleszar's avatar
John Koleszar committed
542
  // change includes all joint functionality
Dmitry Kovalev's avatar
Dmitry Kovalev committed
543
  vp9_change_config(cpi, oxcf);
John Koleszar's avatar
John Koleszar committed
544

John Koleszar's avatar
John Koleszar committed
545
  cpi->static_mb_pct = 0;
546
  cpi->ref_frame_flags = 0;
547

548
  init_buffer_indices(cpi);
549

Ronald S. Bultje's avatar
Ronald S. Bultje committed
550
  set_tile_limits(cpi);
John Koleszar's avatar
John Koleszar committed
551 552
}

553
void vp9_change_config(struct VP9_COMP *cpi, const VP9EncoderConfig *oxcf) {
554
  VP9_COMMON *const cm = &cpi->common;
555
  RATE_CONTROL *const rc = &cpi->rc;
John Koleszar's avatar
John Koleszar committed
556

557 558 559 560 561 562 563 564
  if (cm->profile != oxcf->profile)
    cm->profile = oxcf->profile;
  cm->bit_depth = oxcf->bit_depth;

  if (cm->profile <= PROFILE_1)
    assert(cm->bit_depth == BITS_8);
  else
    assert(cm->bit_depth > BITS_8);
John Koleszar's avatar
John Koleszar committed
565

John Koleszar's avatar
John Koleszar committed
566
  cpi->oxcf = *oxcf;
John Koleszar's avatar
John Koleszar committed
567

568
  rc->baseline_gf_interval = DEFAULT_GF_INTERVAL;
John Koleszar's avatar
John Koleszar committed
569

570 571
  cpi->refresh_golden_frame = 0;
  cpi->refresh_last_frame = 1;
572
  cm->refresh_frame_context = 1;
573
  cm->reset_frame_context = 0;
John Koleszar's avatar
John Koleszar committed
574

575
  vp9_reset_segment_features(&cm->seg);
576
  vp9_set_high_precision_mv(cpi, 0);
John Koleszar's avatar
John Koleszar committed
577

John Koleszar's avatar
John Koleszar committed
578 579
  {
    int i;
John Koleszar's avatar
John Koleszar committed
580

Paul Wilkins's avatar
Paul Wilkins committed
581
    for (i = 0; i < MAX_SEGMENTS; i++)
John Koleszar's avatar
John Koleszar committed
582 583
      cpi->segment_encode_breakout[i] = cpi->oxcf.encode_breakout;
  }
584
  cpi->encode_breakout = cpi->oxcf.encode_breakout;
John Koleszar's avatar
John Koleszar committed
585 586

  // local file playback mode == really big buffer
587
  if (cpi->oxcf.rc_mode == VPX_VBR) {
588 589 590
    cpi->oxcf.starting_buffer_level_ms = 60000;
    cpi->oxcf.optimal_buffer_level_ms = 60000;
    cpi->oxcf.maximum_buffer_size_ms = 240000;
John Koleszar's avatar
John Koleszar committed
591 592
  }

593 594
  rc->starting_buffer_level = vp9_rescale(cpi->oxcf.starting_buffer_level_ms,
                                          cpi->oxcf.target_bandwidth, 1000);
John Koleszar's avatar
John Koleszar committed
595 596

  // Set or reset optimal and maximum buffer levels.
597 598
  if (cpi->oxcf.optimal_buffer_level_ms == 0)
    rc->optimal_buffer_level = cpi->oxcf.target_bandwidth / 8;
John Koleszar's avatar
John Koleszar committed
599
  else
600 601
    rc->optimal_buffer_level = vp9_rescale(cpi->oxcf.optimal_buffer_level_ms,
                                           cpi->oxcf.target_bandwidth, 1000);
John Koleszar's avatar
John Koleszar committed
602

603 604
  if (cpi->oxcf.maximum_buffer_size_ms == 0)
    rc->maximum_buffer_size = cpi->oxcf.target_bandwidth / 8;
John Koleszar's avatar
John Koleszar committed
605
  else
606 607
    rc->maximum_buffer_size = vp9_rescale(cpi->oxcf.maximum_buffer_size_ms,
                                          cpi->oxcf.target_bandwidth, 1000);
608 609
  // Under a configuration change, where maximum_buffer_size may change,
  // keep buffer level clipped to the maximum allowed buffer size.
610 611
  rc->bits_off_target = MIN(rc->bits_off_target, rc->maximum_buffer_size);
  rc->buffer_level = MIN(rc->buffer_level, rc->maximum_buffer_size);
John Koleszar's avatar
John Koleszar committed
612 613

  // Set up frame rate and related parameters rate control values.
James Zern's avatar
James Zern committed
614
  vp9_new_framerate(cpi, cpi->oxcf.framerate);
John Koleszar's avatar
John Koleszar committed
615 616

  // Set absolute upper and lower quality limits
617 618
  rc->worst_quality = cpi->oxcf.worst_allowed_q;
  rc->best_quality = cpi->oxcf.best_allowed_q;
John Koleszar's avatar
John Koleszar committed
619

620
  cm->interp_filter = cpi->sf.default_interp_filter;
John Koleszar's avatar
John Koleszar committed
621

622 623
  cm->display_width = cpi->oxcf.width;
  cm->display_height = cpi->oxcf.height;
John Koleszar's avatar
John Koleszar committed
624

625 626
  if (cpi->initial_width) {
    // Increasing the size of the frame beyond the first seen frame, or some
Adrian Grange's avatar
Adrian Grange committed
627
    // otherwise signaled maximum size, is not supported.
628 629 630
    // TODO(jkoleszar): exit gracefully.
    assert(cm->width <= cpi->initial_width);
    assert(cm->height <= cpi->initial_height);
John Koleszar's avatar
John Koleszar committed
631
  }
632
  update_frame_size(cpi);
John Koleszar's avatar
John Koleszar committed
633

634
  if ((cpi->svc.number_temporal_layers > 1 &&
635
      cpi->oxcf.rc_mode == VPX_CBR) ||
636
      (cpi->svc.number_spatial_layers > 1 && cpi->oxcf.pass == 2)) {
637 638
    vp9_update_layer_context_change_config(cpi,
                                           (int)cpi->oxcf.target_bandwidth);
639 640
  }

John Koleszar's avatar
John Koleszar committed
641
  cpi->alt_ref_source = NULL;
642
  rc->is_src_frame_alt_ref = 0;
Yaowu Xu's avatar
Yaowu Xu committed
643

John Koleszar's avatar
John Koleszar committed
644
#if 0
John Koleszar's avatar
John Koleszar committed
645 646 647
  // Experimental RD Code
  cpi->frame_distortion = 0;
  cpi->last_frame_distortion = 0;
John Koleszar's avatar
John Koleszar committed
648 649
#endif

Ronald S. Bultje's avatar
Ronald S. Bultje committed
650
  set_tile_limits(cpi);
Deb Mukherjee's avatar
Deb Mukherjee committed
651 652 653

  cpi->ext_refresh_frame_flags_pending = 0;
  cpi->ext_refresh_frame_context_pending = 0;
Tim Kopp's avatar
Tim Kopp committed
654

655
#if CONFIG_VP9_TEMPORAL_DENOISING
656 657 658 659 660
  if (cpi->oxcf.noise_sensitivity > 0) {
    vp9_denoiser_alloc(&(cpi->denoiser), cm->width, cm->height,
                       cm->subsampling_x, cm->subsampling_y,
                       VP9_ENC_BORDER_IN_PIXELS);
  }
Tim Kopp's avatar
Tim Kopp committed
661
#endif
John Koleszar's avatar
John Koleszar committed
662 663
}

664
#ifndef M_LOG2_E
John Koleszar's avatar
John Koleszar committed
665
#define M_LOG2_E 0.693147180559945309417
666
#endif
John Koleszar's avatar
John Koleszar committed
667
#define log2f(x) (log (x) / (float) M_LOG2_E)
668 669 670 671 672

static void cal_nmvjointsadcost(int *mvjointsadcost) {
  mvjointsadcost[0] = 600;
  mvjointsadcost[1] = 300;
  mvjointsadcost[2] = 300;
673
  mvjointsadcost[3] = 300;
674 675 676 677 678
}

static void cal_nmvsadcosts(int *mvsadcost[2]) {
  int i = 1;

Dmitry Kovalev's avatar
Dmitry Kovalev committed
679 680
  mvsadcost[0][0] = 0;
  mvsadcost[1][0] = 0;
681 682 683

  do {
    double z = 256 * (2 * (log2f(8 * i) + .6));
Dmitry Kovalev's avatar
Dmitry Kovalev committed
684 685 686 687
    mvsadcost[0][i] = (int)z;
    mvsadcost[1][i] = (int)z;
    mvsadcost[0][-i] = (int)z;
    mvsadcost[1][-i] = (int)z;
688 689 690 691 692 693
  } while (++i <= MV_MAX);
}

static void cal_nmvsadcosts_hp(int *mvsadcost[2]) {
  int i = 1;

Dmitry Kovalev's avatar
Dmitry Kovalev committed
694 695
  mvsadcost[0][0] = 0;
  mvsadcost[1][0] = 0;
696 697 698

  do {
    double z = 256 * (2 * (log2f(8 * i) + .6));
Dmitry Kovalev's avatar
Dmitry Kovalev committed
699 700 701 702
    mvsadcost[0][i] = (int)z;
    mvsadcost[1][i] = (int)z;
    mvsadcost[0][-i] = (int)z;
    mvsadcost[1][-i] = (int)z;
703 704 705
  } while (++i <= MV_MAX);
}

706

707
VP9_COMP *vp9_create_compressor(VP9EncoderConfig *oxcf) {
708
  unsigned int i, j;
709 710
  VP9_COMP *const cpi = vpx_memalign(32, sizeof(VP9_COMP));
  VP9_COMMON *const cm = cpi != NULL ? &cpi->common : NULL;
John Koleszar's avatar
John Koleszar committed
711

Dmitry Kovalev's avatar
Dmitry Kovalev committed
712 713
  if (!cm)
    return NULL;
John Koleszar's avatar
John Koleszar committed
714

Dmitry Kovalev's avatar
Dmitry Kovalev committed
715
  vp9_zero(*cpi);
John Koleszar's avatar
John Koleszar committed
716

John Koleszar's avatar
John Koleszar committed
717
  if (setjmp(cm->error.jmp)) {
Dmitry Kovalev's avatar
Dmitry Kovalev committed
718 719
    cm->error.setjmp = 0;
    vp9_remove_compressor(cpi);
John Koleszar's avatar
John Koleszar committed
720 721 722
    return 0;
  }

723
  cm->error.setjmp = 1;
John Koleszar's avatar
John Koleszar committed
724

Yaowu Xu's avatar
Yaowu Xu committed
725
  vp9_rtcd();
John Koleszar's avatar
John Koleszar committed
726

727 728
  cpi->use_svc = 0;

Dmitry Kovalev's avatar
Dmitry Kovalev committed
729
  init_config(cpi, oxcf);
730
  vp9_rc_init(&cpi->oxcf, oxcf->pass, &cpi->rc);
731

Dmitry Kovalev's avatar
Dmitry Kovalev committed
732
  cm->current_video_frame = 0;
John Koleszar's avatar
John Koleszar committed
733 734

  cpi->gold_is_last = 0;
Dmitry Kovalev's avatar
Dmitry Kovalev committed
735 736
  cpi->alt_is_last = 0;
  cpi->gold_is_alt = 0;
John Koleszar's avatar
John Koleszar committed
737

738 739
  cpi->skippable_frame = 0;

John Koleszar's avatar
John Koleszar committed
740
  // Create the encoder segmentation map and set all entries to 0
741 742
  CHECK_MEM_ERROR(cm, cpi->segmentation_map,
                  vpx_calloc(cm->mi_rows * cm->mi_cols, 1));
John Koleszar's avatar
John Koleszar committed
743

744 745 746 747
  // Create a complexity map used for rd adjustment
  CHECK_MEM_ERROR(cm, cpi->complexity_map,
                  vpx_calloc(cm->mi_rows * cm->mi_cols, 1));

748
  // Create a map used for cyclic background refresh.
749 750
  CHECK_MEM_ERROR(cm, cpi->cyclic_refresh,
                  vp9_cyclic_refresh_alloc(cm->mi_rows, cm->mi_cols));
751

John Koleszar's avatar
John Koleszar committed
752 753
  // And a place holder structure is the coding context
  // for use if we want to save and restore it
754 755
  CHECK_MEM_ERROR(cm, cpi->coding_context.last_frame_seg_map_copy,
                  vpx_calloc(cm->mi_rows * cm->mi_cols, 1));
John Koleszar's avatar
John Koleszar committed
756 757 758

  for (i = 0; i < (sizeof(cpi->mbgraph_stats) /
                   sizeof(cpi->mbgraph_stats[0])); i++) {
759 760 761
    CHECK_MEM_ERROR(cm, cpi->mbgraph_stats[i].mb_stats,
                    vpx_calloc(cm->MBs *
                               sizeof(*cpi->mbgraph_stats[i].mb_stats), 1));
John Koleszar's avatar
John Koleszar committed
762
  }
763

764 765 766
#if CONFIG_FP_MB_STATS
  cpi->use_fp_mb_stats = 0;
  if (cpi->use_fp_mb_stats) {
767 768 769
    // a place holder used to store the first pass mb stats in the first pass
    CHECK_MEM_ERROR(cm, cpi->twopass.frame_mb_stats_buf,
                    vpx_calloc(cm->MBs * sizeof(uint8_t), 1));