From ab691fd4784bea9301e329aa4683b290028bf317 Mon Sep 17 00:00:00 2001 From: Neal Gafter Date: Tue, 10 Apr 2018 12:01:42 -0700 Subject: [PATCH] Fix compiler crash when binding missing property pattern member. --- .../CSharp/Portable/Binder/Binder_Patterns.cs | 14 +++-- .../Semantics/PatternMatchingTests2.cs | 53 +++++++++++++++++++ 2 files changed, 62 insertions(+), 5 deletions(-) diff --git a/src/Compilers/CSharp/Portable/Binder/Binder_Patterns.cs b/src/Compilers/CSharp/Portable/Binder/Binder_Patterns.cs index 2b3a6019634..0c0a549dff4 100644 --- a/src/Compilers/CSharp/Portable/Binder/Binder_Patterns.cs +++ b/src/Compilers/CSharp/Portable/Binder/Binder_Patterns.cs @@ -658,14 +658,16 @@ private BoundPattern BindPropertyPattern(PropertyPatternSyntax node, TypeSymbol { Symbol symbol = BindPropertyPatternMember(inputType, name, ref hasErrors, diagnostics); - if (inputType.IsErrorType() || hasErrors) + if (inputType.IsErrorType() || hasErrors || symbol == (object)null) { memberType = CreateErrorType(); return null; } - - memberType = symbol.GetTypeOrReturnType(); - return symbol; + else + { + memberType = symbol.GetTypeOrReturnType(); + return symbol; + } } private Symbol BindPropertyPatternMember( @@ -726,16 +728,18 @@ private BoundPattern BindPropertyPattern(PropertyPatternSyntax node, TypeSymbol default: Error(diagnostics, ErrorCode.ERR_PropertyLacksGet, memberName, name); - hasErrors = true; break; } } + + hasErrors = true; return null; } if (hasErrors || !CheckValueKind(node: memberName.Parent, expr: boundMember, valueKind: BindValueKind.RValue, checkingReceiver: false, diagnostics: diagnostics)) { + hasErrors = true; return null; } diff --git a/src/Compilers/CSharp/Test/Semantic/Semantics/PatternMatchingTests2.cs b/src/Compilers/CSharp/Test/Semantic/Semantics/PatternMatchingTests2.cs index 5e71ea5e1ea..c0f06540b19 100644 --- a/src/Compilers/CSharp/Test/Semantic/Semantics/PatternMatchingTests2.cs +++ b/src/Compilers/CSharp/Test/Semantic/Semantics/PatternMatchingTests2.cs @@ -1254,6 +1254,59 @@ class Cat {} var comp = CompileAndVerify(compilation, expectedOutput: @"Fox Cat"); } + [Fact] + public void PropertyPatternMemberMissing01() + { + var source = +@"class Program +{ + static void Main(string[] args) + { + Blah b = null; + if (b is Blah { X: int i }) + { + } + } +} + +class Blah +{ +}"; + var compilation = CreatePatternCompilation(source); + compilation.VerifyDiagnostics( + // (6,25): error CS0117: 'Blah' does not contain a definition for 'X' + // if (b is Blah { X: int i }) + Diagnostic(ErrorCode.ERR_NoSuchMember, "X").WithArguments("Blah", "X").WithLocation(6, 25) + ); + } + + [Fact] + public void PropertyPatternMemberMissing02() + { + var source = +@"class Program +{ + static void Main(string[] args) + { + Blah b = null; + if (b is Blah { X: int i }) + { + } + } +} + +class Blah +{ + public int X { set {} } +}"; + var compilation = CreatePatternCompilation(source); + compilation.VerifyDiagnostics( + // (6,25): error CS0154: The property or indexer 'Blah.X' cannot be used in this context because it lacks the get accessor + // if (b is Blah { X: int i }) + Diagnostic(ErrorCode.ERR_PropertyLacksGet, "X:").WithArguments("Blah.X").WithLocation(6, 25) + ); + } + // PROTOTYPE(patterns2): Need to have tests that exercise: // PROTOTYPE(patterns2): Building the decision tree for the var-pattern // PROTOTYPE(patterns2): Definite assignment for the var-pattern -- GitLab