private LuaExpressionSyntax CreateQueryAnonymousType(LuaIdentifierNameSyntax key1, LuaExpressionSyntax value1, LuaIdentifierNameSyntax key2, LuaExpressionSyntax value2) { LuaTableInitializerExpression table = new LuaTableInitializerExpression(); table.Items.Add(new LuaKeyValueTableItemSyntax(new LuaTableLiteralKeySyntax(key1), value1)); table.Items.Add(new LuaKeyValueTableItemSyntax(new LuaTableLiteralKeySyntax(key2), value2)); return(table); }
private LuaExpressionSyntax BuildOrdering(LuaIdentifierNameSyntax methodName, LuaExpressionSyntax collection, OrderingSyntax node, IQueryRangeVariable rangeVariable) { var type = semanticModel_.GetTypeInfo(node.Expression).Type; var typeName = GetTypeName(type); var keySelector = new LuaFunctionExpressionSyntax(); PushFunction(keySelector); keySelector.AddParameter(rangeVariable.Name); var expression = (LuaExpressionSyntax)node.Expression.Accept(this); keySelector.AddStatement(new LuaReturnStatementSyntax(expression)); PopFunction(); return(new LuaInvocationExpressionSyntax(methodName, collection, keySelector, LuaIdentifierNameSyntax.Nil, typeName)); }
public static LuaExpressionStatementSyntax ToStatement(this LuaExpressionSyntax expression) { return(new LuaExpressionStatementSyntax(expression)); }
public static bool IsNil(this LuaExpressionSyntax expression) { return(expression == null || expression == LuaIdentifierNameSyntax.Nil || expression == LuaIdentifierLiteralExpressionSyntax.Nil); }
private void AddCodeTemplateExpression(LuaExpressionSyntax expression, string comma, LuaCodeTemplateExpressionSyntax codeTemplateExpression) { if (!string.IsNullOrEmpty(comma)) { codeTemplateExpression.Expressions.Add(new LuaIdentifierNameSyntax(comma)); } codeTemplateExpression.Expressions.Add(expression); }
private LuaNumericalForStatementSyntax GetNumericalForStatement(ForStatementSyntax node) { if (node.Declaration == null || node.Declaration.Variables.Count > 1) { goto Fail; } if (node.Condition == null) { goto Fail; } if (node.Incrementors.Count != 1) { goto Fail; } var variable = node.Declaration.Variables.First(); if (variable.Initializer == null) { goto Fail; } var conditionKind = node.Condition.Kind(); if (conditionKind < SyntaxKind.NotEqualsExpression || conditionKind > SyntaxKind.GreaterThanOrEqualExpression) { goto Fail; } var condition = (BinaryExpressionSyntax)node.Condition; if (!IsNumericalForVariableMatch(condition.Left, variable.Identifier)) { goto Fail; } var limitConst = semanticModel_.GetConstantValue(condition.Right); if (limitConst.HasValue) { if (!(limitConst.Value is int)) { goto Fail; } } else { bool isReadOnly = false; var symbol = semanticModel_.GetSymbolInfo(condition.Right).Symbol; if (symbol != null) { if (symbol.Kind == SymbolKind.Field) { isReadOnly = ((IFieldSymbol)symbol).IsReadOnly; } else if (symbol.Kind == SymbolKind.Property) { var propertySymbol = (IPropertySymbol)symbol; isReadOnly = propertySymbol.IsReadOnly && IsPropertyField(propertySymbol); } } if (!isReadOnly) { goto Fail; } } bool hasNoEqual; bool isPlus; var incrementor = node.Incrementors.First(); switch (incrementor.Kind()) { case SyntaxKind.PreIncrementExpression: case SyntaxKind.PreDecrementExpression: var prefixUnaryExpression = (PrefixUnaryExpressionSyntax)incrementor; if (!IsNumericalForVariableMatch(prefixUnaryExpression.Operand, variable.Identifier)) { goto Fail; } if (incrementor.IsKind(SyntaxKind.PreIncrementExpression)) { if (!IsNumericalForLess(conditionKind, out hasNoEqual)) { goto Fail; } isPlus = true; } else { if (!IsNumericalForGreater(conditionKind, out hasNoEqual)) { goto Fail; } isPlus = false; } break; case SyntaxKind.PostIncrementExpression: case SyntaxKind.PostDecrementExpression: var postfixUnaryExpression = (PostfixUnaryExpressionSyntax)incrementor; if (!IsNumericalForVariableMatch(postfixUnaryExpression.Operand, variable.Identifier)) { goto Fail; } if (incrementor.IsKind(SyntaxKind.PostIncrementExpression)) { if (!IsNumericalForLess(conditionKind, out hasNoEqual)) { goto Fail; } isPlus = true; } else { if (!IsNumericalForGreater(conditionKind, out hasNoEqual)) { goto Fail; } isPlus = false; } break; default: goto Fail; } LuaIdentifierNameSyntax identifier = new LuaIdentifierNameSyntax(variable.Identifier.ValueText); CheckLocalVariableName(ref identifier, variable); var startExpression = (LuaExpressionSyntax)variable.Initializer.Value.Accept(this); LuaExpressionSyntax limitExpression; LuaExpressionSyntax stepExpression = null; if (hasNoEqual) { if (limitConst.Value != null) { int limit = (int)limitConst.Value; if (isPlus) { --limit; } else { ++limit; stepExpression = new LuaPrefixUnaryExpressionSyntax(LuaIdentifierNameSyntax.One, LuaSyntaxNode.Tokens.Sub); } limitExpression = new LuaIdentifierLiteralExpressionSyntax(limit.ToString()); } else { limitExpression = (LuaExpressionSyntax)condition.Right.Accept(this); if (isPlus) { limitExpression = new LuaBinaryExpressionSyntax(limitExpression, LuaSyntaxNode.Tokens.Sub, LuaIdentifierNameSyntax.One); } else { limitExpression = new LuaBinaryExpressionSyntax(limitExpression, LuaSyntaxNode.Tokens.Plus, LuaIdentifierNameSyntax.One); stepExpression = new LuaPrefixUnaryExpressionSyntax(LuaIdentifierNameSyntax.One, LuaSyntaxNode.Tokens.Sub); } } } else { limitExpression = (LuaExpressionSyntax)condition.Right.Accept(this); if (!isPlus) { stepExpression = new LuaPrefixUnaryExpressionSyntax(LuaIdentifierNameSyntax.One, LuaSyntaxNode.Tokens.Sub); } } var numericalForStatement = new LuaNumericalForStatementSyntax(identifier, startExpression, limitExpression, stepExpression); VisitLoopBody(node.Statement, numericalForStatement.Body); return numericalForStatement; Fail: return null; }
private bool IsNilLuaExpression(LuaExpressionSyntax expression) { return expression == LuaIdentifierNameSyntax.Nil || expression == LuaIdentifierLiteralExpressionSyntax.Nil; }
private LuaExpressionSyntax BuildQueryBody(LuaExpressionSyntax collection, QueryBodySyntax node, IQueryRangeVariable rangeVariable) { foreach (var clause in node.Clauses) { switch (clause.Kind()) { case SyntaxKind.FromClause: { collection = BuildFromClause(collection, (FromClauseSyntax)clause, ref rangeVariable, out bool isOver); if (isOver) { goto Continuation; } break; } case SyntaxKind.LetClause: { collection = BuildLetClause(collection, (LetClauseSyntax)clause, ref rangeVariable); break; } case SyntaxKind.JoinClause: { collection = BuildJoinClause(collection, (JoinClauseSyntax)clause, ref rangeVariable, out bool isOver); if (isOver) { goto Continuation; } break; } case SyntaxKind.WhereClause: { collection = BuildQueryWhere(collection, (WhereClauseSyntax)clause, rangeVariable); break; } case SyntaxKind.OrderByClause: { collection = BuildQueryOrderBy(collection, (OrderByClauseSyntax)clause, rangeVariable); break; } default: { throw new NotSupportedException(); } } } if (node.SelectOrGroup.IsKind(SyntaxKind.SelectClause)) { var selectClause = (SelectClauseSyntax)node.SelectOrGroup; collection = BuildQuerySelect(collection, selectClause, rangeVariable); } else { var groupClause = (GroupClauseSyntax)node.SelectOrGroup; collection = BuildGroupClause(collection, groupClause, rangeVariable); } Continuation: if (node.Continuation != null) { collection = BuildQueryContinuation(collection, node.Continuation); } return(collection); }
private LuaInvocationExpressionSyntax BuildObjectCreationInvocation(IMethodSymbol symbol, LuaExpressionSyntax expression) { int constructorIndex = GetConstructorIndex(symbol); if (constructorIndex > 0) { expression = new LuaMemberAccessExpressionSyntax(expression, LuaIdentifierNameSyntax.New, true); } LuaInvocationExpressionSyntax invocationExpression = new LuaInvocationExpressionSyntax(expression); if (constructorIndex > 0) { invocationExpression.AddArgument(new LuaIdentifierNameSyntax(constructorIndex)); } return invocationExpression; }
private void CheckValueTypeAndConversion(ExpressionSyntax node, ref LuaExpressionSyntax expression) { ITypeSymbol typeSymbol = semanticModel_.GetTypeInfo(node).Type; CheckValueTypeClone(typeSymbol, ref expression); CheckConversion(node, ref expression); }
private LuaExpressionSyntax BuildFieldOrPropertyMemberAccessExpression(LuaExpressionSyntax expression, LuaExpressionSyntax name, bool isStatic) { if (name is LuaPropertyAdapterExpressionSyntax propertyMethod) { var arguments = propertyMethod.ArgumentList.Arguments; if (arguments.Count == 1) { if (arguments[0].Expression == LuaIdentifierNameSyntax.This) { propertyMethod.ArgumentList.Arguments[0] = new LuaArgumentSyntax(expression); } } else { propertyMethod.Update(expression, !isStatic); } return propertyMethod; } else { return new LuaMemberAccessExpressionSyntax(expression, name); } }
private LuaInvocationExpressionSyntax BuildArray(ITypeSymbol elementType, IEnumerable<LuaExpressionSyntax> elements) { LuaExpressionSyntax baseType = GetTypeName(elementType); var arrayType = new LuaInvocationExpressionSyntax(LuaIdentifierNameSyntax.Array, baseType); return new LuaInvocationExpressionSyntax(arrayType, elements); }
private LuaInvocationExpressionSyntax BuildEmptyArray(LuaExpressionSyntax baseType) { return new LuaInvocationExpressionSyntax(LuaIdentifierNameSyntax.ArrayEmpty, baseType); }
private LuaExpressionSyntax CreateQueryAnonymousType(LuaIdentifierNameSyntax key1, LuaExpressionSyntax value1, LuaIdentifierNameSyntax key2, LuaExpressionSyntax value2) { LuaTableExpression table = new LuaTableExpression(); table.Add(key1, value1); table.Add(key2, value2); return(table); }
private void CheckConversion(ExpressionSyntax node, ref LuaExpressionSyntax expression) { var conversion = semanticModel_.GetConversion(node); if (conversion.IsUserDefined && conversion.IsImplicit) { expression = BuildConversionExpression(conversion.MethodSymbol, expression); } }
private bool BuildQueryJoin(JoinClauseSyntax node, out LuaExpressionSyntax resultSelectorExpression, out LuaExpressionSyntax resultSelectorType, ref IQueryRangeVariable rangeVariable, QueryIdentifier queryIdentifier) { var parentNode = (QueryBodySyntax)node.Parent; if (IsSpecialQueryNode(parentNode)) { var selectClause = (SelectClauseSyntax)parentNode.SelectOrGroup; resultSelectorExpression = (LuaExpressionSyntax)selectClause.Expression.Accept(this); var typeSymbol = semanticModel_.GetTypeInfo(selectClause.Expression).Type; resultSelectorType = GetTypeName(typeSymbol); return(true); } else { resultSelectorExpression = CreateQueryAnonymousType(rangeVariable.Name, rangeVariable.Name, queryIdentifier.Name, queryIdentifier.Name); resultSelectorType = LuaIdentifierNameSyntax.AnonymousType; rangeVariable = new QueryPackVariable(rangeVariable, queryIdentifier); return(false); } }
private LuaExpressionSyntax BuildConversionExpression(IMethodSymbol methodSymbol, LuaExpressionSyntax expression) { var memberAccess = GetOperatorMemberAccessExpression(methodSymbol); return new LuaInvocationExpressionSyntax(memberAccess, expression); }
private LuaExpressionSyntax BuildQueryContinuation(LuaExpressionSyntax collection, QueryContinuationSyntax node) { var rangeVariable = AddRangeIdentifier(node.Identifier); return(BuildQueryBody(collection, node.Body, rangeVariable)); }
private LuaExpressionSyntax BuildDeconstructExpression(ExpressionSyntax node, LuaExpressionSyntax expression) { var typeSymbol = semanticModel_.GetTypeInfo(node).Type; return BuildDeconstructExpression(typeSymbol, expression, node); }