aboutsummaryrefslogtreecommitdiff
path: root/ARMeilleure/Instructions/InstEmitMemoryHelper.cs
diff options
context:
space:
mode:
Diffstat (limited to 'ARMeilleure/Instructions/InstEmitMemoryHelper.cs')
-rw-r--r--ARMeilleure/Instructions/InstEmitMemoryHelper.cs67
1 files changed, 65 insertions, 2 deletions
diff --git a/ARMeilleure/Instructions/InstEmitMemoryHelper.cs b/ARMeilleure/Instructions/InstEmitMemoryHelper.cs
index e0b44353..70861d16 100644
--- a/ARMeilleure/Instructions/InstEmitMemoryHelper.cs
+++ b/ARMeilleure/Instructions/InstEmitMemoryHelper.cs
@@ -53,7 +53,7 @@ namespace ARMeilleure.Instructions
if (!isSimd)
{
- Operand value = GetIntOrZR(context, rt);
+ Operand value = GetInt(context, rt);
if (ext == Extension.Sx32 || ext == Extension.Sx64)
{
@@ -67,7 +67,7 @@ namespace ARMeilleure.Instructions
}
}
- SetIntOrZR(context, rt, value);
+ SetInt(context, rt, value);
}
}
@@ -505,5 +505,68 @@ namespace ARMeilleure.Instructions
SetIntOrZR(context, rt, value);
}
}
+
+ // ARM32 helpers.
+ public static Operand GetMemM(ArmEmitterContext context, bool setCarry = true)
+ {
+ switch (context.CurrOp)
+ {
+ case OpCode32MemRsImm op: return GetMShiftedByImmediate(context, op, setCarry);
+
+ case OpCode32MemReg op: return GetIntA32(context, op.Rm);
+
+ case OpCode32Mem op: return Const(op.Immediate);
+
+ case OpCode32SimdMemImm op: return Const(op.Immediate);
+
+ default: throw InvalidOpCodeType(context.CurrOp);
+ }
+ }
+
+ private static Exception InvalidOpCodeType(OpCode opCode)
+ {
+ return new InvalidOperationException($"Invalid OpCode type \"{opCode?.GetType().Name ?? "null"}\".");
+ }
+
+ public static Operand GetMShiftedByImmediate(ArmEmitterContext context, OpCode32MemRsImm op, bool setCarry)
+ {
+ Operand m = GetIntA32(context, op.Rm);
+
+ int shift = op.Immediate;
+
+ if (shift == 0)
+ {
+ switch (op.ShiftType)
+ {
+ case ShiftType.Lsr: shift = 32; break;
+ case ShiftType.Asr: shift = 32; break;
+ case ShiftType.Ror: shift = 1; break;
+ }
+ }
+
+ if (shift != 0)
+ {
+ setCarry &= false;
+
+ switch (op.ShiftType)
+ {
+ case ShiftType.Lsl: m = InstEmitAluHelper.GetLslC(context, m, setCarry, shift); break;
+ case ShiftType.Lsr: m = InstEmitAluHelper.GetLsrC(context, m, setCarry, shift); break;
+ case ShiftType.Asr: m = InstEmitAluHelper.GetAsrC(context, m, setCarry, shift); break;
+ case ShiftType.Ror:
+ if (op.Immediate != 0)
+ {
+ m = InstEmitAluHelper.GetRorC(context, m, setCarry, shift);
+ }
+ else
+ {
+ m = InstEmitAluHelper.GetRrxC(context, m, setCarry);
+ }
+ break;
+ }
+ }
+
+ return m;
+ }
}
} \ No newline at end of file