summaryrefslogtreecommitdiff
path: root/arch/mips
diff options
context:
space:
mode:
authornoone <you@example.com>2024-07-31 20:47:28 -0500
committerAlexander Taylor <alex@vector35.com>2024-08-12 15:50:54 -0400
commitbdc1c7134e14fc18182e33dfa3fe98ba10c38acf (patch)
tree51394bf04591f1b3335997b3595365cc75cdeeca /arch/mips
parent0bf72f94c49f34fc550c2d5c2fbab7a95ac72628 (diff)
Add IL, intrinsics for TLB-related instructions
Diffstat (limited to 'arch/mips')
-rw-r--r--arch/mips/arch_mips.cpp40
-rw-r--r--arch/mips/il.cpp35
-rw-r--r--arch/mips/il.h4
3 files changed, 75 insertions, 4 deletions
diff --git a/arch/mips/arch_mips.cpp b/arch/mips/arch_mips.cpp
index fd90daf0..8d0c70ec 100644
--- a/arch/mips/arch_mips.cpp
+++ b/arch/mips/arch_mips.cpp
@@ -973,6 +973,12 @@ public:
return "_setLeftPart64";
case MIPS_INTRIN_SET_RIGHT_PART64:
return "_setRightPart64";
+ case MIPS_INTRIN_TLBSET:
+ return "_writeTLB";
+ case MIPS_INTRIN_TLBGET:
+ return "_readTLB";
+ case MIPS_INTRIN_TLBSEARCH:
+ return "_probeTLB";
case CNMIPS_INTRIN_SYNCIOBDMA:
return "_synciobdma";
@@ -1034,6 +1040,9 @@ public:
MIPS_INTRIN_GET_RIGHT_PART64,
MIPS_INTRIN_SET_LEFT_PART64,
MIPS_INTRIN_SET_RIGHT_PART64,
+ MIPS_INTRIN_TLBSET,
+ MIPS_INTRIN_TLBGET,
+ MIPS_INTRIN_TLBSEARCH,
CNMIPS_INTRIN_SYNCIOBDMA,
CNMIPS_INTRIN_SYNCS,
@@ -1173,6 +1182,24 @@ public:
return {
NameAndType("rightpart", Type::IntegerType(8, false))
};
+ case MIPS_INTRIN_TLBSET:
+ return {
+ // we use the same order as the pseudocode
+ // in the documentation
+ NameAndType("index", Type::IntegerType(8, false)),
+ NameAndType("PageMask", Type::IntegerType(8, false)),
+ NameAndType("EntryHi", Type::IntegerType(8, false)),
+ NameAndType("EntryLo1", Type::IntegerType(8, false)),
+ NameAndType("EntryLo0", Type::IntegerType(8, false))
+ };
+ case MIPS_INTRIN_TLBGET:
+ return {
+ NameAndType("index", Type::IntegerType(8, false)),
+ };
+ case MIPS_INTRIN_TLBSEARCH:
+ return {
+ NameAndType("match", Type::IntegerType(8, false)),
+ };
default:
return vector<NameAndType>();
}
@@ -1216,6 +1243,19 @@ public:
case MIPS_INTRIN_SET_LEFT_PART64:
case MIPS_INTRIN_SET_RIGHT_PART64:
return {Type::IntegerType(8, false)};
+ case MIPS_INTRIN_TLBGET:
+ return {
+ // we use the same order as the pseudocode
+ // in the documentation:
+
+ // PageMask, EntryHi, EntryLo1, EntryLo0
+ Type::IntegerType(8, false),
+ Type::IntegerType(8, false),
+ Type::IntegerType(8, false),
+ Type::IntegerType(8, false),
+ };
+ case MIPS_INTRIN_TLBSEARCH:
+ return { Type::IntegerType(8, false) };
default:
return vector<Confidence<Ref<Type>>>();
}
diff --git a/arch/mips/il.cpp b/arch/mips/il.cpp
index 14639e74..9719c4f5 100644
--- a/arch/mips/il.cpp
+++ b/arch/mips/il.cpp
@@ -1842,6 +1842,37 @@ bool GetLowLevelILForInstruction(Architecture* arch, uint64_t addr, LowLevelILFu
il.AddInstruction(il.Intrinsic({}, MIPS_INTRIN_CACHE, {il.Const(1, op1.immediate), GetILOperandMemoryAddress(il, op2, addrSize)}));
break;
+ case MIPS_TLBP:
+ il.AddInstruction(il.Intrinsic({RegisterOrFlag::Register(REG_INDEX)}, MIPS_INTRIN_TLBSEARCH, {il.Register(registerSize, REG_ENTRY_HI)}));
+ break;
+ case MIPS_TLBR:
+ il.AddInstruction(il.Intrinsic({
+ RegisterOrFlag::Register(REG_PAGE_MASK),
+ RegisterOrFlag::Register(REG_ENTRY_HI),
+ RegisterOrFlag::Register(REG_ENTRY_LO1),
+ RegisterOrFlag::Register(REG_ENTRY_LO0)
+ }, MIPS_INTRIN_TLBGET, { il.Register(registerSize, REG_INDEX) }));
+ break;
+ case MIPS_TLBWI:
+ il.AddInstruction(il.Intrinsic({}, MIPS_INTRIN_TLBSET, {
+ il.Register(registerSize, REG_INDEX),
+ il.Register(registerSize, REG_PAGE_MASK),
+ il.Register(registerSize, REG_ENTRY_HI),
+ il.Register(registerSize, REG_ENTRY_LO1),
+ il.Register(registerSize, REG_ENTRY_LO0)
+ }));
+ break;
+ case MIPS_TLBWR:
+ il.AddInstruction(il.Intrinsic({}, MIPS_INTRIN_TLBSET, {
+ il.Register(registerSize, REG_RANDOM),
+ il.Register(registerSize, REG_PAGE_MASK),
+ il.Register(registerSize, REG_ENTRY_HI),
+ il.Register(registerSize, REG_ENTRY_LO1),
+ il.Register(registerSize, REG_ENTRY_LO0)
+ }));
+ break;
+
+
case CNMIPS_BADDU:
il.AddInstruction(SetRegisterOrNop(il, 8, registerSize, op1.reg,
il.ZeroExtend(registerSize,
@@ -2135,10 +2166,6 @@ bool GetLowLevelILForInstruction(Architecture* arch, uint64_t addr, LowLevelILFu
case MIPS_MTHC1:
case MIPS_MTHC2:
case MIPS_PREFX:
- case MIPS_TLBP:
- case MIPS_TLBR:
- case MIPS_TLBWI:
- case MIPS_TLBWR:
case MIPS_WRPGPR:
case MIPS_RDPGPR:
case MIPS_RECIP1:
diff --git a/arch/mips/il.h b/arch/mips/il.h
index c4ffff75..9a5a7999 100644
--- a/arch/mips/il.h
+++ b/arch/mips/il.h
@@ -65,6 +65,10 @@ enum MipsIntrinsic : uint32_t
MIPS_INTRIN_SET_LEFT_PART64,
MIPS_INTRIN_SET_RIGHT_PART64,
+ MIPS_INTRIN_TLBSET,
+ MIPS_INTRIN_TLBGET,
+ MIPS_INTRIN_TLBSEARCH,
+
CNMIPS_INTRIN_SYNCIOBDMA,
CNMIPS_INTRIN_SYNCS,
CNMIPS_INTRIN_SYNCW,