1- using System . Collections . Generic ;
1+ using System ;
2+ using System . Collections . Generic ;
23using Microsoft . CodeAnalysis ;
34using Microsoft . CodeAnalysis . CSharp ;
45using Microsoft . CodeAnalysis . CSharp . Syntax ;
@@ -37,7 +38,9 @@ public sealed class DoNotUseFindMethodsInUpdateAnalyzer : DiagnosticAnalyzer
3738 "UnityEngine.Transform" ) ;
3839
3940
40- public override ImmutableArray < DiagnosticDescriptor > SupportedDiagnostics => ImmutableArray . Create ( DiagnosticDescriptors . DoNotUseFindMethodsInUpdate ) ;
41+ public override ImmutableArray < DiagnosticDescriptor > SupportedDiagnostics
42+ => ImmutableArray . Create ( DiagnosticDescriptors . DoNotUseFindMethodsInUpdate ) ;
43+
4144 public override void Initialize ( AnalysisContext context )
4245 {
4346 context . RegisterSyntaxNodeAction ( AnalyzeClassSyntax , SyntaxKind . ClassDeclaration ) ;
@@ -52,27 +55,36 @@ public static void AnalyzeClassSyntax(SyntaxNodeAnalysisContext context)
5255 monoBehaviourInfo . ForEachUpdateMethod ( ( updateMethod ) =>
5356 {
5457 //Debug.WriteLine("Found an update call! " + updateMethod);
55-
58+
5659 var findCalls = SearchForFindCalls ( context , updateMethod , searched ) ;
5760
5861 foreach ( var findCall in findCalls )
5962 {
6063 //Debug.WriteLine("Found a bad call! " + findCall);
6164
62- var diagnostic = Diagnostic . Create ( DiagnosticDescriptors . DoNotUseFindMethodsInUpdate , findCall . GetLocation ( ) , findCall , monoBehaviourInfo . ClassName , updateMethod . Identifier ) ;
65+ var diagnostic = Diagnostic . Create ( DiagnosticDescriptors . DoNotUseFindMethodsInUpdate ,
66+ findCall . GetLocation ( ) , findCall , monoBehaviourInfo . ClassName , updateMethod . Identifier ) ;
6367 context . ReportDiagnostic ( diagnostic ) ;
6468 }
6569 } ) ;
6670 }
6771
6872 //TODO: Try to simplify this method - it's very hard to follow
69- private static IEnumerable < ExpressionSyntax > SearchForFindCalls ( SyntaxNodeAnalysisContext context , MethodDeclarationSyntax method , IDictionary < IMethodSymbol , bool > searched )
73+ private static IEnumerable < ExpressionSyntax > SearchForFindCalls ( SyntaxNodeAnalysisContext context ,
74+ MethodDeclarationSyntax method , IDictionary < IMethodSymbol , bool > searched )
7075 {
7176 var invocations = method . DescendantNodes ( ) . OfType < InvocationExpressionSyntax > ( ) ;
7277
7378 foreach ( var invocation in invocations )
7479 {
75- var methodSymbol = context . SemanticModel . GetSymbolInfo ( invocation ) . Symbol as IMethodSymbol ;
80+ SymbolInfo symbolInfo ;
81+ if ( ! TryGetSymbolInfo ( context , invocation , out symbolInfo ) )
82+ {
83+ break ;
84+ }
85+ //var symbolInfo = context.SemanticModel.GetSymbolInfo(invocation);
86+
87+ var methodSymbol = symbolInfo . Symbol as IMethodSymbol ;
7688
7789 if ( methodSymbol != null )
7890 {
@@ -118,5 +130,25 @@ private static IEnumerable<ExpressionSyntax> SearchForFindCalls(SyntaxNodeAnalys
118130 }
119131 }
120132 }
133+
134+ private static bool TryGetSymbolInfo ( SyntaxNodeAnalysisContext context , SyntaxNode node , out SymbolInfo symbolInfo )
135+ {
136+ //TODO: This code is a temporary solution until i get a better understanding of why we cannot get symbol info for the expressions
137+ //HACK: See Above
138+
139+ try
140+ {
141+ symbolInfo = context . SemanticModel . GetSymbolInfo ( node ) ;
142+ return true ;
143+ }
144+ catch ( Exception generalException )
145+ {
146+ Debug . WriteLine ( "Unable to find Symbol: " + node ) ;
147+ Debug . WriteLine ( generalException ) ;
148+ }
149+
150+ symbolInfo = default ( SymbolInfo ) ;
151+ return false ;
152+ }
121153 }
122154}
0 commit comments