From acc71d0d93dc0f85182845e6ec491d446439f3f2 Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 15:56:15 +0100 Subject: [PATCH 01/10] Parser: recover on unfinished 'as' patterns --- src/Compiler/pars.fsy | 22 +++++++++++++--- .../Expression/Object - Class 08.fs.bsl | 2 +- .../Expression/Object - Class 13.fs.bsl | 2 +- .../data/SyntaxTree/Member/Member 03.fs.bsl | 2 +- .../data/SyntaxTree/Member/Member 07.fs.bsl | 2 +- .../data/SyntaxTree/Member/Member 12.fs.bsl | 2 +- ...ePatternDefinitionWithoutParameters.fs.bsl | 2 +- .../service/data/SyntaxTree/Pattern/As 01.fs | 4 +++ .../data/SyntaxTree/Pattern/As 01.fs.bsl | 22 ++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 02.fs | 4 +++ .../data/SyntaxTree/Pattern/As 02.fs.bsl | 24 ++++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 03.fs | 3 +++ .../data/SyntaxTree/Pattern/As 03.fs.bsl | 21 ++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 04.fs | 3 +++ .../data/SyntaxTree/Pattern/As 04.fs.bsl | 23 +++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 05.fs | 4 +++ .../data/SyntaxTree/Pattern/As 05.fs.bsl | 25 +++++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 06.fs | 3 +++ .../data/SyntaxTree/Pattern/As 06.fs.bsl | 25 +++++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 07.fs | 5 ++++ .../data/SyntaxTree/Pattern/As 07.fs.bsl | 25 +++++++++++++++++++ .../Pattern/Typed - Missing type 01.fs.bsl | 10 ++++---- .../Pattern/Typed - Missing type 05.fs.bsl | 15 +++++------ 23 files changed, 229 insertions(+), 21 deletions(-) create mode 100644 tests/service/data/SyntaxTree/Pattern/As 01.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 01.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 02.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 02.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 03.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 03.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 04.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 05.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 05.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 06.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 07.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index c40a2fe380e..3a6d2c75f17 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -3214,10 +3214,16 @@ localBinding: | opt_inline opt_mutable bindingPattern opt_topReturnTypeWithTypeConstraints recover { if not $5 then reportParseErrorAt (rhs parseState 5) (FSComp.SR.parsUnexpectedEndOfFileDefinition()) + let bindingPat, mBindLhs = $3 let optReturnType = $4 - let mWhole = rhs2 parseState 1 (match optReturnType with None -> 3 | _ -> 4) + let mWhole = + let mStart = rhs parseState 1 + let mEnd = + match optReturnType with + | None -> bindingPat.Range + | Some (_, returnInfo) -> returnInfo.Range + unionRanges mStart mEnd let mRhs = mWhole.EndRange // zero-width range at end of last good token - let bindingPat, mBindLhs = $3 let localBindingBuilder = (fun xmlDoc attrs vis (leadingKeyword: SynLeadingKeyword) -> let spBind = DebugPointAtBinding.Yes(unionRanges leadingKeyword.Range mRhs) @@ -3377,7 +3383,7 @@ constant: bindingPattern: | headBindingPattern - { $1, rhs parseState 1 } + { $1, $1.Range } // Subset of patterns allowed to be used in implicit ctors. // For a better error recovery we could replace these rules with the actual SynPat parsing @@ -3450,6 +3456,11 @@ headBindingPattern: | headBindingPattern AS constrPattern { SynPat.As($1, $3, rhs2 parseState 1 3) } + | headBindingPattern AS recover + { let mAs = rhs parseState 2 + let pat2 = SynPat.Wild(mAs.EndRange) + SynPat.As($1, pat2, rhs2 parseState 1 2) } + | headBindingPattern BAR headBindingPattern { let mBar = rhs parseState 2 SynPat.Or($1, $3, rhs2 parseState 1 3, { BarRange = mBar }) } @@ -3724,6 +3735,11 @@ parenPattern: | parenPattern AS constrPattern { SynPat.As($1, $3, rhs2 parseState 1 3) } + | parenPattern AS recover + { let mAs = rhs parseState 2 + let pat2 = SynPat.Wild(mAs.EndRange) + SynPat.As($1, pat2, rhs2 parseState 1 2) } + | parenPattern BAR parenPattern { let mBar = rhs parseState 2 SynPat.Or($1, $3, rhs2 parseState 1 3, { BarRange = mBar }) } diff --git a/tests/service/data/SyntaxTree/Expression/Object - Class 08.fs.bsl b/tests/service/data/SyntaxTree/Expression/Object - Class 08.fs.bsl index b4a5df07136..da2aa3f44bc 100644 --- a/tests/service/data/SyntaxTree/Expression/Object - Class 08.fs.bsl +++ b/tests/service/data/SyntaxTree/Expression/Object - Class 08.fs.bsl @@ -24,7 +24,7 @@ ImplFile SynArgInfo ([], false, None)), None), Named (SynIdent (this, None), false, None, (4,12--4,16)), None, ArbitraryAfterError ("memberCore2", (4,16--4,16)), - (4,12--4,19), NoneAtInvisible, + (4,12--4,16), NoneAtInvisible, { LeadingKeyword = Member (4,5--4,11) InlineKeyword = None EqualsRange = None }), (4,5--4,16))], [], (3,2--3,9), diff --git a/tests/service/data/SyntaxTree/Expression/Object - Class 13.fs.bsl b/tests/service/data/SyntaxTree/Expression/Object - Class 13.fs.bsl index 3e636b4785c..6567abe2e7b 100644 --- a/tests/service/data/SyntaxTree/Expression/Object - Class 13.fs.bsl +++ b/tests/service/data/SyntaxTree/Expression/Object - Class 13.fs.bsl @@ -24,7 +24,7 @@ ImplFile SynArgInfo ([], false, None)), None), Named (SynIdent (this, None), false, None, (4,12--4,16)), None, ArbitraryAfterError ("memberCore1", (4,16--4,16)), - (4,12--5,5), NoneAtInvisible, + (4,12--4,16), NoneAtInvisible, { LeadingKeyword = Member (4,5--4,11) InlineKeyword = None EqualsRange = None }), (4,5--4,16)); diff --git a/tests/service/data/SyntaxTree/Member/Member 03.fs.bsl b/tests/service/data/SyntaxTree/Member/Member 03.fs.bsl index 09fde9d81da..cb85a85bfc7 100644 --- a/tests/service/data/SyntaxTree/Member/Member 03.fs.bsl +++ b/tests/service/data/SyntaxTree/Member/Member 03.fs.bsl @@ -66,7 +66,7 @@ ImplFile (SynIdent (this, None), false, None, (5,17--5,21)), None, ArbitraryAfterError ("memberCore1", (5,21--5,21)), - (5,4--6,4), NoneAtInvisible, + (5,4--5,21), NoneAtInvisible, { LeadingKeyword = Member (5,10--5,16) InlineKeyword = None EqualsRange = None }), (5,4--5,21)); diff --git a/tests/service/data/SyntaxTree/Member/Member 07.fs.bsl b/tests/service/data/SyntaxTree/Member/Member 07.fs.bsl index 53fff4c46e5..5e5c51e0f2b 100644 --- a/tests/service/data/SyntaxTree/Member/Member 07.fs.bsl +++ b/tests/service/data/SyntaxTree/Member/Member 07.fs.bsl @@ -64,7 +64,7 @@ ImplFile SynArgInfo ([], false, None)), None), Named (SynIdent (this, None), false, None, (5,17--5,21)), - None, Const (Int32 2, (5,25--5,26)), (5,4--5,24), + None, Const (Int32 2, (5,25--5,26)), (5,4--5,21), NoneAtInvisible, { LeadingKeyword = Member (5,10--5,16) InlineKeyword = None diff --git a/tests/service/data/SyntaxTree/Member/Member 12.fs.bsl b/tests/service/data/SyntaxTree/Member/Member 12.fs.bsl index c20d46b6107..94ece410c41 100644 --- a/tests/service/data/SyntaxTree/Member/Member 12.fs.bsl +++ b/tests/service/data/SyntaxTree/Member/Member 12.fs.bsl @@ -29,7 +29,7 @@ ImplFile (SynIdent (this, None), false, None, (4,11--4,15)), None, ArbitraryAfterError ("memberCore2", (4,15--4,15)), - (4,11--6,1), NoneAtInvisible, + (4,11--4,15), NoneAtInvisible, { LeadingKeyword = Member (4,4--4,10) InlineKeyword = None EqualsRange = None }), (4,4--4,15))], (4,4--4,15)), diff --git a/tests/service/data/SyntaxTree/OperatorName/PartialActivePatternDefinitionWithoutParameters.fs.bsl b/tests/service/data/SyntaxTree/OperatorName/PartialActivePatternDefinitionWithoutParameters.fs.bsl index 62cede07065..d3f6d9d59f8 100644 --- a/tests/service/data/SyntaxTree/OperatorName/PartialActivePatternDefinitionWithoutParameters.fs.bsl +++ b/tests/service/data/SyntaxTree/OperatorName/PartialActivePatternDefinitionWithoutParameters.fs.bsl @@ -21,7 +21,7 @@ ImplFile (false, SynLongIdent ([Boolean; parse], [(2,27--2,28)], [None; None]), None, - (2,20--2,33)), (2,4--2,17), Yes (2,0--2,33), + (2,20--2,33)), (2,5--2,16), Yes (2,0--2,33), { LeadingKeyword = Let (2,0--2,3) InlineKeyword = None EqualsRange = Some (2,18--2,19) })], (2,0--2,33))], diff --git a/tests/service/data/SyntaxTree/Pattern/As 01.fs b/tests/service/data/SyntaxTree/Pattern/As 01.fs new file mode 100644 index 00000000000..9c3786b2552 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 01.fs @@ -0,0 +1,4 @@ +module Module + +match Some 1 with +| _ as _ -> () diff --git a/tests/service/data/SyntaxTree/Pattern/As 01.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 01.fs.bsl new file mode 100644 index 00000000000..f0277e7a075 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 01.fs.bsl @@ -0,0 +1,22 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 01.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Expr + (Match + (Yes (3,0--3,17), + App + (NonAtomic, false, Ident Some, Const (Int32 1, (3,11--3,12)), + (3,6--3,12)), + [SynMatchClause + (As (Wild (4,2--4,3), Wild (4,7--4,8), (4,2--4,8)), None, + Const (Unit, (4,12--4,14)), (4,2--4,14), Yes, + { ArrowRange = Some (4,9--4,11) + BarRange = Some (4,0--4,1) })], (3,0--4,14), + { MatchKeyword = (3,0--3,5) + WithKeyword = (3,13--3,17) }), (3,0--4,14))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--4,14), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) diff --git a/tests/service/data/SyntaxTree/Pattern/As 02.fs b/tests/service/data/SyntaxTree/Pattern/As 02.fs new file mode 100644 index 00000000000..2a098980177 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 02.fs @@ -0,0 +1,4 @@ +module Module + +match Some 1 with +| _ as -> () diff --git a/tests/service/data/SyntaxTree/Pattern/As 02.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 02.fs.bsl new file mode 100644 index 00000000000..a39bda6bb7c --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 02.fs.bsl @@ -0,0 +1,24 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 02.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Expr + (Match + (Yes (3,0--3,17), + App + (NonAtomic, false, Ident Some, Const (Int32 1, (3,11--3,12)), + (3,6--3,12)), + [SynMatchClause + (As (Wild (4,2--4,3), Wild (4,6--4,6), (4,2--4,6)), None, + Const (Unit, (4,10--4,12)), (4,2--4,12), Yes, + { ArrowRange = Some (4,7--4,9) + BarRange = Some (4,0--4,1) })], (3,0--4,12), + { MatchKeyword = (3,0--3,5) + WithKeyword = (3,13--3,17) }), (3,0--4,12))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--4,12), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(4,7)-(4,9) parse error Unexpected symbol '->' in pattern diff --git a/tests/service/data/SyntaxTree/Pattern/As 03.fs b/tests/service/data/SyntaxTree/Pattern/As 03.fs new file mode 100644 index 00000000000..6986fa365c0 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 03.fs @@ -0,0 +1,3 @@ +module Module + +let _ as _ = () diff --git a/tests/service/data/SyntaxTree/Pattern/As 03.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 03.fs.bsl new file mode 100644 index 00000000000..87eeb9e821a --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 03.fs.bsl @@ -0,0 +1,21 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 03.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + As (Wild (3,4--3,5), Wild (3,9--3,10), (3,4--3,10)), None, + Const (Unit, (3,13--3,15)), (3,4--3,10), Yes (3,0--3,15), + { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = Some (3,11--3,12) })], (3,0--3,15))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,15), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) diff --git a/tests/service/data/SyntaxTree/Pattern/As 04.fs b/tests/service/data/SyntaxTree/Pattern/As 04.fs new file mode 100644 index 00000000000..9235d0a7966 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 04.fs @@ -0,0 +1,3 @@ +module Module + +let _ as = () diff --git a/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl new file mode 100644 index 00000000000..c2a98cfee37 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl @@ -0,0 +1,23 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 04.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + As (Wild (3,4--3,5), Wild (3,8--3,8), (3,4--3,8)), None, + Const (Unit, (3,11--3,13)), (3,4--3,8), Yes (3,0--3,13), + { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = Some (3,9--3,10) })], (3,0--3,13))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,13), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(3,9)-(3,10) parse error Unexpected symbol '=' in binding diff --git a/tests/service/data/SyntaxTree/Pattern/As 05.fs b/tests/service/data/SyntaxTree/Pattern/As 05.fs new file mode 100644 index 00000000000..66705b3f1a7 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 05.fs @@ -0,0 +1,4 @@ +module Module + +match Some 1 with +| _ as diff --git a/tests/service/data/SyntaxTree/Pattern/As 05.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 05.fs.bsl new file mode 100644 index 00000000000..1e26e340c11 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 05.fs.bsl @@ -0,0 +1,25 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 05.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Expr + (Match + (Yes (3,0--3,17), + App + (NonAtomic, false, Ident Some, Const (Int32 1, (3,11--3,12)), + (3,6--3,12)), + [SynMatchClause + (As (Wild (4,2--4,3), Wild (4,6--4,6), (4,2--4,6)), None, + ArbitraryAfterError ("patternClauses2", (4,6--4,6)), + (4,2--4,6), Yes, { ArrowRange = None + BarRange = Some (4,0--4,1) })], + (3,0--4,6), { MatchKeyword = (3,0--3,5) + WithKeyword = (3,13--3,17) }), (3,0--4,6))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--4,6), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(5,0)-(5,0) parse error Incomplete structured construct at or before this point in pattern +(3,13)-(3,17) parse error Unexpected end of input in 'match' or 'try' expression diff --git a/tests/service/data/SyntaxTree/Pattern/As 06.fs b/tests/service/data/SyntaxTree/Pattern/As 06.fs new file mode 100644 index 00000000000..e58ff922dbd --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 06.fs @@ -0,0 +1,3 @@ +module Module + +let _ as diff --git a/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl new file mode 100644 index 00000000000..d96b1a82ae9 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl @@ -0,0 +1,25 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 06.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + As (Wild (3,4--3,5), Wild (3,8--3,8), (3,4--3,8)), None, + ArbitraryAfterError ("localBinding2", (3,8--3,8)), (3,4--3,8), + Yes (3,0--3,8), { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = None })], (3,0--3,8))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,8), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(4,0)-(4,0) parse error Incomplete structured construct at or before this point in binding +(4,0)-(4,0) parse error Unexpected end of input in value, function or member definition +(3,0)-(3,3) parse error Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword. diff --git a/tests/service/data/SyntaxTree/Pattern/As 07.fs b/tests/service/data/SyntaxTree/Pattern/As 07.fs new file mode 100644 index 00000000000..7c22e88390c --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 07.fs @@ -0,0 +1,5 @@ +module Module + +let _ as + +() diff --git a/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl new file mode 100644 index 00000000000..9bb89467265 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl @@ -0,0 +1,25 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 07.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + As (Wild (3,4--3,5), Wild (3,8--3,8), (3,4--3,8)), None, + ArbitraryAfterError ("localBinding2", (3,8--3,8)), (3,4--3,8), + Yes (3,0--3,8), { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = None })], (3,0--3,8))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,8), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(5,0)-(5,1) parse error Incomplete structured construct at or before this point in binding +(6,0)-(6,0) parse error Unexpected end of input in value, function or member definition +(3,0)-(3,3) parse error Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword. diff --git a/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 01.fs.bsl b/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 01.fs.bsl index da447d5434b..39999d8f69c 100644 --- a/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 01.fs.bsl +++ b/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 01.fs.bsl @@ -17,13 +17,13 @@ ImplFile (FromParseError (3,6--3,6), (3,6--3,6), [], { ColonRange = Some (3,5--3,6) })), Typed - (ArbitraryAfterError ("localBinding2", (5,1--5,1)), - FromParseError (3,6--3,6), (5,1--5,1)), (3,4--3,5), - Yes (3,0--5,1), { LeadingKeyword = Let (3,0--3,3) + (ArbitraryAfterError ("localBinding2", (3,6--3,6)), + FromParseError (3,6--3,6), (3,6--3,6)), (3,4--3,5), + Yes (3,0--3,6), { LeadingKeyword = Let (3,0--3,3) InlineKeyword = None - EqualsRange = None })], (3,0--5,1))], + EqualsRange = None })], (3,0--3,6))], PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, - (1,0--5,1), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + (1,0--3,6), { LeadingKeyword = Module (1,0--1,6) })], (true, true), { ConditionalDirectives = [] CodeComments = [] }, set [])) diff --git a/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 05.fs.bsl b/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 05.fs.bsl index 89f2ca602eb..54749497087 100644 --- a/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 05.fs.bsl +++ b/tests/service/data/SyntaxTree/Pattern/Typed - Missing type 05.fs.bsl @@ -22,17 +22,18 @@ ImplFile (FromParseError (4,10--4,10), (4,10--4,10), [], { ColonRange = Some (4,9--4,10) })), Typed - (ArbitraryAfterError ("localBinding2", (6,5--6,5)), - FromParseError (4,10--4,10), (6,5--6,5)), - (4,8--4,9), Yes (4,4--6,5), + (ArbitraryAfterError + ("localBinding2", (4,10--4,10)), + FromParseError (4,10--4,10), (4,10--4,10)), + (4,8--4,9), Yes (4,4--4,10), { LeadingKeyword = Let (4,4--4,7) InlineKeyword = None EqualsRange = None })], - ArbitraryAfterError ("seqExpr", (6,5--6,5)), (4,4--6,5), - { InKeyword = None }), (4,4--6,5)), (3,0--6,5)), - (3,0--6,5))], + ArbitraryAfterError ("seqExpr", (4,10--4,10)), + (4,4--4,10), { InKeyword = None }), (4,4--4,10)), + (3,0--4,10)), (3,0--4,10))], PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, - (1,0--6,5), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + (1,0--4,10), { LeadingKeyword = Module (1,0--1,6) })], (true, true), { ConditionalDirectives = [] CodeComments = [] }, set [])) From 0d2d516ce4d8eb21f979a56c9912283393de54f0 Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 16:55:35 +0100 Subject: [PATCH 02/10] Baselines --- tests/service/PatternMatchCompilationTests.fs | 27 ++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/tests/service/PatternMatchCompilationTests.fs b/tests/service/PatternMatchCompilationTests.fs index 04da829f524..bd0c6576de7 100644 --- a/tests/service/PatternMatchCompilationTests.fs +++ b/tests/service/PatternMatchCompilationTests.fs @@ -621,6 +621,8 @@ let z as "(16,0--16,3): Unexpected syntax or possible incorrect indentation: this token is offside of context started at position (15:1). Try indenting this further.\u001dTo continue using non-conforming indentation, pass the '--strict-indentation-' flag to the compiler, or set the language version to F# 7."; "(17,16--17,17): Unexpected identifier in pattern. Expected '(' or other token."; "(20,0--20,0): Incomplete structured construct at or before this point in binding"; + "(20,0--20,0): Unexpected end of input in value, function or member definition"; + "(19,0--19,3): Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword."; "(3,13--3,17): This expression was expected to have type\u001d 'int' \u001dbut here has type\u001d 'bool'"; "(3,4--3,10): Incomplete pattern matches on this expression. For example, the value '0' may indicate a case not covered by the pattern(s)."; "(4,16--4,17): This expression was expected to have type\u001d 'bool' \u001dbut here has type\u001d 'int'"; @@ -629,6 +631,11 @@ let z as "(6,9--6,15): This runtime coercion or type test from type\u001d 'a \u001d to \u001d int \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(8,29--8,30): This expression was expected to have type\u001d 'unit' \u001dbut here has type\u001d 'int'"; "(9,26--9,27): This expression was expected to have type\u001d 'unit' \u001dbut here has type\u001d 'int'"; + "(10,15--10,16): This expression was expected to have type\u001d ''a * 'b' \u001dbut here has type\u001d 'int'"; + "(11,11--11,12): The type 'k' is not defined."; + "(12,16--12,18): This expression was expected to have type\u001d ''a list' \u001dbut here has type\u001d 'int'"; + "(12,4--12,13): Incomplete pattern matches on this expression. For example, the value '[]' may indicate a case not covered by the pattern(s)."; + "(14,4--14,12): The two sides of this 'or' pattern bind different sets of variables"; "(18,14--18,15): The value or constructor 'y' is not defined." ] @@ -953,6 +960,8 @@ let :? z as "(16,0--16,3): Unexpected syntax or possible incorrect indentation: this token is offside of context started at position (15:1). Try indenting this further.\u001dTo continue using non-conforming indentation, pass the '--strict-indentation-' flag to the compiler, or set the language version to F# 7."; "(17,19--17,20): Unexpected identifier in pattern. Expected '(' or other token."; "(20,0--20,0): Incomplete structured construct at or before this point in binding"; + "(20,0--20,0): Unexpected end of input in value, function or member definition"; + "(19,0--19,3): Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword."; "(3,7--3,8): The type 'a' is not defined."; "(3,4--3,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(4,7--4,8): The type 'b' is not defined."; @@ -967,10 +976,26 @@ let :? z as "(8,4--8,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(9,7--9,8): The type 'g' is not defined."; "(9,4--9,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(10,7--10,8): The type 'h' is not defined."; + "(10,4--10,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(10,7--10,8): The type 'h' is not defined."; + "(10,4--10,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(11,7--11,8): The type 'j' is not defined."; + "(11,4--11,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(12,7--12,8): The type 'l' is not defined."; + "(12,4--12,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(13,7--13,8): The type 'n' is not defined."; + "(13,4--13,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(14,7--14,8): The type 'p' is not defined."; + "(14,4--14,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(15,7--15,8): The type 'r' is not defined."; "(15,4--15,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(17,7--17,8): The type 'v' is not defined."; + "(17,4--17,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(18,7--18,8): The type 'x' is not defined."; - "(18,4--18,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed." + "(18,4--18,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(19,7--19,8): The type 'z' is not defined."; + "(19,4--19,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed." ] [] From 92c5b12d10ba8cff8abfc745a42ae860d5be66c1 Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 17:50:36 +0100 Subject: [PATCH 03/10] More tests --- .../service/data/SyntaxTree/Pattern/As 08.fs | 5 ++++ .../data/SyntaxTree/Pattern/As 08.fs.bsl | 23 +++++++++++++++++++ 2 files changed, 28 insertions(+) create mode 100644 tests/service/data/SyntaxTree/Pattern/As 08.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 08.fs.bsl diff --git a/tests/service/data/SyntaxTree/Pattern/As 08.fs b/tests/service/data/SyntaxTree/Pattern/As 08.fs new file mode 100644 index 00000000000..6dfd373aec5 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 08.fs @@ -0,0 +1,5 @@ +module Module + +match () with +| _ as +| _ -> () diff --git a/tests/service/data/SyntaxTree/Pattern/As 08.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 08.fs.bsl new file mode 100644 index 00000000000..48501827087 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 08.fs.bsl @@ -0,0 +1,23 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 08.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Expr + (Match + (Yes (3,0--3,13), Const (Unit, (3,6--3,8)), + [SynMatchClause + (Or + (As (Wild (4,2--4,3), Wild (4,6--4,6), (4,2--4,6)), + Wild (5,2--5,3), (4,2--5,3), { BarRange = (5,0--5,1) }), + None, Const (Unit, (5,7--5,9)), (4,2--5,9), Yes, + { ArrowRange = Some (5,4--5,6) + BarRange = Some (4,0--4,1) })], (3,0--5,9), + { MatchKeyword = (3,0--3,5) + WithKeyword = (3,9--3,13) }), (3,0--5,9))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--5,9), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(5,0)-(5,1) parse error Unexpected symbol '|' in pattern From 9405100327e8cce752b3a989be4dd25f9282e301 Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 17:51:00 +0100 Subject: [PATCH 04/10] More recovery --- src/Compiler/pars.fsy | 6 ++++ .../data/SyntaxTree/Pattern/As 04.fs.bsl | 2 +- .../data/SyntaxTree/Pattern/As 06.fs.bsl | 5 ++- .../data/SyntaxTree/Pattern/As 07.fs.bsl | 10 +++--- .../service/data/SyntaxTree/Pattern/As 09.fs | 5 +++ .../data/SyntaxTree/Pattern/As 09.fs.bsl | 36 +++++++++++++++++++ 6 files changed, 55 insertions(+), 9 deletions(-) create mode 100644 tests/service/data/SyntaxTree/Pattern/As 09.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 09.fs.bsl diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index 3a6d2c75f17..15227a3d2d6 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -3461,6 +3461,12 @@ headBindingPattern: let pat2 = SynPat.Wild(mAs.EndRange) SynPat.As($1, pat2, rhs2 parseState 1 2) } + | headBindingPattern AS + { let mAs = rhs parseState 2 + reportParseErrorAt mAs (FSComp.SR.parsExpectingPattern ()) + let pat2 = SynPat.Wild(mAs.EndRange) + SynPat.As($1, pat2, rhs2 parseState 1 2) } + | headBindingPattern BAR headBindingPattern { let mBar = rhs parseState 2 SynPat.Or($1, $3, rhs2 parseState 1 3, { BarRange = mBar }) } diff --git a/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl index c2a98cfee37..dbbdbdd9f3e 100644 --- a/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl +++ b/tests/service/data/SyntaxTree/Pattern/As 04.fs.bsl @@ -20,4 +20,4 @@ ImplFile { ConditionalDirectives = [] CodeComments = [] }, set [])) -(3,9)-(3,10) parse error Unexpected symbol '=' in binding +(3,6)-(3,8) parse error Expecting pattern diff --git a/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl index d96b1a82ae9..5ce6e55db4d 100644 --- a/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl +++ b/tests/service/data/SyntaxTree/Pattern/As 06.fs.bsl @@ -20,6 +20,5 @@ ImplFile { ConditionalDirectives = [] CodeComments = [] }, set [])) -(4,0)-(4,0) parse error Incomplete structured construct at or before this point in binding -(4,0)-(4,0) parse error Unexpected end of input in value, function or member definition -(3,0)-(3,3) parse error Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword. +(3,6)-(3,8) parse error Expecting pattern +(4,0)-(4,0) parse error Incomplete structured construct at or before this point in binding. Expected '=' or other token. diff --git a/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl index 9bb89467265..b462b81d90b 100644 --- a/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl +++ b/tests/service/data/SyntaxTree/Pattern/As 07.fs.bsl @@ -14,12 +14,12 @@ ImplFile ArbitraryAfterError ("localBinding2", (3,8--3,8)), (3,4--3,8), Yes (3,0--3,8), { LeadingKeyword = Let (3,0--3,3) InlineKeyword = None - EqualsRange = None })], (3,0--3,8))], + EqualsRange = None })], (3,0--3,8)); + Expr (Const (Unit, (5,0--5,2)), (5,0--5,2))], PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, - (1,0--3,8), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + (1,0--5,2), { LeadingKeyword = Module (1,0--1,6) })], (true, true), { ConditionalDirectives = [] CodeComments = [] }, set [])) -(5,0)-(5,1) parse error Incomplete structured construct at or before this point in binding -(6,0)-(6,0) parse error Unexpected end of input in value, function or member definition -(3,0)-(3,3) parse error Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword. +(3,6)-(3,8) parse error Expecting pattern +(5,0)-(5,1) parse error Incomplete structured construct at or before this point in binding. Expected '=' or other token. diff --git a/tests/service/data/SyntaxTree/Pattern/As 09.fs b/tests/service/data/SyntaxTree/Pattern/As 09.fs new file mode 100644 index 00000000000..21cb82c90e6 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 09.fs @@ -0,0 +1,5 @@ +module Module + +let _ as + +let _ = () diff --git a/tests/service/data/SyntaxTree/Pattern/As 09.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 09.fs.bsl new file mode 100644 index 00000000000..ad9aa2247c1 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 09.fs.bsl @@ -0,0 +1,36 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 09.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + As (Wild (3,4--3,5), Wild (3,8--3,8), (3,4--3,8)), None, + ArbitraryAfterError ("localBinding2", (3,8--3,8)), (3,4--3,8), + Yes (3,0--3,8), { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = None })], (3,0--3,8)); + Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((5,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + Wild (5,4--5,5), None, Const (Unit, (5,8--5,10)), (5,4--5,5), + Yes (5,0--5,10), { LeadingKeyword = Let (5,0--5,3) + InlineKeyword = None + EqualsRange = Some (5,6--5,7) })], + (5,0--5,10))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--5,10), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(3,6)-(3,8) parse error Expecting pattern +(5,0)-(5,3) parse error Incomplete structured construct at or before this point in binding. Expected '=' or other token. From b0e534afbe0222046b85f0d048a91aae7b084dcf Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 18:05:50 +0100 Subject: [PATCH 05/10] More tests --- .../service/data/SyntaxTree/Pattern/As 10.fs | 3 ++ .../data/SyntaxTree/Pattern/As 10.fs.bsl | 25 +++++++++++++++++ .../service/data/SyntaxTree/Pattern/As 11.fs | 3 ++ .../data/SyntaxTree/Pattern/As 11.fs.bsl | 28 +++++++++++++++++++ 4 files changed, 59 insertions(+) create mode 100644 tests/service/data/SyntaxTree/Pattern/As 10.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 10.fs.bsl create mode 100644 tests/service/data/SyntaxTree/Pattern/As 11.fs create mode 100644 tests/service/data/SyntaxTree/Pattern/As 11.fs.bsl diff --git a/tests/service/data/SyntaxTree/Pattern/As 10.fs b/tests/service/data/SyntaxTree/Pattern/As 10.fs new file mode 100644 index 00000000000..29def47e36b --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 10.fs @@ -0,0 +1,3 @@ +module Module + +let (_ as ) = () diff --git a/tests/service/data/SyntaxTree/Pattern/As 10.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 10.fs.bsl new file mode 100644 index 00000000000..2b44d412f46 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 10.fs.bsl @@ -0,0 +1,25 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 10.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + Paren + (As (Wild (3,5--3,6), Wild (3,9--3,9), (3,5--3,9)), + (3,4--3,11)), None, Const (Unit, (3,14--3,16)), (3,4--3,11), + Yes (3,0--3,16), { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = Some (3,12--3,13) })], + (3,0--3,16))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,16), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(3,10)-(3,11) parse error Unexpected symbol ')' in pattern diff --git a/tests/service/data/SyntaxTree/Pattern/As 11.fs b/tests/service/data/SyntaxTree/Pattern/As 11.fs new file mode 100644 index 00000000000..53c1496b72c --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 11.fs @@ -0,0 +1,3 @@ +module Module + +let 1 as , 3 = () diff --git a/tests/service/data/SyntaxTree/Pattern/As 11.fs.bsl b/tests/service/data/SyntaxTree/Pattern/As 11.fs.bsl new file mode 100644 index 00000000000..84773ba8ee6 --- /dev/null +++ b/tests/service/data/SyntaxTree/Pattern/As 11.fs.bsl @@ -0,0 +1,28 @@ +ImplFile + (ParsedImplFileInput + ("/root/Pattern/As 11.fs", false, QualifiedNameOfFile Module, [], [], + [SynModuleOrNamespace + ([Module], false, NamedModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None), + Tuple + (false, + [As + (Const (Int32 1, (3,4--3,5)), Wild (3,8--3,8), + (3,4--3,8)); Const (Int32 3, (3,11--3,12))], + [(3,9--3,10)], (3,4--3,12)), None, + Const (Unit, (3,15--3,17)), (3,4--3,12), Yes (3,0--3,17), + { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = Some (3,13--3,14) })], (3,0--3,17))], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), [], None, + (1,0--3,17), { LeadingKeyword = Module (1,0--1,6) })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(3,6)-(3,8) parse error Expecting pattern From 9fa13e3c631fe2a3f8c9bc0af03782eee997d1cc Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 18:17:22 +0100 Subject: [PATCH 06/10] Remove unused rule --- src/Compiler/pars.fsy | 5 ----- 1 file changed, 5 deletions(-) diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index 15227a3d2d6..4a7e4698d05 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -3456,11 +3456,6 @@ headBindingPattern: | headBindingPattern AS constrPattern { SynPat.As($1, $3, rhs2 parseState 1 3) } - | headBindingPattern AS recover - { let mAs = rhs parseState 2 - let pat2 = SynPat.Wild(mAs.EndRange) - SynPat.As($1, pat2, rhs2 parseState 1 2) } - | headBindingPattern AS { let mAs = rhs parseState 2 reportParseErrorAt mAs (FSComp.SR.parsExpectingPattern ()) From 13aff58862481c84e334541332fb0b45c548048f Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 18:24:44 +0100 Subject: [PATCH 07/10] Baselines --- tests/service/PatternMatchCompilationTests.fs | 28 +++++++------------ 1 file changed, 10 insertions(+), 18 deletions(-) diff --git a/tests/service/PatternMatchCompilationTests.fs b/tests/service/PatternMatchCompilationTests.fs index bd0c6576de7..8b616d78461 100644 --- a/tests/service/PatternMatchCompilationTests.fs +++ b/tests/service/PatternMatchCompilationTests.fs @@ -611,18 +611,15 @@ let x as () = y let z as """ dumpDiagnostics checkResults |> shouldEqual [ - "(10,9--10,10): Unexpected symbol ',' in binding"; - "(11,9--11,10): Unexpected symbol ':' in binding"; - "(12,9--12,11): Unexpected symbol '::' in binding"; - "(13,9--13,10): Unexpected symbol '&' in binding"; - "(14,9--14,10): Unexpected symbol '|' in binding"; + "(10,6--10,8): Expecting pattern"; "(11,6--11,8): Expecting pattern"; + "(12,6--12,8): Expecting pattern"; "(13,6--13,8): Expecting pattern"; + "(14,6--14,8): Expecting pattern"; "(15,13--15,14): Unexpected symbol '=' in pattern. Expected ')' or other token."; "(15,9--15,10): Unmatched '('"; "(16,0--16,3): Unexpected syntax or possible incorrect indentation: this token is offside of context started at position (15:1). Try indenting this further.\u001dTo continue using non-conforming indentation, pass the '--strict-indentation-' flag to the compiler, or set the language version to F# 7."; "(17,16--17,17): Unexpected identifier in pattern. Expected '(' or other token."; - "(20,0--20,0): Incomplete structured construct at or before this point in binding"; - "(20,0--20,0): Unexpected end of input in value, function or member definition"; - "(19,0--19,3): Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword."; + "(19,6--19,8): Expecting pattern"; + "(20,0--20,0): Incomplete structured construct at or before this point in binding. Expected '=' or other token."; "(3,13--3,17): This expression was expected to have type\u001d 'int' \u001dbut here has type\u001d 'bool'"; "(3,4--3,10): Incomplete pattern matches on this expression. For example, the value '0' may indicate a case not covered by the pattern(s)."; "(4,16--4,17): This expression was expected to have type\u001d 'bool' \u001dbut here has type\u001d 'int'"; @@ -950,18 +947,15 @@ let :? x as () = y let :? z as """ dumpDiagnostics checkResults |> shouldEqual [ - "(10,12--10,13): Unexpected symbol ',' in binding"; - "(11,12--11,13): Unexpected symbol ':' in binding"; - "(12,12--12,14): Unexpected symbol '::' in binding"; - "(13,12--13,13): Unexpected symbol '&' in binding"; - "(14,12--14,13): Unexpected symbol '|' in binding"; + "(10,9--10,11): Expecting pattern"; "(11,9--11,11): Expecting pattern"; + "(12,9--12,11): Expecting pattern"; "(13,9--13,11): Expecting pattern"; + "(14,9--14,11): Expecting pattern"; "(15,16--15,17): Unexpected symbol '=' in pattern. Expected ')' or other token."; "(15,12--15,13): Unmatched '('"; "(16,0--16,3): Unexpected syntax or possible incorrect indentation: this token is offside of context started at position (15:1). Try indenting this further.\u001dTo continue using non-conforming indentation, pass the '--strict-indentation-' flag to the compiler, or set the language version to F# 7."; "(17,19--17,20): Unexpected identifier in pattern. Expected '(' or other token."; - "(20,0--20,0): Incomplete structured construct at or before this point in binding"; - "(20,0--20,0): Unexpected end of input in value, function or member definition"; - "(19,0--19,3): Incomplete value or function definition. If this is in an expression, the body of the expression must be indented to the same column as the 'let' keyword."; + "(19,9--19,11): Expecting pattern"; + "(20,0--20,0): Incomplete structured construct at or before this point in binding. Expected '=' or other token."; "(3,7--3,8): The type 'a' is not defined."; "(3,4--3,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(4,7--4,8): The type 'b' is not defined."; @@ -990,8 +984,6 @@ let :? z as "(14,4--14,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(15,7--15,8): The type 'r' is not defined."; "(15,4--15,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; - "(17,7--17,8): The type 'v' is not defined."; - "(17,4--17,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(18,7--18,8): The type 'x' is not defined."; "(18,4--18,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(19,7--19,8): The type 'z' is not defined."; From 9d23be83bf2a54c204900e90c79b7e61c445d5cf Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Thu, 7 Dec 2023 20:50:30 +0100 Subject: [PATCH 08/10] Restore the rule --- src/Compiler/pars.fsy | 5 +++++ tests/service/PatternMatchCompilationTests.fs | 2 ++ 2 files changed, 7 insertions(+) diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index 4a7e4698d05..15227a3d2d6 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -3456,6 +3456,11 @@ headBindingPattern: | headBindingPattern AS constrPattern { SynPat.As($1, $3, rhs2 parseState 1 3) } + | headBindingPattern AS recover + { let mAs = rhs parseState 2 + let pat2 = SynPat.Wild(mAs.EndRange) + SynPat.As($1, pat2, rhs2 parseState 1 2) } + | headBindingPattern AS { let mAs = rhs parseState 2 reportParseErrorAt mAs (FSComp.SR.parsExpectingPattern ()) diff --git a/tests/service/PatternMatchCompilationTests.fs b/tests/service/PatternMatchCompilationTests.fs index 8b616d78461..30cfd0e03dc 100644 --- a/tests/service/PatternMatchCompilationTests.fs +++ b/tests/service/PatternMatchCompilationTests.fs @@ -984,6 +984,8 @@ let :? z as "(14,4--14,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(15,7--15,8): The type 'r' is not defined."; "(15,4--15,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; + "(17,7--17,8): The type 'v' is not defined."; + "(17,4--17,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(18,7--18,8): The type 'x' is not defined."; "(18,4--18,8): This runtime coercion or type test from type\u001d 'a \u001d to \u001d 'b \u001dinvolves an indeterminate type based on information prior to this program point. Runtime type tests are not allowed on some types. Further type annotations are needed."; "(19,7--19,8): The type 'z' is not defined."; From 6b787de73510d72fbd3e10ff9359a9e3c0131e8e Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Sun, 10 Dec 2023 09:38:11 +0100 Subject: [PATCH 09/10] Update baseline --- tests/service/PatternMatchCompilationTests.fs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/service/PatternMatchCompilationTests.fs b/tests/service/PatternMatchCompilationTests.fs index 30cfd0e03dc..d05e9732a88 100644 --- a/tests/service/PatternMatchCompilationTests.fs +++ b/tests/service/PatternMatchCompilationTests.fs @@ -1226,7 +1226,8 @@ let y as ?z = 8 () """ dumpDiagnostics checkResults |> shouldEqual [ - "(7,9--7,11): Unexpected symbol '[<' in binding" + "(7,6--7,8): Expecting pattern"; + "(7,9--7,11): Unexpected symbol '[<' in binding. Expected '=' or other token." "(8,4--8,11): This is not a valid pattern" "(8,4--8,16): Incomplete pattern matches on this expression." "(9,9--9,16): This is not a valid pattern" From 5f30a7e217952f067c94e79718cb9ae0d11d955c Mon Sep 17 00:00:00 2001 From: Eugene Auduchinok Date: Tue, 12 Dec 2023 12:29:06 +0100 Subject: [PATCH 10/10] Update baseline --- tests/service/PatternMatchCompilationTests.fs | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/service/PatternMatchCompilationTests.fs b/tests/service/PatternMatchCompilationTests.fs index d05e9732a88..c75225aae0c 100644 --- a/tests/service/PatternMatchCompilationTests.fs +++ b/tests/service/PatternMatchCompilationTests.fs @@ -611,8 +611,10 @@ let x as () = y let z as """ dumpDiagnostics checkResults |> shouldEqual [ - "(10,6--10,8): Expecting pattern"; "(11,6--11,8): Expecting pattern"; - "(12,6--12,8): Expecting pattern"; "(13,6--13,8): Expecting pattern"; + "(10,6--10,8): Expecting pattern"; + "(11,6--11,8): Expecting pattern"; + "(12,6--12,8): Expecting pattern"; + "(13,6--13,8): Expecting pattern"; "(14,6--14,8): Expecting pattern"; "(15,13--15,14): Unexpected symbol '=' in pattern. Expected ')' or other token."; "(15,9--15,10): Unmatched '('"; @@ -947,8 +949,10 @@ let :? x as () = y let :? z as """ dumpDiagnostics checkResults |> shouldEqual [ - "(10,9--10,11): Expecting pattern"; "(11,9--11,11): Expecting pattern"; - "(12,9--12,11): Expecting pattern"; "(13,9--13,11): Expecting pattern"; + "(10,9--10,11): Expecting pattern"; + "(11,9--11,11): Expecting pattern"; + "(12,9--12,11): Expecting pattern"; + "(13,9--13,11): Expecting pattern"; "(14,9--14,11): Expecting pattern"; "(15,16--15,17): Unexpected symbol '=' in pattern. Expected ')' or other token."; "(15,12--15,13): Unmatched '('";