Unified · Split
| @@ -44,112 +44,59 @@ static void subpic_width_height(int *pic_width, int *pic_height, · 43 unmodified lines | |||
| 44 | *pic_height = pps->subpic_height[subpic_idx] >> sps->vshift[is_chroma]; | 44 | *pic_height = pps->subpic_height[subpic_idx] >> sps->vshift[is_chroma]; |
| 45 | } | 45 | } |
| 46 | 46 | ||
| 47 | static int emulated_edge(const VVCLocalContext *lc, uint8_t *dst, const uint8_t **src, ptrdiff_t *src_stride, const VVCFrame *src_frame, | 47 | static void emulated_edge(const VVCLocalContext *lc, uint8_t *dst, |
| 48 | int x_off, int y_off, const int block_w, const int block_h, const int is_chroma) | 48 | const uint8_t **src, ptrdiff_t *src_stride, const VVCFrame *src_frame, |
| 49 | int x_sb, int y_sb, int x_off, int y_off, const int block_w, const int block_h, | ||
| 50 | const int is_chroma, const int extra_before, const int extra_after) | ||
| 49 | { | 51 | { |
| 50 | const VVCFrameContext *fc = lc->fc; | 52 | const VVCFrameContext *fc = lc->fc; |
| 51 | const VVCSPS *sps = src_frame->sps; | 53 | const VVCSPS *sps = src_frame->sps; |
| 52 | const VVCPPS *pps = src_frame->pps; | 54 | const VVCPPS *pps = src_frame->pps; |
| 53 | const int subpic_idx = lc->sc->sh.r->curr_subpic_idx; | 55 | const int subpic_idx = lc->sc->sh.r->curr_subpic_idx; |
| 54 | const int extra_before = is_chroma ? CHROMA_EXTRA_BEFORE : LUMA_EXTRA_BEFORE; | 56 | const int extra = extra_before + extra_after; |
| 55 | const int extra_after = is_chroma ? CHROMA_EXTRA_AFTER : LUMA_EXTRA_AFTER; | 57 | const int dmvr_clip = x_sb != x_off || y_sb != y_off; |
| 56 | const int extra = is_chroma ? CHROMA_EXTRA : LUMA_EXTRA; | ||
| 57 | int pic_width, pic_height; | ||
| 58 | |||
| 59 | subpic_offset(&x_off, &y_off, sps, pps, subpic_idx, is_chroma); | ||
| 60 | subpic_width_height(&pic_width, &pic_height, sps, pps, subpic_idx, is_chroma); | ||
| 61 | |||
| 62 | if (x_off < extra_before || y_off < extra_before || | ||
| 63 | x_off >= pic_width - block_w - extra_after || | ||
| 64 | y_off >= pic_height - block_h - extra_after) { | ||
| 65 | const ptrdiff_t edge_emu_stride = EDGE_EMU_BUFFER_STRIDE << fc->ps.sps->pixel_shift; | ||
| 66 | int offset = extra_before * *src_stride + (extra_before << fc->ps.sps->pixel_shift); | ||
| 67 | int buf_offset = extra_before * edge_emu_stride + (extra_before << fc->ps.sps->pixel_shift); | ||
| 68 | |||
| 69 | fc->vdsp.emulated_edge_mc(dst, *src - offset, edge_emu_stride, *src_stride, | ||
| 70 | block_w + extra, block_h + extra, x_off - extra_before, y_off - extra_before, | ||
| 71 | pic_width, pic_height); | ||
| 72 | |||
| 73 | *src = dst + buf_offset; | ||
| 74 | *src_stride = edge_emu_stride; | ||
| 75 | return 1; | ||
| 76 | } | ||
| 77 | return 0; | ||
| 78 | } | ||
| 79 | |||
| 80 | static void emulated_edge_dmvr(const VVCLocalContext *lc, uint8_t *dst, const uint8_t **src, ptrdiff_t *src_stride, | ||
| 81 | int x_sb, int y_sb, int x_off, int y_off, const int block_w, const int block_h, const int is_chroma) | ||
| 82 | { | ||
| 83 | const VVCFrameContext *fc = lc->fc; | ||
| 84 | const VVCSPS *sps = fc->ps.sps; | ||
| 85 | const VVCPPS *pps = fc->ps.pps; | ||
| 86 | const int subpic_idx = lc->sc->sh.r->curr_subpic_idx; | ||
| 87 | const int extra_before = is_chroma ? CHROMA_EXTRA_BEFORE : LUMA_EXTRA_BEFORE; | ||
| 88 | const int extra_after = is_chroma ? CHROMA_EXTRA_AFTER : LUMA_EXTRA_AFTER; | ||
| 89 | const int extra = is_chroma ? CHROMA_EXTRA : LUMA_EXTRA; | ||
| 90 | int pic_width, pic_height; | 58 | int pic_width, pic_height; |
| 91 | 59 | ||
| 92 | subpic_offset(&x_off, &y_off, sps, pps, subpic_idx, is_chroma); | 60 | subpic_offset(&x_off, &y_off, sps, pps, subpic_idx, is_chroma); |
| 93 | subpic_offset(&x_sb, &y_sb, sps, pps, subpic_idx, is_chroma); | 61 | subpic_offset(&x_sb, &y_sb, sps, pps, subpic_idx, is_chroma); |
| 94 | subpic_width_height(&pic_width, &pic_height, sps, pps, subpic_idx, is_chroma); | 62 | subpic_width_height(&pic_width, &pic_height, sps, pps, subpic_idx, is_chroma); |
| 63 | if (dmvr_clip) { | ||
| 64 | const int start_x = FFMIN(FFMAX(x_sb - extra_before, 0), pic_width - 1); | ||
| 65 | const int start_y = FFMIN(FFMAX(y_sb - extra_before, 0), pic_height - 1); | ||
| 66 | pic_width = FFMAX(FFMIN(pic_width, x_sb + block_w + extra_after) - start_x, 1); | ||
| 67 | pic_height = FFMAX(FFMIN(pic_height, y_sb + block_h + extra_after) - start_y, 1); | ||
| 68 | x_off -= start_x; | ||
| 69 | y_off -= start_y; | ||
| 70 | } | ||
| 95 | 71 | ||
| 96 | if (x_off < extra_before || y_off < extra_before || | 72 | if (dmvr_clip || x_off < extra_before || y_off < extra_before || |
| 97 | x_off >= pic_width - block_w - extra_after || | 73 | x_off >= pic_width - block_w - extra_after || |
| 98 | y_off >= pic_height - block_h - extra_after|| | 74 | y_off >= pic_height - block_h - extra_after) { |
| 99 | (x_off != x_sb || y_off != y_sb)) { | ||
| 100 | const int ps = fc->ps.sps->pixel_shift; | 75 | const int ps = fc->ps.sps->pixel_shift; |
| 101 | const ptrdiff_t edge_emu_stride = EDGE_EMU_BUFFER_STRIDE << ps; | 76 | const ptrdiff_t edge_emu_stride = EDGE_EMU_BUFFER_STRIDE << ps; |
| 102 | const int offset = extra_before * *src_stride + (extra_before << ps); | 77 | const int offset = extra_before * *src_stride + (extra_before << ps); |
| 103 | const int buf_offset = extra_before * edge_emu_stride + (extra_before << ps); | 78 | const int buf_offset = extra_before * edge_emu_stride + (extra_before << ps); |
| 104 | 79 | ||
| 105 | const int start_x = FFMIN(FFMAX(x_sb - extra_before, 0), pic_width - 1); | 80 | fc->vdsp.emulated_edge_mc(dst, *src - offset, edge_emu_stride, *src_stride, |
| 106 | const int start_y = FFMIN(FFMAX(y_sb - extra_before, 0), pic_height - 1); | 81 | block_w + extra, block_h + extra, x_off - extra_before, y_off - extra_before, |
| 107 | const int width = FFMAX(FFMIN(pic_width, x_sb + block_w + extra_after) - start_x, 1); | 82 | pic_width, pic_height); |
| 108 | const int height = FFMAX(FFMIN(pic_height, y_sb + block_h + extra_after) - start_y, 1); | ||
| 109 | |||
| 110 | fc->vdsp.emulated_edge_mc(dst, *src - offset, edge_emu_stride, *src_stride, block_w + extra, block_h + extra, | ||
| 111 | x_off - start_x - extra_before, y_off - start_y - extra_before, width, height); | ||
| 112 | |||
| 113 | *src = dst + buf_offset; | ||
| 114 | *src_stride = edge_emu_stride; | ||
| 115 | } | ||
| 116 | } | ||
| 117 | |||
| 118 | static void emulated_edge_bilinear(const VVCLocalContext *lc, uint8_t *dst, const uint8_t **src, ptrdiff_t *src_stride, | ||
| 119 | int x_off, int y_off, const int block_w, const int block_h) | ||
| 120 | { | ||
| 121 | const VVCFrameContext *fc = lc->fc; | ||
| 122 | const VVCSPS *sps = fc->ps.sps; | ||
| 123 | const VVCPPS *pps = fc->ps.pps; | ||
| 124 | const int subpic_idx = lc->sc->sh.r->curr_subpic_idx; | ||
| 125 | int pic_width, pic_height; | ||
| 126 | |||
| 127 | subpic_offset(&x_off, &y_off, sps, pps, subpic_idx, 0); | ||
| 128 | subpic_width_height(&pic_width, &pic_height, sps, pps, subpic_idx, 0); | ||
| 129 | |||
| 130 | if (x_off < BILINEAR_EXTRA_BEFORE || y_off < BILINEAR_EXTRA_BEFORE || | ||
| 131 | x_off >= pic_width - block_w - BILINEAR_EXTRA_AFTER || | ||
| 132 | y_off >= pic_height - block_h - BILINEAR_EXTRA_AFTER) { | ||
| 133 | const ptrdiff_t edge_emu_stride = EDGE_EMU_BUFFER_STRIDE << fc->ps.sps->pixel_shift; | ||
| 134 | const int offset = BILINEAR_EXTRA_BEFORE * *src_stride + (BILINEAR_EXTRA_BEFORE << fc->ps.sps->pixel_shift); | ||
| 135 | const int buf_offset = BILINEAR_EXTRA_BEFORE * edge_emu_stride + (BILINEAR_EXTRA_BEFORE << fc->ps.sps->pixel_shift); | ||
| 136 | |||
| 137 | fc->vdsp.emulated_edge_mc(dst, *src - offset, edge_emu_stride, *src_stride, block_w + BILINEAR_EXTRA, block_h + BILINEAR_EXTRA, | ||
| 138 | x_off - BILINEAR_EXTRA_BEFORE, y_off - BILINEAR_EXTRA_BEFORE, pic_width, pic_height); | ||
| 139 | 83 | ||
| 140 | *src = dst + buf_offset; | 84 | *src = dst + buf_offset; |
| 141 | *src_stride = edge_emu_stride; | 85 | *src_stride = edge_emu_stride; |
| 142 | } | 86 | } |
| 143 | } | 87 | } |
| 144 | 88 | ||
| 145 | #define MC_EMULATED_EDGE(dst, src, src_stride, x_off, y_off) \ | 89 | #define MC_EMULATED_EDGE(dst, src, src_stride, x_off, y_off) \ |
| 146 | emulated_edge(lc, dst, src, src_stride, ref, x_off, y_off, block_w, block_h, is_chroma) | 90 | emulated_edge(lc, dst, src, src_stride, ref, x_off, y_off, x_off, y_off, block_w, block_h, is_chroma, \ |
| 91 | is_chroma ? CHROMA_EXTRA_BEFORE : LUMA_EXTRA_BEFORE, is_chroma ? CHROMA_EXTRA_AFTER : LUMA_EXTRA_AFTER) | ||
| 147 | 92 | ||
| 148 | #define MC_EMULATED_EDGE_DMVR(dst, src, src_stride, x_sb, y_sb, x_off, y_off) \ | 93 | #define MC_EMULATED_EDGE_DMVR(dst, src, src_stride, x_sb, y_sb, x_off, y_off) \ |
| 149 | emulated_edge_dmvr(lc, dst, src, src_stride, x_sb, y_sb, x_off, y_off, block_w, block_h, is_chroma) | 94 | emulated_edge(lc, dst, src, src_stride, ref, x_sb, y_sb, x_off, y_off, block_w, block_h, is_chroma, \ |
| 95 | is_chroma ? CHROMA_EXTRA_BEFORE : LUMA_EXTRA_BEFORE, is_chroma ? CHROMA_EXTRA_AFTER : LUMA_EXTRA_AFTER) | ||
| 150 | 96 | ||
| 151 | #define MC_EMULATED_EDGE_BILINEAR(dst, src, src_stride, x_off, y_off) \ | 97 | #define MC_EMULATED_EDGE_BILINEAR(dst, src, src_stride, x_off, y_off) \ |
| 152 | emulated_edge_bilinear(lc, dst, src, src_stride, x_off, y_off, pred_w, pred_h) | 98 | emulated_edge(lc, dst, src, src_stride, ref, x_off, y_off, x_off, y_off, pred_w, pred_h, 0, \ |
| 99 | BILINEAR_EXTRA_BEFORE, BILINEAR_EXTRA_AFTER) | ||
| 153 | 100 | ||
| 154 | // part of 8.5.6.6 Weighted sample prediction process | 101 | // part of 8.5.6.6 Weighted sample prediction process |
| 155 | static int derive_weight_uni(int *denom, int *wx, int *ox, | 102 | static int derive_weight_uni(int *denom, int *wx, int *ox, |
| @@ -357,23 +304,21 @@ static void scaled_ref_pos_and_step(const VVCLocalContext *lc, const VVCRefPic * · 201 unmodified lines | |||
| 357 | } | 304 | } |
| 358 | 305 | ||
| 359 | static void emulated_edge_scaled(VVCLocalContext *lc, const uint8_t **src, ptrdiff_t *src_stride, int *src_height, | 306 | static void emulated_edge_scaled(VVCLocalContext *lc, const uint8_t **src, ptrdiff_t *src_stride, int *src_height, |
| 360 | const VVCFrame *ref, const int x, const int y, const int dx, const int dy, | 307 | const VVCFrame *ref, const int x, const int y, const int dx, const int dy, const int w, const int h, const int is_chroma) |
| 361 | const int block_w, const int block_h, const int is_chroma) | ||
| 362 | { | 308 | { |
| 363 | const VVCFrameContext *fc = lc->fc; | 309 | const VVCFrameContext *fc = lc->fc; |
| 364 | const int x0 = SCALED_INT(x); | 310 | const int x_off = SCALED_INT(x); |
| 365 | const int y0 = SCALED_INT(y); | 311 | const int y_off = SCALED_INT(y); |
| 366 | const int x_end = SCALED_INT(x + block_w * dx); | 312 | const int x_end = SCALED_INT(x + w * dx); |
| 367 | const int y_end = SCALED_INT(y + block_h * dy); | 313 | const int y_end = SCALED_INT(y + h * dy); |
| 368 | const int x_last = SCALED_INT(x + (block_w - 1) * dx); | 314 | const int x_last = SCALED_INT(x + (w - 1) * dx); |
| 369 | const int y_last = SCALED_INT(y + (block_h - 1) * dy); | 315 | const int y_last = SCALED_INT(y + (h - 1) * dy); |
| 370 | const int src_width = x_end - x0 + (x_end == x_last); | 316 | const int block_w = x_end - x_off + (x_end == x_last); |
| 317 | const int block_h = *src_height = y_end - y_off + (y_end == y_last); | ||
| 371 | 318 | ||
| 372 | *src_height = y_end - y0 + (y_end == y_last); | 319 | *src += y_off * *src_stride + (x_off * (1 << fc->ps.sps->pixel_shift)); |
| 373 | 320 | ||
| 374 | *src += y0 * *src_stride + (x0 * (1 << fc->ps.sps->pixel_shift)); | 321 | MC_EMULATED_EDGE(lc->edge_emu_buffer, src, src_stride, x_off, y_off); |
| 375 | |||
| 376 | emulated_edge(lc, lc->edge_emu_buffer, src, src_stride, ref, x0, y0, src_width, *src_height, is_chroma); | ||
| 377 | } | 322 | } |
| 378 | 323 | ||
| 379 | static void mc_scaled(VVCLocalContext *lc, int16_t *dst, const VVCRefPic *refp, const Mv *mv, | 324 | static void mc_scaled(VVCLocalContext *lc, int16_t *dst, const VVCRefPic *refp, const Mv *mv, |
| @@ -737,11 +682,11 @@ static int parametric_mv_refine(const int *sad, const int stride) · 357 unmodified lines | |||
| 737 | #define SAD_ARRAY_SIZE 5 | 682 | #define SAD_ARRAY_SIZE 5 |
| 738 | //8.5.3 Decoder-side motion vector refinement process | 683 | //8.5.3 Decoder-side motion vector refinement process |
| 739 | static void dmvr_mv_refine(VVCLocalContext *lc, MvField *mvf, MvField *orig_mv, int *sb_bdof_flag, | 684 | static void dmvr_mv_refine(VVCLocalContext *lc, MvField *mvf, MvField *orig_mv, int *sb_bdof_flag, |
| 740 | const AVFrame *ref0, const AVFrame *ref1, const int x_off, const int y_off, const int block_w, const int block_h) | 685 | const VVCFrame *ref0, const VVCFrame *ref1, const int x_off, const int y_off, const int block_w, const int block_h) |
| 741 | { | 686 | { |
| 742 | const VVCFrameContext *fc = lc->fc; | 687 | const VVCFrameContext *fc = lc->fc; |
| 743 | const int sr_range = 2; | 688 | const int sr_range = 2; |
| 744 | const AVFrame *ref[] = { ref0, ref1 }; | 689 | const VVCFrame *refs[] = { ref0, ref1 }; |
| 745 | int16_t *tmp[] = { lc->tmp, lc->tmp1 }; | 690 | int16_t *tmp[] = { lc->tmp, lc->tmp1 }; |
| 746 | int sad[SAD_ARRAY_SIZE][SAD_ARRAY_SIZE]; | 691 | int sad[SAD_ARRAY_SIZE][SAD_ARRAY_SIZE]; |
| 747 | int min_dx, min_dy, min_sad, dx, dy; | 692 | int min_dx, min_dy, min_sad, dx, dy; |
| @@ -757,8 +702,9 @@ static void dmvr_mv_refine(VVCLocalContext *lc, MvField *mvf, MvField *orig_mv, · 9 unmodified lines | |||
| 757 | const int my = mv->y & 0xf; | 702 | const int my = mv->y & 0xf; |
| 758 | const int ox = x_off + (mv->x >> 4) - sr_range; | 703 | const int ox = x_off + (mv->x >> 4) - sr_range; |
| 759 | const int oy = y_off + (mv->y >> 4) - sr_range; | 704 | const int oy = y_off + (mv->y >> 4) - sr_range; |
| 760 | ptrdiff_t src_stride = ref[i]->linesize[LUMA]; | 705 | const VVCFrame *ref = refs[i]; |
| 761 | const uint8_t *src = ref[i]->data[LUMA] + oy * src_stride + (ox * (1 << fc->ps.sps->pixel_shift)); | 706 | ptrdiff_t src_stride = ref->frame->linesize[LUMA]; |
| 707 | const uint8_t *src = ref->frame->data[LUMA] + oy * src_stride + (ox * (1 << fc->ps.sps->pixel_shift)); | ||
| 762 | MC_EMULATED_EDGE_BILINEAR(lc->edge_emu_buffer, &src, &src_stride, ox, oy); | 708 | MC_EMULATED_EDGE_BILINEAR(lc->edge_emu_buffer, &src, &src_stride, ox, oy); |
| 763 | fc->vvcdsp.inter.dmvr[!!my][!!mx](tmp[i], src, src_stride, pred_h, mx, my, pred_w); | 709 | fc->vvcdsp.inter.dmvr[!!my][!!mx](tmp[i], src, src_stride, pred_h, mx, my, pred_w); |
| 764 | } | 710 | } |
| @@ -828,7 +774,7 @@ static void derive_sb_mv(VVCLocalContext *lc, MvField *mv, MvField *orig_mv, int · 63 unmodified lines | |||
| 828 | VVCRefPic *refp[2]; | 774 | VVCRefPic *refp[2]; |
| 829 | if (pred_get_refs(lc, refp, mv) < 0) | 775 | if (pred_get_refs(lc, refp, mv) < 0) |
| 830 | return; | 776 | return; |
| 831 | dmvr_mv_refine(lc, mv, orig_mv, sb_bdof_flag, refp[L0]->ref->frame, refp[L1]->ref->frame, x0, y0, sbw, sbh); | 777 | dmvr_mv_refine(lc, mv, orig_mv, sb_bdof_flag, refp[L0]->ref, refp[L1]->ref, x0, y0, sbw, sbh); |
| 832 | set_dmvr_info(fc, x0, y0, sbw, sbh, mv); | 778 | set_dmvr_info(fc, x0, y0, sbw, sbh, mv); |
| 833 | } | 779 | } |
| 834 | } | 780 | } |