summaryrefslogtreecommitdiffstats
path: root/libs/wpewebkit/patches/153-JavaScriptCore-RISCV64-FPR-scratch-fix.patch
blob: 6e41aeaf79e7c2ff300ff298f8552be990c09eec (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
From 263d7aecb08f96a70a2004c6b1af906fd02f53ea Mon Sep 17 00:00:00 2001
From: Daniel Golle <daniel@makrotopia.org>
Date: Wed, 23 Sep 2026 14:33:27 +0100
Subject: [PATCH] JavaScriptCore: RISCV64: fix nonPreservedNonArgumentFPR0
 aliasing argumentFPR1

On RISCV64, FPRInfo declared

    nonPreservedNonArgumentFPR0 = RISCV64Registers::f11

but f11 is fa1 = argumentFPR1. BBQJIT pins wasmScratchFPR to
nonPreservedNonArgumentFPR0 and uses it to materialise f32/f64
immediates for binary float comparisons (emitCompareF32/F64). When the
non-immediate operand is bound to fa1 (e.g. wasm result/argument 1),
emitMoveConst into the "scratch" register silently overwrites that
value before the comparison runs.

Symptom: spec-tests/wasm/stress multi-return tests that compare each
returned f32/f64 against a constant fail at the fa1 slot:

  wasm-wasm-call-many-return-types-on-stack-no-args.js
  wasm-wasm-call-indirect-many-return-types-on-stack.js
  wasm-js-call-many-return-types-on-stack-no-args.js

The bug is not about spill pressure; it is the scratch FPR aliasing an
argument/return FPR for any value bound to fa1.

Use f0 (ft0) -- a RISC-V caller-saved temporary outside the f10..f17
argument/return set -- matching the pattern used by ARM64 (q16) and
X86_64 (xmm8).

Signed-off-by: Daniel Golle <daniel@makrotopia.org>
---
 Source/JavaScriptCore/jit/FPRInfo.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

--- a/Source/JavaScriptCore/jit/FPRInfo.h
+++ b/Source/JavaScriptCore/jit/FPRInfo.h
@@ -366,7 +366,7 @@ public:
     static constexpr FPRReg argumentFPR7 = RISCV64Registers::f17; // fpRegT7
 
     static constexpr FPRReg returnValueFPR = RISCV64Registers::f10; // fpRegT0
-    static constexpr FPRReg nonPreservedNonArgumentFPR0 = RISCV64Registers::f11;
+    static constexpr FPRReg nonPreservedNonArgumentFPR0 = RISCV64Registers::f0;
 
     static FPRReg toRegister(unsigned index)
     {