Git Inbox Mirror of the ffmpeg-devel mailing list - see https://ffmpeg.org/mailman/listinfo/ffmpeg-devel
 help / color / mirror / Atom feed
From: averne via ffmpeg-devel <ffmpeg-devel@ffmpeg.org>
To: ffmpeg-devel@ffmpeg.org
Cc: averne <code@ffmpeg.org>
Subject: [FFmpeg-devel] [PATCH] vulkan/prores: Adopt the same IDCT routine as the prores-raw hwaccel (PR #20819)
Date: Sun, 02 Nov 2025 19:27:33 -0000
Message-ID: <176211165375.25.10975636295279296971@2cb04c0e5124> (raw)

PR #20819 opened by averne
URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/20819
Patch URL: https://code.ffmpeg.org/FFmpeg/FFmpeg/pulls/20819.patch

The added rounding at the final output conforms
to the SMPTE document and reduces the deviation
against the software decoder.


>From 7639b6fd0cec3e7ae31f1d0c2d1fc491dbd937e5 Mon Sep 17 00:00:00 2001
From: averne <averne381@gmail.com>
Date: Sun, 2 Nov 2025 20:23:28 +0100
Subject: [PATCH] vulkan/prores: Adopt the same IDCT routine as the prores-raw
 hwaccel

The added rounding at the final output conforms
to the SMPTE document and reduces the deviation
against the software decoder.
---
 libavcodec/vulkan/prores_idct.comp | 105 +++++++++++++++++++----------
 1 file changed, 68 insertions(+), 37 deletions(-)

diff --git a/libavcodec/vulkan/prores_idct.comp b/libavcodec/vulkan/prores_idct.comp
index 642fcb5bd5..8ad3b7f58b 100644
--- a/libavcodec/vulkan/prores_idct.comp
+++ b/libavcodec/vulkan/prores_idct.comp
@@ -37,47 +37,77 @@ void put_px(uint tex_idx, ivec2 pos, uint v)
 #endif
 }
 
+const float idct_8x8_scales[] = {
+    0.353553390593274f, // cos(4 * pi/16) / 2
+    0.490392640201615f, // cos(1 * pi/16) / 2
+    0.461939766255643f, // cos(2 * pi/16) / 2
+    0.415734806151273f, // cos(3 * pi/16) / 2
+    0.353553390593274f, // cos(4 * pi/16) / 2
+    0.277785116509801f, // cos(5 * pi/16) / 2
+    0.191341716182545f, // cos(6 * pi/16) / 2
+    0.097545161008064f, // cos(7 * pi/16) / 2
+};
+
 /* 7.4 Inverse Transform */
 void idct(uint block, uint offset, uint stride)
 {
-    float c0 = blocks[block][0*stride + offset];
-    float c1 = blocks[block][1*stride + offset];
-    float c2 = blocks[block][2*stride + offset];
-    float c3 = blocks[block][3*stride + offset];
-    float c4 = blocks[block][4*stride + offset];
-    float c5 = blocks[block][5*stride + offset];
-    float c6 = blocks[block][6*stride + offset];
-    float c7 = blocks[block][7*stride + offset];
+    float t0, t1, t2, t3, t4, t5, t6, t7, u8;
+    float u0, u1, u2, u3, u4, u5, u6, u7;
 
-    float tmp1 = c6 * 1.4142134189605712891 + (c2 - c6);
-    float tmp2 = c6 * 1.4142134189605712891 - (c2 - c6);
+    /* Input */
+    t0 = blocks[block][0*stride + offset];
+    u4 = blocks[block][1*stride + offset];
+    t2 = blocks[block][2*stride + offset];
+    u6 = blocks[block][3*stride + offset];
+    t1 = blocks[block][4*stride + offset];
+    u5 = blocks[block][5*stride + offset];
+    t3 = blocks[block][6*stride + offset];
+    u7 = blocks[block][7*stride + offset];
 
-    float a1 = (c0 + c4) * 0.35355341434478759766 + tmp1 * 0.46193981170654296875;
-    float a4 = (c0 + c4) * 0.35355341434478759766 - tmp1 * 0.46193981170654296875;
+    /* Embedded scaled inverse 4-point Type-II DCT */
+    u0 = t0 + t1;
+    u1 = t0 - t1;
+    u3 = t2 + t3;
+    u2 = (t2 - t3)*(1.4142135623730950488016887242097f) - u3;
+    t0 = u0 + u3;
+    t3 = u0 - u3;
+    t1 = u1 + u2;
+    t2 = u1 - u2;
 
-    float a3 = (c0 - c4) * 0.35355341434478759766 + tmp2 * 0.19134169816970825195;
-    float a2 = (c0 - c4) * 0.35355341434478759766 - tmp2 * 0.19134169816970825195;
+    /* Embedded scaled inverse 4-point Type-IV DST */
+    t5 = u5 + u6;
+    t6 = u5 - u6;
+    t7 = u4 + u7;
+    t4 = u4 - u7;
+    u7 = t7 + t5;
+    u5 = (t7 - t5)*(1.4142135623730950488016887242097f);
+    u8 = (t4 + t6)*(1.8477590650225735122563663787936f);
+    u4 = u8 - t4*(1.0823922002923939687994464107328f);
+    u6 = u8 - t6*(2.6131259297527530557132863468544f);
+    t7 = u7;
+    t6 = t7 - u6;
+    t5 = t6 + u5;
+    t4 = t5 - u4;
 
-    float tmp3 = (c3 - c5) * 0.70710682868957519531 + c7;
-    float tmp4 = (c3 - c5) * 0.70710682868957519531 - c7;
+    /* Butterflies */
+    u0 = t0 + t7;
+    u7 = t0 - t7;
+    u6 = t1 + t6;
+    u1 = t1 - t6;
+    u2 = t2 + t5;
+    u5 = t2 - t5;
+    u4 = t3 + t4;
+    u3 = t3 - t4;
 
-    float tmp5 = (c5 - c7) *  1.4142134189605712891 + (c5 - c7) + (c1 - c3);
-    float tmp6 = (c5 - c7) * -1.4142134189605712891 + (c5 - c7) + (c1 - c3);
-
-    float m1 = tmp3 *  2.6131260395050048828 + tmp5;
-    float m4 = tmp3 * -2.6131260395050048828 + tmp5;
-
-    float m2 = tmp4 *  1.0823919773101806641 + tmp6;
-    float m3 = tmp4 * -1.0823919773101806641 + tmp6;
-
-    blocks[block][0*stride + offset] = m1 *  0.49039259552955627441  + a1;
-    blocks[block][7*stride + offset] = m1 * -0.49039259552955627441  + a1;
-    blocks[block][1*stride + offset] = m2 *  0.41573479771614074707  + a2;
-    blocks[block][6*stride + offset] = m2 * -0.41573479771614074707  + a2;
-    blocks[block][2*stride + offset] = m3 *  0.27778509259223937988  + a3;
-    blocks[block][5*stride + offset] = m3 * -0.27778509259223937988  + a3;
-    blocks[block][3*stride + offset] = m4 *  0.097545139491558074951 + a4;
-    blocks[block][4*stride + offset] = m4 * -0.097545139491558074951 + a4;
+    /* Output */
+    blocks[block][0*stride + offset] = u0;
+    blocks[block][1*stride + offset] = u1;
+    blocks[block][2*stride + offset] = u2;
+    blocks[block][3*stride + offset] = u3;
+    blocks[block][4*stride + offset] = u4;
+    blocks[block][5*stride + offset] = u5;
+    blocks[block][6*stride + offset] = u6;
+    blocks[block][7*stride + offset] = u7;
 }
 
 void main(void)
