예제 #1
0
        private static void EmitHsetp2(
            EmitterContext context,
            FComp cmpOp,
            BoolOp logicOp,
            Operand[] srcA,
            Operand[] srcB,
            int srcPred,
            bool srcPredInv,
            int destPred,
            int destPredInv,
            bool hAnd)
        {
            Operand p0Res = GetFPComparison(context, cmpOp, srcA[0], srcB[0]);
            Operand p1Res = GetFPComparison(context, cmpOp, srcA[1], srcB[1]);

            if (hAnd)
            {
                p0Res = context.BitwiseAnd(p0Res, p1Res);
                p1Res = context.BitwiseNot(p0Res);
            }

            Operand pred = GetPredicate(context, srcPred, srcPredInv);

            p0Res = GetPredLogicalOp(context, logicOp, p0Res, pred);
            p1Res = GetPredLogicalOp(context, logicOp, p1Res, pred);

            context.Copy(Register(destPred, RegisterType.Predicate), p0Res);
            context.Copy(Register(destPredInv, RegisterType.Predicate), p1Res);
        }
예제 #2
0
        private static void EmitFsetp(
            EmitterContext context,
            FComp cmpOp,
            BoolOp logicOp,
            Operand srcA,
            Operand srcB,
            int srcPred,
            bool srcPredInv,
            int destPred,
            int destPredInv,
            bool absoluteA,
            bool absoluteB,
            bool negateA,
            bool negateB,
            bool writeCC,
            bool isFP64 = false)
        {
            Instruction fpType = isFP64 ? Instruction.FP64 : Instruction.FP32;

            srcA = context.FPAbsNeg(srcA, absoluteA, negateA, fpType);
            srcB = context.FPAbsNeg(srcB, absoluteB, negateB, fpType);

            Operand p0Res = GetFPComparison(context, cmpOp, srcA, srcB, fpType);
            Operand p1Res = context.BitwiseNot(p0Res);
            Operand pred  = GetPredicate(context, srcPred, srcPredInv);

            p0Res = GetPredLogicalOp(context, logicOp, p0Res, pred);
            p1Res = GetPredLogicalOp(context, logicOp, p1Res, pred);

            context.Copy(Register(destPred, RegisterType.Predicate), p0Res);
            context.Copy(Register(destPredInv, RegisterType.Predicate), p1Res);
        }
예제 #3
0
        private static void EmitFcmp(EmitterContext context, FComp cmpOp, Operand srcA, Operand srcB, Operand srcC, int rd)
        {
            Operand cmpRes = GetFPComparison(context, cmpOp, srcC, ConstF(0));

            Operand res = context.ConditionalSelect(cmpRes, srcA, srcB);

            context.Copy(GetDest(rd), res);
        }
예제 #4
0
        private static Operand GetFPComparison(EmitterContext context, FComp cond, Operand srcA, Operand srcB, Instruction fpType = Instruction.FP32)
        {
            Operand res;

            if (cond == FComp.T)
            {
                res = Const(IrConsts.True);
            }
            else if (cond == FComp.F)
            {
                res = Const(IrConsts.False);
            }
            else if (cond == FComp.Nan || cond == FComp.Num)
            {
                res = context.BitwiseOr(context.IsNan(srcA, fpType), context.IsNan(srcB, fpType));

                if (cond == FComp.Num)
                {
                    res = context.BitwiseNot(res);
                }
            }
            else
            {
                Instruction inst;

                switch (cond & ~FComp.Nan)
                {
                case FComp.Lt: inst = Instruction.CompareLess; break;

                case FComp.Eq: inst = Instruction.CompareEqual; break;

                case FComp.Le: inst = Instruction.CompareLessOrEqual; break;

                case FComp.Gt: inst = Instruction.CompareGreater; break;

                case FComp.Ne: inst = Instruction.CompareNotEqual; break;

                case FComp.Ge: inst = Instruction.CompareGreaterOrEqual; break;

                default: throw new ArgumentException($"Unexpected condition \"{cond}\".");
                }

                res = context.Add(inst | fpType, Local(), srcA, srcB);

                if ((cond & FComp.Nan) != 0)
                {
                    res = context.BitwiseOr(res, context.IsNan(srcA, fpType));
                    res = context.BitwiseOr(res, context.IsNan(srcB, fpType));
                }
            }

            return(res);
        }
예제 #5
0
        private static void EmitFset(
            EmitterContext context,
            FComp cmpOp,
            BoolOp logicOp,
            Operand srcA,
            Operand srcB,
            int srcPred,
            bool srcPredInv,
            int rd,
            bool absoluteA,
            bool absoluteB,
            bool negateA,
            bool negateB,
            bool boolFloat,
            bool writeCC,
            bool isFP64 = false)
        {
            Instruction fpType = isFP64 ? Instruction.FP64 : Instruction.FP32;

            srcA = context.FPAbsNeg(srcA, absoluteA, negateA, fpType);
            srcB = context.FPAbsNeg(srcB, absoluteB, negateB, fpType);

            Operand res  = GetFPComparison(context, cmpOp, srcA, srcB, fpType);
            Operand pred = GetPredicate(context, srcPred, srcPredInv);

            res = GetPredLogicalOp(context, logicOp, res, pred);

            Operand dest = GetDest(rd);

            if (boolFloat)
            {
                res = context.ConditionalSelect(res, ConstF(1), Const(0));

                context.Copy(dest, res);

                SetFPZnFlags(context, res, writeCC);
            }
            else
            {
                context.Copy(dest, res);

                SetZnFlags(context, res, writeCC, extended: false);
            }
        }
예제 #6
0
        private static void EmitHset2(
            EmitterContext context,
            FComp cmpOp,
            BoolOp logicOp,
            Operand[] srcA,
            Operand[] srcB,
            int srcPred,
            bool srcPredInv,
            int rd,
            bool boolFloat)
        {
            Operand[] res = new Operand[2];

            res[0] = GetFPComparison(context, cmpOp, srcA[0], srcB[0]);
            res[1] = GetFPComparison(context, cmpOp, srcA[1], srcB[1]);

            Operand pred = GetPredicate(context, srcPred, srcPredInv);

            res[0] = GetPredLogicalOp(context, logicOp, res[0], pred);
            res[1] = GetPredLogicalOp(context, logicOp, res[1], pred);

            if (boolFloat)
            {
                res[0] = context.ConditionalSelect(res[0], ConstF(1), Const(0));
                res[1] = context.ConditionalSelect(res[1], ConstF(1), Const(0));

                context.Copy(GetDest(rd), context.PackHalf2x16(res[0], res[1]));
            }
            else
            {
                Operand low  = context.BitwiseAnd(res[0], Const(0xffff));
                Operand high = context.ShiftLeft(res[1], Const(16));

                Operand packed = context.BitwiseOr(low, high);

                context.Copy(GetDest(rd), packed);
            }
        }