Example #1
0
        public static VariableDeclaration CreateDeclarator(Context cx, VariableDeclaratorSyntax d, AnnotatedType type, bool isVar, IExpressionParentEntity parent, int child)
        {
            var ret = Create(cx, d, type, isVar, parent, child);

            cx.Try(d, null, () =>
            {
                var id         = d.Identifier;
                var declSymbol = cx.GetModel(d).GetDeclaredSymbol(d);
                var location   = cx.Create(id.GetLocation());
                var localVar   = LocalVariable.Create(cx, declSymbol, ret, isVar, location);

                if (d.Initializer != null)
                {
                    Create(cx, d.Initializer.Value, ret, 0);

                    // Create an access
                    var access = new Expression(new ExpressionInfo(cx, type, location, ExprKind.LOCAL_VARIABLE_ACCESS, ret, 1, false, null));
                    cx.TrapWriter.Writer.expr_access(access, localVar);
                }

                var decl = d.Parent as VariableDeclarationSyntax;
                if (decl != null)
                {
                    TypeMention.Create(cx, decl.Type, ret, type);
                }
            });
            return(ret);
        }
Example #2
0
        public static VariableDeclaration Create(Context cx, ISymbol symbol, Type type, Extraction.Entities.Location exprLocation, Extraction.Entities.Location declLocation, bool isVar, IExpressionParentEntity parent, int child)
        {
            var ret = new VariableDeclaration(new ExpressionInfo(cx, type, exprLocation, ExprKind.LOCAL_VAR_DECL, parent, child, false, null));

            cx.Try(null, null, () => LocalVariable.Create(cx, symbol, ret, isVar, declLocation));
            return(ret);
        }
Example #3
0
        public static Expression Create(ExpressionNodeInfo info)
        {
            var symbolInfo = info.Context.GetSymbolInfo(info.Node);

            var target = symbolInfo.Symbol;

            if (target == null && symbolInfo.CandidateReason == CandidateReason.OverloadResolutionFailure)
            {
                // The expression is probably a cast
                target = info.Context.GetSymbolInfo((CSharpSyntaxNode)info.Node.Parent).Symbol;
            }

            if (target == null && (symbolInfo.CandidateReason == CandidateReason.Ambiguous || symbolInfo.CandidateReason == CandidateReason.MemberGroup))
            {
                // Pick one at random - they probably resolve to the same ID
                target = symbolInfo.CandidateSymbols.First();
            }

            if (target == null)
            {
                info.Context.ModelError(info.Node, "Failed to resolve name");
                return(new Unknown(info));
            }

            // There is a very strange bug in Microsoft.CodeAnalysis whereby
            // target.Kind throws System.InvalidOperationException for Discard symbols.
            // So, short-circuit that test here.
            // Ideally this would be another case in the switch statement below.
            if (target is IDiscardSymbol)
            {
                return(new Discard(info));
            }

            switch (target.Kind)
            {
            case SymbolKind.TypeParameter:
            case SymbolKind.NamedType:
            case SymbolKind.DynamicType:
                return(TypeAccess.Create(info));

            case SymbolKind.Property:
            case SymbolKind.Field:
            case SymbolKind.Event:
            case SymbolKind.Method:
                return(Access.Create(info, target, true, info.Context.CreateEntity(target)));

            case SymbolKind.Local:
            case SymbolKind.RangeVariable:
                return(Access.Create(info, target, false, LocalVariable.Create(info.Context, target)));

            case SymbolKind.Parameter:
                return(Access.Create(info, target, false, Parameter.Create(info.Context, (IParameterSymbol)target)));

            case SymbolKind.Namespace:
                return(Access.Create(info, target, false, Namespace.Create(info.Context, (INamespaceSymbol)target)));

            default:
                throw new InternalError(info.Node, $"Unhandled identifier kind '{target.Kind}'");
            }
        }
