コード例 #1
0
 public Binary(BinaryOperationKind binaryOperationKind, IOperation left, IOperation right, ITypeSymbol resultType, SyntaxNode syntax)
 {
     this.BinaryOperationKind = binaryOperationKind;
     this.LeftOperand         = left;
     this.RightOperand        = right;
     this.Type   = resultType;
     this.Syntax = syntax;
 }
コード例 #2
0
 public CompoundAssignmentExpression(IOperation target, IOperation value, BinaryOperationKind binaryOperationKind, IMethodSymbol operatorMethod, SyntaxNode syntax)
 {
     this.Target = target;
     this.Value  = value;
     this.BinaryOperationKind = binaryOperationKind;
     this.OperatorMethod      = operatorMethod;
     this.Syntax = syntax;
 }
コード例 #3
0
 public ExpressionStatement(IOperation target, IOperation value, BinaryOperationKind binaryOperationKind, IMethodSymbol operatorMethod, SyntaxNode syntax) :
     this(new CompoundAssignmentExpression(
              binaryOperationKind,
              target,
              value,
              operatorMethod != null,
              operatorMethod,
              IsInvalidOperation(target, value),
              syntax,
              target.Type,
              default(Optional <object>)),
          syntax)
 {
 }
コード例 #4
0
        public static string GetText(BinaryOperationKind binaryOperationKind)
        {
            switch (binaryOperationKind)
            {
            case BinaryOperationKind.Addition:
                return("+");

            case BinaryOperationKind.Subtraction:
                return("-");

            case BinaryOperationKind.Multiplication:
                return("*");

            case BinaryOperationKind.Division:
                return("/");

            case BinaryOperationKind.Equal:
                return("==");

            case BinaryOperationKind.NotEqual:
                return("!=");

            case BinaryOperationKind.LessThan:
                return("<");

            case BinaryOperationKind.LessThanOrEqual:
                return("<=");

            case BinaryOperationKind.GreaterThan:
                return(">");

            case BinaryOperationKind.GreaterThanOrEqual:
                return(">=");

            case BinaryOperationKind.LogicalAnd:
                return("&&");

            case BinaryOperationKind.LogicalOr:
                return("||");

            default:
                return(string.Empty);
            }
        }
コード例 #5
0
        private static ConstantValue ApplyBinaryOperation(ConstantValue leftOperand, BinaryOperationKind operationKind, ConstantValue rightOperand)
        {
            switch (operationKind)
            {
            case BinaryOperationKind.Addition:
                return(leftOperand + rightOperand);

            case BinaryOperationKind.Subtraction:
                return(leftOperand - rightOperand);

            case BinaryOperationKind.Multiplication:
                return(leftOperand * rightOperand);

            case BinaryOperationKind.Division:
                return(leftOperand / rightOperand);

            case BinaryOperationKind.Equal:
                return(leftOperand == rightOperand);

            case BinaryOperationKind.NotEqual:
                return(leftOperand != rightOperand);

            case BinaryOperationKind.LessThan:
                return(leftOperand < rightOperand);

            case BinaryOperationKind.LessThanOrEqual:
                return(leftOperand <= rightOperand);

            case BinaryOperationKind.GreaterThan:
                return(leftOperand > rightOperand);

            case BinaryOperationKind.GreaterThanOrEqual:
                return(leftOperand >= rightOperand);

            case BinaryOperationKind.LogicalAnd:
                return(leftOperand && rightOperand);

            case BinaryOperationKind.LogicalOr:
            default:
                return(leftOperand || rightOperand);
            }
        }
コード例 #6
0
        private void TestBinary(BinaryOperationKind kind)
        {
            string text = "$a " + Operation.GetText(kind) + " $b";
            var    expr = NSScript.ParseExpression(text) as BinaryExpression;

            Assert.NotNull(expr);
            Assert.Equal(SyntaxNodeKind.BinaryExpression, expr.Kind);
            Assert.Equal(kind, expr.OperationKind);

            var left = expr.Left as Variable;

            Assert.NotNull(left);
            Assert.Equal("$a", left.Name.FullName);

            var right = expr.Right as Variable;

            Assert.NotNull(right);
            Assert.Equal("$b", right.Name.FullName);

            Assert.Equal(text, expr.ToString());
        }
コード例 #7
0
 public static BinaryExpression Binary(Expression left, BinaryOperationKind operationKind, Expression right) =>
 new BinaryExpression(left, operationKind, right);
