// Copyright (c) 2007 The Hewlett-Packard Development Company
// Copyright (c) 2012-2013 Mark D. Hill and David A. Wood
// Copyright (c) 2015 Advanced Micro Devices, Inc.
//
// All rights reserved.
//
// The license below extends only to copyright in the software and shall
// not be construed as granting a license to any other intellectual
// property including but not limited to intellectual property relating
// to a hardware implementation of the functionality of the software
// licensed hereunder.  You may use the software subject to the license
// terms below provided that you ensure that this notice is replicated
// unmodified and in its entirety in all distributions of the software,
// modified or unmodified, in source code or in binary form.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met: redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer;
// redistributions in binary form must reproduce the above copyright
// notice, this list of conditions and the following disclaimer in the
// documentation and/or other materials provided with the distribution;
// neither the name of the copyright holders nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

//////////////////////////////////////////////////////////////////////////
//
// FpOp Microop templates
//
//////////////////////////////////////////////////////////////////////////

def template MicroFpOpExecute {{
    Fault
    %(class_name)s::execute(ExecContext *xc,
            Trace::InstRecord *traceData) const
    {
        Fault fault = NoFault;

        DPRINTF(X86, "The data size is %d\n", dataSize);
        %(op_decl)s;
        %(op_rd)s;

        if (%(cond_check)s) {
            %(code)s;
            %(flag_code)s;
            %(tag_code)s;
            %(top_code)s;
        } else {
            %(else_code)s;
        }

        //Write the resulting state to the execution context
        if (fault == NoFault) {
            %(op_wb)s;
        }
        return fault;
    }
}};

def template MicroFpOpDeclare {{
    class %(class_name)s : public %(base_class)s
    {
      private:
        %(reg_idx_arr_decl)s;

      public:
        template <typename ...Args>
        %(class_name)s(ExtMachInst mach_inst, const char *inst_mnem,
                uint64_t set_flags, uint8_t data_size, int8_t _spm,
                Args... args);

        Fault execute(ExecContext *, Trace::InstRecord *) const override;
    };
}};

def template MicroFpOpConstructor {{
    template <typename ...Args>
    %(class_name)s::%(class_name)s(ExtMachInst mach_inst,
            const char *inst_mnem, uint64_t set_flags,
            uint8_t data_size, int8_t _spm, Args... args) :
        %(base_class)s(mach_inst, "%(mnemonic)s", inst_mnem, set_flags,
                %(op_class)s, { args... }, data_size, _spm)
    {
        %(set_reg_idx_arr)s;
        %(constructor)s;
    }
}};

