Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3)  * IEEE754 floating point arithmetic
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4)  * single precision: MADDF.f (Fused Multiply Add)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5)  * MADDF.fmt: FPR[fd] = FPR[fd] + (FPR[fs] x FPR[ft])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6)  *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7)  * MIPS floating point support
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8)  * Copyright (C) 2015 Imagination Technologies, Ltd.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9)  * Author: Markos Chandras <markos.chandras@imgtec.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) #include "ieee754sp.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) static union ieee754sp _sp_maddf(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) 				 union ieee754sp y, enum maddf_flags flags)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) 	int re;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) 	int rs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) 	unsigned int rm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) 	u64 rm64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) 	u64 zm64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) 	int s;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) 	COMPXSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) 	COMPYSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 	COMPZSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 	EXPLODEXSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) 	EXPLODEYSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 	EXPLODEZSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 	FLUSHXSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 	FLUSHYSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 	FLUSHZSP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) 	ieee754_clearcx();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) 	rs = xs ^ ys;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) 	if (flags & MADDF_NEGATE_PRODUCT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 		rs ^= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) 	if (flags & MADDF_NEGATE_ADDITION)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 		zs ^= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) 	 * Handle the cases when at least one of x, y or z is a NaN.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 	 * Order of precedence is sNaN, qNaN and z, x, y.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 	if (zc == IEEE754_CLASS_SNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 		return ieee754sp_nanxcpt(z);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	if (xc == IEEE754_CLASS_SNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 		return ieee754sp_nanxcpt(x);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 	if (yc == IEEE754_CLASS_SNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) 		return ieee754sp_nanxcpt(y);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 	if (zc == IEEE754_CLASS_QNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 		return z;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) 	if (xc == IEEE754_CLASS_QNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) 		return x;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 	if (yc == IEEE754_CLASS_QNAN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 		return y;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) 	if (zc == IEEE754_CLASS_DNORM)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) 		SPDNORMZ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 	/* ZERO z cases are handled separately below */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) 	switch (CLPAIR(xc, yc)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) 	 * Infinity handling
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 	case CLPAIR(IEEE754_CLASS_INF, IEEE754_CLASS_ZERO):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 	case CLPAIR(IEEE754_CLASS_ZERO, IEEE754_CLASS_INF):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) 		ieee754_setcx(IEEE754_INVALID_OPERATION);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 		return ieee754sp_indef();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 	case CLPAIR(IEEE754_CLASS_NORM, IEEE754_CLASS_INF):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) 	case CLPAIR(IEEE754_CLASS_DNORM, IEEE754_CLASS_INF):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	case CLPAIR(IEEE754_CLASS_INF, IEEE754_CLASS_NORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 	case CLPAIR(IEEE754_CLASS_INF, IEEE754_CLASS_DNORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 	case CLPAIR(IEEE754_CLASS_INF, IEEE754_CLASS_INF):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) 		if ((zc == IEEE754_CLASS_INF) && (zs != rs)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 			/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) 			 * Cases of addition of infinities with opposite signs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 			 * or subtraction of infinities with same signs.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 			 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) 			ieee754_setcx(IEEE754_INVALID_OPERATION);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 			return ieee754sp_indef();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 		 * z is here either not an infinity, or an infinity having the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 		 * same sign as product (x*y). The result must be an infinity,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 		 * and its sign is determined only by the sign of product (x*y).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 		return ieee754sp_inf(rs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) 	case CLPAIR(IEEE754_CLASS_ZERO, IEEE754_CLASS_ZERO):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 	case CLPAIR(IEEE754_CLASS_ZERO, IEEE754_CLASS_NORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 	case CLPAIR(IEEE754_CLASS_ZERO, IEEE754_CLASS_DNORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) 	case CLPAIR(IEEE754_CLASS_NORM, IEEE754_CLASS_ZERO):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	case CLPAIR(IEEE754_CLASS_DNORM, IEEE754_CLASS_ZERO):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 		if (zc == IEEE754_CLASS_INF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 			return ieee754sp_inf(zs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 		if (zc == IEEE754_CLASS_ZERO) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) 			/* Handle cases +0 + (-0) and similar ones. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 			if (zs == rs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 				/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) 				 * Cases of addition of zeros of equal signs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 				 * or subtraction of zeroes of opposite signs.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 				 * The sign of the resulting zero is in any
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 				 * such case determined only by the sign of z.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 				 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 				return z;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 			return ieee754sp_zero(ieee754_csr.rm == FPU_CSR_RD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 		/* x*y is here 0, and z is not 0, so just return z */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 		return z;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) 	case CLPAIR(IEEE754_CLASS_DNORM, IEEE754_CLASS_DNORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 		SPDNORMX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 		fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) 	case CLPAIR(IEEE754_CLASS_NORM, IEEE754_CLASS_DNORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 		if (zc == IEEE754_CLASS_INF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 			return ieee754sp_inf(zs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 		SPDNORMY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 	case CLPAIR(IEEE754_CLASS_DNORM, IEEE754_CLASS_NORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) 		if (zc == IEEE754_CLASS_INF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 			return ieee754sp_inf(zs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 		SPDNORMX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) 		break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 	case CLPAIR(IEEE754_CLASS_NORM, IEEE754_CLASS_NORM):
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 		if (zc == IEEE754_CLASS_INF)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 			return ieee754sp_inf(zs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 		/* continue to real computations */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 	/* Finally get to do some computation */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 	 * Do the multiplication bit first
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) 	 * rm = xm * ym, re = xe + ye basically
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 	 *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	 * At this point xm and ym should have been normalized.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 	/* rm = xm * ym, re = xe+ye basically */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) 	assert(xm & SP_HIDDEN_BIT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) 	assert(ym & SP_HIDDEN_BIT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 	re = xe + ye;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 	/* Multiple 24 bit xm and ym to give 48 bit results */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 	rm64 = (uint64_t)xm * ym;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 	/* Shunt to top of word */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 	rm64 = rm64 << 16;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) 	/* Put explicit bit at bit 62 if necessary */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) 	if ((int64_t) rm64 < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) 		rm64 = rm64 >> 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) 		re++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 	assert(rm64 & (1 << 62));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	if (zc == IEEE754_CLASS_ZERO) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 		 * Move explicit bit from bit 62 to bit 26 since the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 		 * ieee754sp_format code expects the mantissa to be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 		 * 27 bits wide (24 + 3 rounding bits).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 		rm = XSPSRS64(rm64, (62 - 26));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 		return ieee754sp_format(rs, re, rm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 	/* Move explicit bit from bit 23 to bit 62 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	zm64 = (uint64_t)zm << (62 - 23);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 	assert(zm64 & (1 << 62));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) 	/* Make the exponents the same */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) 	if (ze > re) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 		 * Have to shift r fraction right to align.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) 		s = ze - re;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 		rm64 = XSPSRS64(rm64, s);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 		re += s;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) 	} else if (re > ze) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 		 * Have to shift z fraction right to align.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 		s = re - ze;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) 		zm64 = XSPSRS64(zm64, s);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 		ze += s;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 	assert(ze == re);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) 	assert(ze <= SP_EMAX);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 	/* Do the addition */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	if (zs == rs) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) 		 * Generate 64 bit result by adding two 63 bit numbers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) 		 * leaving result in zm64, zs and ze.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 		zm64 = zm64 + rm64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 		if ((int64_t)zm64 < 0) {	/* carry out */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 			zm64 = XSPSRS1(zm64);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 			ze++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) 		if (zm64 >= rm64) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 			zm64 = zm64 - rm64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 		} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 			zm64 = rm64 - zm64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) 			zs = rs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) 		if (zm64 == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 			return ieee754sp_zero(ieee754_csr.rm == FPU_CSR_RD);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 		/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 		 * Put explicit bit at bit 62 if necessary.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) 		 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) 		while ((zm64 >> 62) == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) 			zm64 <<= 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) 			ze--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 		}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) 	/*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 	 * Move explicit bit from bit 62 to bit 26 since the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	 * ieee754sp_format code expects the mantissa to be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) 	 * 27 bits wide (24 + 3 rounding bits).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	zm = XSPSRS64(zm64, (62 - 26));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) 	return ieee754sp_format(zs, ze, zm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) union ieee754sp ieee754sp_maddf(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 	return _sp_maddf(z, x, y, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) union ieee754sp ieee754sp_msubf(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 	return _sp_maddf(z, x, y, MADDF_NEGATE_PRODUCT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) union ieee754sp ieee754sp_madd(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) 	return _sp_maddf(z, x, y, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) union ieee754sp ieee754sp_msub(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 	return _sp_maddf(z, x, y, MADDF_NEGATE_ADDITION);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) union ieee754sp ieee754sp_nmadd(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) 	return _sp_maddf(z, x, y, MADDF_NEGATE_PRODUCT|MADDF_NEGATE_ADDITION);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) union ieee754sp ieee754sp_nmsub(union ieee754sp z, union ieee754sp x,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) 				union ieee754sp y)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) 	return _sp_maddf(z, x, y, MADDF_NEGATE_PRODUCT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) }