The "original" C# (access) modifier is available in the "original" MethodDeclarationSyntax from the SyntaxTree, but no longer in the IMethodSymbol retrieved via the SemanticModel where that information can be read from the ISymbol.DeclaredAccessibility property which is an enum of type Accessibility.
DiagnosticAnalyzer
code:
public override void Initialize(AnalysisContext context)
{
context.ConfigureGeneratedCodeAnalysis(GeneratedCodeAnalysisFlags.None);
context.EnableConcurrentExecution();
context.RegisterSyntaxNodeAction(OnMethodDeclaration, SyntaxKind.MethodDeclaration);
context.RegisterSyntaxNodeAction(OnSimpleMemberAccess, SyntaxKind.SimpleMemberAccessExpression);
}
private static void OnMethodDeclaration(SyntaxNodeAnalysisContext context)
{
var methodDeclaration = (MethodDeclarationSyntax)context.Node; // public override async Task ExecuteAsync() => await Task.Yield();
Debug.Assert(methodDeclaration.Modifiers.Count == 3); // public override async
Debug.Assert(methodDeclaration.Modifiers[0].IsKind(SyntaxKind.PublicKeyword)); // public
Debug.Assert(methodDeclaration.Modifiers[1].IsKind(SyntaxKind.OverrideKeyword)); // override
Debug.Assert(methodDeclaration.Modifiers[2].IsKind(SyntaxKind.AsyncKeyword)); // async
}
private static void OnSimpleMemberAccess(SyntaxNodeAnalysisContext context)
{
Debug.Assert(context.Node is MemberAccessExpressionSyntax); // new Class().ExecuteAsync
SymbolInfo info = context.SemanticModel.GetSymbolInfo(context.Node);
Debug.Assert(info.Symbol is IMethodSymbol); // Class.ExecuteAsync()
var method = (IMethodSymbol)info.Symbol;
Debug.Assert(method.DeclaredAccessibility == Accessibility.Public); // Public
}
Example code:
await new Class().ExecuteAsync();
public class Class : Base
{
public override async Task ExecuteAsync() => await Task.Yield();
}