branch.hh revision 7149
1/* 2 * Copyright (c) 2010 ARM Limited 3 * All rights reserved 4 * 5 * The license below extends only to copyright in the software and shall 6 * not be construed as granting a license to any other intellectual 7 * property including but not limited to intellectual property relating 8 * to a hardware implementation of the functionality of the software 9 * licensed hereunder. You may use the software subject to the license 10 * terms below provided that you ensure that this notice is replicated 11 * unmodified and in its entirety in all distributions of the software, 12 * modified or unmodified, in source code or in binary form. 13 * 14 * Copyright (c) 2007-2008 The Florida State University 15 * All rights reserved. 16 * 17 * Redistribution and use in source and binary forms, with or without 18 * modification, are permitted provided that the following conditions are 19 * met: redistributions of source code must retain the above copyright 20 * notice, this list of conditions and the following disclaimer; 21 * redistributions in binary form must reproduce the above copyright 22 * notice, this list of conditions and the following disclaimer in the 23 * documentation and/or other materials provided with the distribution; 24 * neither the name of the copyright holders nor the names of its 25 * contributors may be used to endorse or promote products derived from 26 * this software without specific prior written permission. 27 * 28 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 29 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 30 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 31 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 32 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 33 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 34 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 35 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 36 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 37 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 38 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 39 * 40 * Authors: Stephen Hines 41 */ 42#ifndef __ARCH_ARM_INSTS_BRANCH_HH__ 43#define __ARCH_ARM_INSTS_BRANCH_HH__ 44 45#include "arch/arm/insts/pred_inst.hh" 46 47namespace ArmISA 48{ 49/** 50 * Base class for instructions whose disassembly is not purely a 51 * function of the machine instruction (i.e., it depends on the 52 * PC). This class overrides the disassemble() method to check 53 * the PC and symbol table values before re-using a cached 54 * disassembly string. This is necessary for branches and jumps, 55 * where the disassembly string includes the target address (which 56 * may depend on the PC and/or symbol table). 57 */ 58class PCDependentDisassembly : public PredOp 59{ 60 protected: 61 /// Cached program counter from last disassembly 62 mutable Addr cachedPC; 63 64 /// Cached symbol table pointer from last disassembly 65 mutable const SymbolTable *cachedSymtab; 66 67 /// Constructor 68 PCDependentDisassembly(const char *mnem, ExtMachInst _machInst, 69 OpClass __opClass) 70 : PredOp(mnem, _machInst, __opClass), 71 cachedPC(0), cachedSymtab(0) 72 { 73 } 74 75 const std::string & 76 disassemble(Addr pc, const SymbolTable *symtab) const; 77}; 78 79// Branch to a target computed with an immediate 80class BranchImm : public PredOp 81{ 82 protected: 83 int32_t imm; 84 85 public: 86 BranchImm(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 87 int32_t _imm) : 88 PredOp(mnem, _machInst, __opClass), imm(_imm) 89 {} 90}; 91 92// Conditionally Branch to a target computed with an immediate 93class BranchImmCond : public BranchImm 94{ 95 protected: 96 // This will mask the condition code stored for PredOp. Ideally these two 97 // class would cooperate, but they're not set up to do that at the moment. 98 ConditionCode condCode; 99 100 public: 101 BranchImmCond(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 102 int32_t _imm, ConditionCode _condCode) : 103 BranchImm(mnem, _machInst, __opClass, _imm), condCode(_condCode) 104 {} 105}; 106 107// Branch to a target computed with a register 108class BranchReg : public PredOp 109{ 110 protected: 111 IntRegIndex op1; 112 113 public: 114 BranchReg(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 115 IntRegIndex _op1) : 116 PredOp(mnem, _machInst, __opClass), op1(_op1) 117 {} 118}; 119 120// Conditionally Branch to a target computed with a register 121class BranchRegCond : public BranchReg 122{ 123 protected: 124 // This will mask the condition code stored for PredOp. Ideally these two 125 // class would cooperate, but they're not set up to do that at the moment. 126 ConditionCode condCode; 127 128 public: 129 BranchRegCond(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 130 IntRegIndex _op1, ConditionCode _condCode) : 131 BranchReg(mnem, _machInst, __opClass, _op1), condCode(_condCode) 132 {} 133}; 134 135// Branch to a target computed with two registers 136class BranchRegReg : public PredOp 137{ 138 protected: 139 IntRegIndex op1; 140 IntRegIndex op2; 141 142 public: 143 BranchRegReg(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 144 IntRegIndex _op1, IntRegIndex _op2) : 145 PredOp(mnem, _machInst, __opClass), op1(_op1), op2(_op2) 146 {} 147}; 148 149// Branch to a target computed with an immediate and a register 150class BranchImmReg : public PredOp 151{ 152 protected: 153 int32_t imm; 154 IntRegIndex op1; 155 156 public: 157 BranchImmReg(const char *mnem, ExtMachInst _machInst, OpClass __opClass, 158 int32_t _imm, IntRegIndex _op1) : 159 PredOp(mnem, _machInst, __opClass), imm(_imm), op1(_op1) 160 {} 161}; 162 163/** 164 * Base class for branches (PC-relative control transfers), 165 * conditional or unconditional. 166 */ 167class Branch : public PCDependentDisassembly 168{ 169 protected: 170 /// target address (signed) Displacement . 171 int32_t disp; 172 173 /// Constructor. 174 Branch(const char *mnem, ExtMachInst _machInst, OpClass __opClass) 175 : PCDependentDisassembly(mnem, _machInst, __opClass), 176 disp(machInst.offset << 2) 177 { 178 //If Bit 26 is 1 then Sign Extend 179 if ( (disp & 0x02000000) > 0 ) { 180 disp |= 0xFC000000; 181 } 182 } 183 184 Addr branchTarget(Addr branchPC) const; 185 186 std::string 187 generateDisassembly(Addr pc, const SymbolTable *symtab) const; 188}; 189 190/** 191 * Base class for branch and exchange instructions on the ARM 192 */ 193class BranchExchange : public PredOp 194{ 195 protected: 196 /// Constructor 197 BranchExchange(const char *mnem, ExtMachInst _machInst, 198 OpClass __opClass) 199 : PredOp(mnem, _machInst, __opClass) 200 { 201 } 202 203 std::string 204 generateDisassembly(Addr pc, const SymbolTable *symtab) const; 205}; 206 207} 208 209#endif //__ARCH_ARM_INSTS_BRANCH_HH__ 210