From 2c3c1048746a4622d8c89a29670120dc8fab93c4 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 7 Apr 2024 20:49:45 +0200 Subject: Adding upstream version 6.1.76. Signed-off-by: Daniel Baumann --- arch/parisc/math-emu/denormal.c | 122 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 122 insertions(+) create mode 100644 arch/parisc/math-emu/denormal.c (limited to 'arch/parisc/math-emu/denormal.c') diff --git a/arch/parisc/math-emu/denormal.c b/arch/parisc/math-emu/denormal.c new file mode 100644 index 000000000..7f1a60d59 --- /dev/null +++ b/arch/parisc/math-emu/denormal.c @@ -0,0 +1,122 @@ +// SPDX-License-Identifier: GPL-2.0-or-later +/* + * Linux/PA-RISC Project (http://www.parisc-linux.org/) + * + * Floating-point emulation code + * Copyright (C) 2001 Hewlett-Packard (Paul Bame) + */ +/* + * BEGIN_DESC + * + * File: + * @(#) pa/fp/denormal.c $ Revision: $ + * + * Purpose: + * <> + * + * External Interfaces: + * <> + * dbl_denormalize(dbl_opndp1,dbl_opndp2,inexactflag,rmode) + * sgl_denormalize(sgl_opnd,inexactflag,rmode) + * + * Internal Interfaces: + * <> + * + * Theory: + * <> + * + * END_DESC +*/ + + + +#include "float.h" +#include "sgl_float.h" +#include "dbl_float.h" +#include "hppa.h" +#include +/* #include */ + +#undef Fpustatus_register +#define Fpustatus_register Fpu_register[0] + +void +sgl_denormalize(unsigned int *sgl_opnd, boolean *inexactflag, int rmode) +{ + unsigned int opnd; + int sign, exponent; + boolean guardbit = FALSE, stickybit, inexact; + + opnd = *sgl_opnd; + stickybit = *inexactflag; + exponent = Sgl_exponent(opnd) - SGL_WRAP; + sign = Sgl_sign(opnd); + Sgl_denormalize(opnd,exponent,guardbit,stickybit,inexact); + if (inexact) { + switch (rmode) { + case ROUNDPLUS: + if (sign == 0) { + Sgl_increment(opnd); + } + break; + case ROUNDMINUS: + if (sign != 0) { + Sgl_increment(opnd); + } + break; + case ROUNDNEAREST: + if (guardbit && (stickybit || + Sgl_isone_lowmantissa(opnd))) { + Sgl_increment(opnd); + } + break; + } + } + Sgl_set_sign(opnd,sign); + *sgl_opnd = opnd; + *inexactflag = inexact; + return; +} + +void +dbl_denormalize(unsigned int *dbl_opndp1, + unsigned int * dbl_opndp2, + boolean *inexactflag, + int rmode) +{ + unsigned int opndp1, opndp2; + int sign, exponent; + boolean guardbit = FALSE, stickybit, inexact; + + opndp1 = *dbl_opndp1; + opndp2 = *dbl_opndp2; + stickybit = *inexactflag; + exponent = Dbl_exponent(opndp1) - DBL_WRAP; + sign = Dbl_sign(opndp1); + Dbl_denormalize(opndp1,opndp2,exponent,guardbit,stickybit,inexact); + if (inexact) { + switch (rmode) { + case ROUNDPLUS: + if (sign == 0) { + Dbl_increment(opndp1,opndp2); + } + break; + case ROUNDMINUS: + if (sign != 0) { + Dbl_increment(opndp1,opndp2); + } + break; + case ROUNDNEAREST: + if (guardbit && (stickybit || + Dbl_isone_lowmantissap2(opndp2))) { + Dbl_increment(opndp1,opndp2); + } + break; + } + } + Dbl_set_sign(opndp1,sign); + *dbl_opndp1 = opndp1; + *dbl_opndp2 = opndp2; + *inexactflag = inexact; + return; +} -- cgit v1.2.3