FFmpeg
vvcdec.c
Go to the documentation of this file.
1 /*
2  * VVC video decoder
3  *
4  * Copyright (C) 2021 Nuo Mi
5  * Copyright (C) 2022 Xu Mu
6  *
7  * This file is part of FFmpeg.
8  *
9  * FFmpeg is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2.1 of the License, or (at your option) any later version.
13  *
14  * FFmpeg is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with FFmpeg; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22  */
24 #include "libavcodec/decode.h"
25 #include "libavcodec/profiles.h"
26 #include "libavcodec/refstruct.h"
27 #include "libavutil/cpu.h"
28 #include "libavutil/mem.h"
29 #include "libavutil/thread.h"
30 
31 #include "vvcdec.h"
32 #include "vvc_ctu.h"
33 #include "vvc_data.h"
34 #include "vvc_refs.h"
35 #include "vvc_thread.h"
36 
37 #define TAB_MAX 32
38 
39 typedef struct Tab {
40  void **tab;
41  size_t size;
42 } Tab;
43 
44 typedef struct TabList {
46  int nb_tabs;
47 
48  int zero;
49  int realloc;
50 } TabList;
51 
52 #define TL_ADD(t, s) do { \
53  av_assert0(l->nb_tabs < TAB_MAX); \
54  l->tabs[l->nb_tabs].tab = (void**)&fc->tab.t; \
55  l->tabs[l->nb_tabs].size = sizeof(*fc->tab.t) * (s); \
56  l->nb_tabs++; \
57 } while (0)
58 
59 static void tl_init(TabList *l, const int zero, const int realloc)
60 {
61  l->nb_tabs = 0;
62  l->zero = zero;
63  l->realloc = realloc;
64 }
65 
66 static int tl_free(TabList *l)
67 {
68  for (int i = 0; i < l->nb_tabs; i++)
69  av_freep(l->tabs[i].tab);
70 
71  return 0;
72 }
73 
74 static int tl_create(TabList *l)
75 {
76  if (l->realloc) {
77  tl_free(l);
78 
79  for (int i = 0; i < l->nb_tabs; i++) {
80  Tab *t = l->tabs + i;
81  *t->tab = l->zero ? av_mallocz(t->size) : av_malloc(t->size);
82  if (!*t->tab)
83  return AVERROR(ENOMEM);
84  }
85  } else if (l->zero) {
86  for (int i = 0; i < l->nb_tabs; i++) {
87  Tab *t = l->tabs + i;
88  memset(*t->tab, 0, t->size);
89  }
90  }
91  return 0;
92 }
93 
95 {
96  const VVCPPS *pps = fc->ps.pps;
97  const int ctu_count = pps ? pps->ctb_count : 0;
98  const int changed = fc->tab.sz.ctu_count != ctu_count;
99 
100  tl_init(l, 1, changed);
101 
102  TL_ADD(deblock, ctu_count);
103  TL_ADD(sao, ctu_count);
104  TL_ADD(alf, ctu_count);
105  TL_ADD(ctus, ctu_count);
106 }
107 
109 {
110  const VVCSPS *sps = fc->ps.sps;
111  const VVCPPS *pps = fc->ps.pps;
112  const int ctu_size = sps ? (1 << sps->ctb_log2_size_y << sps->ctb_log2_size_y) : 0;
113  const int ctu_count = pps ? pps->ctb_count : 0;
114  const int changed = fc->tab.sz.ctu_count != ctu_count || fc->tab.sz.ctu_size != ctu_size;
115 
116  tl_init(l, 0, changed);
117  TL_ADD(slice_idx, ctu_count);
118  TL_ADD(coeffs, ctu_count * ctu_size * VVC_MAX_SAMPLE_ARRAYS);
119 }
120 
122 {
123  const VVCPPS *pps = fc->ps.pps;
124  const int pic_size_in_min_cb = pps ? pps->min_cb_width * pps->min_cb_height : 0;
125  const int changed = fc->tab.sz.pic_size_in_min_cb != pic_size_in_min_cb;
126 
127  tl_init(l, 1, changed);
128 
129  TL_ADD(skip, pic_size_in_min_cb);
130  TL_ADD(imf, pic_size_in_min_cb);
131  TL_ADD(imtf, pic_size_in_min_cb);
132  TL_ADD(imm, pic_size_in_min_cb);
133  TL_ADD(ipm, pic_size_in_min_cb);
134 
135  for (int i = LUMA; i <= CHROMA; i++) {
136  TL_ADD(cb_pos_x[i], pic_size_in_min_cb);
137  TL_ADD(cb_pos_y[i], pic_size_in_min_cb);
138  TL_ADD(cb_width[i], pic_size_in_min_cb);
139  TL_ADD(cb_height[i], pic_size_in_min_cb);
140  TL_ADD(cqt_depth[i], pic_size_in_min_cb);
141  TL_ADD(cpm[i], pic_size_in_min_cb);
142  TL_ADD(cp_mv[i], pic_size_in_min_cb * MAX_CONTROL_POINTS);
143  };
144 }
145 
147 {
148  const VVCPPS *pps = fc->ps.pps;
149  const int pic_size_in_min_pu = pps ? pps->min_pu_width * pps->min_pu_height : 0;
150  const int changed = fc->tab.sz.pic_size_in_min_pu != pic_size_in_min_pu;
151 
152  tl_init(l, 1, changed);
153 
154  TL_ADD(msf, pic_size_in_min_pu);
155  TL_ADD(iaf, pic_size_in_min_pu);
156  TL_ADD(mmi, pic_size_in_min_pu);
157  TL_ADD(mvf, pic_size_in_min_pu);
158 }
159 
161 {
162  const VVCPPS *pps = fc->ps.pps;
163  const int pic_size_in_min_tu = pps ? pps->min_tu_width * pps->min_tu_height : 0;
164  const int changed = fc->tab.sz.pic_size_in_min_tu != pic_size_in_min_tu;
165 
166  tl_init(l, 1, changed);
167 
168  TL_ADD(tu_joint_cbcr_residual_flag, pic_size_in_min_tu);
169  for (int i = LUMA; i <= CHROMA; i++) {
170  TL_ADD(tb_pos_x0[i], pic_size_in_min_tu);
171  TL_ADD(tb_pos_y0[i], pic_size_in_min_tu);
172  TL_ADD(tb_width[i], pic_size_in_min_tu);
173  TL_ADD(tb_height[i], pic_size_in_min_tu);
174  TL_ADD(pcmf[i], pic_size_in_min_tu);
175  }
176 
177  for (int i = 0; i < VVC_MAX_SAMPLE_ARRAYS; i++) {
178  TL_ADD(tu_coded_flag[i], pic_size_in_min_tu);
179  TL_ADD(qp[i], pic_size_in_min_tu);
180  }
181 }
182 
184 {
185  const VVCPPS *pps = fc->ps.pps;
186  const int bs_width = pps ? (pps->width >> 2) + 1 : 0;
187  const int bs_height = pps ? (pps->height >> 2) + 1 : 0;
188  const int bs_count = bs_width * bs_height;
189  const int changed = fc->tab.sz.bs_width != bs_width ||
190  fc->tab.sz.bs_height != bs_height;
191 
192  tl_init(l, 1, changed);
193 
194  for (int i = 0; i < VVC_MAX_SAMPLE_ARRAYS; i++) {
195  TL_ADD(horizontal_bs[i], bs_count);
196  TL_ADD(vertical_bs[i], bs_count);
197  }
198  TL_ADD(horizontal_q, bs_count);
199  TL_ADD(horizontal_p, bs_count);
200  TL_ADD(vertical_p, bs_count);
201  TL_ADD(vertical_q, bs_count);
202 }
203 
205 {
206  const VVCSPS *sps = fc->ps.sps;
207  const VVCPPS *pps = fc->ps.pps;
208  const int width = pps ? pps->width : 0;
209  const int height = pps ? pps->height : 0;
210  const int ctu_width = pps ? pps->ctb_width : 0;
211  const int ctu_height = pps ? pps->ctb_height : 0;
212  const int chroma_idc = sps ? sps->r->sps_chroma_format_idc : 0;
213  const int ps = sps ? sps->pixel_shift : 0;
214  const int c_end = chroma_idc ? VVC_MAX_SAMPLE_ARRAYS : 1;
215  const int changed = fc->tab.sz.chroma_format_idc != chroma_idc ||
216  fc->tab.sz.width != width || fc->tab.sz.height != height ||
217  fc->tab.sz.ctu_width != ctu_width || fc->tab.sz.ctu_height != ctu_height;
218 
219  tl_init(l, 0, changed);
220 
221  for (int c_idx = 0; c_idx < c_end; c_idx++) {
222  const int w = width >> (sps ? sps->hshift[c_idx] : 0);
223  const int h = height >> (sps ? sps->vshift[c_idx] : 0);
224  TL_ADD(sao_pixel_buffer_h[c_idx], (w * 2 * ctu_height) << ps);
225  TL_ADD(sao_pixel_buffer_v[c_idx], (h * 2 * ctu_width) << ps);
226  }
227 
228  for (int c_idx = 0; c_idx < c_end; c_idx++) {
229  const int w = width >> (sps ? sps->hshift[c_idx] : 0);
230  const int h = height >> (sps ? sps->vshift[c_idx] : 0);
231  const int border_pixels = c_idx ? ALF_BORDER_CHROMA : ALF_BORDER_LUMA;
232  for (int i = 0; i < 2; i++) {
233  TL_ADD(alf_pixel_buffer_h[c_idx][i], (w * border_pixels * ctu_height) << ps);
234  TL_ADD(alf_pixel_buffer_v[c_idx][i], h * ALF_PADDING_SIZE * ctu_width);
235  }
236  }
237 }
238 
240 {
241  const VVCPPS *pps = fc->ps.pps;
242  const int w32 = pps ? AV_CEIL_RSHIFT(pps->width, 5) : 0;
243  const int h32 = pps ? AV_CEIL_RSHIFT(pps->height, 5) : 0;
244  const int changed = AV_CEIL_RSHIFT(fc->tab.sz.width, 5) != w32 ||
245  AV_CEIL_RSHIFT(fc->tab.sz.height, 5) != h32;
246 
247  tl_init(l, 1, changed);
248 
249  for (int i = LUMA; i <= CHROMA; i++)
250  TL_ADD(msm[i], w32 * h32);
251 }
252 
254 {
255  const VVCPPS *pps = fc->ps.pps;
256  const int w64 = pps ? AV_CEIL_RSHIFT(pps->width, 6) : 0;
257  const int h64 = pps ? AV_CEIL_RSHIFT(pps->height, 6) : 0;
258  const int changed = AV_CEIL_RSHIFT(fc->tab.sz.width, 6) != w64 ||
259  AV_CEIL_RSHIFT(fc->tab.sz.height, 6) != h64;
260 
261  tl_init(l, 1, changed);
262 
263  TL_ADD(ispmf, w64 * h64);
264 }
265 
267 {
268  const VVCSPS *sps = fc->ps.sps;
269  const VVCPPS *pps = fc->ps.pps;
270  const int ctu_height = pps ? pps->ctb_height : 0;
271  const int ctu_size = sps ? sps->ctb_size_y : 0;
272  const int ps = sps ? sps->pixel_shift : 0;
273  const int chroma_idc = sps ? sps->r->sps_chroma_format_idc : 0;
274  const int has_ibc = sps ? sps->r->sps_ibc_enabled_flag : 0;
275  const int changed = fc->tab.sz.chroma_format_idc != chroma_idc ||
276  fc->tab.sz.ctu_height != ctu_height ||
277  fc->tab.sz.ctu_size != ctu_size ||
278  fc->tab.sz.pixel_shift != ps;
279 
280  fc->tab.sz.ibc_buffer_width = ctu_size ? 2 * MAX_CTU_SIZE * MAX_CTU_SIZE / ctu_size : 0;
281 
282  tl_init(l, has_ibc, changed);
283 
284  for (int i = LUMA; i < VVC_MAX_SAMPLE_ARRAYS; i++) {
285  const int hs = sps ? sps->hshift[i] : 0;
286  const int vs = sps ? sps->vshift[i] : 0;
287  TL_ADD(ibc_vir_buf[i], fc->tab.sz.ibc_buffer_width * ctu_size * ctu_height << ps >> hs >> vs);
288  }
289 }
290 
291 typedef void (*tl_init_fn)(TabList *l, VVCFrameContext *fc);
292 
293 static int frame_context_for_each_tl(VVCFrameContext *fc, int (*unary_fn)(TabList *l))
294 {
295  const tl_init_fn init[] = {
296  ctu_tl_init,
301  bs_tl_init,
303  msm_tl_init,
305  ibc_tl_init,
306  };
307 
308  for (int i = 0; i < FF_ARRAY_ELEMS(init); i++) {
309  TabList l;
310  int ret;
311 
312  init[i](&l, fc);
313  ret = unary_fn(&l);
314  if (ret < 0)
315  return ret;
316  }
317  return 0;
318 }
319 
321 {
322  if (fc->tab.ctus) {
323  for (int i = 0; i < fc->tab.sz.ctu_count; i++)
324  ff_vvc_ctu_free_cus(fc->tab.ctus + i);
325  }
326 }
327 
329 {
330  free_cus(fc);
332  ff_refstruct_pool_uninit(&fc->rpl_tab_pool);
333  ff_refstruct_pool_uninit(&fc->tab_dmvr_mvf_pool);
334 
335  memset(&fc->tab.sz, 0, sizeof(fc->tab.sz));
336 }
337 
339 {
340  const VVCSPS *sps = fc->ps.sps;
341  const VVCPPS *pps = fc->ps.pps;
342  const int ctu_count = pps->ctb_count;
343  const int pic_size_in_min_pu = pps->min_pu_width * pps->min_pu_height;
344  int ret;
345 
346  free_cus(fc);
347 
349  if (ret < 0)
350  return ret;
351 
352  memset(fc->tab.slice_idx, -1, sizeof(*fc->tab.slice_idx) * ctu_count);
353 
354  if (fc->tab.sz.ctu_count != ctu_count) {
355  ff_refstruct_pool_uninit(&fc->rpl_tab_pool);
356  fc->rpl_tab_pool = ff_refstruct_pool_alloc(ctu_count * sizeof(RefPicListTab), 0);
357  if (!fc->rpl_tab_pool)
358  return AVERROR(ENOMEM);
359  }
360 
361  if (fc->tab.sz.pic_size_in_min_pu != pic_size_in_min_pu) {
362  ff_refstruct_pool_uninit(&fc->tab_dmvr_mvf_pool);
363  fc->tab_dmvr_mvf_pool = ff_refstruct_pool_alloc(
364  pic_size_in_min_pu * sizeof(MvField), FF_REFSTRUCT_POOL_FLAG_ZERO_EVERY_TIME);
365  if (!fc->tab_dmvr_mvf_pool)
366  return AVERROR(ENOMEM);
367  }
368 
369  fc->tab.sz.ctu_count = pps->ctb_count;
370  fc->tab.sz.ctu_size = 1 << sps->ctb_log2_size_y << sps->ctb_log2_size_y;
371  fc->tab.sz.pic_size_in_min_cb = pps->min_cb_width * pps->min_cb_height;
372  fc->tab.sz.pic_size_in_min_pu = pic_size_in_min_pu;
373  fc->tab.sz.pic_size_in_min_tu = pps->min_tu_width * pps->min_tu_height;
374  fc->tab.sz.width = pps->width;
375  fc->tab.sz.height = pps->height;
376  fc->tab.sz.ctu_width = pps->ctb_width;
377  fc->tab.sz.ctu_height = pps->ctb_height;
378  fc->tab.sz.chroma_format_idc = sps->r->sps_chroma_format_idc;
379  fc->tab.sz.pixel_shift = sps->pixel_shift;
380  fc->tab.sz.bs_width = (fc->ps.pps->width >> 2) + 1;
381  fc->tab.sz.bs_height = (fc->ps.pps->height >> 2) + 1;
382 
383  return 0;
384 }
385 
386 static int min_positive(const int idx, const int diff, const int min_diff)
387 {
388  return diff > 0 && (idx < 0 || diff < min_diff);
389 }
390 
391 static int max_negtive(const int idx, const int diff, const int max_diff)
392 {
393  return diff < 0 && (idx < 0 || diff > max_diff);
394 }
395 
396 typedef int (*smvd_find_fxn)(const int idx, const int diff, const int old_diff);
397 
398 static int8_t smvd_find(const VVCFrameContext *fc, const SliceContext *sc, int lx, smvd_find_fxn find)
399 {
400  const H266RawSliceHeader *rsh = sc->sh.r;
401  const RefPicList *rpl = sc->rpl + lx;
402  const int poc = fc->ref->poc;
403  int8_t idx = -1;
404  int old_diff = -1;
405  for (int i = 0; i < rsh->num_ref_idx_active[lx]; i++) {
406  if (!rpl->isLongTerm[i]) {
407  int diff = poc - rpl->list[i];
408  if (find(idx, diff, old_diff)) {
409  idx = i;
410  old_diff = diff;
411  }
412  }
413  }
414  return idx;
415 }
416 
417 static void smvd_ref_idx(const VVCFrameContext *fc, SliceContext *sc)
418 {
419  VVCSH *sh = &sc->sh;
420  if (IS_B(sh->r)) {
421  sh->ref_idx_sym[0] = smvd_find(fc, sc, 0, min_positive);
422  sh->ref_idx_sym[1] = smvd_find(fc, sc, 1, max_negtive);
423  if (sh->ref_idx_sym[0] == -1 || sh->ref_idx_sym[1] == -1) {
424  sh->ref_idx_sym[0] = smvd_find(fc, sc, 0, max_negtive);
425  sh->ref_idx_sym[1] = smvd_find(fc, sc, 1, min_positive);
426  }
427  }
428 }
429 
430 static void eps_free(SliceContext *slice)
431 {
432  av_freep(&slice->eps);
433  slice->nb_eps = 0;
434 }
435 
437 {
438  if (fc->slices) {
439  for (int i = 0; i < fc->nb_slices_allocated; i++) {
440  SliceContext *slice = fc->slices[i];
441  if (slice) {
442  ff_refstruct_unref(&slice->ref);
443  ff_refstruct_unref(&slice->sh.r);
444  eps_free(slice);
445  av_free(slice);
446  }
447  }
448  av_freep(&fc->slices);
449  }
450  fc->nb_slices_allocated = 0;
451  fc->nb_slices = 0;
452 }
453 
455 {
456  void *p;
457  const int size = (fc->nb_slices_allocated + 1) * 3 / 2;
458 
459  if (fc->nb_slices < fc->nb_slices_allocated)
460  return 0;
461 
462  p = av_realloc_array(fc->slices, size, sizeof(*fc->slices));
463  if (!p)
464  return AVERROR(ENOMEM);
465 
466  fc->slices = p;
467  for (int i = fc->nb_slices_allocated; i < size; i++) {
468  fc->slices[i] = av_mallocz(sizeof(*fc->slices[0]));
469  if (!fc->slices[i]) {
470  fc->nb_slices_allocated = i;
471  return AVERROR(ENOMEM);
472  }
473  fc->slices[i]->slice_idx = i;
474  }
475  fc->nb_slices_allocated = size;
476 
477  return 0;
478 }
479 
480 static void ep_init_cabac_decoder(SliceContext *sc, const int index,
481  const H2645NAL *nal, GetBitContext *gb, const CodedBitstreamUnit *unit)
482 {
483  const H266RawSlice *slice = unit->content_ref;
484  const H266RawSliceHeader *rsh = sc->sh.r;
485  EntryPoint *ep = sc->eps + index;
486  int size;
487 
488  if (index < rsh->num_entry_points) {
489  int skipped = 0;
490  int64_t start = (gb->index >> 3);
491  int64_t end = start + rsh->sh_entry_point_offset_minus1[index] + 1;
492  while (skipped < nal->skipped_bytes && nal->skipped_bytes_pos[skipped] <= start + slice->header_size) {
493  skipped++;
494  }
495  while (skipped < nal->skipped_bytes && nal->skipped_bytes_pos[skipped] <= end + slice->header_size) {
496  end--;
497  skipped++;
498  }
499  size = end - start;
500  } else {
501  size = get_bits_left(gb) / 8;
502  }
503  ff_init_cabac_decoder (&ep->cc, gb->buffer + get_bits_count(gb) / 8, size);
504  skip_bits(gb, size * 8);
505 }
506 
508  VVCFrameContext *fc, const H2645NAL *nal, const CodedBitstreamUnit *unit)
509 {
510  const VVCSH *sh = &sc->sh;
511  const H266RawSlice *slice = unit->content_ref;
512  int nb_eps = sh->r->num_entry_points + 1;
513  int ctu_addr = 0;
514  GetBitContext gb;
515 
516  if (sc->nb_eps != nb_eps) {
517  eps_free(sc);
518  sc->eps = av_calloc(nb_eps, sizeof(*sc->eps));
519  if (!sc->eps)
520  return AVERROR(ENOMEM);
521  sc->nb_eps = nb_eps;
522  }
523 
524  init_get_bits8(&gb, slice->data, slice->data_size);
525  for (int i = 0; i < sc->nb_eps; i++)
526  {
527  EntryPoint *ep = sc->eps + i;
528 
529  ep->ctu_start = ctu_addr;
530  ep->ctu_end = (i + 1 == sc->nb_eps ? sh->num_ctus_in_curr_slice : sh->entry_point_start_ctu[i]);
531 
532  for (int j = ep->ctu_start; j < ep->ctu_end; j++) {
533  const int rs = sc->sh.ctb_addr_in_curr_slice[j];
534  fc->tab.slice_idx[rs] = sc->slice_idx;
535  }
536 
537  ep_init_cabac_decoder(sc, i, nal, &gb, unit);
538 
539  if (i + 1 < sc->nb_eps)
540  ctu_addr = sh->entry_point_start_ctu[i];
541  }
542 
543  return 0;
544 }
545 
547 {
548  const int size = s->nb_fcs;
549  const int idx = (fc - s->fcs + delta + size) % size;
550  return s->fcs + idx;
551 }
552 
553 static int ref_frame(VVCFrame *dst, const VVCFrame *src)
554 {
555  int ret;
556 
557  ret = av_frame_ref(dst->frame, src->frame);
558  if (ret < 0)
559  return ret;
560 
561  ff_refstruct_replace(&dst->progress, src->progress);
562 
563  ff_refstruct_replace(&dst->tab_dmvr_mvf, src->tab_dmvr_mvf);
564 
565  ff_refstruct_replace(&dst->rpl_tab, src->rpl_tab);
566  ff_refstruct_replace(&dst->rpl, src->rpl);
567  dst->nb_rpl_elems = src->nb_rpl_elems;
568 
569  dst->poc = src->poc;
570  dst->ctb_count = src->ctb_count;
571  dst->flags = src->flags;
572  dst->sequence = src->sequence;
573 
574  return 0;
575 }
576 
578 {
579  slices_free(fc);
580 
581  ff_refstruct_pool_uninit(&fc->tu_pool);
582  ff_refstruct_pool_uninit(&fc->cu_pool);
583 
584  for (int i = 0; i < FF_ARRAY_ELEMS(fc->DPB); i++) {
585  ff_vvc_unref_frame(fc, &fc->DPB[i], ~0);
586  av_frame_free(&fc->DPB[i].frame);
587  }
588 
591  av_frame_free(&fc->output_frame);
592  ff_vvc_frame_ps_free(&fc->ps);
593 }
594 
596 {
597 
598  fc->log_ctx = avctx;
599 
600  fc->output_frame = av_frame_alloc();
601  if (!fc->output_frame)
602  return AVERROR(ENOMEM);
603 
604  for (int j = 0; j < FF_ARRAY_ELEMS(fc->DPB); j++) {
605  fc->DPB[j].frame = av_frame_alloc();
606  if (!fc->DPB[j].frame)
607  return AVERROR(ENOMEM);
608  }
609  fc->cu_pool = ff_refstruct_pool_alloc(sizeof(CodingUnit), 0);
610  if (!fc->cu_pool)
611  return AVERROR(ENOMEM);
612 
613  fc->tu_pool = ff_refstruct_pool_alloc(sizeof(TransformUnit), 0);
614  if (!fc->tu_pool)
615  return AVERROR(ENOMEM);
616 
617  return 0;
618 }
619 
621 {
622  int ret;
623 
624  fc->ref = NULL;
625 
626  // copy refs from the last frame
627  if (s->nb_frames && s->nb_fcs > 1) {
628  VVCFrameContext *prev = get_frame_context(s, fc, -1);
629  for (int i = 0; i < FF_ARRAY_ELEMS(fc->DPB); i++) {
630  ff_vvc_unref_frame(fc, &fc->DPB[i], ~0);
631  if (prev->DPB[i].frame->buf[0]) {
632  ret = ref_frame(&fc->DPB[i], &prev->DPB[i]);
633  if (ret < 0)
634  return ret;
635  }
636  }
637  }
638 
639  if (IS_IDR(s)) {
640  s->seq_decode = (s->seq_decode + 1) & 0xff;
642  }
643 
644  ret = pic_arrays_init(s, fc);
645  if (ret < 0)
646  return ret;
647  ff_vvc_dsp_init(&fc->vvcdsp, fc->ps.sps->bit_depth);
648  ff_videodsp_init(&fc->vdsp, fc->ps.sps->bit_depth);
649  return 0;
650 }
651 
653 {
654  const VVCPH *ph = &fc->ps.ph;
655  const H266RawSliceHeader *rsh = sc->sh.r;
656  int ret;
657 
658  // 8.3.1 Decoding process for picture order count
659  if (!s->temporal_id && !ph->r->ph_non_ref_pic_flag && !(IS_RASL(s) || IS_RADL(s)))
660  s->poc_tid0 = ph->poc;
661 
662  if ((ret = ff_vvc_set_new_ref(s, fc, &fc->frame)) < 0)
663  goto fail;
664 
665  if (!IS_IDR(s))
667 
668  av_frame_unref(fc->output_frame);
669 
670  if ((ret = ff_vvc_output_frame(s, fc, fc->output_frame,rsh->sh_no_output_of_prior_pics_flag, 0)) < 0)
671  goto fail;
672 
673  if ((ret = ff_vvc_frame_rpl(s, fc, sc)) < 0)
674  goto fail;
675 
676  if ((ret = ff_vvc_frame_thread_init(fc)) < 0)
677  goto fail;
678  return 0;
679 fail:
680  if (fc->ref)
681  ff_vvc_unref_frame(fc, fc->ref, ~0);
682  fc->ref = NULL;
683  return ret;
684 }
685 
687  const CodedBitstreamUnit *unit, const int is_first_slice)
688 {
689  VVCSH *sh = &sc->sh;
690  int ret;
691 
692  ret = ff_vvc_decode_sh(sh, &fc->ps, unit);
693  if (ret < 0)
694  return ret;
695 
696  ff_refstruct_replace(&sc->ref, unit->content_ref);
697 
698  if (is_first_slice) {
699  ret = frame_start(s, fc, sc);
700  if (ret < 0)
701  return ret;
702  } else if (fc->ref) {
703  if (!IS_I(sh->r)) {
704  ret = ff_vvc_slice_rpl(s, fc, sc);
705  if (ret < 0) {
706  av_log(fc->log_ctx, AV_LOG_WARNING,
707  "Error constructing the reference lists for the current slice.\n");
708  return ret;
709  }
710  }
711  } else {
712  av_log(fc->log_ctx, AV_LOG_ERROR, "First slice in a frame missing.\n");
713  return ret;
714  }
715 
716  if (!IS_I(sh->r))
717  smvd_ref_idx(fc, sc);
718 
719  return 0;
720 }
721 
723 {
724  AVCodecContext *c = s->avctx;
725  const VVCSPS *sps = fc->ps.sps;
726  const VVCPPS *pps = fc->ps.pps;
727 
728  c->pix_fmt = sps->pix_fmt;
729  c->coded_width = pps->width;
730  c->coded_height = pps->height;
731  c->width = pps->width - ((pps->r->pps_conf_win_left_offset + pps->r->pps_conf_win_right_offset) << sps->hshift[CHROMA]);
732  c->height = pps->height - ((pps->r->pps_conf_win_top_offset + pps->r->pps_conf_win_bottom_offset) << sps->vshift[CHROMA]);
733 }
734 
736 {
737  int ret = ff_vvc_decode_frame_ps(&fc->ps, s);
738  if (ret < 0)
739  return ret;
740 
742  if (ret < 0)
743  return ret;
744 
746  return ret;
747 }
748 
749 static int decode_slice(VVCContext *s, VVCFrameContext *fc, const H2645NAL *nal, const CodedBitstreamUnit *unit)
750 {
751  int ret;
752  SliceContext *sc;
753  const int is_first_slice = !fc->nb_slices;
754 
755  ret = slices_realloc(fc);
756  if (ret < 0)
757  return ret;
758 
759  sc = fc->slices[fc->nb_slices];
760 
761  s->vcl_unit_type = nal->type;
762  if (is_first_slice) {
763  ret = frame_setup(fc, s);
764  if (ret < 0)
765  return ret;
766  }
767 
768  ret = slice_start(sc, s, fc, unit, is_first_slice);
769  if (ret < 0)
770  return ret;
771 
772  ret = slice_init_entry_points(sc, fc, nal, unit);
773  if (ret < 0)
774  return ret;
775  fc->nb_slices++;
776 
777  return 0;
778 }
779 
781 {
782  int ret;
783 
784  s->temporal_id = nal->temporal_id;
785 
786  switch (unit->type) {
787  case VVC_VPS_NUT:
788  case VVC_SPS_NUT:
789  case VVC_PPS_NUT:
790  /* vps, sps, sps cached by s->cbc */
791  break;
792  case VVC_TRAIL_NUT:
793  case VVC_STSA_NUT:
794  case VVC_RADL_NUT:
795  case VVC_RASL_NUT:
796  case VVC_IDR_W_RADL:
797  case VVC_IDR_N_LP:
798  case VVC_CRA_NUT:
799  case VVC_GDR_NUT:
800  ret = decode_slice(s, fc, nal, unit);
801  if (ret < 0)
802  return ret;
803  break;
804  case VVC_PREFIX_APS_NUT:
805  case VVC_SUFFIX_APS_NUT:
806  ret = ff_vvc_decode_aps(&s->ps, unit);
807  if (ret < 0)
808  return ret;
809  break;
810  }
811 
812  return 0;
813 }
814 
816 {
817  const CodedBitstreamH266Context *h266 = s->cbc->priv_data;
818  CodedBitstreamFragment *frame = &s->current_frame;
819  int ret = 0;
820  int eos_at_start = 1;
821  s->last_eos = s->eos;
822  s->eos = 0;
823 
825  ret = ff_cbs_read_packet(s->cbc, frame, avpkt);
826  if (ret < 0) {
827  av_log(s->avctx, AV_LOG_ERROR, "Failed to read packet.\n");
828  return ret;
829  }
830  /* decode the NAL units */
831  for (int i = 0; i < frame->nb_units; i++) {
832  const H2645NAL *nal = h266->common.read_packet.nals + i;
833  const CodedBitstreamUnit *unit = frame->units + i;
834 
835  if (unit->type == VVC_EOB_NUT || unit->type == VVC_EOS_NUT) {
836  if (eos_at_start)
837  s->last_eos = 1;
838  else
839  s->eos = 1;
840  } else {
841  ret = decode_nal_unit(s, fc, nal, unit);
842  if (ret < 0) {
843  av_log(s->avctx, AV_LOG_WARNING,
844  "Error parsing NAL unit #%d.\n", i);
845  goto fail;
846  }
847  }
848  }
849  return 0;
850 
851 fail:
852  if (fc->ref)
854  return ret;
855 }
856 
857 static int set_output_format(const VVCContext *s, const AVFrame *output)
858 {
859  AVCodecContext *c = s->avctx;
860  int ret;
861 
862  if (output->width != c->width || output->height != c->height) {
863  if ((ret = ff_set_dimensions(c, output->width, output->height)) < 0)
864  return ret;
865  }
866  c->pix_fmt = output->format;
867  return 0;
868 }
869 
870 static int wait_delayed_frame(VVCContext *s, AVFrame *output, int *got_output)
871 {
872  VVCFrameContext *delayed = get_frame_context(s, s->fcs, s->nb_frames - s->nb_delayed);
873  int ret = ff_vvc_frame_wait(s, delayed);
874 
875  if (!ret && delayed->output_frame->buf[0] && output) {
878  if (!ret)
879  *got_output = 1;
880  }
881  s->nb_delayed--;
882 
883  return ret;
884 }
885 
886 static int submit_frame(VVCContext *s, VVCFrameContext *fc, AVFrame *output, int *got_output)
887 {
888  int ret;
889  s->nb_frames++;
890  s->nb_delayed++;
892  if (s->nb_delayed >= s->nb_fcs) {
893  if ((ret = wait_delayed_frame(s, output, got_output)) < 0)
894  return ret;
895  }
896  return 0;
897 }
898 
899 static int get_decoded_frame(VVCContext *s, AVFrame *output, int *got_output)
900 {
901  int ret;
902  while (s->nb_delayed) {
903  if ((ret = wait_delayed_frame(s, output, got_output)) < 0)
904  return ret;
905  if (*got_output)
906  return 0;
907  }
908  if (s->nb_frames) {
909  //we still have frames cached in dpb.
910  VVCFrameContext *last = get_frame_context(s, s->fcs, s->nb_frames - 1);
911 
912  ret = ff_vvc_output_frame(s, last, output, 0, 1);
913  if (ret < 0)
914  return ret;
915  if (ret) {
916  *got_output = ret;
917  if ((ret = set_output_format(s, output)) < 0)
918  return ret;
919  }
920  }
921  return 0;
922 }
923 
925  int *got_output, AVPacket *avpkt)
926 {
927  VVCContext *s = avctx->priv_data;
929  int ret;
930 
931  if (!avpkt->size)
932  return get_decoded_frame(s, output, got_output);
933 
934  fc = get_frame_context(s, s->fcs, s->nb_frames);
935 
936  fc->nb_slices = 0;
937  fc->decode_order = s->nb_frames;
938 
939  ret = decode_nal_units(s, fc, avpkt);
940  if (ret < 0)
941  return ret;
942 
943  if (!fc->ft)
944  return avpkt->size;
945 
946  ret = submit_frame(s, fc, output, got_output);
947  if (ret < 0)
948  return ret;
949 
950  return avpkt->size;
951 }
952 
954 {
955  VVCContext *s = avctx->priv_data;
956  int got_output = 0;
957 
958  while (s->nb_delayed)
959  wait_delayed_frame(s, NULL, &got_output);
960 
961  if (s->fcs) {
962  VVCFrameContext *last = get_frame_context(s, s->fcs, s->nb_frames - 1);
963  ff_vvc_flush_dpb(last);
964  }
965 
966  s->eos = 1;
967 }
968 
970 {
971  VVCContext *s = avctx->priv_data;
972 
973  ff_cbs_fragment_free(&s->current_frame);
974  vvc_decode_flush(avctx);
975  ff_vvc_executor_free(&s->executor);
976  if (s->fcs) {
977  for (int i = 0; i < s->nb_fcs; i++)
978  frame_context_free(s->fcs + i);
979  av_free(s->fcs);
980  }
981  ff_vvc_ps_uninit(&s->ps);
982  ff_cbs_close(&s->cbc);
983 
984  return 0;
985 }
986 
987 static av_cold void init_default_scale_m(void)
988 {
989  memset(&ff_vvc_default_scale_m, 16, sizeof(ff_vvc_default_scale_m));
990 }
991 
992 #define VVC_MAX_DELAYED_FRAMES 16
994 {
995  VVCContext *s = avctx->priv_data;
996  static AVOnce init_static_once = AV_ONCE_INIT;
997  const int cpu_count = av_cpu_count();
998  const int delayed = FFMIN(cpu_count, VVC_MAX_DELAYED_FRAMES);
999  const int thread_count = avctx->thread_count ? avctx->thread_count : delayed;
1000  int ret;
1001 
1002  s->avctx = avctx;
1003 
1004  ret = ff_cbs_init(&s->cbc, AV_CODEC_ID_VVC, avctx);
1005  if (ret)
1006  return ret;
1007 
1008  if (avctx->extradata_size > 0 && avctx->extradata) {
1009  ret = ff_cbs_read_extradata_from_codec(s->cbc, &s->current_frame, avctx);
1010  if (ret < 0)
1011  return ret;
1012  }
1013 
1014  s->nb_fcs = (avctx->flags & AV_CODEC_FLAG_LOW_DELAY) ? 1 : delayed;
1015  s->fcs = av_calloc(s->nb_fcs, sizeof(*s->fcs));
1016  if (!s->fcs)
1017  return AVERROR(ENOMEM);
1018 
1019  for (int i = 0; i < s->nb_fcs; i++) {
1020  VVCFrameContext *fc = s->fcs + i;
1021  ret = frame_context_init(fc, avctx);
1022  if (ret < 0)
1023  return ret;
1024  }
1025 
1026  s->executor = ff_vvc_executor_alloc(s, thread_count);
1027  if (!s->executor)
1028  return AVERROR(ENOMEM);
1029 
1030  s->eos = 1;
1032  ff_thread_once(&init_static_once, init_default_scale_m);
1033 
1034  return 0;
1035 }
1036 
1038  .p.name = "vvc",
1039  .p.long_name = NULL_IF_CONFIG_SMALL("VVC (Versatile Video Coding)"),
1040  .p.type = AVMEDIA_TYPE_VIDEO,
1041  .p.id = AV_CODEC_ID_VVC,
1042  .priv_data_size = sizeof(VVCContext),
1043  .init = vvc_decode_init,
1044  .close = vvc_decode_free,
1046  .flush = vvc_decode_flush,
1051  .p.profiles = NULL_IF_CONFIG_SMALL(ff_vvc_profiles),
1052 };
VVC_RADL_NUT
@ VVC_RADL_NUT
Definition: vvc.h:31
VVC_RASL_NUT
@ VVC_RASL_NUT
Definition: vvc.h:32
VVC_GDR_NUT
@ VVC_GDR_NUT
Definition: vvc.h:39
VVC_STSA_NUT
@ VVC_STSA_NUT
Definition: vvc.h:30
VVCSPS
Definition: vvc_ps.h:58
smvd_find_fxn
int(* smvd_find_fxn)(const int idx, const int diff, const int old_diff)
Definition: vvcdec.c:396
ALF_BORDER_LUMA
#define ALF_BORDER_LUMA
Definition: vvc_ctu.h:73
vvc_decode_flush
static av_cold void vvc_decode_flush(AVCodecContext *avctx)
Definition: vvcdec.c:953
AV_LOG_WARNING
#define AV_LOG_WARNING
Something somehow does not look correct.
Definition: log.h:186
CodedBitstreamUnit::content_ref
void * content_ref
If content is reference counted, a RefStruct reference backing content.
Definition: cbs.h:112
VVCSH::num_ctus_in_curr_slice
uint32_t num_ctus_in_curr_slice
NumCtusInCurrSlice.
Definition: vvc_ps.h:233
frame_context_init
static av_cold int frame_context_init(VVCFrameContext *fc, AVCodecContext *avctx)
Definition: vvcdec.c:595
VVCPH
Definition: vvc_ps.h:147
VVCFrameContext::output_frame
struct AVFrame * output_frame
Definition: vvcdec.h:99
bs_tl_init
static void bs_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:183
VVCPPS
Definition: vvc_ps.h:92
FF_CODEC_CAP_INIT_CLEANUP
#define FF_CODEC_CAP_INIT_CLEANUP
The codec allows calling the close function for deallocation even if the init function returned a fai...
Definition: codec_internal.h:42
max_negtive
static int max_negtive(const int idx, const int diff, const int max_diff)
Definition: vvcdec.c:391
get_bits_left
static int get_bits_left(GetBitContext *gb)
Definition: get_bits.h:695
AVERROR
Filter the word “frame” indicates either a video frame or a group of audio as stored in an AVFrame structure Format for each input and each output the list of supported formats For video that means pixel format For audio that means channel sample they are references to shared objects When the negotiation mechanism computes the intersection of the formats supported at each end of a all references to both lists are replaced with a reference to the intersection And when a single format is eventually chosen for a link amongst the remaining all references to the list are updated That means that if a filter requires that its input and output have the same format amongst a supported all it has to do is use a reference to the same list of formats query_formats can leave some formats unset and return AVERROR(EAGAIN) to cause the negotiation mechanism toagain later. That can be used by filters with complex requirements to use the format negotiated on one link to set the formats supported on another. Frame references ownership and permissions
cpu_count
static atomic_int cpu_count
Definition: cpu.c:53
VVCSH::entry_point_start_ctu
uint32_t entry_point_start_ctu[VVC_MAX_ENTRY_POINTS]
entry point start in ctu_addr
Definition: vvc_ps.h:255
ff_refstruct_pool_alloc
FFRefStructPool * ff_refstruct_pool_alloc(size_t size, unsigned flags)
Equivalent to ff_refstruct_pool_alloc(size, flags, NULL, NULL, NULL, NULL, NULL)
Definition: refstruct.c:335
ff_vvc_report_frame_finished
void ff_vvc_report_frame_finished(VVCFrame *frame)
Definition: vvc_refs.c:495
frame_setup
static int frame_setup(VVCFrameContext *fc, VVCContext *s)
Definition: vvcdec.c:735
ff_cbs_fragment_free
av_cold void ff_cbs_fragment_free(CodedBitstreamFragment *frag)
Free the units array of a fragment in addition to what ff_cbs_fragment_reset does.
Definition: cbs.c:186
thread.h
slice_init_entry_points
static int slice_init_entry_points(SliceContext *sc, VVCFrameContext *fc, const H2645NAL *nal, const CodedBitstreamUnit *unit)
Definition: vvcdec.c:507
MAX_CTU_SIZE
#define MAX_CTU_SIZE
Definition: vvc_ctu.h:31
CodingUnit
Definition: hevcdec.h:282
output
filter_frame For filters that do not use the this method is called when a frame is pushed to the filter s input It can be called at any time except in a reentrant way If the input frame is enough to produce output
Definition: filter_design.txt:225
H266RawSliceHeader::sh_no_output_of_prior_pics_flag
uint8_t sh_no_output_of_prior_pics_flag
Definition: cbs_h266.h:779
VVCFrameContext::DPB
VVCFrame DPB[VVC_MAX_DPB_SIZE+1]
Definition: vvcdec.h:96
vvc_decode_init
static av_cold int vvc_decode_init(AVCodecContext *avctx)
Definition: vvcdec.c:993
get_bits_count
static int get_bits_count(const GetBitContext *s)
Definition: get_bits.h:266
av_frame_free
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
Definition: frame.c:160
ph
static int FUNC() ph(CodedBitstreamContext *ctx, RWContext *rw, H266RawPH *current)
Definition: cbs_h266_syntax_template.c:3003
AVFrame
This structure describes decoded (raw) audio or video data.
Definition: frame.h:375
w
uint8_t w
Definition: llviddspenc.c:38
ff_cbs_fragment_reset
void ff_cbs_fragment_reset(CodedBitstreamFragment *frag)
Free the units contained in a fragment as well as the fragment's own data buffer, but not the units a...
Definition: cbs.c:172
decode_slice
static int decode_slice(VVCContext *s, VVCFrameContext *fc, const H2645NAL *nal, const CodedBitstreamUnit *unit)
Definition: vvcdec.c:749
IS_RADL
#define IS_RADL(s)
Definition: vvc_ps.h:36
tl_init
static void tl_init(TabList *l, const int zero, const int realloc)
Definition: vvcdec.c:59
VVCSH::r
const H266RawSliceHeader * r
RefStruct reference.
Definition: vvc_ps.h:229
FFCodec
Definition: codec_internal.h:127
vvc_decode_frame
static int vvc_decode_frame(AVCodecContext *avctx, AVFrame *output, int *got_output, AVPacket *avpkt)
Definition: vvcdec.c:924
ff_vvc_decode_aps
int ff_vvc_decode_aps(VVCParamSets *ps, const CodedBitstreamUnit *unit)
Definition: vvc_ps.c:1080
CodedBitstreamUnit::type
CodedBitstreamUnitType type
Codec-specific type of this unit.
Definition: cbs.h:74
ff_vvc_slice_rpl
int ff_vvc_slice_rpl(VVCContext *s, VVCFrameContext *fc, SliceContext *sc)
Definition: vvc_refs.c:417
fc
#define fc(width, name, range_min, range_max)
Definition: cbs_av1.c:464
ff_vvc_default_scale_m
uint8_t ff_vvc_default_scale_m[64 *64]
Definition: vvc_data.c:1641
AVFrame::buf
AVBufferRef * buf[AV_NUM_DATA_POINTERS]
AVBuffer references backing the data for this frame.
Definition: frame.h:588
ff_set_dimensions
int ff_set_dimensions(AVCodecContext *s, int width, int height)
Check that the provided frame dimensions are valid and set them on the codec context.
Definition: utils.c:94
decode_nal_units
static int decode_nal_units(VVCContext *s, VVCFrameContext *fc, AVPacket *avpkt)
Definition: vvcdec.c:815
H2645NAL::temporal_id
int temporal_id
HEVC only, nuh_temporal_id_plus_1 - 1.
Definition: h2645_parse.h:62
RefPicList
Definition: hevcdec.h:189
CodedBitstreamUnit
Coded bitstream unit structure.
Definition: cbs.h:70
ff_cbs_close
av_cold void ff_cbs_close(CodedBitstreamContext **ctx_ptr)
Close a context and free all internal state.
Definition: cbs.c:142
av_malloc
#define av_malloc(s)
Definition: tableprint_vlc.h:30
min_tu_tl_init
static void min_tu_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:160
submit_frame
static int submit_frame(VVCContext *s, VVCFrameContext *fc, AVFrame *output, int *got_output)
Definition: vvcdec.c:886
skip_bits
static void skip_bits(GetBitContext *s, int n)
Definition: get_bits.h:381
msm_tl_init
static void msm_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:239
frame_context_setup
static int frame_context_setup(VVCFrameContext *fc, VVCContext *s)
Definition: vvcdec.c:620
FFCodec::p
AVCodec p
The public AVCodec.
Definition: codec_internal.h:131
vvc_data.h
fail
#define fail()
Definition: checkasm.h:179
AVCodecContext::thread_count
int thread_count
thread count is used to decide how many independent tasks should be passed to execute()
Definition: avcodec.h:1582
ff_refstruct_pool_uninit
static void ff_refstruct_pool_uninit(FFRefStructPool **poolp)
Mark the pool as being available for freeing.
Definition: refstruct.h:292
VVCFrame::rpl
RefPicListTab * rpl
RefStruct reference.
Definition: vvcdec.h:61
GetBitContext
Definition: get_bits.h:108
vvc_refs.h
AVCodecContext::flags
int flags
AV_CODEC_FLAG_*.
Definition: avcodec.h:502
ff_videodsp_init
av_cold void ff_videodsp_init(VideoDSPContext *ctx, int bpc)
Definition: videodsp.c:39
AV_CODEC_FLAG_LOW_DELAY
#define AV_CODEC_FLAG_LOW_DELAY
Force low delay.
Definition: avcodec.h:334
SliceContext::rpl
RefPicList * rpl
Definition: vvcdec.h:88
VVC_IDR_W_RADL
@ VVC_IDR_W_RADL
Definition: vvc.h:36
refstruct.h
VVC_EOS_NUT
@ VVC_EOS_NUT
Definition: vvc.h:50
av_frame_alloc
AVFrame * av_frame_alloc(void)
Allocate an AVFrame and set its fields to default values.
Definition: frame.c:148
export_frame_params
static void export_frame_params(VVCContext *s, const VVCFrameContext *fc)
Definition: vvcdec.c:722
H266RawSliceHeader::num_ref_idx_active
uint8_t num_ref_idx_active[2]
NumRefIdxActive[].
Definition: cbs_h266.h:837
slice_start
static int slice_start(SliceContext *sc, VVCContext *s, VVCFrameContext *fc, const CodedBitstreamUnit *unit, const int is_first_slice)
Definition: vvcdec.c:686
ff_thread_once
static int ff_thread_once(char *control, void(*routine)(void))
Definition: thread.h:205
ff_vvc_unref_frame
void ff_vvc_unref_frame(VVCFrameContext *fc, VVCFrame *frame, int flags)
Definition: vvc_refs.c:46
AV_LOG_ERROR
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:180
H266RawSlice::data
uint8_t * data
Definition: cbs_h266.h:844
AV_CODEC_CAP_EXPERIMENTAL
#define AV_CODEC_CAP_EXPERIMENTAL
Codec is experimental and is thus avoided in favor of non experimental encoders.
Definition: codec.h:102
FF_ARRAY_ELEMS
#define FF_ARRAY_ELEMS(a)
Definition: sinewin_tablegen.c:29
av_cold
#define av_cold
Definition: attributes.h:90
init_get_bits8
static int init_get_bits8(GetBitContext *s, const uint8_t *buffer, int byte_size)
Initialize GetBitContext.
Definition: get_bits.h:545
VVCFrame::flags
uint8_t flags
A combination of VVC_FRAME_FLAG_*.
Definition: vvcdec.h:80
AVCodecContext::extradata_size
int extradata_size
Definition: avcodec.h:524
CodedBitstreamFragment
Coded bitstream fragment structure, combining one or more units.
Definition: cbs.h:122
width
#define width
FF_CODEC_DECODE_CB
#define FF_CODEC_DECODE_CB(func)
Definition: codec_internal.h:287
s
#define s(width, name)
Definition: cbs_vp9.c:198
AV_CEIL_RSHIFT
#define AV_CEIL_RSHIFT(a, b)
Definition: common.h:59
SliceContext::slice_idx
int slice_idx
Definition: vvcdec.h:84
av_realloc_array
void * av_realloc_array(void *ptr, size_t nmemb, size_t size)
Definition: mem.c:217
VVC_MAX_DELAYED_FRAMES
#define VVC_MAX_DELAYED_FRAMES
Definition: vvcdec.c:992
AV_CODEC_CAP_OTHER_THREADS
#define AV_CODEC_CAP_OTHER_THREADS
Codec supports multithreading through a method other than slice- or frame-level multithreading.
Definition: codec.h:124
VVCSH
Definition: vvc_ps.h:228
ALF_PADDING_SIZE
#define ALF_PADDING_SIZE
Definition: vvc_ctu.h:70
decode.h
IS_IDR
#define IS_IDR(s)
Definition: hevcdec.h:75
smvd_ref_idx
static void smvd_ref_idx(const VVCFrameContext *fc, SliceContext *sc)
Definition: vvcdec.c:417
vvcdec.h
H2645NAL::skipped_bytes_pos
int * skipped_bytes_pos
Definition: h2645_parse.h:71
TabList::tabs
Tab tabs[TAB_MAX]
Definition: vvcdec.c:45
ff_vvc_clear_refs
void ff_vvc_clear_refs(VVCFrameContext *fc)
Definition: vvc_refs.c:77
ff_vvc_frame_wait
int ff_vvc_frame_wait(VVCContext *s, VVCFrameContext *fc)
Definition: vvc_thread.c:781
IS_RASL
#define IS_RASL(s)
Definition: vvc_ps.h:35
eps_free
static void eps_free(SliceContext *slice)
Definition: vvcdec.c:430
H2645NAL::type
int type
NAL unit type.
Definition: h2645_parse.h:52
frame_context_for_each_tl
static int frame_context_for_each_tl(VVCFrameContext *fc, int(*unary_fn)(TabList *l))
Definition: vvcdec.c:293
min_positive
static int min_positive(const int idx, const int diff, const int min_diff)
Definition: vvcdec.c:386
ctu_nz_tl_init
static void ctu_nz_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:108
ff_vvc_decode_frame_ps
int ff_vvc_decode_frame_ps(VVCFrameParamSets *fps, struct VVCContext *s)
Definition: vvc_ps.c:865
ctu_tl_init
static void ctu_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:94
MAX_CONTROL_POINTS
#define MAX_CONTROL_POINTS
Definition: vvc_ctu.h:61
GetBitContext::buffer
const uint8_t * buffer
Definition: get_bits.h:109
ff_vvc_flush_dpb
void ff_vvc_flush_dpb(VVCFrameContext *fc)
Definition: vvc_refs.c:84
AV_ONCE_INIT
#define AV_ONCE_INIT
Definition: thread.h:203
wait_delayed_frame
static int wait_delayed_frame(VVCContext *s, AVFrame *output, int *got_output)
Definition: vvcdec.c:870
GDR_SET_RECOVERED
#define GDR_SET_RECOVERED(s)
Definition: vvc_ps.h:44
ff_vvc_decode_sh
int ff_vvc_decode_sh(VVCSH *sh, const VVCFrameParamSets *fps, const CodedBitstreamUnit *unit)
Definition: vvc_ps.c:1269
NULL
#define NULL
Definition: coverity.c:32
TabList
Definition: vvcdec.c:44
min_pu_tl_init
static void min_pu_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:146
VVCSH::ref_idx_sym
int8_t ref_idx_sym[2]
RefIdxSymL0, RefIdxSymL1.
Definition: vvc_ps.h:238
ff_vvc_frame_ps_free
void ff_vvc_frame_ps_free(VVCFrameParamSets *fps)
Definition: vvc_ps.c:881
init_default_scale_m
static av_cold void init_default_scale_m(void)
Definition: vvcdec.c:987
SliceContext::eps
struct EntryPoint * eps
Definition: vvcdec.h:86
ff_vvc_decoder
const FFCodec ff_vvc_decoder
Definition: vvcdec.c:1037
ff_vvc_frame_thread_free
void ff_vvc_frame_thread_free(VVCFrameContext *fc)
Definition: vvc_thread.c:631
profiles.h
CodedBitstreamH266Context::common
CodedBitstreamH2645Context common
Definition: cbs_h266.h:868
CodedBitstreamH2645Context::read_packet
H2645Packet read_packet
Definition: cbs_h2645.h:32
RefPicListTab
Definition: hevcdec.h:196
AVOnce
#define AVOnce
Definition: thread.h:202
pic_arrays_free
static void pic_arrays_free(VVCFrameContext *fc)
Definition: vvcdec.c:328
index
int index
Definition: gxfenc.c:90
c
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
Definition: undefined.txt:32
ff_vvc_ctu_free_cus
void ff_vvc_ctu_free_cus(CTU *ctu)
Definition: vvc_ctu.c:2522
ff_vvc_ps_uninit
void ff_vvc_ps_uninit(VVCParamSets *ps)
Definition: vvc_ps.c:891
TransformUnit
Definition: hevcdec.h:325
VVCFrame::sequence
uint16_t sequence
A sequence counter, so that old frames are output first after a POC reset.
Definition: vvcdec.h:76
SliceContext
Definition: mss12.h:70
ff_vvc_output_frame
int ff_vvc_output_frame(VVCContext *s, VVCFrameContext *fc, AVFrame *out, const int no_output_of_prior_pics_flag, int flush)
Definition: vvc_refs.c:197
pic_arrays_init
static int pic_arrays_init(VVCContext *s, VVCFrameContext *fc)
Definition: vvcdec.c:338
av_cpu_count
int av_cpu_count(void)
Definition: cpu.c:209
H266RawSliceHeader::sh_entry_point_offset_minus1
uint32_t sh_entry_point_offset_minus1[VVC_MAX_ENTRY_POINTS]
Definition: cbs_h266.h:832
init
int(* init)(AVBSFContext *ctx)
Definition: dts2pts.c:366
TabList::nb_tabs
int nb_tabs
Definition: vvcdec.c:46
AV_CODEC_CAP_DR1
#define AV_CODEC_CAP_DR1
Codec uses get_buffer() or get_encode_buffer() for allocating buffers and supports custom allocators.
Definition: codec.h:52
AVPacket::size
int size
Definition: packet.h:525
NULL_IF_CONFIG_SMALL
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification.
Definition: internal.h:94
pps
static int FUNC() pps(CodedBitstreamContext *ctx, RWContext *rw, H264RawPPS *current)
Definition: cbs_h264_syntax_template.c:404
Tab
Definition: vvcdec.c:39
av_frame_ref
int av_frame_ref(AVFrame *dst, const AVFrame *src)
Set up a new reference to the data described by the source frame.
Definition: frame.c:384
codec_internal.h
VVC_VPS_NUT
@ VVC_VPS_NUT
Definition: vvc.h:43
RefPicList::isLongTerm
int isLongTerm[HEVC_MAX_REFS]
Definition: hevcdec.h:192
cpu.h
FF_CODEC_CAP_EXPORTS_CROPPING
#define FF_CODEC_CAP_EXPORTS_CROPPING
The decoder sets the cropping fields in the output frames manually.
Definition: codec_internal.h:60
size
int size
Definition: twinvq_data.h:10344
EntryPoint::cc
CABACContext cc
Definition: vvc_ctu.h:355
EntryPoint::ctu_end
int ctu_end
Definition: vvc_ctu.h:358
H2645NAL
Definition: h2645_parse.h:34
GetBitContext::index
int index
Definition: get_bits.h:110
tl_free
static int tl_free(TabList *l)
Definition: vvcdec.c:66
ibc_tl_init
static void ibc_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:266
SliceContext::ref
void * ref
RefStruct reference, backing slice data.
Definition: vvcdec.h:89
MvField
Definition: hevcdec.h:300
vvc_thread.h
diff
static av_always_inline int diff(const struct color_info *a, const struct color_info *b, const int trans_thresh)
Definition: vf_paletteuse.c:165
ALF_BORDER_CHROMA
#define ALF_BORDER_CHROMA
Definition: vvc_ctu.h:74
VVCFrame
Definition: vvcdec.h:56
ref_frame
static int ref_frame(VVCFrame *dst, const VVCFrame *src)
Definition: vvcdec.c:553
TL_ADD
#define TL_ADD(t, s)
Definition: vvcdec.c:52
height
#define height
VVCFrame::tab_dmvr_mvf
struct MvField * tab_dmvr_mvf
RefStruct reference.
Definition: vvcdec.h:59
CodedBitstreamH266Context
Definition: cbs_h266.h:866
AV_CODEC_ID_VVC
@ AV_CODEC_ID_VVC
Definition: codec_id.h:250
VVCSH::ctb_addr_in_curr_slice
const uint32_t * ctb_addr_in_curr_slice
CtbAddrInCurrSlice.
Definition: vvc_ps.h:234
VVC_TRAIL_NUT
@ VVC_TRAIL_NUT
Definition: vvc.h:29
VVC_SPS_NUT
@ VVC_SPS_NUT
Definition: vvc.h:44
ff_cbs_read_extradata_from_codec
int ff_cbs_read_extradata_from_codec(CodedBitstreamContext *ctx, CodedBitstreamFragment *frag, const AVCodecContext *avctx)
Definition: cbs.c:295
ff_init_cabac_decoder
int ff_init_cabac_decoder(CABACContext *c, const uint8_t *buf, int buf_size)
Definition: cabac.c:162
H2645Packet::nals
H2645NAL * nals
Definition: h2645_parse.h:83
H266RawSliceHeader
Definition: cbs_h266.h:769
H266RawSliceHeader::num_entry_points
uint32_t num_entry_points
NumEntryPoints.
Definition: cbs_h266.h:836
FF_REFSTRUCT_POOL_FLAG_ZERO_EVERY_TIME
#define FF_REFSTRUCT_POOL_FLAG_ZERO_EVERY_TIME
If this flag is set, the entries will be zeroed before being returned to the user (after the init or ...
Definition: refstruct.h:221
get_decoded_frame
static int get_decoded_frame(VVCContext *s, AVFrame *output, int *got_output)
Definition: vvcdec.c:899
TabList::realloc
int realloc
Definition: vvcdec.c:49
SliceContext::nb_eps
int nb_eps
Definition: vvcdec.h:87
min_cb_tl_init
static void min_cb_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:121
VVCFrame::nb_rpl_elems
int nb_rpl_elems
Definition: vvcdec.h:62
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:256
ispmf_tl_init
static void ispmf_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:253
pixel_buffer_nz_tl_init
static void pixel_buffer_nz_tl_init(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:204
AVCodecContext::extradata
uint8_t * extradata
some codecs need / can use extradata like Huffman tables.
Definition: avcodec.h:523
vvc_ctu.h
VVCFrame::progress
struct FrameProgress * progress
RefStruct reference.
Definition: vvcdec.h:70
tl_init_fn
void(* tl_init_fn)(TabList *l, VVCFrameContext *fc)
Definition: vvcdec.c:291
ff_vvc_frame_thread_init
int ff_vvc_frame_thread_init(VVCFrameContext *fc)
Definition: vvc_thread.c:671
IS_B
#define IS_B(rsh)
Definition: vvc_ps.h:40
delta
float delta
Definition: vorbis_enc_data.h:430
slices_free
static void slices_free(VVCFrameContext *fc)
Definition: vvcdec.c:436
H266RawSlice::header_size
size_t header_size
Definition: cbs_h266.h:846
ff_vvc_dsp_init
void ff_vvc_dsp_init(VVCDSPContext *vvcdsp, int bit_depth)
Definition: vvcdsp.c:98
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
av_frame_move_ref
void av_frame_move_ref(AVFrame *dst, AVFrame *src)
Move everything contained in src to dst and reset src.
Definition: frame.c:633
VVC_IDR_N_LP
@ VVC_IDR_N_LP
Definition: vvc.h:37
H266RawSlice::data_size
size_t data_size
Definition: cbs_h266.h:847
av_frame_unref
void av_frame_unref(AVFrame *frame)
Unreference all the buffers referenced by frame and reset the frame fields.
Definition: frame.c:606
av_mallocz
void * av_mallocz(size_t size)
Allocate a memory block with alignment suitable for all memory accesses (including vectors if availab...
Definition: mem.c:256
EntryPoint
Definition: vvc_ctu.h:349
AVCodec::name
const char * name
Name of the codec implementation.
Definition: codec.h:194
vvc_decode_free
static av_cold int vvc_decode_free(AVCodecContext *avctx)
Definition: vvcdec.c:969
av_calloc
void * av_calloc(size_t nmemb, size_t size)
Definition: mem.c:264
decode_nal_unit
static int decode_nal_unit(VVCContext *s, VVCFrameContext *fc, const H2645NAL *nal, const CodedBitstreamUnit *unit)
Definition: vvcdec.c:780
smvd_find
static int8_t smvd_find(const VVCFrameContext *fc, const SliceContext *sc, int lx, smvd_find_fxn find)
Definition: vvcdec.c:398
ret
ret
Definition: filter_design.txt:187
VVCFrame::frame
struct AVFrame * frame
Definition: vvcdec.h:57
frame
these buffered frames must be flushed immediately if a new input produces new the filter must not call request_frame to get more It must just process the frame or queue it The task of requesting more frames is left to the filter s request_frame method or the application If a filter has several the filter must be ready for frames arriving randomly on any input any filter with several inputs will most likely require some kind of queuing mechanism It is perfectly acceptable to have a limited queue and to drop frames when the inputs are too unbalanced request_frame For filters that do not use the this method is called when a frame is wanted on an output For a it should directly call filter_frame on the corresponding output For a if there are queued frames already one of these frames should be pushed If the filter should request a frame on one of its repeatedly until at least one frame has been pushed Return or at least make progress towards producing a frame
Definition: filter_design.txt:264
frame_context_free
static av_cold void frame_context_free(VVCFrameContext *fc)
Definition: vvcdec.c:577
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
ff_refstruct_replace
void ff_refstruct_replace(void *dstp, const void *src)
Ensure *dstp refers to the same object as src.
Definition: refstruct.c:160
VVC_PPS_NUT
@ VVC_PPS_NUT
Definition: vvc.h:45
ff_vvc_executor_free
void ff_vvc_executor_free(AVExecutor **e)
Definition: vvc_thread.c:626
AVCodecContext
main external API structure.
Definition: avcodec.h:445
VVC_PREFIX_APS_NUT
@ VVC_PREFIX_APS_NUT
Definition: vvc.h:46
ff_vvc_frame_submit
void ff_vvc_frame_submit(VVCContext *s, VVCFrameContext *fc)
Definition: vvc_thread.c:761
slices_realloc
static int slices_realloc(VVCFrameContext *fc)
Definition: vvcdec.c:454
VVCFrame::poc
int poc
Definition: vvcdec.h:66
TabList::zero
int zero
Definition: vvcdec.c:48
ep_init_cabac_decoder
static void ep_init_cabac_decoder(SliceContext *sc, const int index, const H2645NAL *nal, GetBitContext *gb, const CodedBitstreamUnit *unit)
Definition: vvcdec.c:480
VVC_SUFFIX_APS_NUT
@ VVC_SUFFIX_APS_NUT
Definition: vvc.h:47
frame_start
static int frame_start(VVCContext *s, VVCFrameContext *fc, SliceContext *sc)
Definition: vvcdec.c:652
Tab::size
size_t size
Definition: vvcdec.c:41
get_frame_context
static VVCFrameContext * get_frame_context(const VVCContext *s, const VVCFrameContext *fc, const int delta)
Definition: vvcdec.c:546
imf
#define imf
Definition: vf_colormatrix.c:113
AV_CODEC_CAP_DELAY
#define AV_CODEC_CAP_DELAY
Encoder or decoder requires flushing with NULL input at the end in order to give the complete and cor...
Definition: codec.h:76
ff_vvc_frame_rpl
int ff_vvc_frame_rpl(VVCContext *s, VVCFrameContext *fc, SliceContext *sc)
Definition: vvc_refs.c:471
RefPicList::list
int list[HEVC_MAX_REFS]
Definition: hevcdec.h:191
VVC_CRA_NUT
@ VVC_CRA_NUT
Definition: vvc.h:38
ff_cbs_read_packet
int ff_cbs_read_packet(CodedBitstreamContext *ctx, CodedBitstreamFragment *frag, const AVPacket *pkt)
Read the data bitstream from a packet into a fragment, then split into units and decompose.
Definition: cbs.c:304
IS_I
#define IS_I(rsh)
Definition: vvc_ps.h:38
ff_vvc_profiles
const AVProfile ff_vvc_profiles[]
Definition: profiles.c:90
AVMEDIA_TYPE_VIDEO
@ AVMEDIA_TYPE_VIDEO
Definition: avutil.h:201
zero
#define zero
Definition: regdef.h:64
mem.h
FF_CODEC_CAP_AUTO_THREADS
#define FF_CODEC_CAP_AUTO_THREADS
Codec handles avctx->thread_count == 0 (auto) internally.
Definition: codec_internal.h:73
tl_create
static int tl_create(TabList *l)
Definition: vvcdec.c:74
ff_cbs_init
av_cold int ff_cbs_init(CodedBitstreamContext **ctx_ptr, enum AVCodecID codec_id, void *log_ctx)
Create and initialise a new context for the given codec.
Definition: cbs.c:90
av_free
#define av_free(p)
Definition: tableprint_vlc.h:33
VVC_MAX_SAMPLE_ARRAYS
@ VVC_MAX_SAMPLE_ARRAYS
Definition: vvc.h:77
AVCodecContext::priv_data
void * priv_data
Definition: avcodec.h:472
AVPacket
This structure stores compressed data.
Definition: packet.h:501
SliceContext::sh
VVCSH sh
Definition: vvcdec.h:85
av_freep
#define av_freep(p)
Definition: tableprint_vlc.h:34
src
INIT_CLIP pixel * src
Definition: h264pred_template.c:418
VVCFrameContext
Definition: vvcdec.h:92
EntryPoint::ctu_start
int ctu_start
Definition: vvc_ctu.h:357
set_output_format
static int set_output_format(const VVCContext *s, const AVFrame *output)
Definition: vvcdec.c:857
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:27
VVC_EOB_NUT
@ VVC_EOB_NUT
Definition: vvc.h:51
h
h
Definition: vp9dsp_template.c:2038
free_cus
static void free_cus(VVCFrameContext *fc)
Definition: vvcdec.c:320
VVCFrame::ctb_count
int ctb_count
Definition: vvcdec.h:64
VVCFrame::rpl_tab
RefPicListTab ** rpl_tab
RefStruct reference.
Definition: vvcdec.h:60
ff_vvc_executor_alloc
AVExecutor * ff_vvc_executor_alloc(VVCContext *s, const int thread_count)
Definition: vvc_thread.c:614
int
int
Definition: ffmpeg_filter.c:409
ff_vvc_set_new_ref
int ff_vvc_set_new_ref(VVCContext *s, VVCFrameContext *fc, AVFrame **frame)
Definition: vvc_refs.c:155
TAB_MAX
#define TAB_MAX
Definition: vvcdec.c:37
ff_refstruct_unref
void ff_refstruct_unref(void *objp)
Decrement the reference count of the underlying object and automatically free the object if there are...
Definition: refstruct.c:120
skip
static void BS_FUNC() skip(BSCTX *bc, unsigned int n)
Skip n bits in the buffer.
Definition: bitstream_template.h:375
LUMA
#define LUMA
Definition: hevc_filter.c:31
H266RawSlice
Definition: cbs_h266.h:841
VVCContext
Definition: vvcdec.h:195
Tab::tab
void ** tab
Definition: vvcdec.c:40
ff_vvc_bump_frame
void ff_vvc_bump_frame(VVCContext *s, VVCFrameContext *fc)
Definition: vvc_refs.c:256