Skip to content

[SPU LLVM] Optimize AVX-512 XFloat conversion - #19244

Merged
elad335 merged 3 commits into
RPCS3:masterfrom
Yahfz:spu-avx512-xfloat-conversions
Aug 20, 2026
Merged

elad335 merged 3 commits into
RPCS3:masterfrom
Yahfz:spu-avx512-xfloat-conversions

Conversation

@Yahfz

@Yahfz Yahfz commented Aug 16, 2026

Copy link
Copy Markdown
Member

Uses vptestmd and vpternlogq to simplify xfloat expansion:

Before:
666: 62 a2 7d 28 35 c7 vpmovzxdq ymm16, xmm23
66c: 62 e1 fd 20 db f1 vpandq ymm22, ymm16, ymm1
672: 62 e1 fd 20 db c2 vpandq ymm16, ymm16, ymm2
678: 62 b1 cd 20 73 f6 20 vpsllq ymm22, ymm22, 0x20
67f: 62 b1 c5 20 73 f0 1d vpsllq ymm23, ymm16, 0x1d
686: 62 f2 fd 20 37 cc vpcmpgtq k1, ymm16, ymm4
68c: 62 a1 c5 20 eb fe vporq ymm23, ymm23, ymm22
692: 62 e1 c5 21 d4 f3 vpaddq ymm22{k1}, ymm23, ymm3
After:
4ad: c4 c2 7d 35 c7 vpmovzxdq ymm0, xmm15
4b2: 62 f2 05 08 27 cc vptestmd k1, xmm15, xmm4
4b8: 62 f1 e5 20 73 f0 20 vpsllq ymm19, ymm0, 0x20
4bf: c5 fd 73 f0 1d vpsllq ymm0, ymm0, 0x1d
4c4: 62 e1 e5 20 db d9 vpandq ymm19, ymm19, ymm1
4ca: 62 f3 e5 20 25 c2 ec vpternlogq ymm0, ymm19, ymm2, 0xec
4d1: 62 e1 fd 29 d4 db vpaddq ymm19{k1}, ymm0, ymm3

It also replaces the fp xfloat clamp with integer compare/min operations:
Before:
605: 62 c2 e5 20 a8 f7 vfmadd213pd ymm22, ymm19, ymm15
60b: 62 c1 cd 20 54 c1 vandpd ymm16, ymm22, ymm9
611: 62 71 cd 20 54 fe vandpd ymm15, ymm22, ymm6
617: 62 d1 fd 20 c2 c8 05 vcmpnltpd k1, ymm16, ymm8
61e: 62 81 fd 20 5d c2 vminpd ymm16, ymm16, ymm26
624: 62 51 fd a1 56 ff vorpd ymm15{k1}{z}, ymm16, ymm15
After:
5c8: 62 22 e5 20 a8 c8 vfmadd213pd ymm25, ymm19, ymm16
5ce: 62 a1 b5 20 54 c6 vandpd ymm16, ymm25, ymm22
5d4: 62 f2 fd 20 37 cf vpcmpgtq k1, ymm16, ymm7
5da: 62 82 fd 20 3b c4 vpminuq ymm16, ymm16, ymm28
5e0: 62 e3 b5 a1 25 c1 f8 vpternlogq ymm16{k1}{z}, ymm25, ymm1, 0xf8

@AniLeo
AniLeo requested a review from Whatcookie August 16, 2026 22:00
@Megamouse Megamouse added CPU Optimization Optimizes existing code labels Aug 17, 2026

@Whatcookie Whatcookie left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe a comment could be added clarifying that these paths make use of vpternlog, as they otherwise use no intrinsics. But otherwise lgtm

@AniLeo
AniLeo requested a review from elad335 August 18, 2026 22:11
const auto smax = splat<u64[4]>(0x47ffffffe0000000).eval(m_ir);
const auto smin = splat<u64[4]>(0x3810000000000000).eval(m_ir);
const auto a = m_ir->CreateAnd(d, 0x7fffffffe0000000);
const auto n = m_ir->CreateICmpUGE(a, smin);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, since the sign bit is cleared, you can use integer comparson on non avx512 path as well. Weird that it got missed.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what do you have in mind? on AVX2 the current path lowers directly to vcmpnltpd + vminpd, while the integer would need two vpcmpgtq plus a blend

@elad335 elad335 Aug 20, 2026 •

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(V)PCMPGTQ - 64bit signed integer comparison, is available for AVX cpus. Is it generated by llvm? If so, you can use this for all AVX cpus as well by using a signed comparison.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok just finished testing this. on avx1 the integer compare gets split into two xmm vpcmpgtqs plus extract/insert, so it takes the path from 7 to 11 instructions
avx2 gets one ymm compare but it’s not really a consistent win. on haswell/broadwell it’s 5 cycle latency vs 3 for vcmppd, and on skylake it has slightly better latency but it’s p5 only with half the throughput
so i think keeping the current avx/avx2 path makes more sense here

@elad335
elad335 enabled auto-merge (rebase) August 20, 2026 06:01
@elad335
elad335 merged commit c4eff69 into RPCS3:master Aug 20, 2026
9 of 10 checks passed
@Yahfz
Yahfz deleted the spu-avx512-xfloat-conversions branch September 4, 2026 07:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CPU Optimization Optimizes existing code

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants