// -*- mode:c++ -*-

// Copyright (c) 2011-2013, 2016, 2018, 2020 ARM Limited
// 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.

let {{

    header_output = ""
    decoder_output = ""
    exec_output = ""

    # B, BL
    for (mnem, link) in (("b", False), ("bl", True)):
        bCode = ('NPC = purifyTaggedAddr(RawPC + imm, xc->tcBase(), '
                 'currEL(xc->tcBase()), true);\n')
        instFlags = ['IsDirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize() + "64",
                                "BranchImm64", bCode, instFlags)
        header_output += BranchImm64Declare.subst(bIop)
        decoder_output += BranchImm64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)

    # BR, BLR
    for (mnem, link) in (("br", False), ("blr", True)):
        bCode = ('NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
                 'currEL(xc->tcBase()), true);\n')
        instFlags = ['IsIndirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize() + "64",
                                "BranchReg64", bCode, instFlags)
        header_output += BranchReg64Declare.subst(bIop)
        decoder_output += BranchReg64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)

    # BRAA, BLRAA
    for (mnem, link) in (("Braa", False), ("Blraa", True)):
        bCode = ' fault = authIA(xc->tcBase(), XOp1, XOp2, &XOp1);\n'
        bCode += ('if (fault == NoFault)\n'
                  '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
                  '                     currEL(xc->tcBase()), true);\n')
        instFlags = ['IsIndirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize(),
                                "BranchRegReg64", bCode, instFlags)
        header_output += BranchRegReg64Declare.subst(bIop)
        decoder_output += BranchRegReg64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)

    # BRAAZ, BLRAAZ
    for (mnem, link) in (("Braaz", False), ("Blraaz", True)):
        bCode = '''
                fault = authIA(xc->tcBase(), XOp1, 0, &XOp1);
                '''
        bCode += ('if (fault == NoFault)\n'
                  '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
                  '                       currEL(xc->tcBase()), true);\n')
        instFlags = ['IsIndirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize(),
                                "BranchReg64", bCode, instFlags)
        header_output += BranchReg64Declare.subst(bIop)
        decoder_output += BranchReg64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)

    # BRAB, BLRAB
    for (mnem, link) in (("Brab", False), ("Blrab", True)):
        bCode = ' fault = authIB(xc->tcBase(), XOp1, XOp2, &XOp1);\n'
        bCode += ('if (fault == NoFault)\n'
                  '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
                  '                        currEL(xc->tcBase()), true);\n')
        instFlags = ['IsIndirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize(),
                                "BranchRegReg64", bCode, instFlags)
        header_output += BranchRegReg64Declare.subst(bIop)
        decoder_output += BranchRegReg64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)

    # BRABZ, BLRABZ
    for (mnem, link) in (("Brabz", False), ("Blrabz", True)):
        bCode = '''
                fault = authIB(xc->tcBase(), XOp1, 0, &XOp1);
                '''
        bCode += ('if (fault == NoFault)\n'
                  '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
                  '                        currEL(xc->tcBase()), true);\n')
        instFlags = ['IsIndirectControl', 'IsUncondControl']
        if (link):
            bCode += 'XLR = RawPC + 4;\n'
            instFlags += ['IsCall']

        bIop = ArmInstObjParams(mnem, mnem.capitalize(),
                                "BranchReg64", bCode, instFlags)
        header_output += BranchReg64Declare.subst(bIop)
        decoder_output += BranchReg64Constructor.subst(bIop)
        exec_output += BasicExecute.subst(bIop)


    # B conditional
    bCode = '''
        if (testPredicate(CondCodesNZ, CondCodesC, CondCodesV, condCode))
            NPC = purifyTaggedAddr(RawPC + imm, xc->tcBase(),
                                   currEL(xc->tcBase()), true);
        else
            NPC = NPC;
    '''
    bIop = ArmInstObjParams("b", "BCond64", "BranchImmCond64", bCode,
                            ['IsCondControl', 'IsDirectControl'])
    header_output += BranchImmCond64Declare.subst(bIop)
    decoder_output += BranchImmCond64Constructor.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # RET
    bCode = ('NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
             'currEL(xc->tcBase()), true);\n')
    instFlags = ['IsIndirectControl', 'IsUncondControl', 'IsReturn']

    bIop = ArmInstObjParams('ret', 'Ret64', "BranchRet64", bCode, instFlags)
    header_output += BranchReg64Declare.subst(bIop)
    decoder_output += BranchReg64Constructor.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # RETAA
    bCode = '''
                fault = authIA(xc->tcBase(), XOp1, XOp2, &XOp1);
                '''
    bCode += (' if (fault == NoFault)\n'
              '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
             'currEL(xc->tcBase()), true);\n')
    bIop = ArmInstObjParams('retaa', 'Retaa', "BranchRetA64", bCode, instFlags)
    header_output += BasicDeclare.subst(bIop)
    decoder_output += BasicConstructor64.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # RETAB
    bCode = '''
                fault = authIB(xc->tcBase(), XOp1, XOp2, &XOp1);
                '''
    bCode += (' if (fault == NoFault)\n'
              '    NPC = purifyTaggedAddr(XOp1, xc->tcBase(), '
             'currEL(xc->tcBase()), true);\n')
    bIop = ArmInstObjParams('retab', 'Retab', "BranchRetA64", bCode, instFlags)
    header_output += BasicDeclare.subst(bIop)
    decoder_output += BasicConstructor64.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # ERET
    bCode = '''
                if (xc->inHtmTransactionalState()) {
                    fault = std::make_shared<GenericHtmFailureFault>(
                        xc->getHtmTransactionUid(),
                        HtmFailureFaultCause::EXCEPTION);
                    return fault;
                }
                Addr newPc;
                CPSR cpsr = Cpsr;
                CPSR spsr = Spsr;

                ExceptionLevel curr_el = currEL(cpsr);
                switch (curr_el) {
                  case EL3:
                    newPc = xc->tcBase()->readMiscReg(MISCREG_ELR_EL3);
                    break;
                  case EL2:
                    newPc = xc->tcBase()->readMiscReg(MISCREG_ELR_EL2);
                    break;
                  case EL1:
                    newPc = xc->tcBase()->readMiscReg(MISCREG_ELR_EL1);
                    break;
                  default:
                    return std::make_shared<UndefinedInstruction>(machInst,
                                                                  false,
                                                                  mnemonic);
                    break;
                }

                %(op)s

                if (fault == NoFault){
                    if (spsr.width) {
                        // Exception return to AArch32.
                        // 32 most significant bits are ignored
                        newPc &= mask(32);

                        if (newPc & mask(2)) {
                            // Mask bits to avoid PC Alignment fault
                            // when returning  to AArch32
                            if (spsr.t)
                                newPc = newPc & ~mask(1);
                            else
                                newPc = newPc & ~mask(2);
                        }
                    }

                    CPSR new_cpsr = getPSTATEFromPSR(xc->tcBase(), cpsr, spsr);

                    Cpsr = new_cpsr;
                    CondCodesNZ = new_cpsr.nz;
                    CondCodesC  = new_cpsr.c;
                    CondCodesV  = new_cpsr.v;

                    NextAArch64 = !new_cpsr.width;
                    // Switch between aarch64 and aarch32, or vice versa.
                    if (new_cpsr.width != cpsr.width) {
                        if (new_cpsr.width) {
                            // Going to aarch32.
                            syncVecRegsToElems(xc->tcBase());
                        } else {
                            // Going to aarch64.
                            syncVecElemsToRegs(xc->tcBase());
                        }
                    }
                    NextItState = itState(new_cpsr);
                    NPC = purifyTaggedAddr(newPc, xc->tcBase(),
                        currEL(new_cpsr), true);

                    LLSCLock = 0;  // Clear exclusive monitor
                    SevMailbox = 1; //Set Event Register
                }
    '''
    instFlags = ['IsSerializeAfter', 'IsNonSpeculative', 'IsSquashAfter']
    bIop = ArmInstObjParams('eret', 'Eret64', "BranchEret64",
                            bCode%{'op': ''}, instFlags)
    header_output += BasicDeclare.subst(bIop)
    decoder_output += BasicConstructor64.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # ERETAA
    pac_code = '''
                fault = authIA(xc->tcBase(), newPc, XOp1, &newPc);
                '''
    bIop = ArmInstObjParams('eretaa', 'Eretaa', "BranchEretA64",
                            bCode % {'op': pac_code} , instFlags)
    header_output  += BasicDeclare.subst(bIop)
    decoder_output += BasicConstructor64.subst(bIop)
    exec_output    += BasicExecute.subst(bIop)

    # ERETAB
    pac_code = '''
                fault = authIB(xc->tcBase(), newPc, XOp1, &newPc);
                '''
    bIop = ArmInstObjParams('eretab', 'Eretab', "BranchEretA64",
                            bCode % {'op': pac_code} , instFlags)
    header_output += BasicDeclare.subst(bIop)
    decoder_output += BasicConstructor64.subst(bIop)
    exec_output += BasicExecute.subst(bIop)

    # CBNZ, CBZ
    for (mnem, test) in (("cbz", "=="), ("cbnz", "!=")):
        code = ('NPC = (Op164 %(test)s 0) ? '
                'purifyTaggedAddr(RawPC + imm, xc->tcBase(), '
                'currEL(xc->tcBase()), true) : NPC;\n')
        code = code % {"test": test}
        iop = ArmInstObjParams(mnem, mnem.capitalize() + "64",
                               "BranchImmReg64", code,
                               ['IsCondControl', 'IsDirectControl'])
        header_output += BranchImmReg64Declare.subst(iop)
        decoder_output += BranchImmReg64Constructor.subst(iop)
        exec_output += BasicExecute.subst(iop)

    # TBNZ, TBZ
    for (mnem, test) in (("tbz", "=="), ("tbnz", "!=")):
        code = ('NPC = ((Op164 & imm1) %(test)s 0) ? '
                'purifyTaggedAddr(RawPC + imm2, xc->tcBase(), '
                'currEL(xc->tcBase()), true) : NPC;\n')
        code = code % {"test": test}
        iop = ArmInstObjParams(mnem, mnem.capitalize() + "64",
                               "BranchImmImmReg64", code,
                               ['IsCondControl', 'IsDirectControl'])
        header_output += BranchImmImmReg64Declare.subst(iop)
        decoder_output += BranchImmImmReg64Constructor.subst(iop)
        exec_output += BasicExecute.subst(iop)
}};