コード例 #8
0
 internal BinaryExpression(Expression left, BinaryOperationKind operationKind, Expression right)
 {
     Left          = left;
     OperationKind = operationKind;
     Right         = right;
 }
コード例 #9
0
        public sealed override void Initialize(AnalysisContext context)
        {
            context.RegisterOperationAction(
                (operationContext) =>
            {
                ILoopStatement loop = (ILoopStatement)operationContext.Operation;
                if (loop.LoopKind == LoopKind.For)
                {
                    IForLoopStatement forLoop = (IForLoopStatement)loop;
                    IExpression forCondition  = forLoop.Condition;

                    if (forCondition.Kind == OperationKind.BinaryOperatorExpression)
                    {
                        IBinaryOperatorExpression condition = (IBinaryOperatorExpression)forCondition;
                        IExpression conditionLeft           = condition.Left;
                        IExpression conditionRight          = condition.Right;

                        if (conditionRight.ConstantValue != null &&
                            conditionRight.ResultType.SpecialType == SpecialType.System_Int32 &&
                            conditionLeft.Kind == OperationKind.LocalReferenceExpression)
                        {
                            // Test is known to be a comparison of a local against a constant.

                            int testValue             = (int)conditionRight.ConstantValue;
                            ILocalSymbol testVariable = ((ILocalReferenceExpression)conditionLeft).Local;

                            if (forLoop.Before.Length == 1)
                            {
                                IStatement setup = forLoop.Before[0];
                                if (setup.Kind == OperationKind.ExpressionStatement && ((IExpressionStatement)setup).Expression.Kind == OperationKind.AssignmentExpression)
                                {
                                    IAssignmentExpression setupAssignment = (IAssignmentExpression)((IExpressionStatement)setup).Expression;
                                    if (setupAssignment.Target.Kind == OperationKind.LocalReferenceExpression &&
                                        ((ILocalReferenceExpression)setupAssignment.Target).Local == testVariable &&
                                        setupAssignment.Value.ConstantValue != null &&
                                        setupAssignment.Value.ResultType.SpecialType == SpecialType.System_Int32)
                                    {
                                        // Setup is known to be an assignment of a constant to the local used in the test.

                                        int initialValue = (int)setupAssignment.Value.ConstantValue;

                                        if (forLoop.AtLoopBottom.Length == 1)
                                        {
                                            IStatement advance = forLoop.AtLoopBottom[0];
                                            if (advance.Kind == OperationKind.ExpressionStatement)
                                            {
                                                IExpression advanceExpression            = ((IExpressionStatement)advance).Expression;
                                                IExpression advanceIncrement             = null;
                                                BinaryOperationKind advanceOperationCode = BinaryOperationKind.None;

                                                if (advanceExpression.Kind == OperationKind.AssignmentExpression)
                                                {
                                                    IAssignmentExpression advanceAssignment = (IAssignmentExpression)advanceExpression;

                                                    if (advanceAssignment.Target.Kind == OperationKind.LocalReferenceExpression &&
                                                        ((ILocalReferenceExpression)advanceAssignment.Target).Local == testVariable &&
                                                        advanceAssignment.Value.Kind == OperationKind.BinaryOperatorExpression &&
                                                        advanceAssignment.Value.ResultType.SpecialType == SpecialType.System_Int32)
                                                    {
                                                        // Advance is known to be an assignment of a binary operation to the local used in the test.

                                                        IBinaryOperatorExpression advanceOperation = (IBinaryOperatorExpression)advanceAssignment.Value;
                                                        if (!advanceOperation.UsesOperatorMethod &&
                                                            advanceOperation.Left.Kind == OperationKind.LocalReferenceExpression &&
                                                            ((ILocalReferenceExpression)advanceOperation.Left).Local == testVariable &&
                                                            advanceOperation.Right.ConstantValue != null &&
                                                            advanceOperation.Right.ResultType.SpecialType == SpecialType.System_Int32)
                                                        {
                                                            // Advance binary operation is known to involve a reference to the local used in the test and a constant.
                                                            advanceIncrement     = advanceOperation.Right;
                                                            advanceOperationCode = advanceOperation.BinaryKind;
                                                        }
                                                    }
                                                }
                                                else if (advanceExpression.Kind == OperationKind.CompoundAssignmentExpression || advanceExpression.Kind == OperationKind.IncrementExpression)
                                                {
                                                    ICompoundAssignmentExpression advanceAssignment = (ICompoundAssignmentExpression)advanceExpression;

                                                    if (advanceAssignment.Target.Kind == OperationKind.LocalReferenceExpression &&
                                                        ((ILocalReferenceExpression)advanceAssignment.Target).Local == testVariable &&
                                                        advanceAssignment.Value.ConstantValue != null &&
                                                        advanceAssignment.Value.ResultType.SpecialType == SpecialType.System_Int32)
                                                    {
                                                        // Advance binary operation is known to involve a reference to the local used in the test and a constant.
                                                        advanceIncrement     = advanceAssignment.Value;
                                                        advanceOperationCode = advanceAssignment.BinaryKind;
                                                    }
                                                }

                                                if (advanceIncrement != null)
                                                {
                                                    int incrementValue = (int)advanceIncrement.ConstantValue;
                                                    if (advanceOperationCode == BinaryOperationKind.IntegerSubtract)
                                                    {
                                                        advanceOperationCode = BinaryOperationKind.IntegerAdd;
                                                        incrementValue       = -incrementValue;
                                                    }

                                                    if (advanceOperationCode == BinaryOperationKind.IntegerAdd &&
                                                        incrementValue != 0 &&
                                                        (condition.BinaryKind == BinaryOperationKind.IntegerLessThan ||
                                                         condition.BinaryKind == BinaryOperationKind.IntegerLessThanOrEqual ||
                                                         condition.BinaryKind == BinaryOperationKind.IntegerNotEquals ||
                                                         condition.BinaryKind == BinaryOperationKind.IntegerGreaterThan ||
                                                         condition.BinaryKind == BinaryOperationKind.IntegerGreaterThanOrEqual))
                                                    {
                                                        int iterationCount = (testValue - initialValue) / incrementValue;
                                                        if (iterationCount >= 1000000)
                                                        {
                                                            Report(operationContext, forLoop.Syntax, BigForDescriptor);
                                                        }
                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            },
                OperationKind.LoopStatement);
        }
コード例 #10
0
 private static bool IsInvalidOperation(BinaryOperationKind binaryOperationKind, IOperation left, IOperation right, ITypeSymbol type)
 {
     return(left == null || left.IsInvalid || right == null ||
            right.IsInvalid || binaryOperationKind == BinaryOperationKind.Invalid || type == null);
 }
コード例 #11
0
ファイル: IExpression.cs プロジェクト: Eyas/roslyn
 public static BinaryOperandsKind GetBinaryOperandsKind(BinaryOperationKind kind)
 {
     return (BinaryOperandsKind)((int)kind & UnaryAndBinaryOperationExtensions.BinaryOperandsKindMask);
 }
コード例 #12
0
 public CompoundAssignment(IReferenceExpression target, IExpression value, BinaryOperationKind binaryKind, IMethodSymbol operatorMethod, SyntaxNode syntax)
 {
     _compoundAssignment = new CompoundAssignmentExpression(target, value, binaryKind, operatorMethod, syntax);
     this.Syntax = syntax;
 }
コード例 #13
0
 public static BinaryOperandsKind GetBinaryOperandsKind(BinaryOperationKind kind)
 {
     return((BinaryOperandsKind)((int)kind & UnaryAndBinaryOperationExtensions.BinaryOperandsKindMask));
 }
コード例 #14
0
 public static SimpleBinaryOperationKind GetSimpleBinaryOperationKind(BinaryOperationKind kind)
 {
     return((SimpleBinaryOperationKind)((int)kind & UnaryAndBinaryOperationExtensions.SimpleBinaryOperationKindMask));
 }
コード例 #15
0
            public IExpression BinaryOperation(INaryOperandExpression left, BinaryOperationKind op, INaryOperandExpression right)
            {
                switch (op)
                {
                case BinaryOperationKind.Assign:
                    return(left.Add(right));

                case BinaryOperationKind.AssignMultiply:
                    return(new AssignmentExpression(left, AssignmentOperation.MultiplicationAssign, right));

                case BinaryOperationKind.AssignModulus:
                    return(new AssignmentExpression(left, AssignmentOperation.ModulusAssign, right));

                case BinaryOperationKind.AssignDivide:
                    return(new AssignmentExpression(left, AssignmentOperation.DivisionAssign, right));

                case BinaryOperationKind.AssignAdd:
                    return(new AssignmentExpression(left, AssignmentOperation.AddAssign, right));

                case BinaryOperationKind.AssignSubtract:
                    return(new AssignmentExpression(left, AssignmentOperation.SubtractionAssign, right));

                case BinaryOperationKind.AssignLeftShift:
                    return(new AssignmentExpression(left, AssignmentOperation.LeftShiftAssign, right));

                case BinaryOperationKind.AssignRightShift:
                    return(new AssignmentExpression(left, AssignmentOperation.RightShiftAssign, right));

                case BinaryOperationKind.AssignBitwiseAnd:
                    return(new AssignmentExpression(left, AssignmentOperation.BitwiseAndAssign, right));

                case BinaryOperationKind.AssignBitwiseOr:
                    return(new AssignmentExpression(left, AssignmentOperation.BitwiseOrAssign, right));

                case BinaryOperationKind.AssignBitwiseExclusiveOr:
                    return(new AssignmentExpression(left, AssignmentOperation.BitwiseExclusiveOrAssign, right));

                case BinaryOperationKind.LogicalOr:
                    return(left.LogicalOr(right));

                case BinaryOperationKind.LogicalAnd:
                    return(left.LogicalAnd(right));

                case BinaryOperationKind.BitwiseOr:
                    return(left.BitwiseOr(right));

                case BinaryOperationKind.BitwiseExclusiveOr:
                    return(left.BitwiseXOr(right));

                case BinaryOperationKind.BitwiseAnd:
                    return(left.BitwiseAnd(right));

                case BinaryOperationKind.Inequality:
                    return(left.InequalTo(right));

                case BinaryOperationKind.Equality:
                    return(left.EqualTo(right));

                case BinaryOperationKind.LessThan:
                    return(left.LessThan(right));

                case BinaryOperationKind.LessThanOrEqualTo:
                    return(left.LessThanOrEqualTo(right));

                case BinaryOperationKind.GreaterThan:
                    return(left.GreaterThan(right));

                case BinaryOperationKind.GreaterThanOrEqualTo:
                    return(left.GreaterThanOrEqualTo(right));

                case BinaryOperationKind.LeftShift:
                    return(left.Shift(CSharpShiftOperation.LeftShift, right));

                case BinaryOperationKind.RightShift:
                    return(left.Shift(CSharpShiftOperation.RightShift, right));

                case BinaryOperationKind.Add:
                    return(left.Add(right));

                case BinaryOperationKind.Subtract:
                    return(left.Subtract(right));

                case BinaryOperationKind.Multiply:
                    return(left.Multiply(right));

                case BinaryOperationKind.Modulus:
                    return(left.Modulus(right));

                case BinaryOperationKind.StrictDivision:
                    return(left.Division(right));

                case BinaryOperationKind.IntegerDivision:
                case BinaryOperationKind.FlexibleDivision:
                    throw new NotSupportedException();

                default:
                    throw new ArgumentOutOfRangeException("op");
                }
            }
コード例 #16
0
ファイル: Expressions.cs プロジェクト: m0nguss/roslyn
 public CompoundAssignment(IOperation target, IOperation value, BinaryOperationKind binaryOperationKind, IMethodSymbol operatorMethod, SyntaxNode syntax)
 {
     _compoundAssignment = new CompoundAssignmentExpression(target, value, binaryOperationKind, operatorMethod, syntax);
     this.Syntax         = syntax;
 }
コード例 #17
0
ファイル: IExpression.cs プロジェクト: Eyas/roslyn
 public static SimpleBinaryOperationKind GetSimpleBinaryOperationKind(BinaryOperationKind kind)
 {
     return (SimpleBinaryOperationKind)((int)kind & UnaryAndBinaryOperationExtensions.SimpleBinaryOperationKindMask);
 }
コード例 #18
0
 public CompoundAssignmentExpression(IReferenceExpression target, IExpression value, BinaryOperationKind binaryKind, IMethodSymbol operatorMethod, SyntaxNode syntax)
 {
     this.Target = target;
     this.Value = value;
     this.BinaryKind = binaryKind;
     this.Operator = operatorMethod;
     this.Syntax = syntax;
 }
コード例 #19
0
 public Binary(BinaryOperationKind binaryKind, IExpression left, IExpression right, ITypeSymbol resultType, SyntaxNode syntax)
 {
     this.BinaryKind = binaryKind;
     this.Left = left;
     this.Right = right;
     this.ResultType = resultType;
     this.Syntax = syntax;
 }
コード例 #20
0
 public abstract void Translate(BinaryOperationKind kind);