1 /*
2 * Copyright (c) 2015 The WebM project authors. All Rights Reserved.
3 *
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.
9 */
10
11 #include <assert.h>
12 #include <string.h>
13 #include "vpx_dsp_rtcd.h"
14 #include "mem.h"
15
eb_vp9_quantize_dc(const tran_low_t * coeff_ptr,int n_coeffs,int skip_block,const int16_t * round_ptr,const int16_t quant,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t dequant_ptr,uint16_t * eob_ptr)16 void eb_vp9_quantize_dc(const tran_low_t *coeff_ptr, int n_coeffs, int skip_block,
17 const int16_t *round_ptr, const int16_t quant,
18 tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
19 const int16_t dequant_ptr, uint16_t *eob_ptr) {
20 const int rc = 0;
21 const int coeff = coeff_ptr[rc];
22 const int coeff_sign = (coeff >> 31);
23 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
24 int tmp, eob = -1;
25
26 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
27 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
28
29 if (!skip_block) {
30 tmp = clamp(abs_coeff + round_ptr[rc != 0], INT16_MIN, INT16_MAX);
31 tmp = (tmp * quant) >> 16;
32 qcoeff_ptr[rc] = (int16_t)((tmp ^ coeff_sign) - coeff_sign);
33 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr;
34 if (tmp) eob = 0;
35 }
36 *eob_ptr = (int16_t)eob + 1;
37 }
38
39 #if CONFIG_VP9_HIGHBITDEPTH
vpx_highbd_quantize_dc(const tran_low_t * coeff_ptr,int n_coeffs,int skip_block,const int16_t * round_ptr,const int16_t quant,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t dequant_ptr,uint16_t * eob_ptr)40 void vpx_highbd_quantize_dc(const tran_low_t *coeff_ptr, int n_coeffs,
41 int skip_block, const int16_t *round_ptr,
42 const int16_t quant, tran_low_t *qcoeff_ptr,
43 tran_low_t *dqcoeff_ptr, const int16_t dequant_ptr,
44 uint16_t *eob_ptr) {
45 int eob = -1;
46
47 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
48 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
49
50 if (!skip_block) {
51 const int coeff = coeff_ptr[0];
52 const int coeff_sign = (coeff >> 31);
53 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
54 const int64_t tmp = abs_coeff + round_ptr[0];
55 const int abs_qcoeff = (int)((tmp * quant) >> 16);
56 qcoeff_ptr[0] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
57 dqcoeff_ptr[0] = qcoeff_ptr[0] * dequant_ptr;
58 if (abs_qcoeff) eob = 0;
59 }
60 *eob_ptr = eob + 1;
61 }
62 #endif
63
eb_vp9_quantize_dc_32x32(const tran_low_t * coeff_ptr,int skip_block,const int16_t * round_ptr,const int16_t quant,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t dequant_ptr,uint16_t * eob_ptr)64 void eb_vp9_quantize_dc_32x32(const tran_low_t *coeff_ptr, int skip_block,
65 const int16_t *round_ptr, const int16_t quant,
66 tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
67 const int16_t dequant_ptr, uint16_t *eob_ptr) {
68 const int n_coeffs = 1024;
69 const int rc = 0;
70 const int coeff = coeff_ptr[rc];
71 const int coeff_sign = (coeff >> 31);
72 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
73 int tmp, eob = -1;
74
75 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
76 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
77
78 if (!skip_block) {
79 tmp = clamp(abs_coeff + ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1),
80 INT16_MIN, INT16_MAX);
81 tmp = (tmp * quant) >> 15;
82 qcoeff_ptr[rc] = (int16_t)((tmp ^ coeff_sign) - coeff_sign);
83 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr / 2;
84 if (tmp) eob = 0;
85 }
86 *eob_ptr = (int16_t)eob + 1;
87 }
88
89 #if CONFIG_VP9_HIGHBITDEPTH
vpx_highbd_quantize_dc_32x32(const tran_low_t * coeff_ptr,int skip_block,const int16_t * round_ptr,const int16_t quant,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t dequant_ptr,uint16_t * eob_ptr)90 void vpx_highbd_quantize_dc_32x32(const tran_low_t *coeff_ptr, int skip_block,
91 const int16_t *round_ptr, const int16_t quant,
92 tran_low_t *qcoeff_ptr,
93 tran_low_t *dqcoeff_ptr,
94 const int16_t dequant_ptr,
95 uint16_t *eob_ptr) {
96 const int n_coeffs = 1024;
97 int eob = -1;
98
99 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
100 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
101
102 if (!skip_block) {
103 const int coeff = coeff_ptr[0];
104 const int coeff_sign = (coeff >> 31);
105 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
106 const int64_t tmp = abs_coeff + ROUND_POWER_OF_TWO(round_ptr[0], 1);
107 const int abs_qcoeff = (int)((tmp * quant) >> 15);
108 qcoeff_ptr[0] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
109 dqcoeff_ptr[0] = qcoeff_ptr[0] * dequant_ptr / 2;
110 if (abs_qcoeff) eob = 0;
111 }
112 *eob_ptr = eob + 1;
113 }
114 #endif
115
eb_vp9_quantize_b_c(const tran_low_t * coeff_ptr,intptr_t n_coeffs,int skip_block,const int16_t * zbin_ptr,const int16_t * round_ptr,const int16_t * quant_ptr,const int16_t * quant_shift_ptr,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t * dequant_ptr,uint16_t * eob_ptr,const int16_t * scan,const int16_t * iscan)116 void eb_vp9_quantize_b_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
117 int skip_block, const int16_t *zbin_ptr,
118 const int16_t *round_ptr, const int16_t *quant_ptr,
119 const int16_t *quant_shift_ptr, tran_low_t *qcoeff_ptr,
120 tran_low_t *dqcoeff_ptr, const int16_t *dequant_ptr,
121 uint16_t *eob_ptr, const int16_t *scan,
122 const int16_t *iscan) {
123 int i, non_zero_count = (int)n_coeffs, eob = -1;
124 const int zbins[2] = { zbin_ptr[0], zbin_ptr[1] };
125 const int nzbins[2] = { zbins[0] * -1, zbins[1] * -1 };
126 (void)iscan;
127 (void)skip_block;
128 assert(!skip_block);
129
130 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
131 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
132
133 // Pre-scan pass
134 for (i = (int)n_coeffs - 1; i >= 0; i--) {
135 const int rc = scan[i];
136 const int coeff = coeff_ptr[rc];
137
138 if (coeff < zbins[rc != 0] && coeff > nzbins[rc != 0])
139 non_zero_count--;
140 else
141 break;
142 }
143
144 // Quantization pass: All coefficients with index >= zero_flag are
145 // skippable. Note: zero_flag can be zero.
146 for (i = 0; i < non_zero_count; i++) {
147 const int rc = scan[i];
148 const int coeff = coeff_ptr[rc];
149 const int coeff_sign = (coeff >> 31);
150 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
151
152 if (abs_coeff >= zbins[rc != 0]) {
153 int tmp = clamp(abs_coeff + round_ptr[rc != 0], INT16_MIN, INT16_MAX);
154 tmp = ((((tmp * quant_ptr[rc != 0]) >> 16) + tmp) *
155 quant_shift_ptr[rc != 0]) >>
156 16; // quantization
157 qcoeff_ptr[rc] = (int16_t)((tmp ^ coeff_sign) - coeff_sign);
158 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
159
160 if (tmp) eob = i;
161 }
162 }
163 *eob_ptr = (int16_t)eob + 1;
164 }
165
166 #if CONFIG_VP9_HIGHBITDEPTH
vpx_highbd_quantize_b_c(const tran_low_t * coeff_ptr,intptr_t n_coeffs,int skip_block,const int16_t * zbin_ptr,const int16_t * round_ptr,const int16_t * quant_ptr,const int16_t * quant_shift_ptr,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t * dequant_ptr,uint16_t * eob_ptr,const int16_t * scan,const int16_t * iscan)167 void vpx_highbd_quantize_b_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
168 int skip_block, const int16_t *zbin_ptr,
169 const int16_t *round_ptr, const int16_t *quant_ptr,
170 const int16_t *quant_shift_ptr,
171 tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
172 const int16_t *dequant_ptr, uint16_t *eob_ptr,
173 const int16_t *scan, const int16_t *iscan) {
174 int i, non_zero_count = (int)n_coeffs, eob = -1;
175 const int zbins[2] = { zbin_ptr[0], zbin_ptr[1] };
176 const int nzbins[2] = { zbins[0] * -1, zbins[1] * -1 };
177 (void)iscan;
178 (void)skip_block;
179 assert(!skip_block);
180
181 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
182 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
183
184 // Pre-scan pass
185 for (i = (int)n_coeffs - 1; i >= 0; i--) {
186 const int rc = scan[i];
187 const int coeff = coeff_ptr[rc];
188
189 if (coeff < zbins[rc != 0] && coeff > nzbins[rc != 0])
190 non_zero_count--;
191 else
192 break;
193 }
194
195 // Quantization pass: All coefficients with index >= zero_flag are
196 // skippable. Note: zero_flag can be zero.
197 for (i = 0; i < non_zero_count; i++) {
198 const int rc = scan[i];
199 const int coeff = coeff_ptr[rc];
200 const int coeff_sign = (coeff >> 31);
201 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
202
203 if (abs_coeff >= zbins[rc != 0]) {
204 const int64_t tmp1 = abs_coeff + round_ptr[rc != 0];
205 const int64_t tmp2 = ((tmp1 * quant_ptr[rc != 0]) >> 16) + tmp1;
206 const int abs_qcoeff = (int)((tmp2 * quant_shift_ptr[rc != 0]) >> 16);
207 qcoeff_ptr[rc] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
208 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
209 if (abs_qcoeff) eob = i;
210 }
211 }
212 *eob_ptr = eob + 1;
213 }
214 #endif
215
eb_vp9_quantize_b_32x32_c(const tran_low_t * coeff_ptr,intptr_t n_coeffs,int skip_block,const int16_t * zbin_ptr,const int16_t * round_ptr,const int16_t * quant_ptr,const int16_t * quant_shift_ptr,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t * dequant_ptr,uint16_t * eob_ptr,const int16_t * scan,const int16_t * iscan)216 void eb_vp9_quantize_b_32x32_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
217 int skip_block, const int16_t *zbin_ptr,
218 const int16_t *round_ptr, const int16_t *quant_ptr,
219 const int16_t *quant_shift_ptr,
220 tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
221 const int16_t *dequant_ptr, uint16_t *eob_ptr,
222 const int16_t *scan, const int16_t *iscan) {
223 const int zbins[2] = { ROUND_POWER_OF_TWO(zbin_ptr[0], 1),
224 ROUND_POWER_OF_TWO(zbin_ptr[1], 1) };
225 const int nzbins[2] = { zbins[0] * -1, zbins[1] * -1 };
226
227 int idx = 0;
228 int idx_arr[1024];
229 int i, eob = -1;
230 (void)iscan;
231 (void)skip_block;
232 assert(!skip_block);
233
234 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
235 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
236
237 // Pre-scan pass
238 for (i = 0; i < n_coeffs; i++) {
239 const int rc = scan[i];
240 const int coeff = coeff_ptr[rc];
241
242 // If the coefficient is out of the base ZBIN range, keep it for
243 // quantization.
244 if (coeff >= zbins[rc != 0] || coeff <= nzbins[rc != 0]) idx_arr[idx++] = i;
245 }
246
247 // Quantization pass: only process the coefficients selected in
248 // pre-scan pass. Note: idx can be zero.
249 for (i = 0; i < idx; i++) {
250 const int rc = scan[idx_arr[i]];
251 const int coeff = coeff_ptr[rc];
252 const int coeff_sign = (coeff >> 31);
253 int tmp;
254 int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
255 abs_coeff += ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1);
256 abs_coeff = clamp(abs_coeff, INT16_MIN, INT16_MAX);
257 tmp = ((((abs_coeff * quant_ptr[rc != 0]) >> 16) + abs_coeff) *
258 quant_shift_ptr[rc != 0]) >>
259 15;
260
261 qcoeff_ptr[rc] = (int16_t)((tmp ^ coeff_sign) - coeff_sign);
262 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0] / 2;
263
264 if (tmp) eob = idx_arr[i];
265 }
266 *eob_ptr = (int16_t)eob + 1;
267 }
268
269 #if CONFIG_VP9_HIGHBITDEPTH
vpx_highbd_quantize_b_32x32_c(const tran_low_t * coeff_ptr,intptr_t n_coeffs,int skip_block,const int16_t * zbin_ptr,const int16_t * round_ptr,const int16_t * quant_ptr,const int16_t * quant_shift_ptr,tran_low_t * qcoeff_ptr,tran_low_t * dqcoeff_ptr,const int16_t * dequant_ptr,uint16_t * eob_ptr,const int16_t * scan,const int16_t * iscan)270 void vpx_highbd_quantize_b_32x32_c(
271 const tran_low_t *coeff_ptr, intptr_t n_coeffs, int skip_block,
272 const int16_t *zbin_ptr, const int16_t *round_ptr, const int16_t *quant_ptr,
273 const int16_t *quant_shift_ptr, tran_low_t *qcoeff_ptr,
274 tran_low_t *dqcoeff_ptr, const int16_t *dequant_ptr, uint16_t *eob_ptr,
275 const int16_t *scan, const int16_t *iscan) {
276 const int zbins[2] = { ROUND_POWER_OF_TWO(zbin_ptr[0], 1),
277 ROUND_POWER_OF_TWO(zbin_ptr[1], 1) };
278 const int nzbins[2] = { zbins[0] * -1, zbins[1] * -1 };
279
280 int idx = 0;
281 int idx_arr[1024];
282 int i, eob = -1;
283 (void)iscan;
284 (void)skip_block;
285 assert(!skip_block);
286
287 memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
288 memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
289
290 // Pre-scan pass
291 for (i = 0; i < n_coeffs; i++) {
292 const int rc = scan[i];
293 const int coeff = coeff_ptr[rc];
294
295 // If the coefficient is out of the base ZBIN range, keep it for
296 // quantization.
297 if (coeff >= zbins[rc != 0] || coeff <= nzbins[rc != 0]) idx_arr[idx++] = i;
298 }
299
300 // Quantization pass: only process the coefficients selected in
301 // pre-scan pass. Note: idx can be zero.
302 for (i = 0; i < idx; i++) {
303 const int rc = scan[idx_arr[i]];
304 const int coeff = coeff_ptr[rc];
305 const int coeff_sign = (coeff >> 31);
306 const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
307 const int64_t tmp1 = abs_coeff + ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1);
308 const int64_t tmp2 = ((tmp1 * quant_ptr[rc != 0]) >> 16) + tmp1;
309 const int abs_qcoeff = (int)((tmp2 * quant_shift_ptr[rc != 0]) >> 15);
310 qcoeff_ptr[rc] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
311 dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0] / 2;
312 if (abs_qcoeff) eob = idx_arr[i];
313 }
314 *eob_ptr = eob + 1;
315 }
316 #endif
317