@@ -90,14 +120,15 @@ void main(void)
     /* Coalesced load of DCT coeffs in shared memory, second part of inverse quantization */
     if (act) {
         /**
-         * According to spec indexing an array in push constant memory with
+         * According to the VK spec indexing an array in push constant memory with
          * a non-dynamically uniform value is illegal ($15.9.1 in v1.4.326),
          * so copy the whole matrix locally.
          */
         uint8_t[64] qmat = comp == 0 ? qmat_luma : qmat_chroma;
         [[unroll]] for (uint i = 0; i < 8; ++i) {
-            int v = sign_extend(int(get_px(comp, ivec2(gid.x, (gid.y << 3) | i))), 16);
-            blocks[block][i * 9 + idx] = float(v * int(qmat[(i << 3) + idx]));
+            int   c = sign_extend(int(get_px(comp, ivec2(gid.x, (gid.y << 3) | i))), 16);
+            float v = float(c * int(qmat[(i << 3) + idx]));
+            blocks[block][i * 9 + idx] = v * idct_8x8_scales[idx] * idct_8x8_scales[i];
         }
     }
 
@@ -116,7 +147,7 @@ void main(void)
     barrier();
     if (act) {
         [[unroll]] for (uint i = 0; i < 8; ++i) {
-            float v = blocks[block][i * 9 + idx] * fact + off;
+            float v = round(blocks[block][i * 9 + idx] * fact + off);
             put_px(comp, ivec2(gid.x, (gid.y << 3) | i), clamp(int(v), 0, maxv) << shift);
         }
     }
-- 
2.49.1

_______________________________________________
ffmpeg-devel mailing list -- ffmpeg-devel@ffmpeg.org
To unsubscribe send an email to ffmpeg-devel-leave@ffmpeg.org

                 reply	other threads:[~2025-11-02 19:28 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=176211165375.25.10975636295279296971@2cb04c0e5124 \
    --to=ffmpeg-devel@ffmpeg.org \
    --cc=code@ffmpeg.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

Git Inbox Mirror of the ffmpeg-devel mailing list - see https://ffmpeg.org/mailman/listinfo/ffmpeg-devel

This inbox may be cloned and mirrored by anyone:

	git clone --mirror https://master.gitmailbox.com/ffmpegdev/0 ffmpegdev/git/0.git

	# If you have public-inbox 1.1+ installed, you may
	# initialize and index your mirror using the following commands:
	public-inbox-init -V2 ffmpegdev ffmpegdev/ https://master.gitmailbox.com/ffmpegdev \
		ffmpegdev@gitmailbox.com
	public-inbox-index ffmpegdev

Example config snippet for mirrors.


AGPL code for this site: git clone https://public-inbox.org/public-inbox.git