• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright (c) 2010 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 <math.h>
12 #include "./vpx_dsp_rtcd.h"
13 #include "vpx_mem/vpx_mem.h"
14 #include "vpx_ports/mem.h"
15 
16 #include "vp9/common/vp9_quant_common.h"
17 #include "vp9/common/vp9_seg_common.h"
18 
19 #include "vp9/encoder/vp9_encoder.h"
20 #include "vp9/encoder/vp9_quantize.h"
21 #include "vp9/encoder/vp9_rd.h"
22 
vp9_quantize_fp_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)23 void vp9_quantize_fp_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
24                        int skip_block,
25                        const int16_t *zbin_ptr, const int16_t *round_ptr,
26                        const int16_t *quant_ptr, const int16_t *quant_shift_ptr,
27                        tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
28                        const int16_t *dequant_ptr,
29                        uint16_t *eob_ptr,
30                        const int16_t *scan, const int16_t *iscan) {
31   int i, eob = -1;
32   // TODO(jingning) Decide the need of these arguments after the
33   // quantization process is completed.
34   (void)zbin_ptr;
35   (void)quant_shift_ptr;
36   (void)iscan;
37 
38   memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
39   memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
40 
41   if (!skip_block) {
42     // Quantization pass: All coefficients with index >= zero_flag are
43     // skippable. Note: zero_flag can be zero.
44     for (i = 0; i < n_coeffs; i++) {
45       const int rc = scan[i];
46       const int coeff = coeff_ptr[rc];
47       const int coeff_sign = (coeff >> 31);
48       const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
49 
50       int tmp = clamp(abs_coeff + round_ptr[rc != 0], INT16_MIN, INT16_MAX);
51       tmp = (tmp * quant_ptr[rc != 0]) >> 16;
52 
53       qcoeff_ptr[rc] = (tmp ^ coeff_sign) - coeff_sign;
54       dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
55 
56       if (tmp)
57         eob = i;
58     }
59   }
60   *eob_ptr = eob + 1;
61 }
62 
63 #if CONFIG_VP9_HIGHBITDEPTH
vp9_highbd_quantize_fp_c(const tran_low_t * coeff_ptr,intptr_t count,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)64 void vp9_highbd_quantize_fp_c(const tran_low_t *coeff_ptr,
65                               intptr_t count,
66                               int skip_block,
67                               const int16_t *zbin_ptr,
68                               const int16_t *round_ptr,
69                               const int16_t *quant_ptr,
70                               const int16_t *quant_shift_ptr,
71                               tran_low_t *qcoeff_ptr,
72                               tran_low_t *dqcoeff_ptr,
73                               const int16_t *dequant_ptr,
74                               uint16_t *eob_ptr,
75                               const int16_t *scan,
76                               const int16_t *iscan) {
77   int i;
78   int eob = -1;
79   // TODO(jingning) Decide the need of these arguments after the
80   // quantization process is completed.
81   (void)zbin_ptr;
82   (void)quant_shift_ptr;
83   (void)iscan;
84 
85   memset(qcoeff_ptr, 0, count * sizeof(*qcoeff_ptr));
86   memset(dqcoeff_ptr, 0, count * sizeof(*dqcoeff_ptr));
87 
88   if (!skip_block) {
89     // Quantization pass: All coefficients with index >= zero_flag are
90     // skippable. Note: zero_flag can be zero.
91     for (i = 0; i < count; i++) {
92       const int rc = scan[i];
93       const int coeff = coeff_ptr[rc];
94       const int coeff_sign = (coeff >> 31);
95       const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
96       const int64_t tmp = abs_coeff + round_ptr[rc != 0];
97       const uint32_t abs_qcoeff = (uint32_t)((tmp * quant_ptr[rc != 0]) >> 16);
98       qcoeff_ptr[rc] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
99       dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0];
100       if (abs_qcoeff)
101         eob = i;
102     }
103   }
104   *eob_ptr = eob + 1;
105 }
106 #endif
107 
108 // TODO(jingning) Refactor this file and combine functions with similar
109 // operations.
vp9_quantize_fp_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)110 void vp9_quantize_fp_32x32_c(const tran_low_t *coeff_ptr, intptr_t n_coeffs,
111                              int skip_block,
112                              const int16_t *zbin_ptr, const int16_t *round_ptr,
113                              const int16_t *quant_ptr,
114                              const int16_t *quant_shift_ptr,
115                              tran_low_t *qcoeff_ptr, tran_low_t *dqcoeff_ptr,
116                              const int16_t *dequant_ptr,
117                              uint16_t *eob_ptr,
118                              const int16_t *scan, const int16_t *iscan) {
119   int i, eob = -1;
120   (void)zbin_ptr;
121   (void)quant_shift_ptr;
122   (void)iscan;
123 
124   memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
125   memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
126 
127   if (!skip_block) {
128     for (i = 0; i < n_coeffs; i++) {
129       const int rc = scan[i];
130       const int coeff = coeff_ptr[rc];
131       const int coeff_sign = (coeff >> 31);
132       int tmp = 0;
133       int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
134 
135       if (abs_coeff >= (dequant_ptr[rc != 0] >> 2)) {
136         abs_coeff += ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1);
137         abs_coeff = clamp(abs_coeff, INT16_MIN, INT16_MAX);
138         tmp = (abs_coeff * quant_ptr[rc != 0]) >> 15;
139         qcoeff_ptr[rc] = (tmp ^ coeff_sign) - coeff_sign;
140         dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0] / 2;
141       }
142 
143       if (tmp)
144         eob = i;
145     }
146   }
147   *eob_ptr = eob + 1;
148 }
149 
150 #if CONFIG_VP9_HIGHBITDEPTH
vp9_highbd_quantize_fp_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)151 void vp9_highbd_quantize_fp_32x32_c(const tran_low_t *coeff_ptr,
152                                     intptr_t n_coeffs, int skip_block,
153                                     const int16_t *zbin_ptr,
154                                     const int16_t *round_ptr,
155                                     const int16_t *quant_ptr,
156                                     const int16_t *quant_shift_ptr,
157                                     tran_low_t *qcoeff_ptr,
158                                     tran_low_t *dqcoeff_ptr,
159                                     const int16_t *dequant_ptr,
160                                     uint16_t *eob_ptr,
161                                     const int16_t *scan, const int16_t *iscan) {
162   int i, eob = -1;
163   (void)zbin_ptr;
164   (void)quant_shift_ptr;
165   (void)iscan;
166 
167   memset(qcoeff_ptr, 0, n_coeffs * sizeof(*qcoeff_ptr));
168   memset(dqcoeff_ptr, 0, n_coeffs * sizeof(*dqcoeff_ptr));
169 
170   if (!skip_block) {
171     for (i = 0; i < n_coeffs; i++) {
172       uint32_t abs_qcoeff = 0;
173       const int rc = scan[i];
174       const int coeff = coeff_ptr[rc];
175       const int coeff_sign = (coeff >> 31);
176       const int abs_coeff = (coeff ^ coeff_sign) - coeff_sign;
177 
178       if (abs_coeff >= (dequant_ptr[rc != 0] >> 2)) {
179         const int64_t tmp = abs_coeff
180                            + ROUND_POWER_OF_TWO(round_ptr[rc != 0], 1);
181         abs_qcoeff = (uint32_t) ((tmp * quant_ptr[rc != 0]) >> 15);
182         qcoeff_ptr[rc] = (tran_low_t)((abs_qcoeff ^ coeff_sign) - coeff_sign);
183         dqcoeff_ptr[rc] = qcoeff_ptr[rc] * dequant_ptr[rc != 0] / 2;
184       }
185 
186       if (abs_qcoeff)
187         eob = i;
188     }
189   }
190   *eob_ptr = eob + 1;
191 }
192 #endif
193 
vp9_regular_quantize_b_4x4(MACROBLOCK * x,int plane,int block,const int16_t * scan,const int16_t * iscan)194 void vp9_regular_quantize_b_4x4(MACROBLOCK *x, int plane, int block,
195                                 const int16_t *scan, const int16_t *iscan) {
196   MACROBLOCKD *const xd = &x->e_mbd;
197   struct macroblock_plane *p = &x->plane[plane];
198   struct macroblockd_plane *pd = &xd->plane[plane];
199 
200 #if CONFIG_VP9_HIGHBITDEPTH
201   if (xd->cur_buf->flags & YV12_FLAG_HIGHBITDEPTH) {
202     vpx_highbd_quantize_b(BLOCK_OFFSET(p->coeff, block),
203                           16, x->skip_block,
204                           p->zbin, p->round, p->quant, p->quant_shift,
205                           BLOCK_OFFSET(p->qcoeff, block),
206                           BLOCK_OFFSET(pd->dqcoeff, block),
207                           pd->dequant, &p->eobs[block],
208                           scan, iscan);
209     return;
210   }
211 #endif
212   vpx_quantize_b(BLOCK_OFFSET(p->coeff, block),
213                  16, x->skip_block,
214                  p->zbin, p->round, p->quant, p->quant_shift,
215                  BLOCK_OFFSET(p->qcoeff, block),
216                  BLOCK_OFFSET(pd->dqcoeff, block),
217                  pd->dequant, &p->eobs[block], scan, iscan);
218 }
219 
invert_quant(int16_t * quant,int16_t * shift,int d)220 static void invert_quant(int16_t *quant, int16_t *shift, int d) {
221   unsigned t;
222   int l;
223   t = d;
224   for (l = 0; t > 1; l++)
225     t >>= 1;
226   t = 1 + (1 << (16 + l)) / d;
227   *quant = (int16_t)(t - (1 << 16));
228   *shift = 1 << (16 - l);
229 }
230 
get_qzbin_factor(int q,vpx_bit_depth_t bit_depth)231 static int get_qzbin_factor(int q, vpx_bit_depth_t bit_depth) {
232   const int quant = vp9_dc_quant(q, 0, bit_depth);
233 #if CONFIG_VP9_HIGHBITDEPTH
234   switch (bit_depth) {
235     case VPX_BITS_8:
236       return q == 0 ? 64 : (quant < 148 ? 84 : 80);
237     case VPX_BITS_10:
238       return q == 0 ? 64 : (quant < 592 ? 84 : 80);
239     case VPX_BITS_12:
240       return q == 0 ? 64 : (quant < 2368 ? 84 : 80);
241     default:
242       assert(0 && "bit_depth should be VPX_BITS_8, VPX_BITS_10 or VPX_BITS_12");
243       return -1;
244   }
245 #else
246   (void) bit_depth;
247   return q == 0 ? 64 : (quant < 148 ? 84 : 80);
248 #endif
249 }
250 
vp9_init_quantizer(VP9_COMP * cpi)251 void vp9_init_quantizer(VP9_COMP *cpi) {
252   VP9_COMMON *const cm = &cpi->common;
253   QUANTS *const quants = &cpi->quants;
254   int i, q, quant;
255 
256   for (q = 0; q < QINDEX_RANGE; q++) {
257     const int qzbin_factor = get_qzbin_factor(q, cm->bit_depth);
258     const int qrounding_factor = q == 0 ? 64 : 48;
259 
260     for (i = 0; i < 2; ++i) {
261       int qrounding_factor_fp = i == 0 ? 48 : 42;
262       if (q == 0)
263         qrounding_factor_fp = 64;
264 
265       // y
266       quant = i == 0 ? vp9_dc_quant(q, cm->y_dc_delta_q, cm->bit_depth)
267                      : vp9_ac_quant(q, 0, cm->bit_depth);
268       invert_quant(&quants->y_quant[q][i], &quants->y_quant_shift[q][i], quant);
269       quants->y_quant_fp[q][i] = (1 << 16) / quant;
270       quants->y_round_fp[q][i] = (qrounding_factor_fp * quant) >> 7;
271       quants->y_zbin[q][i] = ROUND_POWER_OF_TWO(qzbin_factor * quant, 7);
272       quants->y_round[q][i] = (qrounding_factor * quant) >> 7;
273       cpi->y_dequant[q][i] = quant;
274 
275       // uv
276       quant = i == 0 ? vp9_dc_quant(q, cm->uv_dc_delta_q, cm->bit_depth)
277                      : vp9_ac_quant(q, cm->uv_ac_delta_q, cm->bit_depth);
278       invert_quant(&quants->uv_quant[q][i],
279                    &quants->uv_quant_shift[q][i], quant);
280       quants->uv_quant_fp[q][i] = (1 << 16) / quant;
281       quants->uv_round_fp[q][i] = (qrounding_factor_fp * quant) >> 7;
282       quants->uv_zbin[q][i] = ROUND_POWER_OF_TWO(qzbin_factor * quant, 7);
283       quants->uv_round[q][i] = (qrounding_factor * quant) >> 7;
284       cpi->uv_dequant[q][i] = quant;
285     }
286 
287     for (i = 2; i < 8; i++) {
288       quants->y_quant[q][i] = quants->y_quant[q][1];
289       quants->y_quant_fp[q][i] = quants->y_quant_fp[q][1];
290       quants->y_round_fp[q][i] = quants->y_round_fp[q][1];
291       quants->y_quant_shift[q][i] = quants->y_quant_shift[q][1];
292       quants->y_zbin[q][i] = quants->y_zbin[q][1];
293       quants->y_round[q][i] = quants->y_round[q][1];
294       cpi->y_dequant[q][i] = cpi->y_dequant[q][1];
295 
296       quants->uv_quant[q][i] = quants->uv_quant[q][1];
297       quants->uv_quant_fp[q][i] = quants->uv_quant_fp[q][1];
298       quants->uv_round_fp[q][i] = quants->uv_round_fp[q][1];
299       quants->uv_quant_shift[q][i] = quants->uv_quant_shift[q][1];
300       quants->uv_zbin[q][i] = quants->uv_zbin[q][1];
301       quants->uv_round[q][i] = quants->uv_round[q][1];
302       cpi->uv_dequant[q][i] = cpi->uv_dequant[q][1];
303     }
304   }
305 }
306 
vp9_init_plane_quantizers(VP9_COMP * cpi,MACROBLOCK * x)307 void vp9_init_plane_quantizers(VP9_COMP *cpi, MACROBLOCK *x) {
308   const VP9_COMMON *const cm = &cpi->common;
309   MACROBLOCKD *const xd = &x->e_mbd;
310   QUANTS *const quants = &cpi->quants;
311   const int segment_id = xd->mi[0]->mbmi.segment_id;
312   const int qindex = vp9_get_qindex(&cm->seg, segment_id, cm->base_qindex);
313   const int rdmult = vp9_compute_rd_mult(cpi, qindex + cm->y_dc_delta_q);
314   int i;
315 
316   // Y
317   x->plane[0].quant = quants->y_quant[qindex];
318   x->plane[0].quant_fp = quants->y_quant_fp[qindex];
319   x->plane[0].round_fp = quants->y_round_fp[qindex];
320   x->plane[0].quant_shift = quants->y_quant_shift[qindex];
321   x->plane[0].zbin = quants->y_zbin[qindex];
322   x->plane[0].round = quants->y_round[qindex];
323   xd->plane[0].dequant = cpi->y_dequant[qindex];
324 
325   x->plane[0].quant_thred[0] = x->plane[0].zbin[0] * x->plane[0].zbin[0];
326   x->plane[0].quant_thred[1] = x->plane[0].zbin[1] * x->plane[0].zbin[1];
327 
328   // UV
329   for (i = 1; i < 3; i++) {
330     x->plane[i].quant = quants->uv_quant[qindex];
331     x->plane[i].quant_fp = quants->uv_quant_fp[qindex];
332     x->plane[i].round_fp = quants->uv_round_fp[qindex];
333     x->plane[i].quant_shift = quants->uv_quant_shift[qindex];
334     x->plane[i].zbin = quants->uv_zbin[qindex];
335     x->plane[i].round = quants->uv_round[qindex];
336     xd->plane[i].dequant = cpi->uv_dequant[qindex];
337 
338     x->plane[i].quant_thred[0] = x->plane[i].zbin[0] * x->plane[i].zbin[0];
339     x->plane[i].quant_thred[1] = x->plane[i].zbin[1] * x->plane[i].zbin[1];
340   }
341 
342   x->skip_block = segfeature_active(&cm->seg, segment_id, SEG_LVL_SKIP);
343   x->q_index = qindex;
344 
345   x->errorperbit = rdmult >> 6;
346   x->errorperbit += (x->errorperbit == 0);
347 
348   vp9_initialize_me_consts(cpi, x, x->q_index);
349 }
350 
vp9_frame_init_quantizer(VP9_COMP * cpi)351 void vp9_frame_init_quantizer(VP9_COMP *cpi) {
352   vp9_init_plane_quantizers(cpi, &cpi->td.mb);
353 }
354 
vp9_set_quantizer(VP9_COMMON * cm,int q)355 void vp9_set_quantizer(VP9_COMMON *cm, int q) {
356   // quantizer has to be reinitialized with vp9_init_quantizer() if any
357   // delta_q changes.
358   cm->base_qindex = q;
359   cm->y_dc_delta_q = 0;
360   cm->uv_dc_delta_q = 0;
361   cm->uv_ac_delta_q = 0;
362 }
363 
364 // Table that converts 0-63 Q-range values passed in outside to the Qindex
365 // range used internally.
366 static const int quantizer_to_qindex[] = {
367   0,    4,   8,  12,  16,  20,  24,  28,
368   32,   36,  40,  44,  48,  52,  56,  60,
369   64,   68,  72,  76,  80,  84,  88,  92,
370   96,  100, 104, 108, 112, 116, 120, 124,
371   128, 132, 136, 140, 144, 148, 152, 156,
372   160, 164, 168, 172, 176, 180, 184, 188,
373   192, 196, 200, 204, 208, 212, 216, 220,
374   224, 228, 232, 236, 240, 244, 249, 255,
375 };
376 
vp9_quantizer_to_qindex(int quantizer)377 int vp9_quantizer_to_qindex(int quantizer) {
378   return quantizer_to_qindex[quantizer];
379 }
380 
vp9_qindex_to_quantizer(int qindex)381 int vp9_qindex_to_quantizer(int qindex) {
382   int quantizer;
383 
384   for (quantizer = 0; quantizer < 64; ++quantizer)
385     if (quantizer_to_qindex[quantizer] >= qindex)
386       return quantizer;
387 
388   return 63;
389 }
390