let {{

    # Make these empty strings so that concatenating onto
    # them will always work.
    header_output = ""
    decoder_output = ""
    exec_output = ""

    class FpOpMeta(type):
        def buildCppClasses(self, name, Name, suffix, code, flag_code,
                cond_check, else_code, op_class, operand_types):

            # Globals to stick the output in
            global header_output
            global decoder_output
            global exec_output

            # Stick all the code together so it can be searched at once
            allCode = "|".join((code, flag_code, cond_check, else_code))

            # If there's something optional to do with flags, generate
            # a version without it and fix up this version to use it.
            if flag_code != "" or cond_check != "true":
                self.buildCppClasses(name, Name, suffix,
                        code, "", "true", else_code, op_class, operand_types)
                suffix = "Flags" + suffix

            base = "X86ISA::InstOperands<" + \
                ", ".join(["X86ISA::FpOp"] +
                          [op.cxx_class() for op in operand_types]) + ">"

            # Get everything ready for the substitution
            iop_tag = InstObjParams(name, Name + suffix + "TopTag", base,
                    {"code" : code,
                     "flag_code" : flag_code,
                     "cond_check" : cond_check,
                     "else_code" : else_code,
                     "tag_code" : "FTW = genX87Tags(FTW, TOP, spm);",
                     "top_code" : "TOP = (TOP + spm + 8) % 8;",
                     "op_class" : op_class})
            iop_top = InstObjParams(name, Name + suffix + "Top", base,
                    {"code" : code,
                     "flag_code" : flag_code,
                     "cond_check" : cond_check,
                     "else_code" : else_code,
                     "tag_code" : ";",
                     "top_code" : "TOP = (TOP + spm + 8) % 8;",
                     "op_class" : op_class})
            iop = InstObjParams(name, Name + suffix, base,
                    {"code" : code,
                     "flag_code" : flag_code,
                     "cond_check" : cond_check,
                     "else_code" : else_code,
                     "tag_code" : ";",
                     "top_code" : ";",
                     "op_class" : op_class})

            # Generate the actual code (finally!)
            header_output += MicroFpOpDeclare.subst(iop_tag)
            decoder_output += MicroFpOpConstructor.subst(iop_tag)
            exec_output += MicroFpOpExecute.subst(iop_tag)
            header_output += MicroFpOpDeclare.subst(iop_top)
            decoder_output += MicroFpOpConstructor.subst(iop_top)
            exec_output += MicroFpOpExecute.subst(iop_top)
            header_output += MicroFpOpDeclare.subst(iop)
            decoder_output += MicroFpOpConstructor.subst(iop)
            exec_output += MicroFpOpExecute.subst(iop)


        def __new__(mcls, Name, bases, dict):
            abstract = False
            name = Name.lower()
            if "abstract" in dict:
                abstract = dict['abstract']
                del dict['abstract']

            cls = super().__new__(mcls, Name, bases, dict)
            if not abstract:
                cls.className = Name
                cls.mnemonic = name
                code = cls.code
                flag_code = cls.flag_code
                cond_check = cls.cond_check
                else_code = cls.else_code
                op_class = cls.op_class
                operand_types = cls.operand_types

                # Set up the C++ classes
                mcls.buildCppClasses(cls, name, Name, "",
                        code, flag_code, cond_check, else_code, op_class,
                        operand_types)

                # Hook into the microassembler dict
                global microopClasses
                microopClasses[name] = cls

            return cls

    class FpOp(X86Microop, metaclass=FpOpMeta):
        # This class itself doesn't act as a microop
        abstract = True

        # Default template parameter values
        flag_code = ""
        cond_check = "true"
        else_code = ";"
        op_class = "FloatAddOp"

        def __init__(self, *ops, spm=0,
                SetStatus=False, UpdateFTW=True, dataSize="env.dataSize"):
            self.ops = list(map(str, ops))
            self.spm = spm
            self.dataSize = dataSize
            if SetStatus:
                self.className += "Flags"
            if spm:
                self.className += "Top"
            if spm and UpdateFTW:
                self.className += "Tag"

        def getAllocator(self, microFlags):
            # Ensure there's at least one element to join with ","s.
            op_iter = iter(self.ops)
            ops = list([Type(op_iter).ctor_args() for
                    Type in self.operand_types])
            spm_ops = [str(self.spm)] + ops
            return '''new %(class_name)s(machInst, macrocodeBlock,
                    %(flags)s, %(dataSize)s, %(spm_ops)s)''' % {
                "class_name" : self.className,
                "flags" : self.microFlagsText(microFlags),
                "dataSize" : self.dataSize,
                "spm_ops" : ", ".join(spm_ops)}

    class Fp0Op(FpOp):
        abstract = True
        operand_types = ()
        def __init__(self, **kwargs):
            super().__init__(**kwargs)

    class Fp1Op(FpOp):
        abstract = True
        operand_types = (FloatDestOp)
        def __init__(self, reg1, **kwargs):
            super().__init__(reg1, **kwargs)

    class Fp2Op(FpOp):
        abstract = True
        operand_types = (FloatDestOp, FloatSrc1Op)
        def __init__(self, reg1, reg2, **kwargs):
            super().__init__(reg1, reg2, **kwargs)

    class Fp3Op(FpOp):
        abstract = True
        operand_types = (FloatDestOp, FloatSrc1Op, FloatSrc2Op)
        def __init__(self, reg1, reg2, reg3, **kwargs):
            super().__init__(reg1, reg2, reg3, **kwargs)

    class Movfp(Fp2Op):
        code = 'FpDestReg_uqw = FpSrcReg1_uqw;'
        else_code = 'FpDestReg_uqw = FpDestReg_uqw;'
        cond_check = "checkCondition(ccFlagBits | cfofBits | dfBit | \
                                     ecfBit | ezfBit, src1)"
        op_class = 'IntAluOp'

    class Xorfp(Fp3Op):
        code = 'FpDestReg_uqw = FpSrcReg1_uqw ^ FpSrcReg2_uqw;'

    class Sqrtfp(Fp2Op):
        code = 'FpDestReg = sqrt(FpSrcReg1);'
        op_class = 'FloatSqrtOp'

    class Cosfp(Fp2Op):
        code = 'FpDestReg = cos(FpSrcReg1);'
        op_class = 'FloatSqrtOp'

    class Sinfp(Fp2Op):
        code = 'FpDestReg = sin(FpSrcReg1);'
        op_class = 'FloatSqrtOp'

    class Tanfp(Fp2Op):
        code = 'FpDestReg = tan(FpSrcReg1);'
        op_class = 'FloatSqrtOp'


    # Conversion microops
    class ConvOp(Fp2Op):
        abstract = True
        op_class = 'FloatCvtOp'

    # These probably shouldn't look at the ExtMachInst directly to figure
    # out what size to use and should instead delegate that to the macroop's
    # constructor. That would be more efficient, and it would make the
    # microops a little more modular.
    class Cvtf_i2d(ConvOp):
        operand_types = (FloatDestOp, IntSrc1Op)
        code = '''
            X86IntReg intReg = SrcReg1;
            if (REX_W)
                FpDestReg = intReg.SR;
            else
                FpDestReg = intReg.SE;
            '''

    class Cvtf_i2d_hi(ConvOp):
        operand_types = (FloatDestOp, IntSrc1Op)
        code = 'FpDestReg = bits(SrcReg1, 63, 32);'

    class Cvtf_d2i(ConvOp):
        operand_types = (FoldedDestOp, FloatSrc1Op)
        code = '''
            int64_t intSrcReg1 = static_cast<int64_t>(FpSrcReg1);
            DestReg = merge(DestReg, dest, intSrcReg1, dataSize);
            '''

    # Convert two integers registers representing an 80-bit floating
    # point number to an x87 register.
    class Cvtint_fp80(Fp3Op):
        operand_types = (FloatDestOp, IntSrc1Op, IntSrc2Op)
        code = '''
            uint8_t bits[10];
            *(uint64_t *)(bits + 0) = SrcReg1;
            *(uint16_t *)(bits + 8) = (uint16_t)SrcReg2;
            FpDestReg = loadFloat80(bits);
            '''

    # Convert an x87 register (double) into extended precision and
    # extract the highest 64 bits.
    class Cvtfp80h_int(ConvOp):
        operand_types = (IntDestOp, FloatSrc1Op)
        code = '''
            char bits[10];
            storeFloat80(bits, FpSrcReg1);
            DestReg = *(uint64_t *)(bits + 0);
            '''

    # Convert an x87 register (double) into extended precision and
    # extract the lowest 16 bits.
    class Cvtfp80l_int(ConvOp):
        operand_types = (IntDestOp, FloatSrc1Op)
        code = '''
            char bits[10];
            storeFloat80(bits, FpSrcReg1);
            DestReg = *(uint16_t *)(bits + 8);
            '''

    # These need to consider size at some point. They'll always use doubles
    # for the moment.
    class Addfp(Fp3Op):
        code = 'FpDestReg = FpSrcReg1 + FpSrcReg2;'

    class Mulfp(Fp3Op):
        code = 'FpDestReg = FpSrcReg1 * FpSrcReg2;'
        op_class = 'FloatMultOp'

    class Divfp(Fp3Op):
        code = 'FpDestReg = FpSrcReg1 / FpSrcReg2;'
        op_class = 'FloatDivOp'

    class Subfp(Fp3Op):
        code = 'FpDestReg = FpSrcReg1 - FpSrcReg2;'

    class Yl2xFp(Fp3Op):
        code = '''
            FpDestReg = FpSrcReg2 * (log(FpSrcReg1) / log(2));
        '''
        op_class = 'FloatSqrtOp'

    class PremFp(Fp3Op):
        code = '''
            RegVal new_fsw = FSW;
            int src1_exp;
            int src2_exp;
            std::frexp(FpSrcReg1, &src1_exp);
            std::frexp(FpSrcReg2, &src2_exp);

            const int d = src2_exp - src1_exp;
            if (d < 64) {
                const int64_t q = std::trunc(FpSrcReg2 / FpSrcReg1);
                FpDestReg = FpSrcReg2 - FpSrcReg1 * q;
                new_fsw &= ~(CC0Bit | CC1Bit | CC2Bit | CC2Bit);
                new_fsw |= (q & 0x1) ? CC1Bit : 0;
                new_fsw |= (q & 0x2) ? CC3Bit : 0;
                new_fsw |= (q & 0x4) ? CC0Bit : 0;
            } else {
                const int n = 42;
                const int64_t qq = std::trunc(
                    FpSrcReg2 / std::ldexp(FpSrcReg1, d - n));
                FpDestReg = FpSrcReg2 - std::ldexp(FpSrcReg1 * qq, d - n);
                new_fsw |= CC2Bit;
            }
        '''
        op_class = 'FloatDivOp'

        flag_code = 'FSW = new_fsw;'

    class Compfp(Fp2Op):
        operand_types = (FloatSrc1Op, FloatSrc2Op)
        # This class sets the condition codes in rflags according to the
        # rules for comparing floating point.
        code = '''
            //               ZF PF CF
            // Unordered      1  1  1
            // Greater than   0  0  0
            // Less than      0  0  1
            // Equal          1  0  0
            //           OF = SF = AF = 0
            ccFlagBits = ccFlagBits & ~(SFBit | AFBit | ZFBit | PFBit);
            cfofBits = cfofBits & ~(OFBit | CFBit);

            if (std::isnan(FpSrcReg1) || std::isnan(FpSrcReg2)) {
                ccFlagBits = ccFlagBits | (ZFBit | PFBit);
                cfofBits = cfofBits | CFBit;
            }
            else if(FpSrcReg1 < FpSrcReg2)
                cfofBits = cfofBits | CFBit;
            else if(FpSrcReg1 == FpSrcReg2)
                ccFlagBits = ccFlagBits | ZFBit;
        '''
        op_class = 'FloatCmpOp'

    class absfp(Fp2Op):
        code = 'FpDestReg = fabs(FpSrcReg1);'
        flag_code = 'FSW = FSW & (~CC1Bit);'

    class chsfp(Fp2Op):
        code = 'FpDestReg = (-1) * (FpSrcReg1);'
        flag_code = 'FSW = FSW & (~CC1Bit);'

    class Pop87(Fp0Op):
        code = ''
        op_class = 'IntAluOp'
}};
