Skip to content

Fix #633: Overrides analysis and this/base keyword navigation - #3918

Merged
siegfriedpammer merged 2 commits into
masterfrom
feature-633-overrides-analyzer
Jul 27, 2026
Merged

Fix #633: Overrides analysis and this/base keyword navigation#3918
siegfriedpammer merged 2 commits into
masterfrom
feature-633-overrides-analyzer

Conversation

@siegfriedpammer

Copy link
Copy Markdown
Member

Fixes #633.

Two commits, covering the remaining parts of the issue:

1. "Overrides" analyzer — the dual of "Overridden By": for an override method/property/event/indexer, the analyzer panel now shows the base members it overrides. The upward interface direction already exists as the "Implements" analysis, so this adds only the base-class direction. The analyzer walks the override chain member by member via InheritanceHelper.GetBaseMember instead of collecting all signature-equal base members, so it stops at new virtual shadow boundaries, which hide any further base members from overriding. No assembly-scope scan is needed; the walk is a direct type-system lookup. Tests mirror the MemberImplementsInterfaceAnalyzerTests pattern, including a shadowing case.

2. this/base keyword navigation — as primary expressions, this now references the current type and base the base type, matching IDE go-to-definition behavior (both directions together deliberately; linking only base would make the two keywords inconsistent). The override modifier already navigated to the overridden member and constructor initializers already linked this/base to the invoked constructor; new KeywordReferenceTests pin all three behaviors.

Of the issue's four points this delivers the analysis (1) and completes keyword navigation (2, 3); the last point (clicking a declaration selects the whole override chain in the tree) overlaps #819's target-picker idea and is intentionally left out.

Verified: ILSpy.Tests 1099 total / 0 failed / 3 skipped; decompiler suite 2544 total / 0 failed / 38 skipped; XPlat solution filter builds clean.

🤖 This PR was prepared by an AI agent (Claude Code) operated by @siegfriedpammer.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds the remaining pieces of issue #633 by introducing an “Overrides” analyzer (the upward base-class direction complementing “Overridden By”/“Implements”) and by improving keyword navigation so this/base primary expressions link to their respective types, matching IDE go-to-definition behavior.

Changes:

  • Added a new built-in analyzer (MemberOverridesAnalyzer) that walks the override chain upward via InheritanceHelper.GetBaseMember, stopping at new virtual shadow boundaries.
  • Updated TextTokenWriter.WriteKeyword so this/base primary expressions emit type references (in addition to existing constructor-initializer and override-modifier linking).
  • Added NUnit tests covering the new analyzer behavior and keyword reference behaviors.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 1 comment.

File Description
ILSpy.Tests/TextView/KeywordReferenceTests.cs New tests pin this/base primary-expression type references and override modifier member reference.
ILSpy.Tests/Analyzers/Library/MemberOverridesAnalyzerTests.cs New tests validate when “Overrides” shows and what base members it returns (including shadowing boundary).
ICSharpCode.ILSpyX/Analyzers/Builtin/MemberOverridesAnalyzer.cs New analyzer implementation yielding overridden base-class members for override members.
ICSharpCode.Decompiler/Output/TextTokenWriter.cs Emits references for this/base primary expressions to their resolved types.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread ILSpy.Tests/Analyzers/Library/MemberOverridesAnalyzerTests.cs
The analyzer panel could only walk downward (Overridden By, Implemented
By); finding what a member overrides required manually climbing base
types. The upward interface direction already exists as the Implements
analysis, so this adds the missing base-class direction as its dual.

The analyzer walks the override chain member by member via
InheritanceHelper.GetBaseMember instead of collecting all
signature-equal base members, so it stops at 'new virtual' shadow
boundaries, which hide any further base members from overriding. No
assembly-scope scan is needed; the walk is a direct type-system lookup.

Assisted-by: Claude:claude-fable-5:Claude Code
The override modifier already navigates to the overridden member and
constructor initializers link this/base to the invoked constructor, but
the primary expressions carried no reference at all. Matching IDE
go-to-definition behavior, 'this' now references the current type and
'base' the base type; both directions are added together deliberately,
linking only 'base' would make the two keywords behave inconsistently.

Assisted-by: Claude:claude-fable-5:Claude Code
@siegfriedpammer
siegfriedpammer force-pushed the feature-633-overrides-analyzer branch from 86c55b2 to ec72701 Compare July 27, 2026 14:36
@siegfriedpammer
siegfriedpammer merged commit d9b63a5 into master Jul 27, 2026
13 checks passed
@siegfriedpammer
siegfriedpammer deleted the feature-633-overrides-analyzer branch July 27, 2026 15:13
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Feature Request: Add an "overrides" analysis

2 participants