private ExpressionSyntax ConstructType(FuncTerm type) { string typeKind = ((Id)type.Function).Name; ExpressionSyntax typeExpr; string typeName; if (ImportedTypes.ContainsKey(Factory.Instance.ToAST(type))) { typeName = GetNextTypeName(ImportedTypes[Factory.Instance.ToAST(type)]); return(GetTypeExpr(typeName)); } var originalName = "Interface"; if (ExportedTypes.ContainsKey(Factory.Instance.ToAST(type))) { originalName = ExportedTypes[Factory.Instance.ToAST(type)]; typeName = GetNextTypeName(ExportedTypes[Factory.Instance.ToAST(type)]); typeExpr = GetTypeExpr(typeName); } else { typeName = GetNextTypeName(); typeExpr = GetTypeExpr(typeName); } // add declaration and initialization if (typeKind == "BaseType") { string primitiveType = CultureInfo.InvariantCulture.TextInfo.ToTitleCase(((Id)GetArgByIndex(type, 0)).Name.ToLowerInvariant()); Debug.Assert( primitiveType == "Any" || primitiveType == "Null" || primitiveType == "Bool" || primitiveType == "Int" || primitiveType == "Float" || primitiveType == "Event" || primitiveType == "Machine", $"Illegal BaseType: {primitiveType}"); if (primitiveType != "Any") { AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName($"Prt{primitiveType}Type"))); AddTypeDeclaration(typeName); } } else if (typeKind == "AnyType") { AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName("PrtAnyType"))); } else if (typeKind == "NameType") { string enumTypeName = (GetArgByIndex(type, 0) as Cnst).GetStringValue(); if (pToCSharp.allEnums.ContainsKey(enumTypeName)) { var args = new List <ExpressionSyntax> { CSharpHelper.MkCSharpStringLiteralExpression(enumTypeName) }; foreach (KeyValuePair <string, int> x in pToCSharp.allEnums[enumTypeName]) { args.Add(CSharpHelper.MkCSharpStringLiteralExpression(x.Key)); args.Add(CSharpHelper.MkCSharpNumericLiteralExpression(x.Value)); } AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName("PrtEnumType"), args.ToArray())); } else { var args = new List <ExpressionSyntax>(); AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName($"Foreign_{enumTypeName}"), args.ToArray())); } } else if (typeKind == "TupType") { var memberTypes = new List <SyntaxNodeOrToken>(); while (type != null) { memberTypes.Add(PTypeToCSharpExpr((FuncTerm)GetArgByIndex(type, 0))); type = GetArgByIndex(type, 1) as FuncTerm; } var initializer = CSharpHelper.Intersperse(memberTypes, SyntaxFactory.Token(SyntaxKind.CommaToken)); AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression( SyntaxFactory.IdentifierName("PrtTupleType"), CSharpHelper.MkCSharpArrayCreationExpression("PrtType", initializer.ToArray()))); } else if (typeKind == "NmdTupType") { var memberNames = new List <SyntaxNode>(); var memberTypes = new List <SyntaxNode>(); while (type != null) { var typeField = (FuncTerm)GetArgByIndex(type, 0); string nameField = ((Cnst)GetArgByIndex(typeField, 0)).GetStringValue(); memberNames.Add(CSharpHelper.MkCSharpStringLiteralExpression(nameField)); memberTypes.Add(PTypeToCSharpExpr((FuncTerm)GetArgByIndex(typeField, 1))); type = GetArgByIndex(type, 1) as FuncTerm; } var initializer = new List <SyntaxNodeOrToken>(); var ind = 0; foreach (SyntaxNode memberName in memberNames) { initializer.Add(memberName); initializer.Add(SyntaxFactory.Token(SyntaxKind.CommaToken)); initializer.Add(memberTypes[ind++]); initializer.Add(SyntaxFactory.Token(SyntaxKind.CommaToken)); } initializer.RemoveAt(initializer.Count - 1); AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression( SyntaxFactory.IdentifierName("PrtNamedTupleType"), CSharpHelper.MkCSharpArrayCreationExpression("object", initializer.ToArray()))); } else if (typeKind == "SeqType") { SyntaxNode innerType = PTypeToCSharpExpr((FuncTerm)GetArgByIndex(type, 0)); AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName("PrtSeqType"), innerType)); } else if (typeKind == "MapType") { SyntaxNode keyType = PTypeToCSharpExpr((FuncTerm)GetArgByIndex(type, 0)); SyntaxNode valType = PTypeToCSharpExpr((FuncTerm)GetArgByIndex(type, 1)); AddTypeDeclaration(typeName); AddTypeInitialization( typeExpr, CSharpHelper.MkCSharpObjectCreationExpression(SyntaxFactory.IdentifierName("PrtMapType"), keyType, valType)); } else { // typekind == "InterfaceType" ObjectCreationExpressionSyntax initializer = CSharpHelper.MkCSharpObjectCreationExpression( SyntaxFactory.IdentifierName("PrtInterfaceType"), CSharpHelper.MkCSharpStringLiteralExpression(originalName)); AddTypeDeclaration(typeName); AddTypeInitialization(typeExpr, initializer); } return(typeExpr); }