From ac50a6c52a36d781c3322f3b787faa2f8b5c606b Mon Sep 17 00:00:00 2001 From: cl2t Date: Tue, 22 Sep 2026 19:10:41 +0800 Subject: [PATCH] Prevent fused arithmetic from changing round results When Modf is inlined, a fused multiply-subtract can retain extra precision from pow * val and move a half-way fractional part below 0.5. On arm64 and riscv64, round(123.5555, 3) then returns 123.555 instead of 123.556. An explicit float64 conversion rounds the product before Modf examines it. The existing TestRound case covers the regression. Signed-off-by: cl2t --- numeric.go | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/numeric.go b/numeric.go index f68e4182..72c65733 100644 --- a/numeric.go +++ b/numeric.go @@ -114,7 +114,8 @@ func round(a interface{}, p int, rOpt ...float64) float64 { var round float64 pow := math.Pow(10, places) - digit := pow * val + // Round the product before Modf subtracts its integer part. + digit := float64(pow * val) _, div := math.Modf(digit) if div >= roundOn { round = math.Ceil(digit)