diff options
| author | gdkchan <gab.dark.100@gmail.com> | 2018-07-14 13:13:02 -0300 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2018-07-14 13:13:02 -0300 |
| commit | 514218ab98acc1f0ace2e2cc0b8c1091ffccc6ce (patch) | |
| tree | ce7c44f11aa1dad7143678b2444bc297b98e5bff /ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs | |
| parent | 2f37583ab3b49aa5064a72c8d3b4e8245ebb6b5b (diff) | |
Add SMLSL, SQRSHRN and SRSHR (Vector) cpu instructions, nits (#225)
* Add SMLSL, SQRSHRN and SRSHR (Vector) cpu instructions
* Address PR feedback
* Address PR feedback
* Remove another useless temp var
* nit: Alignment
* Replace Context.CurrOp.GetBitsCount() with Op.GetBitsCount()
* Fix encodings and move flag bit test out of the loop
Diffstat (limited to 'ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs')
| -rw-r--r-- | ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs | 118 |
1 files changed, 26 insertions, 92 deletions
diff --git a/ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs b/ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs index 39331f96..2fc8f178 100644 --- a/ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs +++ b/ChocolArm64/Instruction/AInstEmitSimdArithmetic.cs @@ -65,11 +65,12 @@ namespace ChocolArm64.Instruction { AOpCodeSimd Op = (AOpCodeSimd)Context.CurrOp; - int Bytes = Context.CurrOp.GetBitsCount() >> 3; + int Bytes = Op.GetBitsCount() >> 3; + int Elems = Bytes >> Op.Size; EmitVectorExtractZx(Context, Op.Rn, 0, Op.Size); - for (int Index = 1; Index < (Bytes >> Op.Size); Index++) + for (int Index = 1; Index < Elems; Index++) { EmitVectorExtractZx(Context, Op.Rn, Index, Op.Size); @@ -97,9 +98,10 @@ namespace ChocolArm64.Instruction { AOpCodeSimd Op = (AOpCodeSimd)Context.CurrOp; - int Bytes = Context.CurrOp.GetBitsCount() >> 3; + int Bytes = Op.GetBitsCount() >> 3; + int Elems = Bytes >> Op.Size; - for (int Index = 0; Index < (Bytes >> Op.Size); Index++) + for (int Index = 0; Index < Elems; Index++) { EmitVectorExtractZx(Context, Op.Rn, Index, Op.Size); @@ -190,84 +192,6 @@ namespace ChocolArm64.Instruction } } - private static void EmitSaturatingExtNarrow(AILEmitterCtx Context, bool SignedSrc, bool SignedDst, bool Scalar) - { - AOpCodeSimd Op = (AOpCodeSimd)Context.CurrOp; - - int Elems = (!Scalar ? 8 >> Op.Size : 1); - int ESize = 8 << Op.Size; - - int Part = (!Scalar & (Op.RegisterSize == ARegisterSize.SIMD128) ? Elems : 0); - - int TMaxValue = (SignedDst ? (1 << (ESize - 1)) - 1 : (int)((1L << ESize) - 1L)); - int TMinValue = (SignedDst ? -((1 << (ESize - 1))) : 0); - - Context.EmitLdc_I8(0L); - Context.EmitSttmp(); - - for (int Index = 0; Index < Elems; Index++) - { - AILLabel LblLe = new AILLabel(); - AILLabel LblGeEnd = new AILLabel(); - - EmitVectorExtract(Context, Op.Rn, Index, Op.Size + 1, SignedSrc); - - Context.Emit(OpCodes.Dup); - - Context.EmitLdc_I4(TMaxValue); - Context.Emit(OpCodes.Conv_U8); - - Context.Emit(SignedSrc ? OpCodes.Ble_S : OpCodes.Ble_Un_S, LblLe); - - Context.Emit(OpCodes.Pop); - - Context.EmitLdc_I4(TMaxValue); - - Context.EmitLdc_I8(0x8000000L); - Context.EmitSttmp(); - - Context.Emit(OpCodes.Br_S, LblGeEnd); - - Context.MarkLabel(LblLe); - - Context.Emit(OpCodes.Dup); - - Context.EmitLdc_I4(TMinValue); - Context.Emit(OpCodes.Conv_I8); - - Context.Emit(SignedSrc ? OpCodes.Bge_S : OpCodes.Bge_Un_S, LblGeEnd); - - Context.Emit(OpCodes.Pop); - - Context.EmitLdc_I4(TMinValue); - - Context.EmitLdc_I8(0x8000000L); - Context.EmitSttmp(); - - Context.MarkLabel(LblGeEnd); - - if (Scalar) - { - EmitVectorZeroLower(Context, Op.Rd); - } - - EmitVectorInsert(Context, Op.Rd, Part + Index, Op.Size); - } - - if (Part == 0) - { - EmitVectorZeroUpper(Context, Op.Rd); - } - - Context.EmitLdarg(ATranslatedSub.StateArgIdx); - Context.EmitLdarg(ATranslatedSub.StateArgIdx); - Context.EmitCallPropGet(typeof(AThreadState), nameof(AThreadState.Fpsr)); - Context.EmitLdtmp(); - Context.Emit(OpCodes.Conv_I4); - Context.Emit(OpCodes.Or); - Context.EmitCallPropSet(typeof(AThreadState), nameof(AThreadState.Fpsr)); - } - public static void Fabd_S(AILEmitterCtx Context) { EmitScalarBinaryOpF(Context, () => @@ -338,7 +262,7 @@ namespace ChocolArm64.Instruction int SizeF = Op.Size & 1; - int Bytes = Context.CurrOp.GetBitsCount() >> 3; + int Bytes = Op.GetBitsCount() >> 3; int Elems = Bytes >> SizeF + 2; int Half = Elems >> 1; @@ -870,7 +794,7 @@ namespace ChocolArm64.Instruction int SizeF = Op.Size & 1; - int Bytes = Context.CurrOp.GetBitsCount() >> 3; + int Bytes = Op.GetBitsCount() >> 3; for (int Index = 0; Index < Bytes >> SizeF + 2; Index++) { @@ -1102,6 +1026,15 @@ namespace ChocolArm64.Instruction }); } + public static void Smlsl_V(AILEmitterCtx Context) + { + EmitVectorWidenRnRmTernaryOpSx(Context, () => + { + Context.Emit(OpCodes.Mul); + Context.Emit(OpCodes.Sub); + }); + } + public static void Smull_V(AILEmitterCtx Context) { EmitVectorWidenRnRmBinaryOpSx(Context, () => Context.Emit(OpCodes.Mul)); @@ -1109,22 +1042,22 @@ namespace ChocolArm64.Instruction public static void Sqxtn_S(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: true, SignedDst: true, Scalar: true); + EmitScalarSaturatingNarrowOpSxSx(Context, () => { }); } public static void Sqxtn_V(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: true, SignedDst: true, Scalar: false); + EmitVectorSaturatingNarrowOpSxSx(Context, () => { }); } public static void Sqxtun_S(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: true, SignedDst: false, Scalar: true); + EmitScalarSaturatingNarrowOpSxZx(Context, () => { }); } public static void Sqxtun_V(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: true, SignedDst: false, Scalar: false); + EmitVectorSaturatingNarrowOpSxZx(Context, () => { }); } public static void Sub_S(AILEmitterCtx Context) @@ -1198,11 +1131,12 @@ namespace ChocolArm64.Instruction { AOpCodeSimd Op = (AOpCodeSimd)Context.CurrOp; - int Bytes = Context.CurrOp.GetBitsCount() >> 3; + int Bytes = Op.GetBitsCount() >> 3; + int Elems = Bytes >> Op.Size; EmitVectorExtractZx(Context, Op.Rn, 0, Op.Size); - for (int Index = 1; Index < (Bytes >> Op.Size); Index++) + for (int Index = 1; Index < Elems; Index++) { EmitVectorExtractZx(Context, Op.Rn, Index, Op.Size); @@ -1272,12 +1206,12 @@ namespace ChocolArm64.Instruction public static void Uqxtn_S(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: false, SignedDst: false, Scalar: true); + EmitScalarSaturatingNarrowOpZxZx(Context, () => { }); } public static void Uqxtn_V(AILEmitterCtx Context) { - EmitSaturatingExtNarrow(Context, SignedSrc: false, SignedDst: false, Scalar: false); + EmitVectorSaturatingNarrowOpZxZx(Context, () => { }); } } } |
