/// <summary> /// Reads an unsafe type expression. /// </summary> /// <param name="type">The type expression.</param> /// <param name="previousPrecedence">The precedence of the previous expression.</param> /// <param name="parentReference">The parent code unit.</param> /// <returns>Returns the expression.</returns> private UnsafeAccessExpression GetUnsafeTypeExpression(Expression type, ExpressionPrecedence previousPrecedence, Reference<ICodePart> parentReference) { Param.Ignore(type); Param.AssertNotNull(previousPrecedence, "previousPrecedence"); Param.AssertNotNull(parentReference, "parentReference"); UnsafeAccessExpression expression = null; if (CheckPrecedence(previousPrecedence, ExpressionPrecedence.Unary)) { // Get the operator symbol. Symbol symbol = this.GetNextSymbol(parentReference); var expressionReference = new Reference<ICodePart>(); OperatorType operatorType; UnsafeAccessExpression.Operator unsafeOperatorType; if (symbol.SymbolType == SymbolType.LogicalAnd) { operatorType = OperatorType.AddressOf; unsafeOperatorType = UnsafeAccessExpression.Operator.AddressOf; } else if (symbol.SymbolType == SymbolType.Multiplication) { operatorType = OperatorType.Dereference; unsafeOperatorType = UnsafeAccessExpression.Operator.Dereference; } else { Debug.Fail("Unexpected operator type."); throw new InvalidOperationException(); } // Create a token for the operator symbol. this.symbols.Advance(); OperatorSymbol token = new OperatorSymbol( symbol.Text, OperatorCategory.Reference, operatorType, symbol.Location, expressionReference, this.symbols.Generated); this.tokens.Add(token); // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, type.Tokens.First, this.tokens.Last); // Create and return the expression. expression = new UnsafeAccessExpression(partialTokens, unsafeOperatorType, type); expressionReference.Target = expression; } return expression; }
/// <summary> /// Reads a unary expression. /// </summary> /// <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 UnaryExpression GetUnaryExpression(Reference<ICodePart> parentReference, bool unsafeCode) { Param.AssertNotNull(parentReference, "parentReference"); Param.Ignore(unsafeCode); var expressionReference = new Reference<ICodePart>(); // Create the token based on the type of the symbol. Symbol symbol = this.GetNextSymbol(parentReference); OperatorSymbol token; UnaryExpression.Operator operatorType; if (symbol.SymbolType == SymbolType.Plus) { operatorType = UnaryExpression.Operator.Positive; token = new OperatorSymbol(symbol.Text, OperatorCategory.Unary, OperatorType.Positive, symbol.Location, expressionReference, this.symbols.Generated); } else if (symbol.SymbolType == SymbolType.Minus) { operatorType = UnaryExpression.Operator.Negative; token = new OperatorSymbol(symbol.Text, OperatorCategory.Unary, OperatorType.Negative, symbol.Location, expressionReference, this.symbols.Generated); } else if (symbol.SymbolType == SymbolType.Not) { operatorType = UnaryExpression.Operator.Not; token = new OperatorSymbol(symbol.Text, OperatorCategory.Unary, OperatorType.Not, symbol.Location, expressionReference, this.symbols.Generated); } else if (symbol.SymbolType == SymbolType.Tilde) { operatorType = UnaryExpression.Operator.BitwiseCompliment; token = new OperatorSymbol(symbol.Text, OperatorCategory.Unary, OperatorType.BitwiseCompliment, symbol.Location, expressionReference, this.symbols.Generated); } else { // This is not a unary type. Debug.Fail("Unexpected operator type"); throw new StyleCopException(); } Node<CsToken> tokenNode = this.tokens.InsertLast(token); this.symbols.Advance(); // Get the expression after the operator. Expression innerExpression = this.GetNextExpression(ExpressionPrecedence.Unary, expressionReference, unsafeCode); if (innerExpression == null || innerExpression.Tokens.First == null) { throw this.CreateSyntaxException(); } // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, tokenNode, this.tokens.Last); // Create and return the expression. var expression = new UnaryExpression(partialTokens, operatorType, innerExpression); expressionReference.Target = expression; return expression; }
/// <summary> /// Reads an unsafe access expression. /// </summary> /// <param name="parentReference">The parent code unit.</param> /// <param name="unsafeCode">Indicates whether the code being parsed resides in an unsafe code block.</param> /// <returns>Returns the expression.</returns> private UnsafeAccessExpression GetUnsafeAccessExpression(Reference<ICodePart> parentReference, bool unsafeCode) { Param.AssertNotNull(parentReference, "parentReference"); Param.Assert(unsafeCode == true, "unsafeCode", "Un unsafe access must reside in an unsafe code block."); // Get the operator symbol. Symbol symbol = this.GetNextSymbol(parentReference); var expressionReference = new Reference<ICodePart>(); OperatorType operatorType; UnsafeAccessExpression.Operator unsafeOperatorType; if (symbol.SymbolType == SymbolType.LogicalAnd) { operatorType = OperatorType.AddressOf; unsafeOperatorType = UnsafeAccessExpression.Operator.AddressOf; } else if (symbol.SymbolType == SymbolType.Multiplication) { operatorType = OperatorType.Dereference; unsafeOperatorType = UnsafeAccessExpression.Operator.Dereference; } else { Debug.Fail("Unexpected operator type."); throw new InvalidOperationException(); } // Create a token for the operator symbol. this.symbols.Advance(); OperatorSymbol token = new OperatorSymbol( symbol.Text, OperatorCategory.Reference, operatorType, symbol.Location, expressionReference, this.symbols.Generated); Node<CsToken> tokenNode = this.tokens.InsertLast(token); // Get the expression being accessed. Expression innerExpression = this.GetNextExpression(ExpressionPrecedence.Unary, expressionReference, unsafeCode); if (innerExpression == null || innerExpression.Tokens.First == null) { throw new SyntaxException(this.document.SourceCode, symbol.LineNumber); } // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, tokenNode, this.tokens.Last); // Create and return the expression. var expression = new UnsafeAccessExpression(partialTokens, unsafeOperatorType, innerExpression); expressionReference.Target = expression; return expression; }
private UnsafeAccessExpression GetUnsafeAccessExpression(bool unsafeCode) { OperatorType addressOf; UnsafeAccessExpression.Operator dereference; Symbol nextSymbol = this.GetNextSymbol(); if (nextSymbol.SymbolType == SymbolType.LogicalAnd) { addressOf = OperatorType.AddressOf; dereference = UnsafeAccessExpression.Operator.AddressOf; } else { if (nextSymbol.SymbolType != SymbolType.Multiplication) { throw new InvalidOperationException(); } addressOf = OperatorType.Dereference; dereference = UnsafeAccessExpression.Operator.Dereference; } this.symbols.Advance(); OperatorSymbol item = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Reference, addressOf, nextSymbol.Location, this.symbols.Generated); Microsoft.StyleCop.Node<CsToken> firstItemNode = this.tokens.InsertLast(item); Expression nextExpression = this.GetNextExpression(ExpressionPrecedence.Unary, unsafeCode); if ((nextExpression == null) || (nextExpression.Tokens.First == null)) { throw new SyntaxException(this.document.SourceCode, nextSymbol.LineNumber); } return new UnsafeAccessExpression(new CsTokenList(this.tokens, firstItemNode, this.tokens.Last), dereference, nextExpression); }
private UnsafeAccessExpression GetUnsafeTypeExpression(Expression type, ExpressionPrecedence previousPrecedence) { UnsafeAccessExpression expression = null; OperatorType addressOf; UnsafeAccessExpression.Operator dereference; if (!CheckPrecedence(previousPrecedence, ExpressionPrecedence.Unary)) { return expression; } Symbol nextSymbol = this.GetNextSymbol(); if (nextSymbol.SymbolType == SymbolType.LogicalAnd) { addressOf = OperatorType.AddressOf; dereference = UnsafeAccessExpression.Operator.AddressOf; } else { if (nextSymbol.SymbolType != SymbolType.Multiplication) { throw new InvalidOperationException(); } addressOf = OperatorType.Dereference; dereference = UnsafeAccessExpression.Operator.Dereference; } this.symbols.Advance(); OperatorSymbol item = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Reference, addressOf, nextSymbol.Location, this.symbols.Generated); this.tokens.Add(item); return new UnsafeAccessExpression(new CsTokenList(this.tokens, type.Tokens.First, this.tokens.Last), dereference, type); }
private UnaryExpression GetUnaryExpression(bool unsafeCode) { OperatorSymbol symbol2; UnaryExpression.Operator positive; Symbol nextSymbol = this.GetNextSymbol(); if (nextSymbol.SymbolType == SymbolType.Plus) { positive = UnaryExpression.Operator.Positive; symbol2 = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Unary, OperatorType.Positive, nextSymbol.Location, this.symbols.Generated); } else if (nextSymbol.SymbolType == SymbolType.Minus) { positive = UnaryExpression.Operator.Negative; symbol2 = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Unary, OperatorType.Negative, nextSymbol.Location, this.symbols.Generated); } else if (nextSymbol.SymbolType == SymbolType.Not) { positive = UnaryExpression.Operator.Not; symbol2 = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Unary, OperatorType.Not, nextSymbol.Location, this.symbols.Generated); } else { if (nextSymbol.SymbolType != SymbolType.Tilde) { throw new StyleCopException(); } positive = UnaryExpression.Operator.BitwiseCompliment; symbol2 = new OperatorSymbol(nextSymbol.Text, OperatorCategory.Unary, OperatorType.BitwiseCompliment, nextSymbol.Location, this.symbols.Generated); } Microsoft.StyleCop.Node<CsToken> firstItemNode = this.tokens.InsertLast(symbol2); this.symbols.Advance(); Expression nextExpression = this.GetNextExpression(ExpressionPrecedence.Unary, unsafeCode); if ((nextExpression == null) || (nextExpression.Tokens.First == null)) { throw this.CreateSyntaxException(); } return new UnaryExpression(new CsTokenList(this.tokens, firstItemNode, this.tokens.Last), positive, nextExpression); }
private UnaryExpression GetConditionalPreprocessorNotExpression(SourceCode sourceCode) { this.AdvanceToNextConditionalDirectiveCodeSymbol(); Symbol symbol = this.symbols.Peek(1); OperatorSymbol item = new OperatorSymbol(symbol.Text, OperatorCategory.Unary, OperatorType.Not, symbol.Location, this.symbols.Generated); Microsoft.StyleCop.Node<CsToken> firstItemNode = this.tokens.InsertLast(item); this.symbols.Advance(); Expression nextConditionalPreprocessorExpression = this.GetNextConditionalPreprocessorExpression(sourceCode, ExpressionPrecedence.Unary); if ((nextConditionalPreprocessorExpression == null) || (nextConditionalPreprocessorExpression.Tokens.First == null)) { throw new SyntaxException(sourceCode, symbol.LineNumber); } return new UnaryExpression(new CsTokenList(this.tokens, firstItemNode, this.tokens.Last), UnaryExpression.Operator.Not, nextConditionalPreprocessorExpression); }
private RelationalExpression GetConditionalPreprocessorEqualityExpression(SourceCode sourceCode, Expression leftHandSide, ExpressionPrecedence previousPrecedence) { RelationalExpression expression = null; OperatorType type; OperatorCategory category; RelationalExpression.Operator equalTo; this.AdvanceToNextConditionalDirectiveCodeSymbol(); Symbol symbol = this.symbols.Peek(1); if (symbol == null) { throw new SyntaxException(sourceCode, symbol.LineNumber); } GetOperatorType(symbol, out type, out category); OperatorSymbol item = new OperatorSymbol(symbol.Text, category, type, symbol.Location, this.symbols.Generated); ExpressionPrecedence operatorPrecedence = GetOperatorPrecedence(item.SymbolType); if (!CheckPrecedence(previousPrecedence, operatorPrecedence)) { return expression; } this.symbols.Advance(); this.tokens.Add(item); Expression nextConditionalPreprocessorExpression = this.GetNextConditionalPreprocessorExpression(sourceCode, operatorPrecedence); if (nextConditionalPreprocessorExpression == null) { throw new SyntaxException(sourceCode, item.LineNumber); } CsTokenList tokens = new CsTokenList(this.tokens, leftHandSide.Tokens.First, this.tokens.Last); switch (item.SymbolType) { case OperatorType.ConditionalEquals: equalTo = RelationalExpression.Operator.EqualTo; break; case OperatorType.NotEquals: equalTo = RelationalExpression.Operator.NotEqualTo; break; default: throw new SyntaxException(sourceCode, item.LineNumber); } return new RelationalExpression(tokens, equalTo, leftHandSide, nextConditionalPreprocessorExpression); }
/// <summary> /// Reads a NOT expression. /// </summary> /// <param name="sourceCode">The source code containing the expression.</param> /// <param name="parentReference">The parent code part.</param> /// <returns>Returns the expression.</returns> private UnaryExpression GetConditionalPreprocessorNotExpression(SourceCode sourceCode, Reference<ICodePart> parentReference) { Param.AssertNotNull(sourceCode, "sourceCode"); Param.AssertNotNull(parentReference, "parentReference"); var expressionReference = new Reference<ICodePart>(); // Get the symbol. this.AdvanceToNextConditionalDirectiveCodeSymbol(parentReference); Symbol symbol = this.symbols.Peek(1); Debug.Assert(symbol != null, "The next symbol should not be null"); // Create the token based on the type of the symbol. OperatorSymbol token = new OperatorSymbol( symbol.Text, OperatorCategory.Unary, OperatorType.Not, symbol.Location, expressionReference, this.symbols.Generated); Node<CsToken> tokenNode = this.tokens.InsertLast(token); // Advance up to the symbol and add it to the document. this.symbols.Advance(); // Get the expression after the operator. Expression innerExpression = this.GetNextConditionalPreprocessorExpression(sourceCode, ExpressionPrecedence.Unary); if (innerExpression == null || innerExpression.Tokens.First == null) { throw new SyntaxException(sourceCode, symbol.LineNumber); } // Create the partial token list for the expression. CsTokenList partialTokens = new CsTokenList(this.tokens, tokenNode, this.tokens.Last); // Create and return the expression. var expression = new UnaryExpression(partialTokens, UnaryExpression.Operator.Not, innerExpression); expressionReference.Target = expression; return expression; }
/// <summary> /// Reads a relational expression. /// </summary> /// <param name="sourceCode">The file 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 RelationalExpression GetConditionalPreprocessorEqualityExpression( SourceCode sourceCode, Reference<ICodePart> parentReference, Expression leftHandSide, ExpressionPrecedence previousPrecedence) { Param.AssertNotNull(sourceCode, "sourceCode"); Param.AssertNotNull(parentReference, "parentReference"); Param.AssertNotNull(leftHandSide, "leftHandSide"); Param.Ignore(previousPrecedence); RelationalExpression 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. RelationalExpression.Operator relationalType; switch (operatorToken.SymbolType) { case OperatorType.ConditionalEquals: relationalType = RelationalExpression.Operator.EqualTo; break; case OperatorType.NotEquals: relationalType = RelationalExpression.Operator.NotEqualTo; break; default: throw new SyntaxException(sourceCode, operatorToken.LineNumber); } // Create and return the expression. expression = new RelationalExpression(partialTokens, relationalType, leftHandSide, rightHandSide); expressionReference.Target = expression; } return expression; }