Message ID | AS8P250MB07442BB411A6556D803295C78F229@AS8P250MB0744.EURP250.PROD.OUTLOOK.COM |
---|---|
State | Accepted |
Commit | ac8afdb9b5228e79ab5582f932434b0dc0bbd186 |
Headers | show |
Series | [FFmpeg-devel,1/6] avcodec/mpegvideo_motion: Move mspel/gmc motion to mpeg4videodec.c | expand |
Context | Check | Description |
---|---|---|
andriy/make_x86 | success | Make finished |
andriy/make_fate_x86 | success | Make fate finished |
Andreas Rheinhardt: > It is the only codec for which mcsel is ever set. > > Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt@outlook.com> > --- > libavcodec/mpeg4videodec.c | 168 ++++++++++++++++++++++++++++++++++ > libavcodec/mpeg4videodec.h | 3 + > libavcodec/mpegvideo_motion.c | 166 +-------------------------------- > 3 files changed, 174 insertions(+), 163 deletions(-) > > diff --git a/libavcodec/mpeg4videodec.c b/libavcodec/mpeg4videodec.c > index 4dbf37afe5..58a8ac9027 100644 > --- a/libavcodec/mpeg4videodec.c > +++ b/libavcodec/mpeg4videodec.c > @@ -72,6 +72,174 @@ static const int mb_type_b_map[4] = { > MB_TYPE_L0 | MB_TYPE_16x16, > }; > > +static void gmc1_motion(MpegEncContext *s, > + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > + uint8_t *const *ref_picture) > +{ > + const uint8_t *ptr; > + int src_x, src_y, motion_x, motion_y; > + ptrdiff_t offset, linesize, uvlinesize; > + int emu = 0; > + > + motion_x = s->sprite_offset[0][0]; > + motion_y = s->sprite_offset[0][1]; > + src_x = s->mb_x * 16 + (motion_x >> (s->sprite_warping_accuracy + 1)); > + src_y = s->mb_y * 16 + (motion_y >> (s->sprite_warping_accuracy + 1)); > + motion_x *= 1 << (3 - s->sprite_warping_accuracy); > + motion_y *= 1 << (3 - s->sprite_warping_accuracy); > + src_x = av_clip(src_x, -16, s->width); > + if (src_x == s->width) > + motion_x = 0; > + src_y = av_clip(src_y, -16, s->height); > + if (src_y == s->height) > + motion_y = 0; > + > + linesize = s->linesize; > + uvlinesize = s->uvlinesize; > + > + ptr = ref_picture[0] + src_y * linesize + src_x; > + > + if ((unsigned)src_x >= FFMAX(s->h_edge_pos - 17, 0) || > + (unsigned)src_y >= FFMAX(s->v_edge_pos - 17, 0)) { > + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > + linesize, linesize, > + 17, 17, > + src_x, src_y, > + s->h_edge_pos, s->v_edge_pos); > + ptr = s->sc.edge_emu_buffer; > + } > + > + if ((motion_x | motion_y) & 7) { > + s->mdsp.gmc1(dest_y, ptr, linesize, 16, > + motion_x & 15, motion_y & 15, 128 - s->no_rounding); > + s->mdsp.gmc1(dest_y + 8, ptr + 8, linesize, 16, > + motion_x & 15, motion_y & 15, 128 - s->no_rounding); > + } else { > + int dxy; > + > + dxy = ((motion_x >> 3) & 1) | ((motion_y >> 2) & 2); > + if (s->no_rounding) { > + s->hdsp.put_no_rnd_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); > + } else { > + s->hdsp.put_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); > + } > + } > + > + if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) > + return; > + > + motion_x = s->sprite_offset[1][0]; > + motion_y = s->sprite_offset[1][1]; > + src_x = s->mb_x * 8 + (motion_x >> (s->sprite_warping_accuracy + 1)); > + src_y = s->mb_y * 8 + (motion_y >> (s->sprite_warping_accuracy + 1)); > + motion_x *= 1 << (3 - s->sprite_warping_accuracy); > + motion_y *= 1 << (3 - s->sprite_warping_accuracy); > + src_x = av_clip(src_x, -8, s->width >> 1); > + if (src_x == s->width >> 1) > + motion_x = 0; > + src_y = av_clip(src_y, -8, s->height >> 1); > + if (src_y == s->height >> 1) > + motion_y = 0; > + > + offset = (src_y * uvlinesize) + src_x; > + ptr = ref_picture[1] + offset; > + if ((unsigned)src_x >= FFMAX((s->h_edge_pos >> 1) - 9, 0) || > + (unsigned)src_y >= FFMAX((s->v_edge_pos >> 1) - 9, 0)) { > + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > + uvlinesize, uvlinesize, > + 9, 9, > + src_x, src_y, > + s->h_edge_pos >> 1, s->v_edge_pos >> 1); > + ptr = s->sc.edge_emu_buffer; > + emu = 1; > + } > + s->mdsp.gmc1(dest_cb, ptr, uvlinesize, 8, > + motion_x & 15, motion_y & 15, 128 - s->no_rounding); > + > + ptr = ref_picture[2] + offset; > + if (emu) { > + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > + uvlinesize, uvlinesize, > + 9, 9, > + src_x, src_y, > + s->h_edge_pos >> 1, s->v_edge_pos >> 1); > + ptr = s->sc.edge_emu_buffer; > + } > + s->mdsp.gmc1(dest_cr, ptr, uvlinesize, 8, > + motion_x & 15, motion_y & 15, 128 - s->no_rounding); > +} > + > +static void gmc_motion(MpegEncContext *s, > + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > + uint8_t *const *ref_picture) > +{ > + const uint8_t *ptr; > + int linesize, uvlinesize; > + const int a = s->sprite_warping_accuracy; > + int ox, oy; > + > + linesize = s->linesize; > + uvlinesize = s->uvlinesize; > + > + ptr = ref_picture[0]; > + > + ox = s->sprite_offset[0][0] + s->sprite_delta[0][0] * s->mb_x * 16 + > + s->sprite_delta[0][1] * s->mb_y * 16; > + oy = s->sprite_offset[0][1] + s->sprite_delta[1][0] * s->mb_x * 16 + > + s->sprite_delta[1][1] * s->mb_y * 16; > + > + s->mdsp.gmc(dest_y, ptr, linesize, 16, > + ox, oy, > + s->sprite_delta[0][0], s->sprite_delta[0][1], > + s->sprite_delta[1][0], s->sprite_delta[1][1], > + a + 1, (1 << (2 * a + 1)) - s->no_rounding, > + s->h_edge_pos, s->v_edge_pos); > + s->mdsp.gmc(dest_y + 8, ptr, linesize, 16, > + ox + s->sprite_delta[0][0] * 8, > + oy + s->sprite_delta[1][0] * 8, > + s->sprite_delta[0][0], s->sprite_delta[0][1], > + s->sprite_delta[1][0], s->sprite_delta[1][1], > + a + 1, (1 << (2 * a + 1)) - s->no_rounding, > + s->h_edge_pos, s->v_edge_pos); > + > + if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) > + return; > + > + ox = s->sprite_offset[1][0] + s->sprite_delta[0][0] * s->mb_x * 8 + > + s->sprite_delta[0][1] * s->mb_y * 8; > + oy = s->sprite_offset[1][1] + s->sprite_delta[1][0] * s->mb_x * 8 + > + s->sprite_delta[1][1] * s->mb_y * 8; > + > + ptr = ref_picture[1]; > + s->mdsp.gmc(dest_cb, ptr, uvlinesize, 8, > + ox, oy, > + s->sprite_delta[0][0], s->sprite_delta[0][1], > + s->sprite_delta[1][0], s->sprite_delta[1][1], > + a + 1, (1 << (2 * a + 1)) - s->no_rounding, > + (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); > + > + ptr = ref_picture[2]; > + s->mdsp.gmc(dest_cr, ptr, uvlinesize, 8, > + ox, oy, > + s->sprite_delta[0][0], s->sprite_delta[0][1], > + s->sprite_delta[1][0], s->sprite_delta[1][1], > + a + 1, (1 << (2 * a + 1)) - s->no_rounding, > + (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); > +} > + > +void ff_mpeg4_mcsel_motion(MpegEncContext *s, > + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > + uint8_t *const *ref_picture) > +{ > + if (s->real_sprite_warping_points == 1) { > + gmc1_motion(s, dest_y, dest_cb, dest_cr, > + ref_picture); > + } else { > + gmc_motion(s, dest_y, dest_cb, dest_cr, > + ref_picture); > + } > +} > + > void ff_mpeg4_decode_studio(MpegEncContext *s, uint8_t *dest_y, uint8_t *dest_cb, > uint8_t *dest_cr, int block_size, int uvlinesize, > int dct_linesize, int dct_offset) > diff --git a/libavcodec/mpeg4videodec.h b/libavcodec/mpeg4videodec.h > index 65d846aed0..8d1e121b67 100644 > --- a/libavcodec/mpeg4videodec.h > +++ b/libavcodec/mpeg4videodec.h > @@ -87,6 +87,9 @@ int ff_mpeg4_decode_picture_header(Mpeg4DecContext *ctx, GetBitContext *gb, > void ff_mpeg4_decode_studio(MpegEncContext *s, uint8_t *dest_y, uint8_t *dest_cb, > uint8_t *dest_cr, int block_size, int uvlinesize, > int dct_linesize, int dct_offset); > +void ff_mpeg4_mcsel_motion(MpegEncContext *s, > + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > + uint8_t *const *ref_picture); > int ff_mpeg4_decode_partitions(Mpeg4DecContext *ctx); > int ff_mpeg4_decode_video_packet_header(Mpeg4DecContext *ctx); > int ff_mpeg4_decode_studio_slice_header(Mpeg4DecContext *ctx); > diff --git a/libavcodec/mpegvideo_motion.c b/libavcodec/mpegvideo_motion.c > index fe3bfc4454..8922f5b1a5 100644 > --- a/libavcodec/mpegvideo_motion.c > +++ b/libavcodec/mpegvideo_motion.c > @@ -31,164 +31,10 @@ > #include "h261.h" > #include "mpegutils.h" > #include "mpegvideo.h" > +#include "mpeg4videodec.h" > #include "qpeldsp.h" > #include "wmv2.h" > > -static void gmc1_motion(MpegEncContext *s, > - uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > - uint8_t *const *ref_picture) > -{ > - const uint8_t *ptr; > - int src_x, src_y, motion_x, motion_y; > - ptrdiff_t offset, linesize, uvlinesize; > - int emu = 0; > - > - motion_x = s->sprite_offset[0][0]; > - motion_y = s->sprite_offset[0][1]; > - src_x = s->mb_x * 16 + (motion_x >> (s->sprite_warping_accuracy + 1)); > - src_y = s->mb_y * 16 + (motion_y >> (s->sprite_warping_accuracy + 1)); > - motion_x *= 1 << (3 - s->sprite_warping_accuracy); > - motion_y *= 1 << (3 - s->sprite_warping_accuracy); > - src_x = av_clip(src_x, -16, s->width); > - if (src_x == s->width) > - motion_x = 0; > - src_y = av_clip(src_y, -16, s->height); > - if (src_y == s->height) > - motion_y = 0; > - > - linesize = s->linesize; > - uvlinesize = s->uvlinesize; > - > - ptr = ref_picture[0] + src_y * linesize + src_x; > - > - if ((unsigned)src_x >= FFMAX(s->h_edge_pos - 17, 0) || > - (unsigned)src_y >= FFMAX(s->v_edge_pos - 17, 0)) { > - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > - linesize, linesize, > - 17, 17, > - src_x, src_y, > - s->h_edge_pos, s->v_edge_pos); > - ptr = s->sc.edge_emu_buffer; > - } > - > - if ((motion_x | motion_y) & 7) { > - s->mdsp.gmc1(dest_y, ptr, linesize, 16, > - motion_x & 15, motion_y & 15, 128 - s->no_rounding); > - s->mdsp.gmc1(dest_y + 8, ptr + 8, linesize, 16, > - motion_x & 15, motion_y & 15, 128 - s->no_rounding); > - } else { > - int dxy; > - > - dxy = ((motion_x >> 3) & 1) | ((motion_y >> 2) & 2); > - if (s->no_rounding) { > - s->hdsp.put_no_rnd_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); > - } else { > - s->hdsp.put_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); > - } > - } > - > - if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) > - return; > - > - motion_x = s->sprite_offset[1][0]; > - motion_y = s->sprite_offset[1][1]; > - src_x = s->mb_x * 8 + (motion_x >> (s->sprite_warping_accuracy + 1)); > - src_y = s->mb_y * 8 + (motion_y >> (s->sprite_warping_accuracy + 1)); > - motion_x *= 1 << (3 - s->sprite_warping_accuracy); > - motion_y *= 1 << (3 - s->sprite_warping_accuracy); > - src_x = av_clip(src_x, -8, s->width >> 1); > - if (src_x == s->width >> 1) > - motion_x = 0; > - src_y = av_clip(src_y, -8, s->height >> 1); > - if (src_y == s->height >> 1) > - motion_y = 0; > - > - offset = (src_y * uvlinesize) + src_x; > - ptr = ref_picture[1] + offset; > - if ((unsigned)src_x >= FFMAX((s->h_edge_pos >> 1) - 9, 0) || > - (unsigned)src_y >= FFMAX((s->v_edge_pos >> 1) - 9, 0)) { > - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > - uvlinesize, uvlinesize, > - 9, 9, > - src_x, src_y, > - s->h_edge_pos >> 1, s->v_edge_pos >> 1); > - ptr = s->sc.edge_emu_buffer; > - emu = 1; > - } > - s->mdsp.gmc1(dest_cb, ptr, uvlinesize, 8, > - motion_x & 15, motion_y & 15, 128 - s->no_rounding); > - > - ptr = ref_picture[2] + offset; > - if (emu) { > - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, > - uvlinesize, uvlinesize, > - 9, 9, > - src_x, src_y, > - s->h_edge_pos >> 1, s->v_edge_pos >> 1); > - ptr = s->sc.edge_emu_buffer; > - } > - s->mdsp.gmc1(dest_cr, ptr, uvlinesize, 8, > - motion_x & 15, motion_y & 15, 128 - s->no_rounding); > -} > - > -static void gmc_motion(MpegEncContext *s, > - uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, > - uint8_t *const *ref_picture) > -{ > - const uint8_t *ptr; > - int linesize, uvlinesize; > - const int a = s->sprite_warping_accuracy; > - int ox, oy; > - > - linesize = s->linesize; > - uvlinesize = s->uvlinesize; > - > - ptr = ref_picture[0]; > - > - ox = s->sprite_offset[0][0] + s->sprite_delta[0][0] * s->mb_x * 16 + > - s->sprite_delta[0][1] * s->mb_y * 16; > - oy = s->sprite_offset[0][1] + s->sprite_delta[1][0] * s->mb_x * 16 + > - s->sprite_delta[1][1] * s->mb_y * 16; > - > - s->mdsp.gmc(dest_y, ptr, linesize, 16, > - ox, oy, > - s->sprite_delta[0][0], s->sprite_delta[0][1], > - s->sprite_delta[1][0], s->sprite_delta[1][1], > - a + 1, (1 << (2 * a + 1)) - s->no_rounding, > - s->h_edge_pos, s->v_edge_pos); > - s->mdsp.gmc(dest_y + 8, ptr, linesize, 16, > - ox + s->sprite_delta[0][0] * 8, > - oy + s->sprite_delta[1][0] * 8, > - s->sprite_delta[0][0], s->sprite_delta[0][1], > - s->sprite_delta[1][0], s->sprite_delta[1][1], > - a + 1, (1 << (2 * a + 1)) - s->no_rounding, > - s->h_edge_pos, s->v_edge_pos); > - > - if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) > - return; > - > - ox = s->sprite_offset[1][0] + s->sprite_delta[0][0] * s->mb_x * 8 + > - s->sprite_delta[0][1] * s->mb_y * 8; > - oy = s->sprite_offset[1][1] + s->sprite_delta[1][0] * s->mb_x * 8 + > - s->sprite_delta[1][1] * s->mb_y * 8; > - > - ptr = ref_picture[1]; > - s->mdsp.gmc(dest_cb, ptr, uvlinesize, 8, > - ox, oy, > - s->sprite_delta[0][0], s->sprite_delta[0][1], > - s->sprite_delta[1][0], s->sprite_delta[1][1], > - a + 1, (1 << (2 * a + 1)) - s->no_rounding, > - (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); > - > - ptr = ref_picture[2]; > - s->mdsp.gmc(dest_cr, ptr, uvlinesize, 8, > - ox, oy, > - s->sprite_delta[0][0], s->sprite_delta[0][1], > - s->sprite_delta[1][0], s->sprite_delta[1][1], > - a + 1, (1 << (2 * a + 1)) - s->no_rounding, > - (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); > -} > - > static inline int hpel_motion(MpegEncContext *s, > uint8_t *dest, uint8_t *src, > int src_x, int src_y, > @@ -849,14 +695,8 @@ static av_always_inline void mpv_motion_internal(MpegEncContext *s, > > switch (s->mv_type) { > case MV_TYPE_16X16: > - if (!is_mpeg12 && s->mcsel) { > - if (s->real_sprite_warping_points == 1) { > - gmc1_motion(s, dest_y, dest_cb, dest_cr, > - ref_picture); > - } else { > - gmc_motion(s, dest_y, dest_cb, dest_cr, > - ref_picture); > - } > + if (CONFIG_MPEG4_DECODER && !is_mpeg12 && s->mcsel) { > + ff_mpeg4_mcsel_motion(s, dest_y, dest_cb, dest_cr, ref_picture); > } else if (!is_mpeg12 && s->quarter_sample) { > qpel_motion(s, dest_y, dest_cb, dest_cr, > 0, 0, 0, Will apply this patchset tomorrow unless there are objections. - Andreas
diff --git a/libavcodec/mpeg4videodec.c b/libavcodec/mpeg4videodec.c index 4dbf37afe5..58a8ac9027 100644 --- a/libavcodec/mpeg4videodec.c +++ b/libavcodec/mpeg4videodec.c @@ -72,6 +72,174 @@ static const int mb_type_b_map[4] = { MB_TYPE_L0 | MB_TYPE_16x16, }; +static void gmc1_motion(MpegEncContext *s, + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, + uint8_t *const *ref_picture) +{ + const uint8_t *ptr; + int src_x, src_y, motion_x, motion_y; + ptrdiff_t offset, linesize, uvlinesize; + int emu = 0; + + motion_x = s->sprite_offset[0][0]; + motion_y = s->sprite_offset[0][1]; + src_x = s->mb_x * 16 + (motion_x >> (s->sprite_warping_accuracy + 1)); + src_y = s->mb_y * 16 + (motion_y >> (s->sprite_warping_accuracy + 1)); + motion_x *= 1 << (3 - s->sprite_warping_accuracy); + motion_y *= 1 << (3 - s->sprite_warping_accuracy); + src_x = av_clip(src_x, -16, s->width); + if (src_x == s->width) + motion_x = 0; + src_y = av_clip(src_y, -16, s->height); + if (src_y == s->height) + motion_y = 0; + + linesize = s->linesize; + uvlinesize = s->uvlinesize; + + ptr = ref_picture[0] + src_y * linesize + src_x; + + if ((unsigned)src_x >= FFMAX(s->h_edge_pos - 17, 0) || + (unsigned)src_y >= FFMAX(s->v_edge_pos - 17, 0)) { + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, + linesize, linesize, + 17, 17, + src_x, src_y, + s->h_edge_pos, s->v_edge_pos); + ptr = s->sc.edge_emu_buffer; + } + + if ((motion_x | motion_y) & 7) { + s->mdsp.gmc1(dest_y, ptr, linesize, 16, + motion_x & 15, motion_y & 15, 128 - s->no_rounding); + s->mdsp.gmc1(dest_y + 8, ptr + 8, linesize, 16, + motion_x & 15, motion_y & 15, 128 - s->no_rounding); + } else { + int dxy; + + dxy = ((motion_x >> 3) & 1) | ((motion_y >> 2) & 2); + if (s->no_rounding) { + s->hdsp.put_no_rnd_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); + } else { + s->hdsp.put_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); + } + } + + if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) + return; + + motion_x = s->sprite_offset[1][0]; + motion_y = s->sprite_offset[1][1]; + src_x = s->mb_x * 8 + (motion_x >> (s->sprite_warping_accuracy + 1)); + src_y = s->mb_y * 8 + (motion_y >> (s->sprite_warping_accuracy + 1)); + motion_x *= 1 << (3 - s->sprite_warping_accuracy); + motion_y *= 1 << (3 - s->sprite_warping_accuracy); + src_x = av_clip(src_x, -8, s->width >> 1); + if (src_x == s->width >> 1) + motion_x = 0; + src_y = av_clip(src_y, -8, s->height >> 1); + if (src_y == s->height >> 1) + motion_y = 0; + + offset = (src_y * uvlinesize) + src_x; + ptr = ref_picture[1] + offset; + if ((unsigned)src_x >= FFMAX((s->h_edge_pos >> 1) - 9, 0) || + (unsigned)src_y >= FFMAX((s->v_edge_pos >> 1) - 9, 0)) { + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, + uvlinesize, uvlinesize, + 9, 9, + src_x, src_y, + s->h_edge_pos >> 1, s->v_edge_pos >> 1); + ptr = s->sc.edge_emu_buffer; + emu = 1; + } + s->mdsp.gmc1(dest_cb, ptr, uvlinesize, 8, + motion_x & 15, motion_y & 15, 128 - s->no_rounding); + + ptr = ref_picture[2] + offset; + if (emu) { + s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, + uvlinesize, uvlinesize, + 9, 9, + src_x, src_y, + s->h_edge_pos >> 1, s->v_edge_pos >> 1); + ptr = s->sc.edge_emu_buffer; + } + s->mdsp.gmc1(dest_cr, ptr, uvlinesize, 8, + motion_x & 15, motion_y & 15, 128 - s->no_rounding); +} + +static void gmc_motion(MpegEncContext *s, + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, + uint8_t *const *ref_picture) +{ + const uint8_t *ptr; + int linesize, uvlinesize; + const int a = s->sprite_warping_accuracy; + int ox, oy; + + linesize = s->linesize; + uvlinesize = s->uvlinesize; + + ptr = ref_picture[0]; + + ox = s->sprite_offset[0][0] + s->sprite_delta[0][0] * s->mb_x * 16 + + s->sprite_delta[0][1] * s->mb_y * 16; + oy = s->sprite_offset[0][1] + s->sprite_delta[1][0] * s->mb_x * 16 + + s->sprite_delta[1][1] * s->mb_y * 16; + + s->mdsp.gmc(dest_y, ptr, linesize, 16, + ox, oy, + s->sprite_delta[0][0], s->sprite_delta[0][1], + s->sprite_delta[1][0], s->sprite_delta[1][1], + a + 1, (1 << (2 * a + 1)) - s->no_rounding, + s->h_edge_pos, s->v_edge_pos); + s->mdsp.gmc(dest_y + 8, ptr, linesize, 16, + ox + s->sprite_delta[0][0] * 8, + oy + s->sprite_delta[1][0] * 8, + s->sprite_delta[0][0], s->sprite_delta[0][1], + s->sprite_delta[1][0], s->sprite_delta[1][1], + a + 1, (1 << (2 * a + 1)) - s->no_rounding, + s->h_edge_pos, s->v_edge_pos); + + if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) + return; + + ox = s->sprite_offset[1][0] + s->sprite_delta[0][0] * s->mb_x * 8 + + s->sprite_delta[0][1] * s->mb_y * 8; + oy = s->sprite_offset[1][1] + s->sprite_delta[1][0] * s->mb_x * 8 + + s->sprite_delta[1][1] * s->mb_y * 8; + + ptr = ref_picture[1]; + s->mdsp.gmc(dest_cb, ptr, uvlinesize, 8, + ox, oy, + s->sprite_delta[0][0], s->sprite_delta[0][1], + s->sprite_delta[1][0], s->sprite_delta[1][1], + a + 1, (1 << (2 * a + 1)) - s->no_rounding, + (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); + + ptr = ref_picture[2]; + s->mdsp.gmc(dest_cr, ptr, uvlinesize, 8, + ox, oy, + s->sprite_delta[0][0], s->sprite_delta[0][1], + s->sprite_delta[1][0], s->sprite_delta[1][1], + a + 1, (1 << (2 * a + 1)) - s->no_rounding, + (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); +} + +void ff_mpeg4_mcsel_motion(MpegEncContext *s, + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, + uint8_t *const *ref_picture) +{ + if (s->real_sprite_warping_points == 1) { + gmc1_motion(s, dest_y, dest_cb, dest_cr, + ref_picture); + } else { + gmc_motion(s, dest_y, dest_cb, dest_cr, + ref_picture); + } +} + void ff_mpeg4_decode_studio(MpegEncContext *s, uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, int block_size, int uvlinesize, int dct_linesize, int dct_offset) diff --git a/libavcodec/mpeg4videodec.h b/libavcodec/mpeg4videodec.h index 65d846aed0..8d1e121b67 100644 --- a/libavcodec/mpeg4videodec.h +++ b/libavcodec/mpeg4videodec.h @@ -87,6 +87,9 @@ int ff_mpeg4_decode_picture_header(Mpeg4DecContext *ctx, GetBitContext *gb, void ff_mpeg4_decode_studio(MpegEncContext *s, uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, int block_size, int uvlinesize, int dct_linesize, int dct_offset); +void ff_mpeg4_mcsel_motion(MpegEncContext *s, + uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, + uint8_t *const *ref_picture); int ff_mpeg4_decode_partitions(Mpeg4DecContext *ctx); int ff_mpeg4_decode_video_packet_header(Mpeg4DecContext *ctx); int ff_mpeg4_decode_studio_slice_header(Mpeg4DecContext *ctx); diff --git a/libavcodec/mpegvideo_motion.c b/libavcodec/mpegvideo_motion.c index fe3bfc4454..8922f5b1a5 100644 --- a/libavcodec/mpegvideo_motion.c +++ b/libavcodec/mpegvideo_motion.c @@ -31,164 +31,10 @@ #include "h261.h" #include "mpegutils.h" #include "mpegvideo.h" +#include "mpeg4videodec.h" #include "qpeldsp.h" #include "wmv2.h" -static void gmc1_motion(MpegEncContext *s, - uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, - uint8_t *const *ref_picture) -{ - const uint8_t *ptr; - int src_x, src_y, motion_x, motion_y; - ptrdiff_t offset, linesize, uvlinesize; - int emu = 0; - - motion_x = s->sprite_offset[0][0]; - motion_y = s->sprite_offset[0][1]; - src_x = s->mb_x * 16 + (motion_x >> (s->sprite_warping_accuracy + 1)); - src_y = s->mb_y * 16 + (motion_y >> (s->sprite_warping_accuracy + 1)); - motion_x *= 1 << (3 - s->sprite_warping_accuracy); - motion_y *= 1 << (3 - s->sprite_warping_accuracy); - src_x = av_clip(src_x, -16, s->width); - if (src_x == s->width) - motion_x = 0; - src_y = av_clip(src_y, -16, s->height); - if (src_y == s->height) - motion_y = 0; - - linesize = s->linesize; - uvlinesize = s->uvlinesize; - - ptr = ref_picture[0] + src_y * linesize + src_x; - - if ((unsigned)src_x >= FFMAX(s->h_edge_pos - 17, 0) || - (unsigned)src_y >= FFMAX(s->v_edge_pos - 17, 0)) { - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, - linesize, linesize, - 17, 17, - src_x, src_y, - s->h_edge_pos, s->v_edge_pos); - ptr = s->sc.edge_emu_buffer; - } - - if ((motion_x | motion_y) & 7) { - s->mdsp.gmc1(dest_y, ptr, linesize, 16, - motion_x & 15, motion_y & 15, 128 - s->no_rounding); - s->mdsp.gmc1(dest_y + 8, ptr + 8, linesize, 16, - motion_x & 15, motion_y & 15, 128 - s->no_rounding); - } else { - int dxy; - - dxy = ((motion_x >> 3) & 1) | ((motion_y >> 2) & 2); - if (s->no_rounding) { - s->hdsp.put_no_rnd_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); - } else { - s->hdsp.put_pixels_tab[0][dxy](dest_y, ptr, linesize, 16); - } - } - - if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) - return; - - motion_x = s->sprite_offset[1][0]; - motion_y = s->sprite_offset[1][1]; - src_x = s->mb_x * 8 + (motion_x >> (s->sprite_warping_accuracy + 1)); - src_y = s->mb_y * 8 + (motion_y >> (s->sprite_warping_accuracy + 1)); - motion_x *= 1 << (3 - s->sprite_warping_accuracy); - motion_y *= 1 << (3 - s->sprite_warping_accuracy); - src_x = av_clip(src_x, -8, s->width >> 1); - if (src_x == s->width >> 1) - motion_x = 0; - src_y = av_clip(src_y, -8, s->height >> 1); - if (src_y == s->height >> 1) - motion_y = 0; - - offset = (src_y * uvlinesize) + src_x; - ptr = ref_picture[1] + offset; - if ((unsigned)src_x >= FFMAX((s->h_edge_pos >> 1) - 9, 0) || - (unsigned)src_y >= FFMAX((s->v_edge_pos >> 1) - 9, 0)) { - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, - uvlinesize, uvlinesize, - 9, 9, - src_x, src_y, - s->h_edge_pos >> 1, s->v_edge_pos >> 1); - ptr = s->sc.edge_emu_buffer; - emu = 1; - } - s->mdsp.gmc1(dest_cb, ptr, uvlinesize, 8, - motion_x & 15, motion_y & 15, 128 - s->no_rounding); - - ptr = ref_picture[2] + offset; - if (emu) { - s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr, - uvlinesize, uvlinesize, - 9, 9, - src_x, src_y, - s->h_edge_pos >> 1, s->v_edge_pos >> 1); - ptr = s->sc.edge_emu_buffer; - } - s->mdsp.gmc1(dest_cr, ptr, uvlinesize, 8, - motion_x & 15, motion_y & 15, 128 - s->no_rounding); -} - -static void gmc_motion(MpegEncContext *s, - uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr, - uint8_t *const *ref_picture) -{ - const uint8_t *ptr; - int linesize, uvlinesize; - const int a = s->sprite_warping_accuracy; - int ox, oy; - - linesize = s->linesize; - uvlinesize = s->uvlinesize; - - ptr = ref_picture[0]; - - ox = s->sprite_offset[0][0] + s->sprite_delta[0][0] * s->mb_x * 16 + - s->sprite_delta[0][1] * s->mb_y * 16; - oy = s->sprite_offset[0][1] + s->sprite_delta[1][0] * s->mb_x * 16 + - s->sprite_delta[1][1] * s->mb_y * 16; - - s->mdsp.gmc(dest_y, ptr, linesize, 16, - ox, oy, - s->sprite_delta[0][0], s->sprite_delta[0][1], - s->sprite_delta[1][0], s->sprite_delta[1][1], - a + 1, (1 << (2 * a + 1)) - s->no_rounding, - s->h_edge_pos, s->v_edge_pos); - s->mdsp.gmc(dest_y + 8, ptr, linesize, 16, - ox + s->sprite_delta[0][0] * 8, - oy + s->sprite_delta[1][0] * 8, - s->sprite_delta[0][0], s->sprite_delta[0][1], - s->sprite_delta[1][0], s->sprite_delta[1][1], - a + 1, (1 << (2 * a + 1)) - s->no_rounding, - s->h_edge_pos, s->v_edge_pos); - - if (CONFIG_GRAY && s->avctx->flags & AV_CODEC_FLAG_GRAY) - return; - - ox = s->sprite_offset[1][0] + s->sprite_delta[0][0] * s->mb_x * 8 + - s->sprite_delta[0][1] * s->mb_y * 8; - oy = s->sprite_offset[1][1] + s->sprite_delta[1][0] * s->mb_x * 8 + - s->sprite_delta[1][1] * s->mb_y * 8; - - ptr = ref_picture[1]; - s->mdsp.gmc(dest_cb, ptr, uvlinesize, 8, - ox, oy, - s->sprite_delta[0][0], s->sprite_delta[0][1], - s->sprite_delta[1][0], s->sprite_delta[1][1], - a + 1, (1 << (2 * a + 1)) - s->no_rounding, - (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); - - ptr = ref_picture[2]; - s->mdsp.gmc(dest_cr, ptr, uvlinesize, 8, - ox, oy, - s->sprite_delta[0][0], s->sprite_delta[0][1], - s->sprite_delta[1][0], s->sprite_delta[1][1], - a + 1, (1 << (2 * a + 1)) - s->no_rounding, - (s->h_edge_pos + 1) >> 1, (s->v_edge_pos + 1) >> 1); -} - static inline int hpel_motion(MpegEncContext *s, uint8_t *dest, uint8_t *src, int src_x, int src_y, @@ -849,14 +695,8 @@ static av_always_inline void mpv_motion_internal(MpegEncContext *s, switch (s->mv_type) { case MV_TYPE_16X16: - if (!is_mpeg12 && s->mcsel) { - if (s->real_sprite_warping_points == 1) { - gmc1_motion(s, dest_y, dest_cb, dest_cr, - ref_picture); - } else { - gmc_motion(s, dest_y, dest_cb, dest_cr, - ref_picture); - } + if (CONFIG_MPEG4_DECODER && !is_mpeg12 && s->mcsel) { + ff_mpeg4_mcsel_motion(s, dest_y, dest_cb, dest_cr, ref_picture); } else if (!is_mpeg12 && s->quarter_sample) { qpel_motion(s, dest_y, dest_cb, dest_cr, 0, 0, 0,
It is the only codec for which mcsel is ever set. Signed-off-by: Andreas Rheinhardt <andreas.rheinhardt@outlook.com> --- libavcodec/mpeg4videodec.c | 168 ++++++++++++++++++++++++++++++++++ libavcodec/mpeg4videodec.h | 3 + libavcodec/mpegvideo_motion.c | 166 +-------------------------------- 3 files changed, 174 insertions(+), 163 deletions(-)