A32 Support

(WIP)
This commit is contained in:
riperiperi 2020-02-05 01:56:20 +00:00
parent cc9ab3471b
commit 16a850d588
3 changed files with 21 additions and 13 deletions

View file

@ -5,6 +5,7 @@ using ARMeilleure.Translation;
using static ARMeilleure.Instructions.InstEmitFlowHelper;
using static ARMeilleure.Instructions.InstEmitHelper;
using static ARMeilleure.Instructions.InstEmitFlowHelper;
using static ARMeilleure.IntermediateRepresentation.OperandHelper;
namespace ARMeilleure.Instructions
@ -21,7 +22,6 @@ namespace ARMeilleure.Instructions
}
else
{
context.StoreToContext();
context.Return(Const(op.Immediate));
}
}
@ -57,7 +57,7 @@ namespace ARMeilleure.Instructions
SetFlag(context, PState.TFlag, Const(isThumb ? 0 : 1));
}
InstEmitFlowHelper.EmitCall(context, (ulong)op.Immediate);
EmitJumpTableCall(context, Const((int)op.Immediate));
}
public static void Blxr(ArmEmitterContext context)
@ -66,9 +66,8 @@ namespace ARMeilleure.Instructions
uint pc = op.GetPc();
Operand addr = GetIntA32(context, op.Rm);
Operand addr = context.Copy(GetIntA32(context, op.Rm));
Operand bitOne = context.BitwiseAnd(addr, Const(1));
addr = context.BitwiseOr(addr, Const((int)CallFlag)); // Set call flag.
bool isThumb = IsThumb(context.CurrOp);
@ -80,15 +79,13 @@ namespace ARMeilleure.Instructions
SetFlag(context, PState.TFlag, bitOne);
context.Return(addr); // Call.
EmitJumpTableCall(context, addr);
}
public static void Bx(ArmEmitterContext context)
{
IOpCode32BReg op = (IOpCode32BReg)context.CurrOp;
context.StoreToContext();
EmitBxWritePc(context, GetIntA32(context, op.Rm));
}
}

View file

@ -144,22 +144,33 @@ namespace ARMeilleure.Instructions
}
}
public static void EmitBxWritePc(ArmEmitterContext context, Operand pc)
public static void EmitBxWritePc(ArmEmitterContext context, Operand pc, int sourceRegister = 0)
{
bool allowRejit = sourceRegister != RegisterAlias.Aarch32Lr && context.CurrOp.Instruction.Name != InstName.Ldm;
Operand mode = context.BitwiseAnd(pc, Const(1));
SetFlag(context, PState.TFlag, mode);
Operand lblArmMode = Label();
context.BranchIfTrue(lblArmMode, mode);
context.BranchIfFalse(lblArmMode, mode);
// Make this count as a call, the translator will ignore the low bit for the address.
context.Return(context.ZeroExtend32(OperandType.I64, context.BitwiseOr(pc, Const((int)InstEmitFlowHelper.CallFlag))));
Operand thumbAddr = allowRejit ? context.BitwiseOr(pc, Const((int)InstEmitFlowHelper.CallFlag)) : pc;
// Make this count for rejit, the translator will ignore the low bit for the address.
context.Return(context.ZeroExtend32(OperandType.I64, thumbAddr));
context.MarkLabel(lblArmMode);
context.Return(context.ZeroExtend32(OperandType.I64, context.BitwiseOr(context.BitwiseAnd(pc, Const(~3)), Const((int)InstEmitFlowHelper.CallFlag))));
Operand a32Addr = context.BitwiseAnd(pc, Const(~3));
if (allowRejit)
{
InstEmitFlowHelper.EmitJumpTableCall(context, a32Addr, true);
}
else
{
context.Return(context.ZeroExtend32(OperandType.I64, a32Addr));
}
}
public static Operand GetIntOrZR(ArmEmitterContext context, int regIndex)

View file

@ -51,7 +51,7 @@ namespace ARMeilleure.Instructions
EmitReadInt(context, address, rt, size);
}
if (!isSimd)
if (!isSimd && !(context.CurrOp is OpCode32 && rt == State.RegisterAlias.Aarch32Pc))
{
Operand value = GetInt(context, rt);