summaryrefslogtreecommitdiffstats
path: root/fpu
diff options
context:
space:
mode:
authorSong Gao2022-07-16 10:54:20 +0200
committerRichard Henderson2022-07-19 18:23:58 +0200
commit2344f98e9cf78d508758a7f0c9e0b4d0d37acf3d (patch)
tree11f8c48c22cabbf9069797705194e764943d9120 /fpu
parenttarget/loongarch/cpu: Fix cpucfg default value (diff)
downloadqemu-2344f98e9cf78d508758a7f0c9e0b4d0d37acf3d.tar.gz
qemu-2344f98e9cf78d508758a7f0c9e0b4d0d37acf3d.tar.xz
qemu-2344f98e9cf78d508758a7f0c9e0b4d0d37acf3d.zip
fpu/softfloat: Add LoongArch specializations for pickNaN*
The muladd (inf,zero,nan) case sets InvalidOp and returns the input value 'c', and prefer sNaN over qNaN, in c,a,b order. Binary operations prefer sNaN over qNaN and a,b order. Signed-off-by: Song Gao <gaosong@loongson.cn> Message-Id: <20220716085426.3098060-3-gaosong@loongson.cn> [rth: Add specialization for pickNaN] Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Diffstat (limited to 'fpu')
-rw-r--r--fpu/softfloat-specialize.c.inc26
1 files changed, 25 insertions, 1 deletions
diff --git a/fpu/softfloat-specialize.c.inc b/fpu/softfloat-specialize.c.inc
index 943e3301d2..9096fb302b 100644
--- a/fpu/softfloat-specialize.c.inc
+++ b/fpu/softfloat-specialize.c.inc
@@ -390,7 +390,8 @@ bool float32_is_signaling_nan(float32 a_, float_status *status)
static int pickNaN(FloatClass a_cls, FloatClass b_cls,
bool aIsLargerSignificand, float_status *status)
{
-#if defined(TARGET_ARM) || defined(TARGET_MIPS) || defined(TARGET_HPPA)
+#if defined(TARGET_ARM) || defined(TARGET_MIPS) || defined(TARGET_HPPA) \
+ || defined(TARGET_LOONGARCH64)
/* ARM mandated NaN propagation rules (see FPProcessNaNs()), take
* the first of:
* 1. A if it is signaling
@@ -574,6 +575,29 @@ static int pickNaNMulAdd(FloatClass a_cls, FloatClass b_cls, FloatClass c_cls,
return 1;
}
}
+#elif defined(TARGET_LOONGARCH64)
+ /*
+ * For LoongArch systems that conform to IEEE754-2008, the (inf,zero,nan)
+ * case sets InvalidOp and returns the input value 'c'
+ */
+ if (infzero) {
+ float_raise(float_flag_invalid | float_flag_invalid_imz, status);
+ return 2;
+ }
+ /* Prefer sNaN over qNaN, in the c, a, b order. */
+ if (is_snan(c_cls)) {
+ return 2;
+ } else if (is_snan(a_cls)) {
+ return 0;
+ } else if (is_snan(b_cls)) {
+ return 1;
+ } else if (is_qnan(c_cls)) {
+ return 2;
+ } else if (is_qnan(a_cls)) {
+ return 0;
+ } else {
+ return 1;
+ }
#elif defined(TARGET_PPC)
/* For PPC, the (inf,zero,qnan) case sets InvalidOp, but we prefer
* to return an input NaN if we have one (ie c) rather than generating