public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { if (IsMember(node)) { MemberAccessExpressionSyntax parent = node.Parent as MemberAccessExpressionSyntax; // If the parent expression isn't a member access expression then we need to // add a 'this.'. bool rewrite = parent == null; // If the parent expression is a member access expression, but the identifier is // on the left, then we need to add a 'this.'. if (!rewrite) { rewrite = parent.ChildNodes().First() == node; } if (rewrite) { return Syntax.MemberAccessExpression( SyntaxKind.MemberAccessExpression, Syntax.ThisExpression(), Syntax.IdentifierName(node.Identifier.ValueText)) .WithLeadingTrivia(node.GetLeadingTrivia()) .WithTrailingTrivia(node.GetTrailingTrivia()); } } return base.VisitIdentifierName(node); }
bool IsMember(IdentifierNameSyntax identifier) { SymbolInfo identifierSymbol; bool result = false; // If we're in an object initializer, don't add a 'this.'. if (identifier.FirstAncestorOrSelf<InitializerExpressionSyntax>() != null || identifier.FirstAncestorOrSelf<AnonymousObjectCreationExpressionSyntax>() != null) { return false; } try { // GetSymbolInfo sometimes throws a NullReferenceException in the June 2012 // Roslyn CTP with a symbol in a using statement can't be resolved. // This occurance is tested by the UsingCrash test. identifierSymbol = this.semanticModel.GetSymbolInfo(identifier); } catch { return false; } IEnumerable<Symbol> symbols; if (identifierSymbol.Symbol != null) { symbols = new[] { identifierSymbol.Symbol }; } else if (identifierSymbol.CandidateReason == CandidateReason.OverloadResolutionFailure) { symbols = identifierSymbol.CandidateSymbols.ToArray(); } else { return false; } result = true; foreach (Symbol symbol in symbols) { FieldSymbol field = symbol.OriginalDefinition as FieldSymbol; MethodSymbol method = symbol.OriginalDefinition as MethodSymbol; PropertySymbol property = symbol.OriginalDefinition as PropertySymbol; EventSymbol @event = symbol.OriginalDefinition as EventSymbol; result &= ((field != null && !field.IsStatic) || (method != null && !method.IsStatic && method.MethodKind != MethodKind.Constructor) || (property != null && !property.IsStatic) || (@event != null && [email protected])); } return result; }
protected override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { // Locate the block that is related to the unbreakable keyword // Don't do anything with it yet, just save the block and remove the unbreakable identifier if (node.PlainName == "unbreakable") { var block = (from child in node.Parent.Parent.ChildNodes() where child.Kind == SyntaxKind.Block select child).FirstOrDefault(); _blockToProtect = block as BlockSyntax; return Syntax.IdentifierName(""); } return base.VisitIdentifierName(node); }
public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax name) { if (backingField != null) { if (name.Identifier.ValueText.Equals(backingField.Name)) { var symbolInfo = semanticModel.GetSymbolInfo(name); // Check binding info if (symbolInfo.Symbol != null && symbolInfo.Symbol.OriginalDefinition == backingField) { name = name.WithIdentifier( Syntax.Identifier(property.Identifier.ValueText)); return CodeAnnotations.Formatting.AddAnnotationTo(name); } } } return name; }
private LockHierarchy CreateLockHiearchyFromIdentifier(IdentifierNameSyntax identifier) { //Go up the syntax tree looking at locks and record them in //LAST TO FIRST order List<string> lastToFirstLockList = new List<string>(); //Assuming this traverses the tree upwards and reports nodes in order var lockStatements = identifier.Ancestors().OfType<LockStatementSyntax>(); foreach (LockStatementSyntax lockStatement in lockStatements) { string lockName = lockStatement.DescendantNodes() .OfType<IdentifierNameSyntax>() .First().Identifier.ValueText; lastToFirstLockList.Add(lockName); } //Reverse list to put it in locks taken FIRST-TO-LAST order lastToFirstLockList.Reverse(); return LockHierarchy.FromStringList(lastToFirstLockList); }
public override void VisitIdentifierName(IdentifierNameSyntax node) { base.VisitIdentifierName(node); }
private string EmitIdentifierName(IdentifierNameSyntax node) { return node.Identifier.GetText().ToLowerCamelCase(); }
// Replace all occurances of old class name with new one. public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { var updatedIdentifierName = (IdentifierNameSyntax)base.VisitIdentifierName(node); // Get TypeSymbol corresponding to the IdentifierNameSyntax and check whether // it is the same as the TypeSymbol we are searching for. Symbol identifierSymbol = SemanticModel.GetSymbolInfo(node).Symbol; // Handle |C| x = new C(). var isMatchingTypeName = identifierSymbol.Equals(SearchSymbol); // Handle C x = new |C|(). var isMatchingConstructor = identifierSymbol is MethodSymbol && ((MethodSymbol)identifierSymbol).MethodKind == MethodKind.Constructor && identifierSymbol.ContainingSymbol.Equals(SearchSymbol); if (isMatchingTypeName || isMatchingConstructor) { // Replace the identifier token containing the name of the class. SyntaxToken updatedIdentifierToken = Syntax.Identifier( updatedIdentifierName.Identifier.LeadingTrivia, NewName, updatedIdentifierName.Identifier.TrailingTrivia); updatedIdentifierName = updatedIdentifierName.WithIdentifier(updatedIdentifierToken); } return updatedIdentifierName; }
public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { return RewriteRoleExpression(node); }
//public override SyntaxNode VisitMemberAccessExpression(MemberAccessExpressionSyntax node) //{ // // check for existing this prefix // if (node.Expression.Kind == SyntaxKind.ThisExpression) // return node; // // find the candidate for this prefix // var target = node.Expression.DescendantNodesAndSelf() // .OfType<SimpleNameSyntax>().FirstOrDefault(); // if (target != null) // { // var result = Visit(target); // if (result.Kind == SyntaxKind.MemberAccessExpression) // return node.ReplaceNodes(new[] { target }, (o, n) => { return n; }); // } // return node; //} public override SyntaxNode VisitIdentifierName(IdentifierNameSyntax node) { return RewriteSyntax(node); }
public ConsoleRewriter(string consoleClassName, SemanticModel semanticModel) { model = semanticModel; name = Syntax.IdentifierName(consoleClassName); }
protected override void CompileIdentifierName(IdentifierNameSyntax syntax) { var info = GetModel(syntax).GetSymbolInfo(syntax); var symbol = info.Symbol; if (symbol != null) { if (LocalSymbolMap.ContainsKey(symbol)) { var translation = LocalSymbolMap[symbol]; Write(translation); } else if (symbol is LocalSymbol || symbol is ParameterSymbol) { string name = syntax.Identifier.ValueText; if (symbol is ParameterSymbol) name = FunctionParameterPrefix + name; Write(name); } else if (TranslationLookup.SymbolMap.ContainsKey(symbol)) { var translation_info = TranslationLookup.SymbolMap[symbol]; Write(translation_info.Translation); } else { if (ReferencedMethods.Contains(symbol)) { var method = symbol as MethodSymbol; if (null != method) WriteFullMethodName(method); else Write(symbol.Name); } else { var const_val = GetModel(syntax).GetConstantValue(syntax); if (const_val.HasValue) { CompileLiteral(const_val.Value); } else { if (CompilingLeftSideOfAssignment) { Write("ERROR(Non-local assignment : {0})", syntax); } else { //Write("ERROR(Non-local symbol : {0})", syntax); string name = syntax.Identifier.ValueText; if (IsSamplerType(GetType(symbol))) name = "fs_param_" + name; else name = "foreign_" + name; Write(name); ReferencedForeignVars.AddUnique(symbol); } } } } } }
public FlatOperand Resolve(IdentifierNameSyntax ins, TypeInfo result_type, List<FlatStatement> instructions) { SymbolInfo si = Model.GetSymbolInfo(ins); string name = ins.Identifier.ToString(); switch (si.Symbol.Kind) { case SymbolKind.NamedType: { FlatOperand fop_type = Resolve((TypeSymbol)si.Symbol, null, instructions); return fop_type; } break; case SymbolKind.Local: { int nRegister; if (!CurrentVariableScope.Resolve(name, out nRegister)) { throw new NotImplementedException("Unresolved local symbol " + name); } FlatValue retval = FlatValue.Null(); return FlatOperand.RegisterRef(nRegister, retval); } break; case SymbolKind.Parameter: { int nParameter = 0; if (!MethodSymbol.ReturnsVoid) nParameter++; foreach (ParameterSymbol ps in MethodSymbol.Parameters) { if (name == ps.Name) { FlatValue retval = FlatValue.FromType(ps.Type); return FlatOperand.InputRef(nParameter, retval); } nParameter++; } throw new NotImplementedException("parameter '"+name+"' not found"); } break; case SymbolKind.Field: { if (si.Symbol.IsStatic) { FieldSymbol field = (FieldSymbol)si.Symbol; TypeExtraInfo tei = Chunk.GetTypeExtraInfo(field.ContainingType); if (tei == null) { throw new NotImplementedException("no TypeExtraInfo for field container type " + field.ContainingType.GetFullyQualifiedName()); } int nField; if (!tei.ResolveRuntimeStaticField(field.Name, out nField)) { throw new NotImplementedException("field " + field.Name + " not found in type " + field.ContainingType.GetFullyQualifiedName()); } FlatOperand fop_type = Resolve(si.Symbol.ContainingType, null, instructions); FlatOperand fop_field = Resolve((FieldSymbol)si.Symbol, fop_type, null, instructions); FlatOperand into_lvalue; { FlatOperand register_fop = AllocateRegister(""); into_lvalue = register_fop.GetLValue(this, instructions); } instructions.Add(FlatStatement.GETSTATICFIELD(into_lvalue, fop_field)); return into_lvalue.AsRValue(FlatValue.FromType(result_type.ConvertedType)); } else { FieldSymbol field = (FieldSymbol)si.Symbol; TypeExtraInfo tei = Chunk.GetTypeExtraInfo(field.ContainingType); if (tei == null) { throw new NotImplementedException("no TypeExtraInfo for field container type " + field.ContainingType.GetFullyQualifiedName()); } int nField; if (!tei.ResolveRuntimeField(field.Name, out nField)) { throw new NotImplementedException("field " + field.Name + " not found in type " + field.ContainingType.GetFullyQualifiedName()); } FlatValue retval = FlatValue.FromType(field.Type); return FlatOperand.FieldRef(nField, retval); } } break; case SymbolKind.Property: { if (si.Symbol.IsStatic) { FlatOperand fop_type = Resolve(si.Symbol.ContainingType, null, instructions); FlatOperand fop_property = Resolve((PropertySymbol)si.Symbol, fop_type, null, instructions); FlatOperand into_lvalue; { FlatOperand register_fop = AllocateRegister(""); into_lvalue = register_fop.GetLValue(this, instructions); } instructions.Add(FlatStatement.GETSTATICPROPERTY(into_lvalue, fop_property)); return into_lvalue.AsRValue(FlatValue.FromType(result_type.ConvertedType)); } else { // implied "this" FlatValue thisValue = FlatValue.ObjectRef(si.Symbol.ContainingType); FlatOperand fop_type = TypeOf(FlatOperand.ThisRef(thisValue), si.Symbol.ContainingType, null, instructions); FlatOperand fop_property = Resolve((PropertySymbol)si.Symbol, fop_type, null, instructions); FlatOperand into_lvalue; { FlatOperand register_fop = AllocateRegister(""); into_lvalue = register_fop.GetLValue(this, instructions); } instructions.Add(FlatStatement.GETPROPERTY(into_lvalue, fop_property, FlatOperand.ThisRef(thisValue))); return into_lvalue.AsRValue(FlatValue.FromType(result_type.ConvertedType)); } } break; } throw new NotImplementedException(si.Symbol.Kind.ToString()); }
// NamespaceDeclaration/IdentiferName/IdentifierToken, // Expression.../IdentiferName/IdentifierToken protected override void VisitIdentifierName(IdentifierNameSyntax node) { check(node); base.VisitIdentifierName(node); }
protected abstract void CompileIdentifierName(IdentifierNameSyntax syntax);
// A simple-name is either of the form I or of the form I<A1, ..., AK>, where I is a single // identifier and <A1, ..., AK> is an optional type-argument-list. When no type-argument-list // is specified, consider K to be zero. The simple-name is evaluated and classified as follows: private BoundExpression BindIdentifier(IdentifierNameSyntax node) { Debug.Assert(node != null); // If K is zero and the simple-name appears within a block and if the block’s // (or an enclosing block’s) local variable declaration space contains a local variable, parameter // or constant with name I, then the simple-name refers to that local variable, parameter // or constant and is classified as a variable or value. // If K is zero and the simple-name appears within the body of a generic method declaration // and if that declaration includes a type parameter with name I, then the simple-name refers // to that type parameter. // UNDONE: I think we need to use a form of Lookup that takes an arity, and explicity pass 0. Otherwise // UNDONE: we will find generic var result = context.Lookup(node.PlainName, null, null); if (result.IsViable) { SymbolOrMethodGroup symbolOrMethods = GetSymbolOrMethodGroup(result); if (symbolOrMethods.IsMethodGroup) { // If T is the instance type of the immediately enclosing class or struct type and the lookup identifies // one or more methods, the result is a method group with an associated instance expression of this. // The semantics of lookup mean that we'll only find members associated with one containing // class or struct, or bases thereof. // UNDONE: Construct the type argument list if there is one. if (IsMemberOfType(symbolOrMethods.MethodGroup[0], this.containingMethod.ContainingType)) return new BoundMethodGroup(node, null, new BoundThisReference(null, this.containingMethod.ContainingType), symbolOrMethods.MethodGroup); else { // UNDONE: diagnose error, it was a method in an enclosing type that wasn't immediately enclosing. return null; } } else { Symbol symbol = symbolOrMethods.NonMethod; switch (symbol.Kind) { case SymbolKind.Local: // UNDONE: Better ctor for local that doesn't take a type. return new BoundLocal(node, (LocalSymbol)symbol, ((LocalSymbol)symbol).Type); case SymbolKind.Parameter: // UNDONE: Formal parameter Debug.Fail("Undone: formal parameters"); return null; case SymbolKind.NamedType: case SymbolKind.ErrorType: // If I identifies a type, then the result is that type constructed with the given type arguments. // UNDONE: Construct the child type if it is generic! return new BoundTypeExpression(node, (TypeSymbol)symbol); case SymbolKind.Property: case SymbolKind.Field: // UNDONE: Otherwise, if T is the instance type of the immediately enclosing class or struct type, // UNDONE: if the lookup identifies an instance member, and if the reference occurs within the // UNDONE: block of an instance constructor, an instance method, or an instance accessor, the // UNDONE: result is the same as a member access of the form this.I. This can only happen when K is zero. // UNDONE: Otherwise, the result is the same as a member access of the form T.I or T.I<A1, ..., AK>. In this case, it is a // UNDONE: compile-time error for the simple-name to refer to an instance member. bool inImmediateEnclosing = IsMemberOfType(symbol, this.containingMethod.ContainingType); bool isStatic = symbol.IsStatic; return null; case SymbolKind.Namespace: return new BoundNamespaceExpression(node, (NamespaceSymbol)symbol); default: Debug.Fail("Unexpected symbol kind"); return null; } } } #if SLOW // A lookup in the containing types is already done by context.Lookup. // So no need to do it again. // Otherwise, for each instance type T, starting with the instance type of the immediately enclosing // type declaration and continuing with the instance type of each enclosing class or struct declaration (if any): foreach (NamedTypeSymbol t in this.containingMethod.ContainingType.TypeAndOuterTypes()) { // If K is zero and the declaration of T includes a type parameter with name I, // then the simple-name refers to that type parameter. var typeParameter = t.TypeParameters.FirstOrDefault(p => p.Name == node.PlainName); if (typeParameter != null) { Debug.Fail("Undone: type parameters"); return null; // UNDONE: Type parameter } // Otherwise, if a member lookup of I in T with K type arguments produces a match: var lookupResult = MemberLookup(t, node.PlainName, 0, false); if (lookupResult.IsViable) { Debug.Assert(lookupResult.Symbols.Any()); // If T is the instance type of the immediately enclosing class or struct type and the lookup identifies // one or more methods, the result is a method group with an associated instance expression of this. if (t == this.containingMethod.ContainingType) { if (lookupResult.Symbols.OfType<MethodSymbol>().Any()) { return new BoundMethodGroup(node, null, new BoundThisReference(null, t), lookupResult.Symbols.OfType<MethodSymbol>().ToList()); } // UNDONE: Otherwise, if T is the instance type of the immediately enclosing class or struct type, // UNDONE: if the lookup identifies an instance member, and if the reference occurs within the // UNDONE: block of an instance constructor, an instance method, or an instance accessor, the // UNDONE: result is the same as a member access of the form this.I. This can only happen when K is zero. // UNDONE: Field, event, property... } // UNDONE: Otherwise, the result is the same as a member access of the form T.I or T.I<A1, ..., AK>. In this case, it is a // UNDONE: compile-time error for the simple-name to refer to an instance member. } } #endif #if false // Otherwise, for each namespace N, starting with the namespace in which the simple-name occurs, // continuing with each enclosing namespace (if any), and ending with the global namespace, // the following steps are evaluated until an entity is located: foreach(var ns in containingMethod.ContainingNamespaces()) { // If K is zero and I is the name of a namespace in N, then: var childNamespace = ns.GetMembers(node.PlainName).OfType<NamespaceSymbol>().FirstOrDefault(); if (childNamespace != null) { // UNDONE: If the location where the simple-name occurs is enclosed by a // UNDONE: namespace declaration for N and the namespace declaration contains // UNDONE: an extern-alias-directive or using-alias-directive that associates the // UNDONE: name I with a namespace or type, then the simple-name is ambiguous and // UNDONE: a compile-time error occurs. // Otherwise, the simple-name refers to the namespace named I in N. return new NamespaceExpression(node, childNamespace); } // Otherwise, if N contains an accessible type having name I and K type parameters, then: var childType = ns.GetMembers(node.PlainName).OfType<TypeSymbol>().FirstOrDefault(); // UNDONE: Check accessibility if (childType != null) { // UNDONE: If K is zero and the location where the simple-name occurs // UNDONE: is enclosed by a namespace declaration for N and the namespace // UNDONE: declaration contains an extern-alias-directive or using-alias-directive // UNDONE: that associates the name I with a namespace or type, then the simple-name // UNDONE: is ambiguous and a compile-time error occurs. // Otherwise, the namespace-or-type-name refers to the type constructed with the given type arguments. return new TypeExpression(node, childType); } // UNDONE: Otherwise, if the location where the simple-name occurs is enclosed by a namespace declaration for N: // UNDONE: If K is zero and the namespace declaration contains an extern-alias-directive or using-alias-directive // UNDONE: that associates the name I with an imported namespace or type, then the simple-name refers to that namespace or type. // UNDONE: Otherwise, if the namespaces imported by the using-namespace-directives of the namespace declaration // UNDONE: contain exactly one type having name I and K type parameters, then the simple-name refers to that type // UNDONE: constructed with the given type arguments. // UNDONE: Otherwise, if the namespaces imported by the using-namespace-directives of the namespace declaration contain more than one type having name I and K type parameters, then the simple-name is ambiguous and an error occurs. } #endif // UNDONE: Otherwise, the simple-name is undefined and a compile-time error occurs. return null; }