qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: Peter Maydell <peter.maydell@linaro.org>
To: qemu-devel@nongnu.org
Cc: Blue Swirl <blauwirbel@gmail.com>,
	Anthony Liguori <aliguori@us.ibm.com>,
	Aurelien Jarno <aurelien@aurel32.net>,
	patches@linaro.org
Subject: [Qemu-devel] [PATCH] fpu: Correct edgecase in float64_muladd
Date: Fri, 12 Apr 2013 16:37:52 +0100	[thread overview]
Message-ID: <1365781072-24979-1-git-send-email-peter.maydell@linaro.org> (raw)

In handling float64_muladd, if we end up doing a subtraction of the
product and c, and the 128 bit result of this subtraction happens to
have its most significant bit in bit 63, we weren't handling this
correctly when attempting to normalize to put the most significant
bit into bit 126.  We would end up doing a right shift by a negative
number (undefined behaviour in C) so at best we would return an
incorrect result to the guest.  MSB in bit 63 has to be handled as a
special case separately from MSB in 0..62 and MSB in 63..126.  (MSB
in 127 is not possible.)

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
Specific test vector which triggers this:
 a = 3fffffffffe00000 b = 3fffffffffe00000 c = c00fffffffc00000

Also tested with my usual set of random test vectors.

 fpu/softfloat.c |   12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/fpu/softfloat.c b/fpu/softfloat.c
index 83ccc4b..7ba51b6 100644
--- a/fpu/softfloat.c
+++ b/fpu/softfloat.c
@@ -3898,9 +3898,15 @@ float64 float64_muladd(float64 a, float64 b, float64 c, int flags STATUS_PARAM)
             }
             zExp -= shiftcount;
         } else {
-            shiftcount = countLeadingZeros64(zSig1) - 1;
-            zSig0 = zSig1 << shiftcount;
-            zExp -= (shiftcount + 64);
+            shiftcount = countLeadingZeros64(zSig1);
+            if (shiftcount == 0) {
+                zSig0 = (zSig1 >> 1) | (zSig1 & 1);
+                zExp -= 63;
+            } else {
+                shiftcount--;
+                zSig0 = zSig1 << shiftcount;
+                zExp -= (shiftcount + 64);
+            }
         }
         return roundAndPackFloat64(zSign, zExp, zSig0 STATUS_VAR);
     }
-- 
1.7.9.5

             reply	other threads:[~2013-04-12 15:38 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-04-12 15:37 Peter Maydell [this message]
2013-04-13 13:57 ` [Qemu-devel] [PATCH] fpu: Correct edgecase in float64_muladd Aurelien Jarno
2013-04-15 14:25 ` Aurelien Jarno

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=1365781072-24979-1-git-send-email-peter.maydell@linaro.org \
    --to=peter.maydell@linaro.org \
    --cc=aliguori@us.ibm.com \
    --cc=aurelien@aurel32.net \
    --cc=blauwirbel@gmail.com \
    --cc=patches@linaro.org \
    --cc=qemu-devel@nongnu.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
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).