FFmpeg
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Modules Pages
intra.c
Go to the documentation of this file.
1 /*
2  * VVC intra prediction
3  *
4  * Copyright (C) 2021 Nuo Mi
5  *
6  * This file is part of FFmpeg.
7  *
8  * FFmpeg is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * FFmpeg is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with FFmpeg; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
21  */
22 #include "libavutil/frame.h"
23 #include "libavutil/imgutils.h"
24 
25 #include "data.h"
26 #include "inter.h"
27 #include "intra.h"
28 #include "itx_1d.h"
29 
30 #define POS(c_idx, x, y) \
31  &fc->frame->data[c_idx][((y) >> fc->ps.sps->vshift[c_idx]) * fc->frame->linesize[c_idx] + \
32  (((x) >> fc->ps.sps->hshift[c_idx]) << fc->ps.sps->pixel_shift)]
33 
34 static int is_cclm(enum IntraPredMode mode)
35 {
36  return mode == INTRA_LT_CCLM || mode == INTRA_L_CCLM || mode == INTRA_T_CCLM;
37 }
38 
40 {
41  const VVCFrameContext *fc = lc->fc;
42  const VVCSPS *sps = fc->ps.sps;
43  const CodingUnit *cu = lc->cu;
44  const int x_tb = tb->x0 >> fc->ps.sps->min_cb_log2_size_y;
45  const int y_tb = tb->y0 >> fc->ps.sps->min_cb_log2_size_y;
46  const int x_c = (tb->x0 + (tb->tb_width << sps->hshift[1] >> 1) ) >> fc->ps.sps->min_cb_log2_size_y;
47  const int y_c = (tb->y0 + (tb->tb_height << sps->vshift[1] >> 1)) >> fc->ps.sps->min_cb_log2_size_y;
48  const int min_cb_width = fc->ps.pps->min_cb_width;
49  const int intra_mip_flag = SAMPLE_CTB(fc->tab.imf, x_tb, y_tb);
50  int pred_mode_intra = tb->c_idx == 0 ? cu->intra_pred_mode_y : cu->intra_pred_mode_c;
51  if (intra_mip_flag && !tb->c_idx) {
52  pred_mode_intra = INTRA_PLANAR;
53  } else if (is_cclm(pred_mode_intra)) {
54  int intra_mip_flag_c = SAMPLE_CTB(fc->tab.imf, x_c, y_c);
55  int cu_pred_mode = SAMPLE_CTB(fc->tab.cpm[0], x_c, y_c);
56  if (intra_mip_flag_c) {
57  pred_mode_intra = INTRA_PLANAR;
58  } else if (cu_pred_mode == MODE_IBC || cu_pred_mode == MODE_PLT) {
59  pred_mode_intra = INTRA_DC;
60  } else {
61  pred_mode_intra = SAMPLE_CTB(fc->tab.ipm, x_c, y_c);
62  }
63  }
64  pred_mode_intra = ff_vvc_wide_angle_mode_mapping(cu, tb->tb_width, tb->tb_height, tb->c_idx, pred_mode_intra);
65 
66  return pred_mode_intra;
67 }
68 
69 //8.7.4 Transformation process for scaled transform coefficients
70 static void ilfnst_transform(const VVCLocalContext *lc, TransformBlock *tb)
71 {
72  const VVCSPS *sps = lc->fc->ps.sps;
73  const CodingUnit *cu = lc->cu;
74  const int w = tb->tb_width;
75  const int h = tb->tb_height;
76  const int n_lfnst_out_size = (w >= 8 && h >= 8) ? 48 : 16; ///< nLfnstOutSize
77  const int log2_lfnst_size = (w >= 8 && h >= 8) ? 3 : 2; ///< log2LfnstSize
78  const int n_lfnst_size = 1 << log2_lfnst_size; ///< nLfnstSize
79  const int non_zero_size = ((w == 8 && h == 8) || (w == 4 && h == 4)) ? 8 : 16; ///< nonZeroSize
80  const int pred_mode_intra = derive_ilfnst_pred_mode_intra(lc, tb);
81  const int transpose = pred_mode_intra > 34;
82  int u[16], v[48];
83 
84  for (int x = 0; x < non_zero_size; x++) {
85  int xc = ff_vvc_diag_scan_x[2][2][x];
86  int yc = ff_vvc_diag_scan_y[2][2][x];
87  u[x] = tb->coeffs[w * yc + xc];
88  }
89  ff_vvc_inv_lfnst_1d(v, u, non_zero_size, n_lfnst_out_size, pred_mode_intra,
90  cu->lfnst_idx, sps->log2_transform_range);
91  if (transpose) {
92  int *dst = tb->coeffs;
93  const int *src = v;
94  if (n_lfnst_size == 4) {
95  for (int y = 0; y < 4; y++) {
96  dst[0] = src[0];
97  dst[1] = src[4];
98  dst[2] = src[8];
99  dst[3] = src[12];
100  src++;
101  dst += w;
102  }
103  } else {
104  for (int y = 0; y < 8; y++) {
105  dst[0] = src[0];
106  dst[1] = src[8];
107  dst[2] = src[16];
108  dst[3] = src[24];
109  if (y < 4) {
110  dst[4] = src[32];
111  dst[5] = src[36];
112  dst[6] = src[40];
113  dst[7] = src[44];
114  }
115  src++;
116  dst += w;
117  }
118  }
119 
120  } else {
121  int *dst = tb->coeffs;
122  const int *src = v;
123  for (int y = 0; y < n_lfnst_size; y++) {
124  int size = (y < 4) ? n_lfnst_size : 4;
125  memcpy(dst, src, size * sizeof(int));
126  src += size;
127  dst += w;
128  }
129  }
130  tb->max_scan_x = n_lfnst_size - 1;
131  tb->max_scan_y = n_lfnst_size - 1;
132 }
133 
134 //part of 8.7.4 Transformation process for scaled transform coefficients
135 static void derive_transform_type(const VVCFrameContext *fc, const VVCLocalContext *lc, const TransformBlock *tb, enum VVCTxType *trh, enum VVCTxType *trv)
136 {
137  const CodingUnit *cu = lc->cu;
138  static const enum VVCTxType mts_to_trh[] = { VVC_DCT2, VVC_DST7, VVC_DCT8, VVC_DST7, VVC_DCT8 };
139  static const enum VVCTxType mts_to_trv[] = { VVC_DCT2, VVC_DST7, VVC_DST7, VVC_DCT8, VVC_DCT8 };
140  const VVCSPS *sps = fc->ps.sps;
141  int implicit_mts_enabled = 0;
142  if (tb->c_idx || (cu->isp_split_type != ISP_NO_SPLIT && cu->lfnst_idx)) {
143  *trh = *trv = VVC_DCT2;
144  return;
145  }
146 
147  if (sps->r->sps_mts_enabled_flag) {
148  if (cu->isp_split_type != ISP_NO_SPLIT ||
149  (cu->sbt_flag && FFMAX(tb->tb_width, tb->tb_height) <= 32) ||
150  (!sps->r->sps_explicit_mts_intra_enabled_flag && cu->pred_mode == MODE_INTRA &&
151  !cu->lfnst_idx && !cu->intra_mip_flag)) {
152  implicit_mts_enabled = 1;
153  }
154  }
155  if (implicit_mts_enabled) {
156  const int w = tb->tb_width;
157  const int h = tb->tb_height;
158  if (cu->sbt_flag) {
159  *trh = (cu->sbt_horizontal_flag || cu->sbt_pos_flag) ? VVC_DST7 : VVC_DCT8;
160  *trv = (!cu->sbt_horizontal_flag || cu->sbt_pos_flag) ? VVC_DST7 : VVC_DCT8;
161  } else {
162  *trh = (w >= 4 && w <= 16) ? VVC_DST7 : VVC_DCT2;
163  *trv = (h >= 4 && h <= 16) ? VVC_DST7 : VVC_DCT2;
164  }
165  return;
166  }
167  *trh = mts_to_trh[cu->mts_idx];
168  *trv = mts_to_trv[cu->mts_idx];
169 }
170 
171 static int add_reconstructed_area(VVCLocalContext *lc, const int ch_type, const int x0, const int y0, const int w, const int h)
172 {
173  const VVCSPS *sps = lc->fc->ps.sps;
174  const int hs = sps->hshift[ch_type];
175  const int vs = sps->vshift[ch_type];
177 
178  if (lc->num_ras[ch_type] >= FF_ARRAY_ELEMS(lc->ras[ch_type]))
179  return AVERROR_INVALIDDATA;
180 
181  a = &lc->ras[ch_type][lc->num_ras[ch_type]];
182  a->x = x0 >> hs;
183  a->y = y0 >> vs;
184  a->w = w >> hs;
185  a->h = h >> vs;
186  lc->num_ras[ch_type]++;
187 
188  return 0;
189 }
190 
191 static void add_tu_area(const TransformUnit *tu, int *x0, int *y0, int *w, int *h)
192 {
193  *x0 = tu->x0;
194  *y0 = tu->y0;
195  *w = tu->width;
196  *h = tu->height;
197 }
198 
199 #define MIN_ISP_PRED_WIDTH 4
200 static int get_luma_predict_unit(const CodingUnit *cu, const TransformUnit *tu, const int idx, int *x0, int *y0, int *w, int *h)
201 {
202  int has_luma = 1;
203  add_tu_area(tu, x0, y0, w, h);
206  has_luma = !(idx % (MIN_ISP_PRED_WIDTH / tu->width));
207  }
208  return has_luma;
209 }
210 
211 static int get_chroma_predict_unit(const CodingUnit *cu, const TransformUnit *tu, const int idx, int *x0, int *y0, int *w, int *h)
212 {
213  if (cu->isp_split_type == ISP_NO_SPLIT) {
214  add_tu_area(tu, x0, y0, w, h);
215  return 1;
216  }
217  if (idx == cu->num_intra_subpartitions - 1) {
218  *x0 = cu->x0;
219  *y0 = cu->y0;
220  *w = cu->cb_width;
221  *h = cu->cb_height;
222  return 1;
223  }
224  return 0;
225 }
226 
227 //8.4.5.1 General decoding process for intra blocks
228 static void predict_intra(VVCLocalContext *lc, const TransformUnit *tu, const int idx, const int target_ch_type)
229 {
230  const VVCFrameContext *fc = lc->fc;
231  const CodingUnit *cu = lc->cu;
232  const VVCTreeType tree_type = cu->tree_type;
233  int x0, y0, w, h;
234  if (cu->pred_mode != MODE_INTRA) {
235  add_reconstructed_area(lc, target_ch_type, tu->x0, tu->y0, tu->width, tu->height);
236  return;
237  }
238  if (!target_ch_type && tree_type != DUAL_TREE_CHROMA) {
239  if (get_luma_predict_unit(cu, tu, idx, &x0, &y0, &w, &h)) {
240  ff_vvc_set_neighbour_available(lc, x0, y0, w, h);
241  fc->vvcdsp.intra.intra_pred(lc, x0, y0, w, h, 0);
242  add_reconstructed_area(lc, 0, x0, y0, w, h);
243  }
244  }
245  if (target_ch_type && tree_type != DUAL_TREE_LUMA) {
246  if (get_chroma_predict_unit(cu, tu, idx, &x0, &y0, &w, &h)){
247  ff_vvc_set_neighbour_available(lc, x0, y0, w, h);
248  if (is_cclm(cu->intra_pred_mode_c)) {
249  fc->vvcdsp.intra.intra_cclm_pred(lc, x0, y0, w, h);
250  } else {
251  fc->vvcdsp.intra.intra_pred(lc, x0, y0, w, h, 1);
252  fc->vvcdsp.intra.intra_pred(lc, x0, y0, w, h, 2);
253  }
254  add_reconstructed_area(lc, 1, x0, y0, w, h);
255  }
256  }
257 }
258 
259 static void scale_clip(int *coeff, const int nzw, const int w, const int h,
260  const int shift, const int log2_transform_range)
261 {
262  const int add = 1 << (shift - 1);
263  for (int y = 0; y < h; y++) {
264  int *p = coeff + y * w;
265  for (int x = 0; x < nzw; x++) {
266  *p = av_clip_intp2((*p + add) >> shift, log2_transform_range);
267  p++;
268  }
269  memset(p, 0, sizeof(*p) * (w - nzw));
270  }
271 }
272 
273 static void scale(int *out, const int *in, const int w, const int h, const int shift)
274 {
275  const int add = 1 << (shift - 1);
276  for (int y = 0; y < h; y++) {
277  for (int x = 0; x < w; x++) {
278  int *o = out + y * w + x;
279  const int *i = in + y * w + x;
280  *o = (*i + add) >> shift;
281  }
282  }
283 }
284 
285 // part of 8.7.3 Scaling process for transform coefficients
286 static void derive_qp(const VVCLocalContext *lc, const TransformUnit *tu, TransformBlock *tb)
287 {
288  const VVCSPS *sps = lc->fc->ps.sps;
289  const H266RawSliceHeader *rsh = lc->sc->sh.r;
290  const CodingUnit *cu = lc->cu;
291  const bool is_jcbcr = tb->c_idx && tu->joint_cbcr_residual_flag && tu->coded_flag[CB] && tu->coded_flag[CR];
292  const int idx = is_jcbcr ? JCBCR : tb->c_idx;
293  const int qp = cu->qp[idx] + (idx ? 0 : sps->qp_bd_offset);
294  const int act_offset[] = { -5, 1, 3, 1 };
295  const int qp_act_offset = cu->act_enabled_flag ? act_offset[idx] : 0;
296 
297  if (tb->ts) {
298  const int qp_prime_ts_min = 4 + 6 * sps->r->sps_min_qp_prime_ts;
299 
300  tb->qp = av_clip(qp + qp_act_offset, qp_prime_ts_min, 63 + sps->qp_bd_offset);
301  tb->rect_non_ts_flag = 0;
302  tb->bd_shift = 10;
303  } else {
304  const int log_sum = tb->log2_tb_width + tb->log2_tb_height;
305  const int rect_non_ts_flag = log_sum & 1;
306 
307  tb->qp = av_clip(qp + qp_act_offset, 0, 63 + sps->qp_bd_offset);
308  tb->rect_non_ts_flag = rect_non_ts_flag;
309  tb->bd_shift = sps->bit_depth + rect_non_ts_flag + (log_sum / 2)
310  + 10 - sps->log2_transform_range + rsh->sh_dep_quant_used_flag;
311  }
312  tb->bd_offset = (1 << tb->bd_shift) >> 1;
313 }
314 
315 static const uint8_t rem6[63 + 8 * 6 + 1] = {
316  0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5,
317  0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5,
318  0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5,
319  0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5,
320  0, 1, 2, 3, 4, 5, 0, 1, 2, 3, 4, 5, 0, 1, 2, 3,
321 };
322 
323 static const uint8_t div6[63 + 8 * 6 + 1] = {
324  0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
325  4, 4, 4, 4, 4, 4, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 7, 7, 7, 7, 7, 7,
326  8, 8, 8, 8, 8, 8, 9, 9, 9, 9, 9, 9, 10, 10, 10, 10, 10, 10, 11, 11, 11, 11, 11, 11,
327  12, 12, 12, 12, 12, 12, 13, 13, 13, 13, 13, 13, 14, 14, 14, 14, 14, 14, 15, 15, 15, 15, 15, 15,
328  16, 16, 16, 16, 16, 16, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18,
329 };
330 
331 const static int level_scale[2][6] = {
332  { 40, 45, 51, 57, 64, 72 },
333  { 57, 64, 72, 80, 90, 102 }
334 };
335 
336 //8.7.3 Scaling process for transform coefficients
337 static av_always_inline int derive_scale(const TransformBlock *tb, const int sh_dep_quant_used_flag)
338 {
339  const int addin = sh_dep_quant_used_flag && !tb->ts;
340  const int qp = tb->qp + addin;
341 
342  return level_scale[tb->rect_non_ts_flag][rem6[qp]] << div6[qp];
343 }
344 
345 //8.7.3 Scaling process for transform coefficients
346 static const uint8_t* derive_scale_m(const VVCLocalContext *lc, const TransformBlock *tb, uint8_t *scale_m)
347 {
348  //Table 38 – Specification of the scaling matrix identifier variable id according to predMode, cIdx, nTbW, and nTbH
349  const int ids[2][3][6] = {
350  {
351  { 0, 2, 8, 14, 20, 26 },
352  { 0, 3, 9, 15, 21, 21 },
353  { 0, 4, 10, 16, 22, 22 }
354  },
355  {
356  { 0, 5, 11, 17, 23, 27 },
357  { 0, 6, 12, 18, 24, 24 },
358  { 1, 7, 13, 19, 25, 25 },
359  }
360  };
361  const VVCFrameParamSets *ps = &lc->fc->ps;
362  const VVCSPS *sps = ps->sps;
363  const H266RawSliceHeader *rsh = lc->sc->sh.r;
364  const CodingUnit *cu = lc->cu;
365  const VVCScalingList *sl = ps->sl;
366  const int id = ids[cu->pred_mode != MODE_INTRA][tb->c_idx][FFMAX(tb->log2_tb_height, tb->log2_tb_width) - 1];
367  const int log2_matrix_size = (id < 2) ? 1 : (id < 8) ? 2 : 3;
368  uint8_t *p = scale_m;
369 
370  av_assert0(!sps->r->sps_scaling_matrix_for_alternative_colour_space_disabled_flag);
371 
372  if (!rsh->sh_explicit_scaling_list_used_flag || tb->ts ||
373  sps->r->sps_scaling_matrix_for_lfnst_disabled_flag && cu->apply_lfnst_flag[tb->c_idx])
374  return ff_vvc_default_scale_m;
375 
376  if (!sl) {
377  av_log(lc->fc->log_ctx, AV_LOG_WARNING, "bug: no scaling list aps, id = %d", ps->ph.r->ph_scaling_list_aps_id);
378  return ff_vvc_default_scale_m;
379  }
380 
381  for (int y = tb->min_scan_y; y <= tb->max_scan_y; y++) {
382  const int off = y << log2_matrix_size >> tb->log2_tb_height << log2_matrix_size;
383  const uint8_t *m = &sl->scaling_matrix_rec[id][off];
384 
385  for (int x = tb->min_scan_x; x <= tb->max_scan_x; x++)
386  *p++ = m[x << log2_matrix_size >> tb->log2_tb_width];
387  }
388  if (id >= SL_START_16x16 && !tb->min_scan_x && !tb->min_scan_y)
389  *scale_m = sl->scaling_matrix_dc_rec[id - SL_START_16x16];
390 
391  return scale_m;
392 }
393 
394 //8.7.3 Scaling process for transform coefficients
396  const int scale, const int scale_m, const int log2_transform_range)
397 {
398  coeff = ((int64_t) coeff * scale * scale_m + tb->bd_offset) >> tb->bd_shift;
399  coeff = av_clip_intp2(coeff, log2_transform_range);
400  return coeff;
401 }
402 
403 static void dequant(const VVCLocalContext *lc, const TransformUnit *tu, TransformBlock *tb)
404 {
405  uint8_t tmp[MAX_TB_SIZE * MAX_TB_SIZE];
406  const H266RawSliceHeader *rsh = lc->sc->sh.r;
407  const VVCSPS *sps = lc->fc->ps.sps;
408  const uint8_t *scale_m = derive_scale_m(lc, tb, tmp);
409  int scale;
410 
411  derive_qp(lc, tu, tb);
413 
414  for (int y = tb->min_scan_y; y <= tb->max_scan_y; y++) {
415  for (int x = tb->min_scan_x; x <= tb->max_scan_x; x++) {
416  int *coeff = tb->coeffs + y * tb->tb_width + x;
417 
418  if (*coeff)
419  *coeff = scale_coeff(tb, *coeff, scale, *scale_m, sps->log2_transform_range);
420  scale_m++;
421  }
422  }
423 }
424 
425 //transmatrix[0][0]
426 #define DCT_A 64
427 static void itx_2d(const VVCFrameContext *fc, TransformBlock *tb, const enum VVCTxType trh, const enum VVCTxType trv)
428 {
429  const VVCSPS *sps = fc->ps.sps;
430  const int w = tb->tb_width;
431  const int h = tb->tb_height;
432  const size_t nzw = tb->max_scan_x + 1;
433  const size_t nzh = tb->max_scan_y + 1;
434  const int shift[] = { 7, 5 + sps->log2_transform_range - sps->bit_depth };
435 
436  if (w == h && nzw == 1 && nzh == 1 && trh == VVC_DCT2 && trv == VVC_DCT2) {
437  const int add[] = { 1 << (shift[0] - 1), 1 << (shift[1] - 1) };
438  const int t = (tb->coeffs[0] * DCT_A + add[0]) >> shift[0];
439  const int dc = (t * DCT_A + add[1]) >> shift[1];
440 
441  for (int i = 0; i < w * h; i++)
442  tb->coeffs[i] = dc;
443 
444  return;
445  }
446 
447  for (int x = 0; x < nzw; x++)
448  fc->vvcdsp.itx.itx[trv][tb->log2_tb_height - 1](tb->coeffs + x, w, nzh);
449  scale_clip(tb->coeffs, nzw, w, h, shift[0], sps->log2_transform_range);
450 
451  for (int y = 0; y < h; y++)
452  fc->vvcdsp.itx.itx[trh][tb->log2_tb_width - 1](tb->coeffs + y * w, 1, nzw);
453  scale(tb->coeffs, tb->coeffs, w, h, shift[1]);
454 }
455 
456 static void itx_1d(const VVCFrameContext *fc, TransformBlock *tb, const enum VVCTxType trh, const enum VVCTxType trv)
457 {
458  const VVCSPS *sps = fc->ps.sps;
459  const int w = tb->tb_width;
460  const int h = tb->tb_height;
461  const size_t nzw = tb->max_scan_x + 1;
462  const size_t nzh = tb->max_scan_y + 1;
463 
464  if ((w > 1 && nzw == 1 && trh == VVC_DCT2) || (h > 1 && nzh == 1 && trv == VVC_DCT2)) {
465  const int shift = 6 + sps->log2_transform_range - sps->bit_depth;
466  const int add = 1 << (shift - 1);
467  const int dc = (tb->coeffs[0] * DCT_A + add) >> shift;
468 
469  for (int i = 0; i < w * h; i++)
470  tb->coeffs[i] = dc;
471 
472  return;
473  }
474 
475  if (w > 1)
476  fc->vvcdsp.itx.itx[trh][tb->log2_tb_width - 1](tb->coeffs, 1, nzw);
477  else
478  fc->vvcdsp.itx.itx[trv][tb->log2_tb_height - 1](tb->coeffs, 1, nzh);
479  scale(tb->coeffs, tb->coeffs, w, h, 6 + sps->log2_transform_range - sps->bit_depth);
480 }
481 
482 static void transform_bdpcm(TransformBlock *tb, const VVCLocalContext *lc, const CodingUnit *cu)
483 {
484  const VVCSPS *sps = lc->fc->ps.sps;
486  const int vertical = mode == INTRA_VERT;
487  lc->fc->vvcdsp.itx.transform_bdpcm(tb->coeffs, tb->tb_width, tb->tb_height,
488  vertical, sps->log2_transform_range);
489  if (vertical)
490  tb->max_scan_y = tb->tb_height - 1;
491  else
492  tb->max_scan_x = tb->tb_width - 1;
493 }
494 
495 static void lmcs_scale_chroma(VVCLocalContext *lc, TransformUnit *tu, TransformBlock *tb, const int target_ch_type)
496 {
497  const VVCFrameContext *fc = lc->fc;
498  const VVCSH *sh = &lc->sc->sh;
499  const CodingUnit *cu = lc->cu;
500  const int c_idx = tb->c_idx;
501  const int ch_type = c_idx > 0;
502  const int w = tb->tb_width;
503  const int h = tb->tb_height;
504  const int chroma_scale = ch_type && sh->r->sh_lmcs_used_flag && fc->ps.ph.r->ph_chroma_residual_scale_flag && (w * h > 4);
505  const int has_jcbcr = tu->joint_cbcr_residual_flag && c_idx;
506 
507  for (int j = 0; j < 1 + has_jcbcr; j++) {
508  const bool is_jcbcr = j > 0;
509  const int jcbcr_idx = CB + tu->coded_flag[CB];
510  TransformBlock *jcbcr = &tu->tbs[jcbcr_idx - tu->tbs[0].c_idx];
511  int *coeffs = is_jcbcr ? jcbcr->coeffs : tb->coeffs;
512 
513  if (!j && has_jcbcr) {
514  const int c_sign = 1 - 2 * fc->ps.ph.r->ph_joint_cbcr_sign_flag;
515  const int shift = tu->coded_flag[CB] ^ tu->coded_flag[CR];
516  fc->vvcdsp.itx.pred_residual_joint(jcbcr->coeffs, tb->coeffs, w, h, c_sign, shift);
517  }
518  if (chroma_scale)
519  fc->vvcdsp.intra.lmcs_scale_chroma(lc, coeffs, w, h, cu->x0, cu->y0);
520  }
521 }
522 
523 static void add_residual(const VVCLocalContext *lc, TransformUnit *tu, const int target_ch_type)
524 {
525  const VVCFrameContext *fc = lc->fc;
526  const CodingUnit *cu = lc->cu;
527 
528  for (int i = 0; i < tu->nb_tbs; i++) {
529  TransformBlock *tb = tu->tbs + i;
530  const int c_idx = tb->c_idx;
531  const int ch_type = c_idx > 0;
532  const ptrdiff_t stride = fc->frame->linesize[c_idx];
533  const bool has_residual = tb->has_coeffs || cu->act_enabled_flag ||
534  (c_idx && tu->joint_cbcr_residual_flag);
535  uint8_t *dst = POS(c_idx, tb->x0, tb->y0);
536 
537  if (ch_type == target_ch_type && has_residual)
538  fc->vvcdsp.itx.add_residual(dst, tb->coeffs, tb->tb_width, tb->tb_height, stride);
539  }
540 }
541 
542 static void itransform(VVCLocalContext *lc, TransformUnit *tu, const int target_ch_type)
543 {
544  const VVCFrameContext *fc = lc->fc;
545  const CodingUnit *cu = lc->cu;
546  TransformBlock *tbs = tu->tbs;
547  const bool is_act_luma = cu->act_enabled_flag && target_ch_type == LUMA;
548 
549  for (int i = 0; i < tu->nb_tbs; i++) {
550  TransformBlock *tb = tbs + i;
551  const int c_idx = tb->c_idx;
552  const int ch_type = c_idx > 0;
553  const bool do_itx = is_act_luma || !cu->act_enabled_flag && ch_type == target_ch_type;
554 
555  if (tb->has_coeffs && do_itx) {
556  if (cu->bdpcm_flag[tb->c_idx])
557  transform_bdpcm(tb, lc, cu);
558  dequant(lc, tu, tb);
559  if (!tb->ts) {
560  enum VVCTxType trh, trv;
561 
562  if (cu->apply_lfnst_flag[c_idx])
563  ilfnst_transform(lc, tb);
564  derive_transform_type(fc, lc, tb, &trh, &trv);
565  if (tb->tb_width > 1 && tb->tb_height > 1)
566  itx_2d(fc, tb, trh, trv);
567  else
568  itx_1d(fc, tb, trh, trv);
569  }
570  lmcs_scale_chroma(lc, tu, tb, target_ch_type);
571  }
572  }
573 
574  if (is_act_luma) {
575  fc->vvcdsp.itx.adaptive_color_transform(
576  tbs[LUMA].coeffs, tbs[CB].coeffs, tbs[CR].coeffs,
577  tbs[LUMA].tb_width, tbs[LUMA].tb_height);
578  }
579 
580  add_residual(lc, tu, target_ch_type);
581 }
582 
584 {
585  VVCFrameContext *fc = lc->fc;
586  CodingUnit *cu = lc->cu;
587  const int start = cu->tree_type == DUAL_TREE_CHROMA;
588  const int end = fc->ps.sps->r->sps_chroma_format_idc && (cu->tree_type != DUAL_TREE_LUMA);
589 
590  for (int ch_type = start; ch_type <= end; ch_type++) {
591  TransformUnit *tu = cu->tus.head;
592  for (int i = 0; tu; i++) {
593  predict_intra(lc, tu, i, ch_type);
594  itransform(lc, tu, ch_type);
595  tu = tu->next;
596  }
597  }
598  return 0;
599 }
600 
601 #define IBC_POS(c_idx, x, y) \
602  (fc->tab.ibc_vir_buf[c_idx] + \
603  (x << ps) + (y + ((cu->y0 & ~(sps->ctb_size_y - 1)) >> vs)) * ibc_stride)
604 #define IBC_X(x) ((x) & ((fc->tab.sz.ibc_buffer_width >> hs) - 1))
605 #define IBC_Y(y) ((y) & ((1 << sps->ctb_log2_size_y >> vs) - 1))
606 
607 static void intra_block_copy(const VVCLocalContext *lc, const int c_idx)
608 {
609  const CodingUnit *cu = lc->cu;
610  const PredictionUnit *pu = &cu->pu;
611  const VVCFrameContext *fc = lc->fc;
612  const VVCSPS *sps = fc->ps.sps;
613  const Mv *bv = &pu->mi.mv[L0][0];
614  const int hs = sps->hshift[c_idx];
615  const int vs = sps->vshift[c_idx];
616  const int ps = sps->pixel_shift;
617  const int ref_x = IBC_X((cu->x0 >> hs) + (bv->x >> (4 + hs)));
618  const int ref_y = IBC_Y((cu->y0 >> vs) + (bv->y >> (4 + vs)));
619  const int w = cu->cb_width >> hs;
620  const int h = cu->cb_height >> vs;
621  const int ibc_buf_width = fc->tab.sz.ibc_buffer_width >> hs; ///< IbcBufWidthY and IbcBufWidthC
622  const int rw = FFMIN(w, ibc_buf_width - ref_x);
623  const int ibc_stride = ibc_buf_width << ps;
624  const int dst_stride = fc->frame->linesize[c_idx];
625  const uint8_t *ibc_buf = IBC_POS(c_idx, ref_x, ref_y);
626  uint8_t *dst = POS(c_idx, cu->x0, cu->y0);
627 
628  av_image_copy_plane(dst, dst_stride, ibc_buf, ibc_stride, rw << ps, h);
629 
630  if (w > rw) {
631  //wrap around, left part
632  ibc_buf = IBC_POS(c_idx, 0, ref_y);
633  dst += rw << ps;
634  av_image_copy_plane(dst, dst_stride, ibc_buf, ibc_stride, (w - rw) << ps, h);
635  }
636 }
637 
638 static void vvc_predict_ibc(const VVCLocalContext *lc)
639 {
640  const H266RawSPS *rsps = lc->fc->ps.sps->r;
641 
642  intra_block_copy(lc, LUMA);
643  if (lc->cu->tree_type == SINGLE_TREE && rsps->sps_chroma_format_idc) {
644  intra_block_copy(lc, CB);
645  intra_block_copy(lc, CR);
646  }
647 }
648 
649 static void ibc_fill_vir_buf(const VVCLocalContext *lc, const CodingUnit *cu)
650 {
651  const VVCFrameContext *fc = lc->fc;
652  const VVCSPS *sps = fc->ps.sps;
653  int start, end;
654 
655  ff_vvc_channel_range(&start, &end, cu->tree_type, sps->r->sps_chroma_format_idc);
656 
657  for (int c_idx = start; c_idx < end; c_idx++) {
658  const int hs = sps->hshift[c_idx];
659  const int vs = sps->vshift[c_idx];
660  const int ps = sps->pixel_shift;
661  const int x = IBC_X(cu->x0 >> hs);
662  const int y = IBC_Y(cu->y0 >> vs);
663  const int src_stride = fc->frame->linesize[c_idx];
664  const int ibc_stride = fc->tab.sz.ibc_buffer_width >> hs << ps;
665  const uint8_t *src = POS(c_idx, cu->x0, cu->y0);
666  uint8_t *ibc_buf = IBC_POS(c_idx, x, y);
667 
668  av_image_copy_plane(ibc_buf, ibc_stride, src, src_stride, cu->cb_width >> hs << ps , cu->cb_height >> vs);
669  }
670 }
671 
673 {
674  const VVCSPS *sps = lc->fc->ps.sps;
675  const int qp_prime_ts_min = 4 + 6 * sps->r->sps_min_qp_prime_ts;
676  int qp;
677 
678  derive_qp(lc, tu, tb);
679  qp = FFMAX(qp_prime_ts_min, tb->qp);
680  return level_scale[0][rem6[qp]] << div6[qp];
681 }
682 
683 // 8.4.5.3 Decoding process for palette mode
685 {
686  const VVCFrameContext *fc = lc->fc;
687  const CodingUnit *cu = lc->cu;
688  TransformUnit *tu = cu->tus.head;
689  const VVCSPS *sps = fc->ps.sps;
690  const int ps = sps->pixel_shift;
691 
692  for (int i = 0; i < tu->nb_tbs; i++) {
693  TransformBlock *tb = &tu->tbs[i];
694  const int c_idx = tb->c_idx;
695  const int w = tb->tb_width;
696  const int h = tb->tb_height;
697  const ptrdiff_t stride = fc->frame->linesize[c_idx];
698  uint8_t *dst = POS(c_idx, cu->x0, cu->y0);
699 
700  av_image_copy_plane(dst, stride, (uint8_t*)tb->coeffs, w << ps, w << ps, h);
701  }
702 }
703 
704 int ff_vvc_reconstruct(VVCLocalContext *lc, const int rs, const int rx, const int ry)
705 {
706  const VVCFrameContext *fc = lc->fc;
707  const VVCSPS *sps = fc->ps.sps;
708  const int x_ctb = rx << sps->ctb_log2_size_y;
709  const int y_ctb = ry << sps->ctb_log2_size_y;
710  CodingUnit *cu = fc->tab.cus[rs];
711  int ret = 0;
712 
713  lc->num_ras[0] = lc->num_ras[1] = 0;
714  lc->lmcs.x_vpdu = -1;
715  lc->lmcs.y_vpdu = -1;
716  ff_vvc_decode_neighbour(lc, x_ctb, y_ctb, rx, ry, rs);
717  while (cu) {
718  lc->cu = cu;
719 
720  if (cu->ciip_flag)
722  else if (cu->pred_mode == MODE_IBC)
723  vvc_predict_ibc(lc);
724  else if (cu->pred_mode == MODE_PLT)
726  if (cu->coded_flag) {
727  ret = reconstruct(lc);
728  } else {
729  if (cu->tree_type != DUAL_TREE_CHROMA)
730  add_reconstructed_area(lc, LUMA, cu->x0, cu->y0, cu->cb_width, cu->cb_height);
731  if (sps->r->sps_chroma_format_idc && cu->tree_type != DUAL_TREE_LUMA)
732  add_reconstructed_area(lc, CHROMA, cu->x0, cu->y0, cu->cb_width, cu->cb_height);
733  }
734  if (sps->r->sps_ibc_enabled_flag)
735  ibc_fill_vir_buf(lc, cu);
736  cu = cu->next;
737  }
738  ff_vvc_ctu_free_cus(fc->tab.cus + rs);
739  return ret;
740 }
741 
ff_vvc_reconstruct
int ff_vvc_reconstruct(VVCLocalContext *lc, const int rs, const int rx, const int ry)
reconstruct a CTU
Definition: intra.c:704
VVCSPS
Definition: ps.h:58
get_luma_predict_unit
static int get_luma_predict_unit(const CodingUnit *cu, const TransformUnit *tu, const int idx, int *x0, int *y0, int *w, int *h)
Definition: intra.c:200
AV_LOG_WARNING
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:216
derive_ilfnst_pred_mode_intra
static int derive_ilfnst_pred_mode_intra(const VVCLocalContext *lc, const TransformBlock *tb)
Definition: intra.c:39
VVC_DCT8
@ VVC_DCT8
Definition: dsp.h:33
av_clip
#define av_clip
Definition: common.h:100
LUMA
#define LUMA
Definition: filter.c:31
TransformBlock::tb_width
int tb_width
Definition: ctu.h:149
predict_intra
static void predict_intra(VVCLocalContext *lc, const TransformUnit *tu, const int idx, const int target_ch_type)
Definition: intra.c:228
MotionInfo::mv
Mv mv[2][MAX_CONTROL_POINTS]
Definition: ctu.h:251
H266RawSliceHeader::sh_explicit_scaling_list_used_flag
uint8_t sh_explicit_scaling_list_used_flag
Definition: cbs_h266.h:795
out
FILE * out
Definition: movenc.c:55
TransformUnit::height
int height
Definition: ctu.h:177
CB
#define CB
Definition: filter.c:32
vvc_predict_ibc
static void vvc_predict_ibc(const VVCLocalContext *lc)
Definition: intra.c:638
INTRA_T_CCLM
@ INTRA_T_CCLM
Definition: ctu.h:241
CodingUnit
Definition: hevcdec.h:292
int64_t
long long int64_t
Definition: coverity.c:34
CodingUnit::act_enabled_flag
uint8_t act_enabled_flag
Definition: ctu.h:305
VVC_DCT2
@ VVC_DCT2
Definition: dsp.h:31
CodingUnit::head
TransformUnit * head
RefStruct reference.
Definition: ctu.h:330
TransformUnit::nb_tbs
uint8_t nb_tbs
Definition: ctu.h:183
CodingUnit::bdpcm_flag
int bdpcm_flag[VVC_MAX_SAMPLE_ARRAYS]
BdpcmFlag.
Definition: ctu.h:325
TransformBlock::min_scan_y
int min_scan_y
Definition: ctu.h:157
MODE_IBC
@ MODE_IBC
Definition: ctu.h:194
scale_clip
static void scale_clip(int *coeff, const int nzw, const int w, const int h, const int shift, const int log2_transform_range)
Definition: intra.c:259
data.h
scale_coeff
static av_always_inline int scale_coeff(const TransformBlock *tb, int coeff, const int scale, const int scale_m, const int log2_transform_range)
Definition: intra.c:395
mode
Definition: swscale.c:56
w
uint8_t w
Definition: llviddspenc.c:38
level_scale
const static int level_scale[2][6]
Definition: intra.c:331
CodingUnit::intra_mip_flag
uint8_t intra_mip_flag
intra_mip_flag
Definition: ctu.h:308
VVCLocalContext::sc
SliceContext * sc
Definition: ctu.h:445
INTRA_DC
@ INTRA_DC
Definition: hevcdec.h:128
itx_1d
static void itx_1d(const VVCFrameContext *fc, TransformBlock *tb, const enum VVCTxType trh, const enum VVCTxType trv)
Definition: intra.c:456
Mv::y
int16_t y
vertical component of motion vector
Definition: hevcdec.h:307
TransformUnit::x0
int x0
Definition: ctu.h:174
VVCSH::r
const H266RawSliceHeader * r
RefStruct reference.
Definition: ps.h:239
VVCDSPContext::itx
VVCItxDSPContext itx
Definition: dsp.h:173
TransformBlock::min_scan_x
int min_scan_x
Definition: ctu.h:156
ReconstructedArea
Definition: ctu.h:349
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
add_residual
static void add_residual(const VVCLocalContext *lc, TransformUnit *tu, const int target_ch_type)
Definition: intra.c:523
add_tu_area
static void add_tu_area(const TransformUnit *tu, int *x0, int *y0, int *w, int *h)
Definition: intra.c:191
TransformBlock::max_scan_y
int max_scan_y
Definition: ctu.h:155
VVCLocalContext::ras
ReconstructedArea ras[2][MAX_PARTS_IN_CTU]
Definition: ctu.h:430
ff_vvc_channel_range
void ff_vvc_channel_range(int *start, int *end, const VVCTreeType tree_type, const uint8_t chroma_format_idc)
Definition: ctu.c:2900
TransformBlock::max_scan_x
int max_scan_x
Definition: ctu.h:154
av_image_copy_plane
void av_image_copy_plane(uint8_t *dst, int dst_linesize, const uint8_t *src, int src_linesize, int bytewidth, int height)
Copy image plane from src to dst.
Definition: imgutils.c:374
div6
static const uint8_t div6[63+8 *6+1]
Definition: intra.c:323
JCBCR
#define JCBCR
Definition: dec.h:39
VVCFrameParamSets::sps
const VVCSPS * sps
RefStruct reference.
Definition: ps.h:230
VVCFrameParamSets
Definition: ps.h:229
u
#define u(width, name, range_min, range_max)
Definition: cbs_apv.c:83
VVCLocalContext::fc
VVCFrameContext * fc
Definition: ctu.h:446
PredictionUnit
Definition: hevcdec.h:325
CodingUnit::apply_lfnst_flag
int apply_lfnst_flag[VVC_MAX_SAMPLE_ARRAYS]
ApplyLfnstFlag[].
Definition: ctu.h:327
TransformBlock::c_idx
uint8_t c_idx
Definition: ctu.h:144
CodingUnit::sbt_pos_flag
uint8_t sbt_pos_flag
Definition: ctu.h:300
IBC_POS
#define IBC_POS(c_idx, x, y)
Definition: intra.c:601
TransformBlock::x0
int x0
Definition: ctu.h:146
VVCFrameParamSets::sl
const VVCScalingList * sl
RefStruct reference.
Definition: ps.h:235
ISP_VER_SPLIT
@ ISP_VER_SPLIT
Definition: ctu.h:122
CodingUnit::cb_width
int cb_width
Definition: ctu.h:291
get_chroma_predict_unit
static int get_chroma_predict_unit(const CodingUnit *cu, const TransformUnit *tu, const int idx, int *x0, int *y0, int *w, int *h)
Definition: intra.c:211
CodingUnit::pu
PredictionUnit pu
Definition: ctu.h:338
H266RawSPS::sps_chroma_format_idc
uint8_t sps_chroma_format_idc
Definition: cbs_h266.h:314
FF_ARRAY_ELEMS
#define FF_ARRAY_ELEMS(a)
Definition: sinewin_tablegen.c:29
TransformBlock::y0
int y0
Definition: ctu.h:147
TransformUnit::next
struct TransformUnit * next
RefStruct reference.
Definition: ctu.h:186
derive_scale
static av_always_inline int derive_scale(const TransformBlock *tb, const int sh_dep_quant_used_flag)
Definition: intra.c:337
reconstruct
static int reconstruct(VVCLocalContext *lc)
Definition: intra.c:583
fc
#define fc(width, name, range_min, range_max)
Definition: cbs_av1.c:493
av_assert0
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Definition: avassert.h:41
VVCSH
Definition: ps.h:238
POS
#define POS(c_idx, x, y)
Definition: intra.c:30
CodingUnit::tree_type
VVCTreeType tree_type
Definition: ctu.h:288
VVCFrameParamSets::ph
VVCPH ph
Definition: ps.h:232
CodingUnit::mts_idx
MtsIdx mts_idx
Definition: ctu.h:303
TransformUnit::coded_flag
uint8_t coded_flag[VVC_MAX_SAMPLE_ARRAYS]
tu_y_coded_flag, tu_cb_coded_flag, tu_cr_coded_flag
Definition: ctu.h:182
VVCLocalContext::num_ras
int num_ras[2]
Definition: ctu.h:431
ff_vvc_default_scale_m
uint8_t ff_vvc_default_scale_m[64 *64]
Definition: data.c:1641
VVCFrameContext::log_ctx
void * log_ctx
Definition: dec.h:123
ilfnst_transform
static void ilfnst_transform(const VVCLocalContext *lc, TransformBlock *tb)
Definition: intra.c:70
H266RawSliceHeader::sh_lmcs_used_flag
uint8_t sh_lmcs_used_flag
Definition: cbs_h266.h:794
H266RawSPS
Definition: cbs_h266.h:308
DCT_A
#define DCT_A
Definition: intra.c:426
ff_vvc_palette_derive_scale
int ff_vvc_palette_derive_scale(VVCLocalContext *lc, const TransformUnit *tu, TransformBlock *tb)
Definition: intra.c:672
CodingUnit::sbt_flag
uint8_t sbt_flag
Definition: ctu.h:298
inter.h
VVCTreeType
VVCTreeType
Definition: ctu.h:167
av_clip_intp2
#define av_clip_intp2
Definition: common.h:121
TransformBlock::rect_non_ts_flag
int rect_non_ts_flag
Definition: ctu.h:160
tmp
static uint8_t tmp[20]
Definition: aes_ctr.c:47
VVCLocalContext
Definition: ctu.h:384
VVCFrameContext::vvcdsp
VVCDSPContext vvcdsp
Definition: dec.h:140
lmcs_scale_chroma
static void lmcs_scale_chroma(VVCLocalContext *lc, TransformUnit *tu, TransformBlock *tb, const int target_ch_type)
Definition: intra.c:495
H266RawSliceHeader::sh_dep_quant_used_flag
uint8_t sh_dep_quant_used_flag
Definition: cbs_h266.h:824
TransformBlock::log2_tb_width
int log2_tb_width
Definition: ctu.h:151
transform_bdpcm
static void transform_bdpcm(TransformBlock *tb, const VVCLocalContext *lc, const CodingUnit *cu)
Definition: intra.c:482
L0
#define L0
Definition: hevcdec.h:58
itransform
static void itransform(VVCLocalContext *lc, TransformUnit *tu, const int target_ch_type)
Definition: intra.c:542
Mv::x
int16_t x
horizontal component of motion vector
Definition: hevcdec.h:306
VVCPH::r
const H266RawPictureHeader * r
Definition: ps.h:148
VVCItxDSPContext::transform_bdpcm
void(* transform_bdpcm)(int *coeffs, int width, int height, int vertical, int log2_transform_range)
Definition: dsp.h:128
ff_vvc_diag_scan_y
const uint8_t ff_vvc_diag_scan_y[5][5][16 *16]
Definition: data.c:152
SAMPLE_CTB
#define SAMPLE_CTB(tab, x, y)
Definition: hevcdec.h:74
TransformUnit
Definition: hevcdec.h:335
DUAL_TREE_LUMA
@ DUAL_TREE_LUMA
Definition: ctu.h:169
derive_qp
static void derive_qp(const VVCLocalContext *lc, const TransformUnit *tu, TransformBlock *tb)
Definition: intra.c:286
TransformBlock::bd_offset
int bd_offset
Definition: ctu.h:162
ff_vvc_decode_neighbour
void ff_vvc_decode_neighbour(VVCLocalContext *lc, const int x_ctb, const int y_ctb, const int rx, const int ry, const int rs)
Definition: ctu.c:2816
VVCScalingList
Definition: ps.h:196
TransformBlock::tb_height
int tb_height
Definition: ctu.h:150
TransformBlock::ts
uint8_t ts
transform_skip_flag
Definition: ctu.h:145
dc
Tag MUST be and< 10hcoeff half pel interpolation filter coefficients, hcoeff[0] are the 2 middle coefficients[1] are the next outer ones and so on, resulting in a filter like:...eff[2], hcoeff[1], hcoeff[0], hcoeff[0], hcoeff[1], hcoeff[2] ... the sign of the coefficients is not explicitly stored but alternates after each coeff and coeff[0] is positive, so ...,+,-,+,-,+,+,-,+,-,+,... hcoeff[0] is not explicitly stored but found by subtracting the sum of all stored coefficients with signs from 32 hcoeff[0]=32 - hcoeff[1] - hcoeff[2] - ... a good choice for hcoeff and htaps is htaps=6 hcoeff={40,-10, 2} an alternative which requires more computations at both encoder and decoder side and may or may not be better is htaps=8 hcoeff={42,-14, 6,-2}ref_frames minimum of the number of available reference frames and max_ref_frames for example the first frame after a key frame always has ref_frames=1spatial_decomposition_type wavelet type 0 is a 9/7 symmetric compact integer wavelet 1 is a 5/3 symmetric compact integer wavelet others are reserved stored as delta from last, last is reset to 0 if always_reset||keyframeqlog quality(logarithmic quantizer scale) stored as delta from last, last is reset to 0 if always_reset||keyframemv_scale stored as delta from last, last is reset to 0 if always_reset||keyframe FIXME check that everything works fine if this changes between framesqbias dequantization bias stored as delta from last, last is reset to 0 if always_reset||keyframeblock_max_depth maximum depth of the block tree stored as delta from last, last is reset to 0 if always_reset||keyframequant_table quantization tableHighlevel bitstream structure:==============================--------------------------------------------|Header|--------------------------------------------|------------------------------------|||Block0||||split?||||yes no||||......... intra?||||:Block01 :yes no||||:Block02 :....... ..........||||:Block03 ::y DC ::ref index:||||:Block04 ::cb DC ::motion x :||||......... :cr DC ::motion y :||||....... ..........|||------------------------------------||------------------------------------|||Block1|||...|--------------------------------------------|------------ ------------ ------------|||Y subbands||Cb subbands||Cr subbands||||--- ---||--- ---||--- ---|||||LL0||HL0||||LL0||HL0||||LL0||HL0|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||LH0||HH0||||LH0||HH0||||LH0||HH0|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||HL1||LH1||||HL1||LH1||||HL1||LH1|||||--- ---||--- ---||--- ---||||--- ---||--- ---||--- ---|||||HH1||HL2||||HH1||HL2||||HH1||HL2|||||...||...||...|||------------ ------------ ------------|--------------------------------------------Decoding process:=================------------|||Subbands|------------||||------------|Intra DC||||LL0 subband prediction ------------|\ Dequantization ------------------- \||Reference frames|\ IDWT|------- -------|Motion \|||Frame 0||Frame 1||Compensation . OBMC v -------|------- -------|--------------. \------> Frame n output Frame Frame<----------------------------------/|...|------------------- Range Coder:============Binary Range Coder:------------------- The implemented range coder is an adapted version based upon "Range encoding: an algorithm for removing redundancy from a digitised message." by G. N. N. Martin. The symbols encoded by the Snow range coder are bits(0|1). The associated probabilities are not fix but change depending on the symbol mix seen so far. bit seen|new state ---------+----------------------------------------------- 0|256 - state_transition_table[256 - old_state];1|state_transition_table[old_state];state_transition_table={ 0, 0, 0, 0, 0, 0, 0, 0, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 190, 191, 192, 194, 194, 195, 196, 197, 198, 199, 200, 201, 202, 202, 204, 205, 206, 207, 208, 209, 209, 210, 211, 212, 213, 215, 215, 216, 217, 218, 219, 220, 220, 222, 223, 224, 225, 226, 227, 227, 229, 229, 230, 231, 232, 234, 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, 248, 248, 0, 0, 0, 0, 0, 0, 0};FIXME Range Coding of integers:------------------------- FIXME Neighboring Blocks:===================left and top are set to the respective blocks unless they are outside of the image in which case they are set to the Null block top-left is set to the top left block unless it is outside of the image in which case it is set to the left block if this block has no larger parent block or it is at the left side of its parent block and the top right block is not outside of the image then the top right block is used for top-right else the top-left block is used Null block y, cb, cr are 128 level, ref, mx and my are 0 Motion Vector Prediction:=========================1. the motion vectors of all the neighboring blocks are scaled to compensate for the difference of reference frames scaled_mv=(mv *(256 *(current_reference+1)/(mv.reference+1))+128)> the median of the scaled top and top right vectors is used as motion vector prediction the used motion vector is the sum of the predictor and(mvx_diff, mvy_diff) *mv_scale Intra DC Prediction block[y][x] dc[1]
Definition: snow.txt:400
IBC_Y
#define IBC_Y(y)
Definition: intra.c:605
CodingUnit::intra_pred_mode_y
IntraPredMode intra_pred_mode_y
IntraPredModeY.
Definition: ctu.h:321
shift
static int shift(int a, int b)
Definition: bonk.c:261
dst
uint8_t ptrdiff_t const uint8_t ptrdiff_t int intptr_t intptr_t int int16_t * dst
Definition: dsp.h:87
derive_transform_type
static void derive_transform_type(const VVCFrameContext *fc, const VVCLocalContext *lc, const TransformBlock *tb, enum VVCTxType *trh, enum VVCTxType *trv)
Definition: intra.c:135
INTRA_PLANAR
@ INTRA_PLANAR
Definition: hevcdec.h:127
size
int size
Definition: twinvq_data.h:10344
CodingUnit::sbt_horizontal_flag
uint8_t sbt_horizontal_flag
Definition: ctu.h:299
intra.h
H266RawPictureHeader::ph_scaling_list_aps_id
uint8_t ph_scaling_list_aps_id
Definition: cbs_h266.h:704
frame.h
CodingUnit::coded_flag
uint8_t coded_flag
Definition: ctu.h:296
a
The reader does not expect b to be semantically here and if the code is changed by maybe adding a a division or other the signedness will almost certainly be mistaken To avoid this confusion a new type was SUINT is the C unsigned type but it holds a signed int to use the same example SUINT a
Definition: undefined.txt:41
CodingUnit::lfnst_idx
int lfnst_idx
Definition: ctu.h:302
VVCScalingList::scaling_matrix_dc_rec
uint8_t scaling_matrix_dc_rec[SL_MAX_ID - SL_START_16x16]
ScalingMatrixDcRec[refId − 14].
Definition: ps.h:198
add_reconstructed_area
static int add_reconstructed_area(VVCLocalContext *lc, const int ch_type, const int x0, const int y0, const int w, const int h)
Definition: intra.c:171
ff_vvc_predict_ciip
void ff_vvc_predict_ciip(VVCLocalContext *lc)
CIIP(Combined Inter-Intra Prediction) for a coding block.
Definition: inter.c:1018
CodingUnit::intra_pred_mode_c
IntraPredMode intra_pred_mode_c
IntraPredModeC.
Definition: ctu.h:322
itx_1d.h
dequant
static void dequant(const VVCLocalContext *lc, const TransformUnit *tu, TransformBlock *tb)
Definition: intra.c:403
H266RawSliceHeader
Definition: cbs_h266.h:771
PredictionUnit::mi
MotionInfo mi
Definition: ctu.h:271
MODE_INTRA
#define MODE_INTRA
Definition: vp3.c:84
CR
#define CR
Definition: filter.c:33
MODE_PLT
@ MODE_PLT
Definition: ctu.h:193
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:256
ISP_NO_SPLIT
@ ISP_NO_SPLIT
Definition: ctu.h:120
ff_vvc_diag_scan_x
const uint8_t ff_vvc_diag_scan_x[5][5][16 *16]
Definition: data.c:27
rem6
static const uint8_t rem6[63+8 *6+1]
Definition: intra.c:315
MIN_ISP_PRED_WIDTH
#define MIN_ISP_PRED_WIDTH
Definition: intra.c:199
av_always_inline
#define av_always_inline
Definition: attributes.h:49
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
CodingUnit::x0
int x0
Definition: ctu.h:289
TransformUnit::tbs
TransformBlock tbs[VVC_MAX_SAMPLE_ARRAYS]
Definition: ctu.h:184
TransformBlock::coeffs
int * coeffs
Definition: ctu.h:164
TransformBlock::bd_shift
int bd_shift
Definition: ctu.h:161
itx_2d
static void itx_2d(const VVCFrameContext *fc, TransformBlock *tb, const enum VVCTxType trh, const enum VVCTxType trv)
Definition: intra.c:427
TransformUnit::width
int width
Definition: ctu.h:176
VVCLocalContext::cu
CodingUnit * cu
Definition: ctu.h:429
ff_vvc_wide_angle_mode_mapping
int ff_vvc_wide_angle_mode_mapping(const CodingUnit *cu, int tb_width, int tb_height, int c_idx, int pred_mode_intra)
Definition: intra_utils.c:197
stride
#define stride
Definition: h264pred_template.c:536
INTRA_VERT
@ INTRA_VERT
Definition: ctu.h:237
ret
ret
Definition: filter_design.txt:187
IntraPredMode
IntraPredMode
Definition: hevcdec.h:126
CHROMA
@ CHROMA
Definition: vf_waveform.c:49
sps
static int FUNC() sps(CodedBitstreamContext *ctx, RWContext *rw, H264RawSPS *current)
Definition: cbs_h264_syntax_template.c:260
id
enum AVCodecID id
Definition: dts2pts.c:367
CodingUnit::cb_height
int cb_height
Definition: ctu.h:292
TransformBlock::log2_tb_height
int log2_tb_height
Definition: ctu.h:152
ff_vvc_set_neighbour_available
void ff_vvc_set_neighbour_available(VVCLocalContext *lc, const int x0, const int y0, const int w, const int h)
Definition: ctu.c:2849
DUAL_TREE_CHROMA
@ DUAL_TREE_CHROMA
Definition: ctu.h:170
TransformBlock::has_coeffs
uint8_t has_coeffs
Definition: ctu.h:143
INTRA_L_CCLM
@ INTRA_L_CCLM
Definition: ctu.h:240
TransformBlock
Definition: ctu.h:142
CodingUnit::pred_mode
enum PredMode pred_mode
PredMode.
Definition: hevcdec.h:296
ff_vvc_inv_lfnst_1d
void ff_vvc_inv_lfnst_1d(int *v, const int *u, int no_zero_size, int n_tr_s, int pred_mode_intra, int lfnst_idx, int log2_transform_range)
Definition: itx_1d.c:695
intra_block_copy
static void intra_block_copy(const VVCLocalContext *lc, const int c_idx)
Definition: intra.c:607
TransformUnit::y0
int y0
Definition: ctu.h:175
CodingUnit::next
struct CodingUnit * next
RefStruct reference.
Definition: ctu.h:340
Mv
Definition: hevcdec.h:305
VVCFrameContext::ps
VVCFrameParamSets ps
Definition: dec.h:131
VVCLocalContext::x_vpdu
int x_vpdu
Definition: ctu.h:425
SINGLE_TREE
@ SINGLE_TREE
Definition: ctu.h:168
scale
static void scale(int *out, const int *in, const int w, const int h, const int shift)
Definition: intra.c:273
VVCLocalContext::y_vpdu
int y_vpdu
Definition: ctu.h:426
VVCSPS::r
const H266RawSPS * r
RefStruct reference.
Definition: ps.h:59
SliceContext::sh
VVCSH sh
Definition: dec.h:115
TransformBlock::qp
int qp
Definition: ctu.h:159
CodingUnit::isp_split_type
enum IspType isp_split_type
IntraSubPartitionsSplitType.
Definition: ctu.h:315
VVCFrameContext
Definition: dec.h:122
VVCTxType
VVCTxType
Definition: dsp.h:30
imgutils.h
VVC_DST7
@ VVC_DST7
Definition: dsp.h:32
coeff
static const double coeff[2][5]
Definition: vf_owdenoise.c:80
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:27
vvc_predict_palette
static void vvc_predict_palette(VVCLocalContext *lc)
Definition: intra.c:684
MAX_TB_SIZE
#define MAX_TB_SIZE
Definition: hevcdec.h:49
AVERROR_INVALIDDATA
#define AVERROR_INVALIDDATA
Invalid data found when processing input.
Definition: error.h:61
TransformUnit::joint_cbcr_residual_flag
uint8_t joint_cbcr_residual_flag
tu_joint_cbcr_residual_flag
Definition: ctu.h:180
h
h
Definition: vp9dsp_template.c:2070
ibc_fill_vir_buf
static void ibc_fill_vir_buf(const VVCLocalContext *lc, const CodingUnit *cu)
Definition: intra.c:649
transpose
#define transpose(x)
INTRA_LT_CCLM
@ INTRA_LT_CCLM
Definition: ctu.h:239
CodingUnit::ciip_flag
uint8_t ciip_flag
Definition: ctu.h:312
SL_START_16x16
@ SL_START_16x16
Definition: ps.h:188
IBC_X
#define IBC_X(x)
Definition: intra.c:604
src
#define src
Definition: vp8dsp.c:248
CodingUnit::num_intra_subpartitions
int num_intra_subpartitions
Definition: ctu.h:319
VVCLocalContext::lmcs
struct VVCLocalContext::@323 lmcs
VVCScalingList::scaling_matrix_rec
uint8_t scaling_matrix_rec[SL_MAX_ID][SL_MAX_MATRIX_SIZE *SL_MAX_MATRIX_SIZE]
ScalingMatrixRec.
Definition: ps.h:197
CodingUnit::y0
int y0
Definition: ctu.h:290
CodingUnit::qp
int8_t qp[4]
QpY, Qp′Cb, Qp′Cr, Qp′CbCr.
Definition: ctu.h:334
derive_scale_m
static const uint8_t * derive_scale_m(const VVCLocalContext *lc, const TransformBlock *tb, uint8_t *scale_m)
Definition: intra.c:346
is_cclm
static int is_cclm(enum IntraPredMode mode)
Definition: intra.c:34
ff_vvc_ctu_free_cus
void ff_vvc_ctu_free_cus(CodingUnit **cus)
Definition: ctu.c:2864
CodingUnit::tus
struct CodingUnit::@321 tus