PR #25007 opened by zuxy URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/25007 Patch URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/25007.patch
Convert the last MMX (mmxext) chroma MC functions, 8-bit mc2 put/avg and 10-bit mc4/mc2 put/avg, to SSE2. pshufw becomes pshuflw (identical low half); the 10-bit MC4 macro needs no code change (SPLATW is dual-ISA). Dispatch moves from EXTERNAL_MMXEXT to EXTERNAL_SSE2. checkasm h264chroma passes. No difference in performance. >From d7e92a52b6cd814ad1b1ed6e70ebec2a9da54dcc Mon Sep 17 00:00:00 2001 From: Zuxy Meng <[email protected]> Date: Sat, 10 Oct 2026 21:52:31 -0700 Subject: [PATCH] avcodec/x86/h264: convert chroma MC MMX to SSE2 Convert the last MMX (mmxext) chroma MC functions, 8-bit mc2 put/avg and 10-bit mc4/mc2 put/avg, to SSE2. pshufw becomes pshuflw (identical low half); the 10-bit MC4 macro needs no code change (SPLATW is dual-ISA). Dispatch moves from EXTERNAL_MMXEXT to EXTERNAL_SSE2. checkasm h264chroma passes. No difference in performance. --- libavcodec/x86/h264_chromamc.asm | 14 ++++++------- libavcodec/x86/h264_chromamc_10bit.asm | 14 ++++++------- libavcodec/x86/h264chroma_init.c | 29 ++++++++++++-------------- tests/checkasm/h264chroma.c | 4 ++-- 4 files changed, 28 insertions(+), 33 deletions(-) diff --git a/libavcodec/x86/h264_chromamc.asm b/libavcodec/x86/h264_chromamc.asm index 705da95feb..8d9665e711 100644 --- a/libavcodec/x86/h264_chromamc.asm +++ b/libavcodec/x86/h264_chromamc.asm @@ -1,5 +1,5 @@ ;****************************************************************************** -;* MMX/SSSE3-optimized functions for H.264 chroma MC +;* SSE2/SSSE3-optimized functions for H.264 chroma MC ;* Copyright (c) 2005 Zoltan Hidvegi <hzoli -a- hzoli -d- com>, ;* 2005-2008 Loren Merritt ;* @@ -67,7 +67,7 @@ SECTION .text jne .next4rows %endmacro -%macro chroma_mc2_mmx_func 2 +%macro chroma_mc2_sse2_func 2 cglobal %1_%2_chroma_mc2, 6, 7, 0 mov r6d, r4d shl r4d, 16 @@ -84,7 +84,7 @@ cglobal %1_%2_chroma_mc2, 6, 7, 0 pxor m7, m7 movd m2, [r1] punpcklbw m2, m7 - pshufw m2, m2, 0x94 ; mm0 = src[0,1,1,2] + pshuflw m2, m2, 0x94 ; mm0 = src[0,1,1,2] .nextrow: add r1, r2 @@ -92,7 +92,7 @@ cglobal %1_%2_chroma_mc2, 6, 7, 0 pmaddwd m1, m5 ; mm1 = A * src[0,1] + B * src[1,2] movd m0, [r1] punpcklbw m0, m7 - pshufw m0, m0, 0x94 ; mm0 = src[0,1,1,2] + pshuflw m0, m0, 0x94 ; mm0 = src[0,1,1,2] movq m2, m0 pmaddwd m0, m6 paddw m1, [rnd_2d_%2] @@ -125,14 +125,14 @@ cglobal %1_%2_chroma_mc2, 6, 7, 0 %endmacro -INIT_MMX mmxext +INIT_XMM sse2 %define CHROMAMC_AVG NOTHING %define CHROMAMC_AVG4 NOTHING -chroma_mc2_mmx_func put, h264 +chroma_mc2_sse2_func put, h264 %define CHROMAMC_AVG DIRECT_AVG %define CHROMAMC_AVG4 COPY_AVG -chroma_mc2_mmx_func avg, h264 +chroma_mc2_sse2_func avg, h264 %macro chroma_mc8_ssse3_func 2-3 cglobal %1_%2_chroma_mc8%3, 6, 7+UNIX64, 8 diff --git a/libavcodec/x86/h264_chromamc_10bit.asm b/libavcodec/x86/h264_chromamc_10bit.asm index d4f92c90c7..667cedc04d 100644 --- a/libavcodec/x86/h264_chromamc_10bit.asm +++ b/libavcodec/x86/h264_chromamc_10bit.asm @@ -216,13 +216,13 @@ cglobal %1_h264_chroma_mc2_10, 6,7 punpckldq m5, m5 ; mm5 = {A,B,A,B} punpckldq m6, m6 ; mm6 = {C,D,C,D} pxor m7, m7 - pshufw m2, [r1], 0x94 ; mm0 = src[0,1,1,2] + pshuflw m2, [r1], 0x94 ; mm0 = src[0,1,1,2] .nextrow: add r1, r2 movq m1, m2 pmaddwd m1, m5 ; mm1 = A * src[0,1] + B * src[1,2] - pshufw m0, [r1], 0x94 ; mm0 = src[0,1,1,2] + pshuflw m0, [r1], 0x94 ; mm0 = src[0,1,1,2] movq m2, m0 pmaddwd m0, m6 paddw m1, [pw_32] @@ -247,23 +247,21 @@ cglobal %1_h264_chroma_mc2_10, 6,7 %endmacro %define CHROMAMC_AVG NOTHING -INIT_XMM sse2 -CHROMA_MC8 put %if HAVE_AVX_EXTERNAL INIT_XMM avx CHROMA_MC8 put %endif -INIT_MMX mmxext +INIT_XMM sse2 +CHROMA_MC8 put CHROMA_MC4 put CHROMA_MC2 put %define CHROMAMC_AVG AVG -INIT_XMM sse2 -CHROMA_MC8 avg %if HAVE_AVX_EXTERNAL INIT_XMM avx CHROMA_MC8 avg %endif -INIT_MMX mmxext +INIT_XMM sse2 +CHROMA_MC8 avg CHROMA_MC4 avg CHROMA_MC2 avg diff --git a/libavcodec/x86/h264chroma_init.c b/libavcodec/x86/h264chroma_init.c index 6eb52746ad..6a5d24614d 100644 --- a/libavcodec/x86/h264chroma_init.c +++ b/libavcodec/x86/h264chroma_init.c @@ -24,9 +24,9 @@ #include "libavutil/x86/cpu.h" #include "libavcodec/h264chroma.h" -void ff_put_h264_chroma_mc2_mmxext (uint8_t *dst, const uint8_t *src, +void ff_put_h264_chroma_mc2_sse2 (uint8_t *dst, const uint8_t *src, ptrdiff_t stride, int h, int x, int y); -void ff_avg_h264_chroma_mc2_mmxext (uint8_t *dst, const uint8_t *src, +void ff_avg_h264_chroma_mc2_sse2 (uint8_t *dst, const uint8_t *src, ptrdiff_t stride, int h, int x, int y); void ff_put_h264_chroma_mc8_rnd_ssse3(uint8_t *dst, const uint8_t *src, @@ -44,10 +44,10 @@ void ff_ ## OP ## _h264_chroma_mc ## NUM ## _ ## DEPTH ## _ ## OPT \ (uint8_t *dst, const uint8_t *src, \ ptrdiff_t stride, int h, int x, int y); -CHROMA_MC(put, 2, 10, mmxext) -CHROMA_MC(avg, 2, 10, mmxext) -CHROMA_MC(put, 4, 10, mmxext) -CHROMA_MC(avg, 4, 10, mmxext) +CHROMA_MC(put, 2, 10, sse2) +CHROMA_MC(avg, 2, 10, sse2) +CHROMA_MC(put, 4, 10, sse2) +CHROMA_MC(avg, 4, 10, sse2) CHROMA_MC(put, 8, 10, sse2) CHROMA_MC(avg, 8, 10, sse2) CHROMA_MC(put, 8, 10, avx) @@ -58,19 +58,16 @@ av_cold void ff_h264chroma_init_x86(H264ChromaContext *c, int bit_depth) int high_bit_depth = bit_depth > 8; int cpu_flags = av_get_cpu_flags(); - if (EXTERNAL_MMXEXT(cpu_flags) && !high_bit_depth) { - c->avg_h264_chroma_pixels_tab[2] = ff_avg_h264_chroma_mc2_mmxext; - c->put_h264_chroma_pixels_tab[2] = ff_put_h264_chroma_mc2_mmxext; - } - - if (EXTERNAL_MMXEXT(cpu_flags) && bit_depth > 8 && bit_depth <= 10) { - c->put_h264_chroma_pixels_tab[2] = ff_put_h264_chroma_mc2_10_mmxext; - c->avg_h264_chroma_pixels_tab[2] = ff_avg_h264_chroma_mc2_10_mmxext; - c->put_h264_chroma_pixels_tab[1] = ff_put_h264_chroma_mc4_10_mmxext; - c->avg_h264_chroma_pixels_tab[1] = ff_avg_h264_chroma_mc4_10_mmxext; + if (EXTERNAL_SSE2(cpu_flags) && !high_bit_depth) { + c->avg_h264_chroma_pixels_tab[2] = ff_avg_h264_chroma_mc2_sse2; + c->put_h264_chroma_pixels_tab[2] = ff_put_h264_chroma_mc2_sse2; } if (EXTERNAL_SSE2(cpu_flags) && bit_depth > 8 && bit_depth <= 10) { + c->put_h264_chroma_pixels_tab[2] = ff_put_h264_chroma_mc2_10_sse2; + c->avg_h264_chroma_pixels_tab[2] = ff_avg_h264_chroma_mc2_10_sse2; + c->put_h264_chroma_pixels_tab[1] = ff_put_h264_chroma_mc4_10_sse2; + c->avg_h264_chroma_pixels_tab[1] = ff_avg_h264_chroma_mc4_10_sse2; c->put_h264_chroma_pixels_tab[0] = ff_put_h264_chroma_mc8_10_sse2; c->avg_h264_chroma_pixels_tab[0] = ff_avg_h264_chroma_mc8_10_sse2; } diff --git a/tests/checkasm/h264chroma.c b/tests/checkasm/h264chroma.c index 5115b8b3f1..5697b2b2d8 100644 --- a/tests/checkasm/h264chroma.c +++ b/tests/checkasm/h264chroma.c @@ -46,8 +46,8 @@ static void check_chroma_mc(void) DECLARE_ALIGNED_16(uint8_t, dst0)[16 * 18 * 2]; DECLARE_ALIGNED_16(uint8_t, dst1)[16 * 18 * 2]; - declare_func_emms(AV_CPU_FLAG_MMX, void, uint8_t *dst, const uint8_t *src, - ptrdiff_t stride, int h, int x, int y); + declare_func(void, uint8_t *dst, const uint8_t *src, + ptrdiff_t stride, int h, int x, int y); for (int bit_depth = 8; bit_depth <= 10; bit_depth++) { ff_h264chroma_init(&h, bit_depth); -- 2.52.0 _______________________________________________ ffmpeg-devel mailing list -- [email protected] To unsubscribe send an email to [email protected]
