Repository navigation
Supersede: Support the tractable C# patterns when converting to VB - #1290
Merged
GrahamTheCoder merged 10 commits intoOct 19, 2026
Merged
Conversation
VisitIsPatternExpression handled only declaration and constant patterns and threw for everything else, so most pattern matching failed to convert. It is now split into a recursive ConvertPattern that also covers: * type patterns, as TypeOf x Is T * negated patterns, flipped in place to TypeOf x IsNot T or TryCast(x, T) Is Nothing rather than wrapped in Not * relational patterns, as plain comparisons A constant pattern whose expression binds to a type is a type test, not a comparison, and was being emitted as Is, which compares references in VB. It now emits TypeOf x Is T. A constant compared by value went the same way and did not compile at all; it now uses = for a value type and Equals for anything else, which is what the pattern means when the operand is an Object. "x is not T v" declares v just as "x is T v" does, so the hoisting in CommonConversions follows the negation to find it. Also here, both smaller and separable: * ImplicitObjectCreationExpression had no visitor, so target-typed new threw. The type the compiler settled on is written out instead. * GetSymbolInfo(node.Left).Symbol was dereferenced without a null check while converting an event subscription, so an unresolved symbol crashed the whole file rather than degrading. * A failed expression conversion comes back as an empty statement carrying its report as trivia. A return statement dropped both, losing the value and the diagnostic together; the report now travels with the statement. Property patterns and ??= are deliberately left out: both need the tested expression evaluated once, which needs a temporary rather than repeating it. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
"n is 5" on an int? became "n = 5", which lifts to Boolean? and throws when narrowed to Boolean while n is Nothing. Equals boxes the value and answers False, matching C#. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
"o is > 0" on an Object also tests that o is an int; "o > 0" late-binds instead, answering True for "5" and throwing for "abc". On an int? the comparison lifts to Boolean? and throws when narrowed from Nothing. Report these as not converted rather than silently changing behaviour. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
"x is not null" became "Not x Is Nothing"; emit "x IsNot Nothing" as the negated declaration pattern already does for its own Nothing test. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
Covers the return trivia change: the error comment survives, Return stays on its own line, and the original comments appear once each. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
On Windows the VB error comment ended in an empty "''' " line, and the line break ReturnStatement added after it was dropped by LineTriviaMapper, which only kept annotated leading trivia. The Return was commented out. Build the comment by splitting on either line ending so every line is prefixed on every platform (on Linux the stack trace lines were left uncommented) with no trailing empty line, and keep the line break that follows a leading error comment when mapping trivia. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
In C# "is" binds tighter than ==, but VB's comparison operators, Is included, share one precedence level and group left to right, so "flag == x is 5" became "flag = x = 5", read as "(flag = x) = 5". Simplification still removes the parentheses where they are redundant. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
Equals compares boxed types, so "l is 5" on a long? became "Equals(l, 5)", which is False even when l is 5. "=" instead lifts to Boolean? and throws when narrowed from Nothing. Neither matches C#, so report the pattern rather than emit silently wrong code. Null tests on a nullable are unaffected. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
"d is double.NaN" matches NaN, but became "d = Double.NaN", which is always False. Emit Double.IsNaN(d) / Single.IsNaN(f) instead. On Object the existing Equals path already answers True for a boxed NaN. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
Property patterns, which apply a nested pattern to a member, are not supported; the type travels along to pick the comparison. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UxCQrzahEZZWcfrGNSR4Sc
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
No description provided.