X-Git-Url: http://pilppa.org/gitweb/gitweb.cgi?a=blobdiff_plain;f=arch%2Farm%2Fnwfpe%2Ffpa11_cpdo.c;h=2cebb1529607438c99fd81f3ecf18aea5431bc97;hb=c0bc8721b8d0380ec69fa97578c91201201b05a9;hp=1bea67437b6f2bc5ed859b7aa0db2237e84a7c6e;hpb=1da177e4c3f41524e886b7f1b8a0c1fc7321cac2;p=linux-2.6-omap-h63xx.git diff --git a/arch/arm/nwfpe/fpa11_cpdo.c b/arch/arm/nwfpe/fpa11_cpdo.c index 1bea67437b6..2cebb152960 100644 --- a/arch/arm/nwfpe/fpa11_cpdo.c +++ b/arch/arm/nwfpe/fpa11_cpdo.c @@ -20,19 +20,19 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ -#include #include "fpa11.h" #include "fpopcode.h" -unsigned int SingleCPDO(const unsigned int opcode, FPREG * rFd); -unsigned int DoubleCPDO(const unsigned int opcode, FPREG * rFd); -unsigned int ExtendedCPDO(const unsigned int opcode, FPREG * rFd); +unsigned int SingleCPDO(struct roundingData *roundData, const unsigned int opcode, FPREG * rFd); +unsigned int DoubleCPDO(struct roundingData *roundData, const unsigned int opcode, FPREG * rFd); +unsigned int ExtendedCPDO(struct roundingData *roundData, const unsigned int opcode, FPREG * rFd); unsigned int EmulateCPDO(const unsigned int opcode) { FPA11 *fpa11 = GET_FPA11(); FPREG *rFd; unsigned int nType, nDest, nRc; + struct roundingData roundData; /* Get the destination size. If not valid let Linux perform an invalid instruction trap. */ @@ -40,7 +40,9 @@ unsigned int EmulateCPDO(const unsigned int opcode) if (typeNone == nDest) return 0; - SetRoundingMode(opcode); + roundData.mode = SetRoundingMode(opcode); + roundData.precision = SetRoundingPrecision(opcode); + roundData.exception = 0; /* Compare the size of the operands in Fn and Fm. Choose the largest size and perform operations in that size, @@ -63,14 +65,14 @@ unsigned int EmulateCPDO(const unsigned int opcode) switch (nType) { case typeSingle: - nRc = SingleCPDO(opcode, rFd); + nRc = SingleCPDO(&roundData, opcode, rFd); break; case typeDouble: - nRc = DoubleCPDO(opcode, rFd); + nRc = DoubleCPDO(&roundData, opcode, rFd); break; #ifdef CONFIG_FPE_NWFPE_XP case typeExtended: - nRc = ExtendedCPDO(opcode, rFd); + nRc = ExtendedCPDO(&roundData, opcode, rFd); break; #endif default: @@ -93,9 +95,9 @@ unsigned int EmulateCPDO(const unsigned int opcode) case typeSingle: { if (typeDouble == nType) - rFd->fSingle = float64_to_float32(rFd->fDouble); + rFd->fSingle = float64_to_float32(&roundData, rFd->fDouble); else - rFd->fSingle = floatx80_to_float32(rFd->fExtended); + rFd->fSingle = floatx80_to_float32(&roundData, rFd->fExtended); } break; @@ -104,7 +106,7 @@ unsigned int EmulateCPDO(const unsigned int opcode) if (typeSingle == nType) rFd->fDouble = float32_to_float64(rFd->fSingle); else - rFd->fDouble = floatx80_to_float64(rFd->fExtended); + rFd->fDouble = floatx80_to_float64(&roundData, rFd->fExtended); } break; @@ -121,12 +123,15 @@ unsigned int EmulateCPDO(const unsigned int opcode) #else if (nDest != nType) { if (nDest == typeSingle) - rFd->fSingle = float64_to_float32(rFd->fDouble); + rFd->fSingle = float64_to_float32(&roundData, rFd->fDouble); else rFd->fDouble = float32_to_float64(rFd->fSingle); } #endif } + if (roundData.exception) + float_raise(roundData.exception); + return nRc; }