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.GetAlreadyCreated(info.Context, target))); case SymbolKind.Parameter: return(Access.Create(info, target, false, Parameter.GetAlreadyCreated(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}'"); } }
protected Expression DeclareRangeVariable(Context cx, IExpressionParentEntity parent, int child, bool getElement, ISymbol variableSymbol, SyntaxToken name) { var type = Type.Create(cx, cx.GetType(Expr)); Extraction.Entities.Location nameLoc; Type declType; TypeSyntax declTypeSyntax = null; if (getElement) { var from = node as FromClauseSyntax; (declType, declTypeSyntax) = from != null && from.Type != null ? (Type.Create(cx, cx.GetType(from.Type)), from.Type) : (type.ElementType, null); } else { declType = type; } var decl = VariableDeclaration.Create(cx, variableSymbol, declType, declTypeSyntax, cx.Create(node.GetLocation()), nameLoc = cx.Create(name.GetLocation()), true, parent, child ); Expression.Create(cx, Expr, decl, 0); var access = new Expression(new ExpressionInfo(cx, type, nameLoc, ExprKind.LOCAL_VARIABLE_ACCESS, decl, 1, false, null)); cx.Emit(Tuples.expr_access(access, LocalVariable.GetAlreadyCreated(cx, variableSymbol))); return(decl); }