changeset 18368caa8489 in /z/repo/m5 details: http://repo.m5sim.org/m5?cmd=changeset;node=18368caa8489 description: ARM: Identify branches as conditional or unconditional and direct or indirect.
diffstat: src/arch/arm/insts/branch.hh | 1 + src/arch/arm/isa/insts/branch.isa | 35 ++++++++++++++++++++++++++------ src/arch/arm/isa/templates/branch.isa | 37 +++++++++++++++++++++++++++++++++++ src/arch/arm/predecoder.hh | 7 +++-- src/arch/arm/types.hh | 13 ++++++++++++ 5 files changed, 83 insertions(+), 10 deletions(-) diffs (294 lines): diff -r 21e4f3a569fb -r 18368caa8489 src/arch/arm/insts/branch.hh --- a/src/arch/arm/insts/branch.hh Thu Mar 17 19:20:20 2011 -0500 +++ b/src/arch/arm/insts/branch.hh Thu Mar 17 19:20:20 2011 -0500 @@ -57,6 +57,7 @@ int32_t _imm) : PredOp(mnem, _machInst, __opClass), imm(_imm) {} + }; // Conditionally Branch to a target computed with an immediate diff -r 21e4f3a569fb -r 18368caa8489 src/arch/arm/isa/insts/branch.isa --- a/src/arch/arm/isa/insts/branch.isa Thu Mar 17 19:20:20 2011 -0500 +++ b/src/arch/arm/isa/insts/branch.isa Thu Mar 17 19:20:20 2011 -0500 @@ -48,6 +48,8 @@ bCode = ''' NPC = (uint32_t)(PC + imm); ''' + br_tgt_code = '''pcs.instNPC(branchPC.instPC() + imm);''' + instFlags = ["IsDirectControl"] if (link): bCode += ''' if (Thumb) @@ -55,12 +57,15 @@ else LR = PC - 4; ''' + instFlags += ["IsCall"] + bIop = InstObjParams(mnem, mnem.capitalize(), "BranchImmCond", - {"code": bCode, - "predicate_test": predicateTest}) + {"code": bCode, "predicate_test": predicateTest, + "brTgtCode" : br_tgt_code}, instFlags) header_output += BranchImmCondDeclare.subst(bIop) - decoder_output += BranchImmCondConstructor.subst(bIop) + decoder_output += BranchImmCondConstructor.subst(bIop) + \ + BranchTarget.subst(bIop) exec_output += PredOpExecute.subst(bIop) # BX, BLX @@ -81,15 +86,22 @@ # Since we're switching ISAs, the target ISA will be the opposite # of the current ISA. Thumb is whether the target is ARM. newPC = '(Thumb ? (roundDown(PC, 4) + imm) : (PC + imm))' + br_tgt_code = ''' + pcs.instNPC((branchPC.thumb() ? (roundDown(branchPC.instPC(),4) + imm) : + (branchPC.instPC() + imm))); + ''' base = "BranchImmCond" declare = BranchImmCondDeclare constructor = BranchImmCondConstructor + instFlags = ["IsDirectControl"] else: Name += "Reg" newPC = 'Op1' + br_tgt_code = '' base = "BranchRegCond" declare = BranchRegCondDeclare constructor = BranchRegCondConstructor + instFlags = ["IsIndirectControl"] if link and imm: linkStr = ''' // The immediate version of the blx thumb instruction @@ -100,6 +112,7 @@ else LR = PC - 4; ''' + instFlags += ["IsCall"] elif link: linkStr = ''' if (Thumb) @@ -107,14 +120,18 @@ else LR = PC - 4; ''' + instFlags += ["IsCall"] else: linkStr = "" + instFlags += ["IsReturn"] if imm and link: #blx with imm branchStr = ''' NextThumb = !Thumb; NPC = %(newPC)s; ''' + br_tgt_code = '''pcs.nextThumb(!branchPC.thumb());\n''' + \ + br_tgt_code else: branchStr = "IWNPC = %(newPC)s;" branchStr = branchStr % { "newPC" : newPC } @@ -123,11 +140,13 @@ "newPC": newPC, "branch": branchStr} blxIop = InstObjParams(mnem, Name, base, - {"code": code, - "predicate_test": predicateTest}) + {"code": code, "brTgtCode" : br_tgt_code, + "predicate_test": predicateTest}, instFlags) header_output += declare.subst(blxIop) decoder_output += constructor.subst(blxIop) exec_output += PredOpExecute.subst(blxIop) + if imm: + decoder_output += BranchTarget.subst(blxIop) #Ignore BXJ for now @@ -136,7 +155,8 @@ code = 'NPC = (uint32_t)(PC + imm);\n' predTest = "Op1 %(test)s 0" % {"test": test} iop = InstObjParams(mnem, mnem.capitalize(), "BranchImmReg", - {"code": code, "predicate_test": predTest}) + {"code": code, "predicate_test": predTest}, + ["IsIndirectControl"]) header_output += BranchImmRegDeclare.subst(iop) decoder_output += BranchImmRegConstructor.subst(iop) exec_output += PredOpExecute.subst(iop) @@ -164,7 +184,8 @@ iop = InstObjParams(mnem, mnem.capitalize(), "BranchRegReg", {'ea_code': eaCode, 'memacc_code': accCode, - 'predicate_test': predicateTest}) + 'predicate_test': predicateTest}, + ["IsIndirectControl"]) header_output += BranchTableDeclare.subst(iop) decoder_output += BranchRegRegConstructor.subst(iop) exec_output += LoadExecute.subst(iop) + \ diff -r 21e4f3a569fb -r 18368caa8489 src/arch/arm/isa/templates/branch.isa --- a/src/arch/arm/isa/templates/branch.isa Thu Mar 17 19:20:20 2011 -0500 +++ b/src/arch/arm/isa/templates/branch.isa Thu Mar 17 19:20:20 2011 -0500 @@ -57,7 +57,11 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } + } }}; @@ -69,6 +73,7 @@ %(class_name)s(ExtMachInst machInst, int32_t _imm, ConditionCode _condCode); %(BasicExecDeclare)s + ArmISA::PCState branchTarget(const ArmISA::PCState &branchPC) const; }; }}; @@ -84,6 +89,9 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } } }}; @@ -108,6 +116,9 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } } }}; @@ -135,6 +146,9 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } } }}; @@ -176,6 +190,9 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } } }}; @@ -202,6 +219,26 @@ for (int x = 0; x < _numDestRegs; x++) { _srcRegIdx[_numSrcRegs++] = _destRegIdx[x]; } + flags[IsCondControl] = true; + } else { + flags[IsUncondControl] = true; } } }}; + +def template BranchTarget {{ + + ArmISA::PCState + %(class_name)s::branchTarget(const ArmISA::PCState &branchPC) const + { + %(op_decl)s; + %(op_rd)s; + + ArmISA::PCState pcs = branchPC; + %(brTgtCode)s + pcs.advance(); + return pcs; + } +}}; + + diff -r 21e4f3a569fb -r 18368caa8489 src/arch/arm/predecoder.hh --- a/src/arch/arm/predecoder.hh Thu Mar 17 19:20:20 2011 -0500 +++ b/src/arch/arm/predecoder.hh Thu Mar 17 19:20:20 2011 -0500 @@ -128,17 +128,17 @@ outOfBytes = true; } - bool needMoreBytes() + bool needMoreBytes() const { return outOfBytes; } - bool extMachInstReady() + bool extMachInstReady() const { return emiReady; } - int getInstSize() + int getInstSize() const { return (!emi.thumb || emi.bigThumb) ? 4 : 2; } @@ -151,6 +151,7 @@ pc.npc(pc.pc() + getInstSize()); predAddrValid = true; predAddr = pc.pc() + getInstSize(); + pc.size(getInstSize()); emi = 0; emiReady = false; return thisEmi; diff -r 21e4f3a569fb -r 18368caa8489 src/arch/arm/types.hh --- a/src/arch/arm/types.hh Thu Mar 17 19:20:20 2011 -0500 +++ b/src/arch/arm/types.hh Thu Mar 17 19:20:20 2011 -0500 @@ -203,6 +203,7 @@ uint8_t flags; uint8_t nextFlags; uint8_t forcedItStateValue; + uint8_t _size; bool forcedItStateValid; public: PCState() : flags(0), nextFlags(0), forcedItStateValue(0), forcedItStateValid(false) @@ -248,6 +249,16 @@ nextFlags &= ~ThumbBit; } + void size(uint8_t s) { _size = s; } + uint8_t size() const { return _size; } + + bool + branching() const + { + return ((this->pc() + this->size()) != this->npc()); + } + + bool jazelle() const { @@ -392,6 +403,7 @@ { Base::serialize(os); SERIALIZE_SCALAR(flags); + SERIALIZE_SCALAR(_size); SERIALIZE_SCALAR(nextFlags); SERIALIZE_SCALAR(forcedItStateValue); SERIALIZE_SCALAR(forcedItStateValid); @@ -402,6 +414,7 @@ { Base::unserialize(cp, section); UNSERIALIZE_SCALAR(flags); + UNSERIALIZE_SCALAR(_size); UNSERIALIZE_SCALAR(nextFlags); UNSERIALIZE_SCALAR(forcedItStateValue); UNSERIALIZE_SCALAR(forcedItStateValid); _______________________________________________ m5-dev mailing list m5-dev@m5sim.org http://m5sim.org/mailman/listinfo/m5-dev