Example #4
0
        public static VariableDeclaration Create(Context cx, CatchDeclarationSyntax d, bool isVar, IExpressionParentEntity parent, int child)
        {
            var type = Type.Create(cx, cx.Model(d).GetDeclaredSymbol(d).Type);
            var ret  = Create(cx, d, type, isVar, parent, child);

            cx.Try(d, null, () =>
            {
                var id         = d.Identifier;
                var declSymbol = cx.Model(d).GetDeclaredSymbol(d);
                var location   = cx.Create(id.GetLocation());
                LocalVariable.Create(cx, declSymbol, ret, isVar, location);
                TypeMention.Create(cx, d.Type, ret, type);
            });
            return(ret);
        }
Example #5
0
        public static VariableDeclaration Create(Context cx, ISymbol symbol, AnnotatedTypeSymbol?type, TypeSyntax?optionalSyntax, Extraction.Entities.Location exprLocation, bool isVar, IExpressionParentEntity parent, int child)
        {
            var ret = new VariableDeclaration(new ExpressionInfo(cx, type, exprLocation, ExprKind.LOCAL_VAR_DECL, parent, child, false, null));

            cx.Try(null, null, () =>
            {
                var l = LocalVariable.Create(cx, symbol);
                l.PopulateManual(ret, isVar);
                if (optionalSyntax is not null)
                {
                    TypeMention.Create(cx, optionalSyntax, ret, type);
                }
            });
            return(ret);
        }
Example #6
0
        public static VariableDeclaration Create(Context cx, CatchDeclarationSyntax d, bool isVar, IExpressionParentEntity parent, int child)
        {
            var symbol = cx.GetModel(d).GetDeclaredSymbol(d) !;
            var type   = symbol.GetAnnotatedType();
            var ret    = Create(cx, d, type, parent, child);

            cx.Try(d, null, () =>
            {
                var declSymbol = cx.GetModel(d).GetDeclaredSymbol(d) !;
                var l          = LocalVariable.Create(cx, declSymbol);
                l.PopulateManual(ret, isVar);
                TypeMention.Create(cx, d.Type, ret, type);
            });
            return(ret);
        }
Example #7
0
        public static Expression CreateParenthesized(Context cx, VarPatternSyntax varPattern, ParenthesizedVariableDesignationSyntax designation, IExpressionParentEntity parent, int child)
        {
            var type  = NullType.Create(cx); // Should ideally be a corresponding tuple type
            var tuple = new Expression(new ExpressionInfo(cx, type, cx.Create(varPattern.GetLocation()), ExprKind.TUPLE, parent, child, false, null));

            cx.Try(null, null, () =>
            {
                var child0 = 0;
                foreach (var variable in designation.Variables)
                {
                    switch (variable)
                    {
                    case ParenthesizedVariableDesignationSyntax paren:
                        CreateParenthesized(cx, varPattern, paren, tuple, child0++);
                        break;

                    case SingleVariableDesignationSyntax single:
                        if (cx.GetModel(variable).GetDeclaredSymbol(single) is ILocalSymbol local)
                        {
                            var decl     = Create(cx, variable, Entities.Type.Create(cx, local.GetAnnotatedType()), true, tuple, child0++);
                            var id       = single.Identifier;
                            var location = cx.Create(id.GetLocation());
                            LocalVariable.Create(cx, local, decl, true, location);
                        }
                        else
                        {
                            throw new InternalError(single, "Failed to access local variable");
                        }
                        break;

                    case DiscardDesignationSyntax discard:
                        new Discard(cx, discard, tuple, child0++);
                        break;

                    default:
                        throw new InternalError(variable, "Unhandled designation type");
                    }
                }
            });

            return(tuple);
        }
