3 // Copyright (c) 2015 Riscv Developers
4 // Copyright (c) 2016-2017 The University of Virginia
5 // Copyright (c) 2020 Barkhausen Institut
6 // All rights reserved.
8 // Redistribution and use in source and binary forms, with or without
9 // modification, are permitted provided that the following conditions are
10 // met: redistributions of source code must retain the above copyright
11 // notice, this list of conditions and the following disclaimer;
12 // redistributions in binary form must reproduce the above copyright
13 // notice, this list of conditions and the following disclaimer in the
14 // documentation and/or other materials provided with the distribution;
15 // neither the name of the copyright holders nor the names of its
16 // contributors may be used to endorse or promote products derived from
17 // this software without specific prior written permission.
19 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 ////////////////////////////////////////////////////////////////////
33 // Floating point operation instructions
35 def template FloatExecute {{
36 Fault %(class_name)s::execute(ExecContext *xc,
37 Trace::InstRecord *traceData) const
39 Fault fault = NoFault;
41 STATUS status = xc->readMiscReg(MISCREG_STATUS);
42 if (status.fs == FPUStatus::OFF)
43 fault = std::make_shared<IllegalInstFault>("FPU is off", machInst);
47 if (fault == NoFault) {
50 std::fesetround(FE_TONEAREST);
53 std::fesetround(FE_TOWARDZERO);
56 std::fesetround(FE_DOWNWARD);
59 std::fesetround(FE_UPWARD);
62 // Round to nearest, ties to max magnitude not implemented
63 fault = std::make_shared<IllegalFrmFault>(
64 ROUND_MODE, machInst);
67 uint8_t frm = xc->readMiscReg(MISCREG_FRM);
70 std::fesetround(FE_TONEAREST);
73 std::fesetround(FE_TOWARDZERO);
76 std::fesetround(FE_DOWNWARD);
79 std::fesetround(FE_UPWARD);
82 // Round to nearest, ties to max magnitude not implemented
83 fault = std::make_shared<IllegalFrmFault>(
84 ROUND_MODE, machInst);
87 fault = std::make_shared<IllegalFrmFault>(frm, machInst);
93 fault = std::make_shared<IllegalFrmFault>(ROUND_MODE,
98 if (fault == NoFault) {
99 RegVal FFLAGS = xc->readMiscReg(MISCREG_FFLAGS);
100 std::feclearexcept(FE_ALL_EXCEPT);
102 if (std::fetestexcept(FE_INEXACT)) {
103 FFLAGS |= FloatInexact;
105 if (std::fetestexcept(FE_UNDERFLOW)) {
106 FFLAGS |= FloatUnderflow;
108 if (std::fetestexcept(FE_OVERFLOW)) {
109 FFLAGS |= FloatOverflow;
111 if (std::fetestexcept(FE_DIVBYZERO)) {
112 FFLAGS |= FloatDivZero;
114 if (std::fetestexcept(FE_INVALID)) {
115 FFLAGS |= FloatInvalid;
117 xc->setMiscReg(MISCREG_FFLAGS, FFLAGS);
120 if (fault == NoFault) {
128 def format FPROp(code, *opt_flags) {{
129 iop = InstObjParams(name, Name, 'RegOp', code, opt_flags)
130 header_output = BasicDeclare.subst(iop)
131 decoder_output = BasicConstructor.subst(iop)
132 decode_block = BasicDecode.subst(iop)
133 exec_output = FloatExecute.subst(iop)