2 * Copyright (c) 2010 The WebM project authors. All Rights Reserved.
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * 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.
11 #include "vpx_mem/vpx_mem.h"
12 #include "vpx_ports/mem.h"
14 #include "vp9/common/vp9_blockd.h"
15 #include "vp9/common/vp9_common.h"
16 #include "vp9/common/vp9_entropy.h"
17 #if CONFIG_COEFFICIENT_RANGE_CHECKING
18 #include "vp9/common/vp9_idct.h"
20 #include "vp9/common/vp9_scan.h"
22 #include "vp9/decoder/vp9_detokenize.h"
24 #define EOB_CONTEXT_NODE 0
25 #define ZERO_CONTEXT_NODE 1
26 #define ONE_CONTEXT_NODE 2
27 #define LOW_VAL_CONTEXT_NODE 0
28 #define TWO_CONTEXT_NODE 1
29 #define THREE_CONTEXT_NODE 2
30 #define HIGH_LOW_CONTEXT_NODE 3
31 #define CAT_ONE_CONTEXT_NODE 4
32 #define CAT_THREEFOUR_CONTEXT_NODE 5
33 #define CAT_THREE_CONTEXT_NODE 6
34 #define CAT_FIVE_CONTEXT_NODE 7
36 #define INCREMENT_COUNT(token) \
38 if (!cm->frame_parallel_decoding_mode) \
39 ++coef_counts[band][ctx][token]; \
42 static INLINE
int read_coeff(const vp9_prob
*probs
, int n
, vp9_reader
*r
) {
44 for (i
= 0; i
< n
; ++i
)
45 val
= (val
<< 1) | vp9_read(r
, probs
[i
]);
49 static int decode_coefs(VP9_COMMON
*cm
, const MACROBLOCKD
*xd
,
50 FRAME_COUNTS
*counts
, PLANE_TYPE type
,
51 tran_low_t
*dqcoeff
, TX_SIZE tx_size
, const int16_t *dq
,
52 int ctx
, const int16_t *scan
, const int16_t *nb
,
54 const int max_eob
= 16 << (tx_size
<< 1);
55 const FRAME_CONTEXT
*const fc
= cm
->fc
;
56 const int ref
= is_inter_block(&xd
->mi
[0]->mbmi
);
58 const vp9_prob (*coef_probs
)[COEFF_CONTEXTS
][UNCONSTRAINED_NODES
] =
59 fc
->coef_probs
[tx_size
][type
][ref
];
61 unsigned int (*coef_counts
)[COEFF_CONTEXTS
][UNCONSTRAINED_NODES
+ 1] =
62 counts
->coef
[tx_size
][type
][ref
];
63 unsigned int (*eob_branch_count
)[COEFF_CONTEXTS
] =
64 counts
->eob_branch
[tx_size
][type
][ref
];
65 uint8_t token_cache
[32 * 32];
66 const uint8_t *band_translate
= get_band_translate(tx_size
);
67 const int dq_shift
= (tx_size
== TX_32X32
);
70 const uint8_t *cat1_prob
;
71 const uint8_t *cat2_prob
;
72 const uint8_t *cat3_prob
;
73 const uint8_t *cat4_prob
;
74 const uint8_t *cat5_prob
;
75 const uint8_t *cat6_prob
;
77 #if CONFIG_VP9_HIGHBITDEPTH
78 if (cm
->use_highbitdepth
) {
79 if (cm
->bit_depth
== VPX_BITS_10
) {
80 cat1_prob
= vp9_cat1_prob_high10
;
81 cat2_prob
= vp9_cat2_prob_high10
;
82 cat3_prob
= vp9_cat3_prob_high10
;
83 cat4_prob
= vp9_cat4_prob_high10
;
84 cat5_prob
= vp9_cat5_prob_high10
;
85 cat6_prob
= vp9_cat6_prob_high10
;
87 cat1_prob
= vp9_cat1_prob_high12
;
88 cat2_prob
= vp9_cat2_prob_high12
;
89 cat3_prob
= vp9_cat3_prob_high12
;
90 cat4_prob
= vp9_cat4_prob_high12
;
91 cat5_prob
= vp9_cat5_prob_high12
;
92 cat6_prob
= vp9_cat6_prob_high12
;
95 cat1_prob
= vp9_cat1_prob
;
96 cat2_prob
= vp9_cat2_prob
;
97 cat3_prob
= vp9_cat3_prob
;
98 cat4_prob
= vp9_cat4_prob
;
99 cat5_prob
= vp9_cat5_prob
;
100 cat6_prob
= vp9_cat6_prob
;
103 cat1_prob
= vp9_cat1_prob
;
104 cat2_prob
= vp9_cat2_prob
;
105 cat3_prob
= vp9_cat3_prob
;
106 cat4_prob
= vp9_cat4_prob
;
107 cat5_prob
= vp9_cat5_prob
;
108 cat6_prob
= vp9_cat6_prob
;
111 while (c
< max_eob
) {
113 band
= *band_translate
++;
114 prob
= coef_probs
[band
][ctx
];
115 if (!cm
->frame_parallel_decoding_mode
)
116 ++eob_branch_count
[band
][ctx
];
117 if (!vp9_read(r
, prob
[EOB_CONTEXT_NODE
])) {
118 INCREMENT_COUNT(EOB_MODEL_TOKEN
);
122 while (!vp9_read(r
, prob
[ZERO_CONTEXT_NODE
])) {
123 INCREMENT_COUNT(ZERO_TOKEN
);
125 token_cache
[scan
[c
]] = 0;
128 return c
; // zero tokens at the end (no eob token)
129 ctx
= get_coef_context(nb
, token_cache
, c
);
130 band
= *band_translate
++;
131 prob
= coef_probs
[band
][ctx
];
134 if (!vp9_read(r
, prob
[ONE_CONTEXT_NODE
])) {
135 INCREMENT_COUNT(ONE_TOKEN
);
139 INCREMENT_COUNT(TWO_TOKEN
);
140 token
= vp9_read_tree(r
, vp9_coef_con_tree
,
141 vp9_pareto8_full
[prob
[PIVOT_NODE
] - 1]);
148 case CATEGORY1_TOKEN
:
149 val
= CAT1_MIN_VAL
+ read_coeff(cat1_prob
, 1, r
);
151 case CATEGORY2_TOKEN
:
152 val
= CAT2_MIN_VAL
+ read_coeff(cat2_prob
, 2, r
);
154 case CATEGORY3_TOKEN
:
155 val
= CAT3_MIN_VAL
+ read_coeff(cat3_prob
, 3, r
);
157 case CATEGORY4_TOKEN
:
158 val
= CAT4_MIN_VAL
+ read_coeff(cat4_prob
, 4, r
);
160 case CATEGORY5_TOKEN
:
161 val
= CAT5_MIN_VAL
+ read_coeff(cat5_prob
, 5, r
);
163 case CATEGORY6_TOKEN
:
164 #if CONFIG_VP9_HIGHBITDEPTH
165 switch (cm
->bit_depth
) {
167 val
= CAT6_MIN_VAL
+ read_coeff(cat6_prob
, 14, r
);
170 val
= CAT6_MIN_VAL
+ read_coeff(cat6_prob
, 16, r
);
173 val
= CAT6_MIN_VAL
+ read_coeff(cat6_prob
, 18, r
);
180 val
= CAT6_MIN_VAL
+ read_coeff(cat6_prob
, 14, r
);
185 v
= (val
* dqv
) >> dq_shift
;
186 #if CONFIG_COEFFICIENT_RANGE_CHECKING
187 #if CONFIG_VP9_HIGHBITDEPTH
188 dqcoeff
[scan
[c
]] = highbd_check_range((vp9_read_bit(r
) ? -v
: v
),
191 dqcoeff
[scan
[c
]] = check_range(vp9_read_bit(r
) ? -v
: v
);
192 #endif // CONFIG_VP9_HIGHBITDEPTH
194 dqcoeff
[scan
[c
]] = vp9_read_bit(r
) ? -v
: v
;
195 #endif // CONFIG_COEFFICIENT_RANGE_CHECKING
196 token_cache
[scan
[c
]] = vp9_pt_energy_class
[token
];
198 ctx
= get_coef_context(nb
, token_cache
, c
);
205 int vp9_decode_block_tokens(VP9_COMMON
*cm
, MACROBLOCKD
*xd
,
206 FRAME_COUNTS
*counts
, int plane
, int block
,
207 BLOCK_SIZE plane_bsize
, int x
, int y
,
208 TX_SIZE tx_size
, vp9_reader
*r
,
210 struct macroblockd_plane
*const pd
= &xd
->plane
[plane
];
211 const int16_t *const dequant
= (plane
== 0) ? cm
->y_dequant
[seg_id
]
212 : cm
->uv_dequant
[seg_id
];
213 const int ctx
= get_entropy_context(tx_size
, pd
->above_context
+ x
,
214 pd
->left_context
+ y
);
215 const scan_order
*so
= get_scan(xd
, tx_size
, pd
->plane_type
, block
);
216 const int eob
= decode_coefs(cm
, xd
, counts
, pd
->plane_type
,
217 BLOCK_OFFSET(pd
->dqcoeff
, block
), tx_size
,
218 dequant
, ctx
, so
->scan
, so
->neighbors
, r
);
219 vp9_set_contexts(xd
, pd
, plane_bsize
, tx_size
, eob
> 0, x
, y
);