/// <summary> /// Checks whether parenthesis are needed within the conditional logical expressions. /// </summary> /// <param name="element">The parent element.</param> /// <param name="expression">The parent conditional logical expression.</param> /// <param name="childExpression">The child conditional logical expression.</param> /// <returns>Returns true if there is no violation, or false if there is a violation.</returns> private bool CheckConditionalLogicalParenthesisForExpressionAndChild( CsElement element, ConditionalLogicalExpression expression, ConditionalLogicalExpression childExpression) { Param.AssertNotNull(element, "element"); Param.AssertNotNull(expression, "expression"); Param.AssertNotNull(childExpression, "childExpression"); // If the two expressions are both of the same type (OR or AND), then there is // no need for parenthesis. if (expression.OperatorType != childExpression.OperatorType) { // The expressions are not of the same type. One of them should be enclosed // by parenthesis to indicate the precedence. this.AddViolation(element, expression.LineNumber, Rules.ConditionalExpressionsMustDeclarePrecedence); return(false); } return(true); }
/// <summary> /// Checks that parenthesis are used correctly within a conditional logical expression. /// </summary> /// <param name="element">The parent element.</param> /// <param name="expression">The expression to check.</param> private void CheckConditionalLogicalExpressionParenthesis( CsElement element, ConditionalLogicalExpression expression) { Param.AssertNotNull(element, "element"); Param.AssertNotNull(expression, "expression"); if (expression.LeftHandSide.ExpressionType == ExpressionType.ConditionalLogical) { if (!this.CheckConditionalLogicalParenthesisForExpressionAndChild( element, expression, (ConditionalLogicalExpression)expression.LeftHandSide)) { return; } } if (expression.RightHandSide.ExpressionType == ExpressionType.ConditionalLogical) { this.CheckConditionalLogicalParenthesisForExpressionAndChild( element, expression, (ConditionalLogicalExpression)expression.RightHandSide); } }
/// <summary> /// Reads a conditional logical expression. /// </summary> /// <param name="leftHandSide">The expression on the left hand side of the operator.</param> /// <param name="previousPrecedence">The precedence of the expression just before this one.</param> /// <param name="parentReference">The parent code part.</param> /// <param name="unsafeCode">Indicates whether the code being parsed resides in an unsafe code block.</param> /// <returns>Returns the expression.</returns> private ConditionalLogicalExpression GetConditionalLogicalExpression( Expression leftHandSide, ExpressionPrecedence previousPrecedence, Reference<ICodePart> parentReference, bool unsafeCode) { Param.AssertNotNull(leftHandSide, "leftHandSide"); Param.Ignore(previousPrecedence); Param.AssertNotNull(parentReference, "parentReference"); Param.Ignore(unsafeCode); ConditionalLogicalExpression expression = null; var expressionReference = new Reference<ICodePart>(); // Read the details of the expression. OperatorSymbol operatorToken = this.PeekOperatorToken(parentReference, expressionReference); Debug.Assert(operatorToken.Category == OperatorCategory.Logical, "Expected a logical operator"); // Check the precedence of the operators to make sure we can gather this statement now. ExpressionPrecedence precedence = GetOperatorPrecedence(operatorToken.SymbolType); if (CheckPrecedence(previousPrecedence, precedence)) { // Add the operator token to the document and advance the symbol manager up to it. this.symbols.Advance(); this.tokens.Add(operatorToken); // Get the expression on the right-hand side of the operator. Expression rightHandSide = this.GetOperatorRightHandExpression(precedence, expressionReference, unsafeCode); // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, leftHandSide.Tokens.First, this.tokens.Last); // Get the expression operator type. ConditionalLogicalExpression.Operator type; switch (operatorToken.SymbolType) { case OperatorType.ConditionalAnd: type = ConditionalLogicalExpression.Operator.And; break; case OperatorType.ConditionalOr: type = ConditionalLogicalExpression.Operator.Or; break; default: Debug.Fail("Unexpected operator type"); throw new InvalidOperationException(); } // Create and return the expression. expression = new ConditionalLogicalExpression(partialTokens, type, leftHandSide, rightHandSide); expressionReference.Target = expression; } return expression; }
private bool CheckConditionalLogicalParenthesisForExpressionAndChild(CsElement element, ConditionalLogicalExpression expression, ConditionalLogicalExpression childExpression) { if (expression.OperatorType != childExpression.OperatorType) { base.AddViolation(element, expression.LineNumber, Microsoft.StyleCop.CSharp.Rules.ConditionalExpressionsMustDeclarePrecedence, new object[0]); return false; } return true; }
private void CheckConditionalLogicalExpressionParenthesis(CsElement element, ConditionalLogicalExpression expression) { if (((expression.LeftHandSide.ExpressionType != ExpressionType.ConditionalLogical) || this.CheckConditionalLogicalParenthesisForExpressionAndChild(element, expression, (ConditionalLogicalExpression) expression.LeftHandSide)) && (expression.RightHandSide.ExpressionType == ExpressionType.ConditionalLogical)) { this.CheckConditionalLogicalParenthesisForExpressionAndChild(element, expression, (ConditionalLogicalExpression) expression.RightHandSide); } }
/// <summary> /// Reads a conditional logical expression. /// </summary> /// <param name="sourceCode">The source code containing the expression.</param> /// <param name="parentReference">The parent code unit.</param> /// <param name="leftHandSide">The expression on the left hand side of the operator.</param> /// <param name="previousPrecedence">The precedence of the expression just before this one.</param> /// <returns>Returns the expression.</returns> private ConditionalLogicalExpression GetConditionalPreprocessorAndOrExpression( SourceCode sourceCode, Reference<ICodePart> parentReference, Expression leftHandSide, ExpressionPrecedence previousPrecedence) { Param.AssertNotNull(sourceCode, "sourceCode"); Param.AssertNotNull(parentReference, "parentReference"); Param.AssertNotNull(leftHandSide, "leftHandSide"); Param.Ignore(previousPrecedence); ConditionalLogicalExpression expression = null; this.AdvanceToNextConditionalDirectiveCodeSymbol(parentReference); Symbol firstSymbol = this.symbols.Peek(1); if (firstSymbol == null) { throw new SyntaxException(sourceCode, firstSymbol.LineNumber); } var expressionReference = new Reference<ICodePart>(); // Create the operator symbol. OperatorType type; OperatorCategory category; GetOperatorType(firstSymbol, out type, out category); OperatorSymbol operatorToken = new OperatorSymbol( firstSymbol.Text, category, type, firstSymbol.Location, expressionReference, this.symbols.Generated); // Check the precedence of the operators to make sure we can gather this statement now. ExpressionPrecedence precedence = GetOperatorPrecedence(operatorToken.SymbolType); if (CheckPrecedence(previousPrecedence, precedence)) { // Add the operator token to the document and advance the symbol manager up to it. this.symbols.Advance(); this.tokens.Add(operatorToken); // Get the expression on the right-hand side of the operator. Expression rightHandSide = this.GetNextConditionalPreprocessorExpression(sourceCode, precedence); if (rightHandSide == null) { throw new SyntaxException(sourceCode, operatorToken.LineNumber); } // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, leftHandSide.Tokens.First, this.tokens.Last); // Get the expression operator type. ConditionalLogicalExpression.Operator conditionalType; switch (operatorToken.SymbolType) { case OperatorType.ConditionalAnd: conditionalType = ConditionalLogicalExpression.Operator.And; break; case OperatorType.ConditionalOr: conditionalType = ConditionalLogicalExpression.Operator.Or; break; default: throw new SyntaxException(sourceCode, operatorToken.LineNumber); } // Create and return the expression. expression = new ConditionalLogicalExpression(partialTokens, conditionalType, leftHandSide, rightHandSide); } return expression; }
/// <summary> /// Checks whether parenthesis are needed within the conditional logical expressions. /// </summary> /// <param name="element">The parent element.</param> /// <param name="expression">The parent conditional logical expression.</param> /// <param name="childExpression">The child conditional logical expression.</param> /// <returns>Returns true if there is no violation, or false if there is a violation.</returns> private bool CheckConditionalLogicalParenthesisForExpressionAndChild( Element element, ConditionalLogicalExpression expression, ConditionalLogicalExpression childExpression) { Param.AssertNotNull(element, "element"); Param.AssertNotNull(expression, "expression"); Param.AssertNotNull(childExpression, "childExpression"); // If the two expressions are both of the same type (OR or AND), then there is // no need for parenthesis. if (expression.ConditionalLogicalExpressionType != childExpression.ConditionalLogicalExpressionType) { // The expressions are not of the same type. One of them should be enclosed // by parenthesis to indicate the precedence. this.AddViolation(element, expression.LineNumber, Rules.ConditionalExpressionsMustDeclarePrecedence); return false; } return true; }
/// <summary> /// Checks that parenthesis are used correctly within a conditional logical expression. /// </summary> /// <param name="element">The parent element.</param> /// <param name="expression">The expression to check.</param> private void CheckConditionalLogicalExpressionParenthesis( Element element, ConditionalLogicalExpression expression) { Param.AssertNotNull(element, "element"); Param.AssertNotNull(expression, "expression"); if (expression.LeftHandSide.ExpressionType == ExpressionType.ConditionalLogical) { if (!this.CheckConditionalLogicalParenthesisForExpressionAndChild( element, expression, (ConditionalLogicalExpression)expression.LeftHandSide)) { return; } } if (expression.RightHandSide.ExpressionType == ExpressionType.ConditionalLogical) { this.CheckConditionalLogicalParenthesisForExpressionAndChild( element, expression, (ConditionalLogicalExpression)expression.RightHandSide); } }