Example #8
0
        static VariableDeclaration CreateSingle(Context cx, DeclarationExpressionSyntax node, SingleVariableDesignationSyntax designation, IExpressionParentEntity parent, int child)
        {
            bool isVar = node.Type.IsVar;

            var variableSymbol = cx.GetModel(designation).GetDeclaredSymbol(designation) as ILocalSymbol;

            if (variableSymbol == null)
            {
                cx.ModelError(node, "Failed to determine local variable");
                return(Create(cx, node, NullType.Create(cx), isVar, parent, child));
            }

            var type     = Entities.Type.Create(cx, variableSymbol.GetAnnotatedType());
            var location = cx.Create(designation.GetLocation());

            var ret = Create(cx, designation, type, isVar, parent, child);

            cx.Try(null, null, () => LocalVariable.Create(cx, variableSymbol, ret, isVar, location));
            return(ret);
        }
Example #9
0
        private static VariableDeclaration CreateSingle(Context cx, DeclarationExpressionSyntax node, SingleVariableDesignationSyntax designation, IExpressionParentEntity parent, int child)
        {
            var variableSymbol = cx.GetModel(designation).GetDeclaredSymbol(designation) as ILocalSymbol;

            if (variableSymbol is null)
            {
                cx.ModelError(node, "Failed to determine local variable");
                return(Create(cx, node, (AnnotatedTypeSymbol?)null, parent, child));
            }

            var type = variableSymbol.GetAnnotatedType();
            var ret  = Create(cx, designation, type, parent, child);

            cx.Try(null, null, () =>
            {
                var l = LocalVariable.Create(cx, variableSymbol);
                l.PopulateManual(ret, node.Type.IsVar);
            });
            return(ret);
        }
Example #10
0
        public static Expression CreateParenthesized(Context cx, VarPatternSyntax varPattern, ParenthesizedVariableDesignationSyntax designation, IExpressionParentEntity parent, int child)
        {
            var tuple = new Expression(
                new ExpressionInfo(cx, null, cx.CreateLocation(varPattern.GetLocation()), ExprKind.TUPLE, parent, child, false, null),
                shouldPopulate: false);

            var elementTypes = new List <ITypeSymbol?>();

            cx.Try(null, null, () =>
            {
                var child0 = 0;
                foreach (var variable in designation.Variables)
                {
                    Expression sub;
                    switch (variable)
                    {
                    case ParenthesizedVariableDesignationSyntax paren:
                        sub = CreateParenthesized(cx, varPattern, paren, tuple, child0++);
                        break;

                    case SingleVariableDesignationSyntax single:
                        if (cx.GetModel(variable).GetDeclaredSymbol(single) is ILocalSymbol local)
                        {
                            var decl = Create(cx, variable, local.GetAnnotatedType(), tuple, child0++);
                            var l    = LocalVariable.Create(cx, local);
                            l.PopulateManual(decl, true);
                            sub = decl;
                        }
                        else
                        {
                            throw new InternalError(single, "Failed to access local variable");
                        }
                        break;

                    case DiscardDesignationSyntax discard:
                        sub = new Discard(cx, discard, tuple, child0++);
                        if (!sub.Type.HasValue || sub.Type.Value.Symbol is null)
                        {
                            // The type is only updated in memory, it will not be written to the trap file.
                            sub.SetType(cx.Compilation.GetSpecialType(SpecialType.System_Object));
                        }
                        break;

                    default:
                        var type = variable.GetType().ToString() ?? "null";
                        throw new InternalError(variable, $"Unhandled designation type {type}");
                    }

                    elementTypes.Add(sub.Type.HasValue && sub.Type.Value.Symbol?.Kind != SymbolKind.ErrorType
                        ? sub.Type.Value.Symbol
                        : null);
                }
            });

            INamedTypeSymbol?tupleType = null;

            if (!elementTypes.Any(et => et is null))
            {
                tupleType = cx.Compilation.CreateTupleTypeSymbol(elementTypes.ToImmutableArray() !);
            }

            tuple.SetType(tupleType);
            tuple.TryPopulate();

            return(tuple);
        }