in src/Microsoft.VisualStudio.Threading.Analyzers.CSharp/VSTHRD010MainThreadUsageAnalyzer.cs [230:285]
private void AddToCallerCalleeMap(OperationAnalysisContext context, Dictionary<IMethodSymbol, List<CallInfo>> callerToCalleeMap)
{
if (CSharpUtils.IsWithinNameOf(context.Operation.Syntax))
{
return;
}
IMethodSymbol? GetPropertyAccessor(IPropertySymbol? propertySymbol)
{
if (propertySymbol is object)
{
return CSharpUtils.IsOnLeftHandOfAssignment(context.Operation.Syntax)
? propertySymbol.SetMethod
: propertySymbol.GetMethod;
}
return null;
}
ISymbol? targetMethod = null;
SyntaxNode locationToBlame = context.Operation.Syntax;
switch (context.Operation)
{
case IInvocationOperation invocationOperation:
targetMethod = invocationOperation.TargetMethod;
locationToBlame = this.languageUtils.IsolateMethodName(invocationOperation);
break;
case IPropertyReferenceOperation propertyReference:
targetMethod = GetPropertyAccessor(propertyReference.Property);
break;
case IEventAssignmentOperation eventAssignmentOperation:
IOperation eventReferenceOp = eventAssignmentOperation.EventReference;
if (eventReferenceOp is IEventReferenceOperation eventReference)
{
targetMethod = eventAssignmentOperation.Adds
? eventReference.Event.AddMethod
: eventReference.Event.RemoveMethod;
locationToBlame = eventReference.Syntax;
}
break;
}
if (context.ContainingSymbol is IMethodSymbol caller && targetMethod is IMethodSymbol callee)
{
lock (callerToCalleeMap)
{
if (!callerToCalleeMap.TryGetValue(caller, out List<CallInfo> callees))
{
callerToCalleeMap[caller] = callees = new List<CallInfo>();
}
callees.Add(new CallInfo(methodSymbol: callee, invocationSyntax: locationToBlame));
}
}
}