media/libvpx/vp9/decoder/vp9_detokenize.c

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/media/libvpx/vp9/decoder/vp9_detokenize.c	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,236 @@
     1.4 +/*
     1.5 + *  Copyright (c) 2010 The WebM project authors. All Rights Reserved.
     1.6 + *
     1.7 + *  Use of this source code is governed by a BSD-style license
     1.8 + *  that can be found in the LICENSE file in the root of the source
     1.9 + *  tree. An additional intellectual property rights grant can be found
    1.10 + *  in the file PATENTS.  All contributing project authors may
    1.11 + *  be found in the AUTHORS file in the root of the source tree.
    1.12 + */
    1.13 +
    1.14 +#include "vpx_mem/vpx_mem.h"
    1.15 +#include "vpx_ports/mem.h"
    1.16 +
    1.17 +#include "vp9/common/vp9_blockd.h"
    1.18 +#include "vp9/common/vp9_common.h"
    1.19 +#include "vp9/common/vp9_seg_common.h"
    1.20 +
    1.21 +#include "vp9/decoder/vp9_dboolhuff.h"
    1.22 +#include "vp9/decoder/vp9_detokenize.h"
    1.23 +#include "vp9/decoder/vp9_onyxd_int.h"
    1.24 +#include "vp9/decoder/vp9_treereader.h"
    1.25 +
    1.26 +#define EOB_CONTEXT_NODE            0
    1.27 +#define ZERO_CONTEXT_NODE           1
    1.28 +#define ONE_CONTEXT_NODE            2
    1.29 +#define LOW_VAL_CONTEXT_NODE        3
    1.30 +#define TWO_CONTEXT_NODE            4
    1.31 +#define THREE_CONTEXT_NODE          5
    1.32 +#define HIGH_LOW_CONTEXT_NODE       6
    1.33 +#define CAT_ONE_CONTEXT_NODE        7
    1.34 +#define CAT_THREEFOUR_CONTEXT_NODE  8
    1.35 +#define CAT_THREE_CONTEXT_NODE      9
    1.36 +#define CAT_FIVE_CONTEXT_NODE       10
    1.37 +
    1.38 +#define CAT1_MIN_VAL    5
    1.39 +#define CAT2_MIN_VAL    7
    1.40 +#define CAT3_MIN_VAL   11
    1.41 +#define CAT4_MIN_VAL   19
    1.42 +#define CAT5_MIN_VAL   35
    1.43 +#define CAT6_MIN_VAL   67
    1.44 +#define CAT1_PROB0    159
    1.45 +#define CAT2_PROB0    145
    1.46 +#define CAT2_PROB1    165
    1.47 +
    1.48 +#define CAT3_PROB0 140
    1.49 +#define CAT3_PROB1 148
    1.50 +#define CAT3_PROB2 173
    1.51 +
    1.52 +#define CAT4_PROB0 135
    1.53 +#define CAT4_PROB1 140
    1.54 +#define CAT4_PROB2 155
    1.55 +#define CAT4_PROB3 176
    1.56 +
    1.57 +#define CAT5_PROB0 130
    1.58 +#define CAT5_PROB1 134
    1.59 +#define CAT5_PROB2 141
    1.60 +#define CAT5_PROB3 157
    1.61 +#define CAT5_PROB4 180
    1.62 +
    1.63 +static const vp9_prob cat6_prob[15] = {
    1.64 +  254, 254, 254, 252, 249, 243, 230, 196, 177, 153, 140, 133, 130, 129, 0
    1.65 +};
    1.66 +
    1.67 +static const int token_to_counttoken[MAX_ENTROPY_TOKENS] = {
    1.68 +  ZERO_TOKEN, ONE_TOKEN, TWO_TOKEN, TWO_TOKEN,
    1.69 +  TWO_TOKEN, TWO_TOKEN, TWO_TOKEN, TWO_TOKEN,
    1.70 +  TWO_TOKEN, TWO_TOKEN, TWO_TOKEN, DCT_EOB_MODEL_TOKEN
    1.71 +};
    1.72 +
    1.73 +#define INCREMENT_COUNT(token)                              \
    1.74 +  do {                                                      \
    1.75 +     if (!cm->frame_parallel_decoding_mode)                 \
    1.76 +       ++coef_counts[band][pt][token_to_counttoken[token]]; \
    1.77 +  } while (0)
    1.78 +
    1.79 +
    1.80 +#define WRITE_COEF_CONTINUE(val, token)                  \
    1.81 +  {                                                      \
    1.82 +    dqcoeff_ptr[scan[c]] = (vp9_read_bit(r) ? -val : val) * \
    1.83 +                            dq[c > 0] / (1 + (tx_size == TX_32X32)); \
    1.84 +    INCREMENT_COUNT(token);                              \
    1.85 +    token_cache[scan[c]] = vp9_pt_energy_class[token];   \
    1.86 +    ++c;                                                 \
    1.87 +    continue;                                            \
    1.88 +  }
    1.89 +
    1.90 +#define ADJUST_COEF(prob, bits_count)                   \
    1.91 +  do {                                                  \
    1.92 +    val += (vp9_read(r, prob) << bits_count);           \
    1.93 +  } while (0)
    1.94 +
    1.95 +static int decode_coefs(VP9_COMMON *cm, const MACROBLOCKD *xd,
    1.96 +                        vp9_reader *r, int block_idx,
    1.97 +                        PLANE_TYPE type, int seg_eob, int16_t *dqcoeff_ptr,
    1.98 +                        TX_SIZE tx_size, const int16_t *dq, int pt,
    1.99 +                        uint8_t *token_cache) {
   1.100 +  const FRAME_CONTEXT *const fc = &cm->fc;
   1.101 +  FRAME_COUNTS *const counts = &cm->counts;
   1.102 +  const int ref = is_inter_block(&xd->mi_8x8[0]->mbmi);
   1.103 +  int band, c = 0;
   1.104 +  const vp9_prob (*coef_probs)[PREV_COEF_CONTEXTS][UNCONSTRAINED_NODES] =
   1.105 +      fc->coef_probs[tx_size][type][ref];
   1.106 +  vp9_prob coef_probs_full[COEF_BANDS][PREV_COEF_CONTEXTS][ENTROPY_NODES];
   1.107 +  uint8_t load_map[COEF_BANDS][PREV_COEF_CONTEXTS] = { { 0 } };
   1.108 +  const vp9_prob *prob;
   1.109 +  unsigned int (*coef_counts)[PREV_COEF_CONTEXTS][UNCONSTRAINED_NODES + 1] =
   1.110 +      counts->coef[tx_size][type][ref];
   1.111 +  unsigned int (*eob_branch_count)[PREV_COEF_CONTEXTS] =
   1.112 +      counts->eob_branch[tx_size][type][ref];
   1.113 +  const int16_t *scan, *nb;
   1.114 +  const uint8_t *cat6;
   1.115 +  const uint8_t *band_translate = get_band_translate(tx_size);
   1.116 +  get_scan(xd, tx_size, type, block_idx, &scan, &nb);
   1.117 +
   1.118 +  while (c < seg_eob) {
   1.119 +    int val;
   1.120 +    if (c)
   1.121 +      pt = get_coef_context(nb, token_cache, c);
   1.122 +    band = *band_translate++;
   1.123 +    prob = coef_probs[band][pt];
   1.124 +    if (!cm->frame_parallel_decoding_mode)
   1.125 +      ++eob_branch_count[band][pt];
   1.126 +    if (!vp9_read(r, prob[EOB_CONTEXT_NODE]))
   1.127 +      break;
   1.128 +    goto DECODE_ZERO;
   1.129 +
   1.130 +  SKIP_START:
   1.131 +    if (c >= seg_eob)
   1.132 +      break;
   1.133 +    if (c)
   1.134 +      pt = get_coef_context(nb, token_cache, c);
   1.135 +    band = *band_translate++;
   1.136 +    prob = coef_probs[band][pt];
   1.137 +
   1.138 +  DECODE_ZERO:
   1.139 +    if (!vp9_read(r, prob[ZERO_CONTEXT_NODE])) {
   1.140 +      INCREMENT_COUNT(ZERO_TOKEN);
   1.141 +      token_cache[scan[c]] = vp9_pt_energy_class[ZERO_TOKEN];
   1.142 +      ++c;
   1.143 +      goto SKIP_START;
   1.144 +    }
   1.145 +
   1.146 +    // ONE_CONTEXT_NODE_0_
   1.147 +    if (!vp9_read(r, prob[ONE_CONTEXT_NODE])) {
   1.148 +      WRITE_COEF_CONTINUE(1, ONE_TOKEN);
   1.149 +    }
   1.150 +    // Load full probabilities if not already loaded
   1.151 +    if (!load_map[band][pt]) {
   1.152 +      vp9_model_to_full_probs(coef_probs[band][pt],
   1.153 +                              coef_probs_full[band][pt]);
   1.154 +      load_map[band][pt] = 1;
   1.155 +    }
   1.156 +    prob = coef_probs_full[band][pt];
   1.157 +    // LOW_VAL_CONTEXT_NODE_0_
   1.158 +    if (!vp9_read(r, prob[LOW_VAL_CONTEXT_NODE])) {
   1.159 +      if (!vp9_read(r, prob[TWO_CONTEXT_NODE])) {
   1.160 +        WRITE_COEF_CONTINUE(2, TWO_TOKEN);
   1.161 +      }
   1.162 +      if (!vp9_read(r, prob[THREE_CONTEXT_NODE])) {
   1.163 +        WRITE_COEF_CONTINUE(3, THREE_TOKEN);
   1.164 +      }
   1.165 +      WRITE_COEF_CONTINUE(4, FOUR_TOKEN);
   1.166 +    }
   1.167 +    // HIGH_LOW_CONTEXT_NODE_0_
   1.168 +    if (!vp9_read(r, prob[HIGH_LOW_CONTEXT_NODE])) {
   1.169 +      if (!vp9_read(r, prob[CAT_ONE_CONTEXT_NODE])) {
   1.170 +        val = CAT1_MIN_VAL;
   1.171 +        ADJUST_COEF(CAT1_PROB0, 0);
   1.172 +        WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY1);
   1.173 +      }
   1.174 +      val = CAT2_MIN_VAL;
   1.175 +      ADJUST_COEF(CAT2_PROB1, 1);
   1.176 +      ADJUST_COEF(CAT2_PROB0, 0);
   1.177 +      WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY2);
   1.178 +    }
   1.179 +    // CAT_THREEFOUR_CONTEXT_NODE_0_
   1.180 +    if (!vp9_read(r, prob[CAT_THREEFOUR_CONTEXT_NODE])) {
   1.181 +      if (!vp9_read(r, prob[CAT_THREE_CONTEXT_NODE])) {
   1.182 +        val = CAT3_MIN_VAL;
   1.183 +        ADJUST_COEF(CAT3_PROB2, 2);
   1.184 +        ADJUST_COEF(CAT3_PROB1, 1);
   1.185 +        ADJUST_COEF(CAT3_PROB0, 0);
   1.186 +        WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY3);
   1.187 +      }
   1.188 +      val = CAT4_MIN_VAL;
   1.189 +      ADJUST_COEF(CAT4_PROB3, 3);
   1.190 +      ADJUST_COEF(CAT4_PROB2, 2);
   1.191 +      ADJUST_COEF(CAT4_PROB1, 1);
   1.192 +      ADJUST_COEF(CAT4_PROB0, 0);
   1.193 +      WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY4);
   1.194 +    }
   1.195 +    // CAT_FIVE_CONTEXT_NODE_0_:
   1.196 +    if (!vp9_read(r, prob[CAT_FIVE_CONTEXT_NODE])) {
   1.197 +      val = CAT5_MIN_VAL;
   1.198 +      ADJUST_COEF(CAT5_PROB4, 4);
   1.199 +      ADJUST_COEF(CAT5_PROB3, 3);
   1.200 +      ADJUST_COEF(CAT5_PROB2, 2);
   1.201 +      ADJUST_COEF(CAT5_PROB1, 1);
   1.202 +      ADJUST_COEF(CAT5_PROB0, 0);
   1.203 +      WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY5);
   1.204 +    }
   1.205 +    val = 0;
   1.206 +    cat6 = cat6_prob;
   1.207 +    while (*cat6)
   1.208 +      val = (val << 1) | vp9_read(r, *cat6++);
   1.209 +    val += CAT6_MIN_VAL;
   1.210 +
   1.211 +    WRITE_COEF_CONTINUE(val, DCT_VAL_CATEGORY6);
   1.212 +  }
   1.213 +
   1.214 +  if (c < seg_eob) {
   1.215 +    if (!cm->frame_parallel_decoding_mode)
   1.216 +      ++coef_counts[band][pt][DCT_EOB_MODEL_TOKEN];
   1.217 +  }
   1.218 +
   1.219 +  return c;
   1.220 +}
   1.221 +
   1.222 +int vp9_decode_block_tokens(VP9_COMMON *cm, MACROBLOCKD *xd,
   1.223 +                            int plane, int block, BLOCK_SIZE plane_bsize,
   1.224 +                            int x, int y, TX_SIZE tx_size, vp9_reader *r,
   1.225 +                            uint8_t *token_cache) {
   1.226 +  struct macroblockd_plane *const pd = &xd->plane[plane];
   1.227 +  const int seg_eob = get_tx_eob(&cm->seg, xd->mi_8x8[0]->mbmi.segment_id,
   1.228 +                                 tx_size);
   1.229 +  const int pt = get_entropy_context(tx_size, pd->above_context + x,
   1.230 +                                              pd->left_context + y);
   1.231 +  const int eob = decode_coefs(cm, xd, r, block, pd->plane_type, seg_eob,
   1.232 +                               BLOCK_OFFSET(pd->dqcoeff, block), tx_size,
   1.233 +                               pd->dequant, pt, token_cache);
   1.234 +  set_contexts(xd, pd, plane_bsize, tx_size, eob > 0, x, y);
   1.235 +  pd->eobs[block] = eob;
   1.236 +  return eob;
   1.237 +}
   1.238 +
   1.239 +

mercurial