From 7d7bc6e2725cd4b1a769ffe762563ea97f3312b8 Mon Sep 17 00:00:00 2001 From: "Alexey.Berezhnykh" Date: Mon, 13 Nov 2023 22:15:24 +0300 Subject: [PATCH 1/2] wip --- src/Compiler/pars.fsy | 22 ++++++ .../Language/DotLambdaTests.fs | 4 +- .../DotLambda - _ Recovery - Casts.fsx | 3 + .../DotLambda - _ Recovery - Casts.fsx.bsl | 70 +++++++++++++++++++ .../DotLambda - _ Recovery - Eof.fsx | 1 + .../DotLambda - _ Recovery - Eof.fsx.bsl | 23 ++++++ .../Expression/DotLambda - _ Recovery.fsx | 1 + .../Expression/DotLambda - _ Recovery.fsx.bsl | 15 ++++ .../DotLambda - _. Recovery - Eof.fsx | 1 + .../DotLambda - _. Recovery - Eof.fsx.bsl | 26 +++++++ .../Expression/DotLambda - _. Recovery.fsx | 1 + .../DotLambda - _. Recovery.fsx.bsl | 18 +++++ 12 files changed, 182 insertions(+), 3 deletions(-) create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx.bsl create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx.bsl create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx.bsl create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx create mode 100644 tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl diff --git a/src/Compiler/pars.fsy b/src/Compiler/pars.fsy index 3a9e75023cd..1e44ef874da 100644 --- a/src/Compiler/pars.fsy +++ b/src/Compiler/pars.fsy @@ -4885,6 +4885,28 @@ atomicExpr: let trivia: SynExprDotLambdaTrivia = { UnderscoreRange = mUnderscore ; DotRange = mDot } SynExpr.DotLambda(expr, unionRanges mUnderscore expr.Range, trivia), false } + + | UNDERSCORE DOT recover %prec dot_lambda + { let mUnderscore = rhs parseState 1 + let mDot = rhs parseState 2 + let mWhole = unionRanges mUnderscore mDot + parseState.LexBuffer.CheckLanguageFeatureAndRecover LanguageFeature.AccessorFunctionShorthand mWhole + + let mExpr = mDot.EndRange + if not $3 then reportParseErrorAt mDot (FSComp.SR.parsUnexpectedEndOfFileExpression()) + + let expr = arbExpr ("dotLambda1", mExpr) + let trivia: SynExprDotLambdaTrivia = { UnderscoreRange = mUnderscore ; DotRange = mDot } + SynExpr.DotLambda(expr, mWhole, trivia), false } + + | UNDERSCORE recover %prec dot_lambda + { let mUnderscore = rhs parseState 1 + + if not $2 then reportParseErrorAt mUnderscore (FSComp.SR.parsUnexpectedEndOfFileExpression()) + + let expr = SynExpr.Ident(Ident("_", mUnderscore)) + SynExpr.FromParseError(expr, mUnderscore), false } + | atomicExpr HIGH_PRECEDENCE_BRACK_APP atomicExpr { let arg1, _ = $1 let arg2, hpa = $3 diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index a91045f49a2..f0e5c77e865 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -173,9 +173,7 @@ let c = ( _ :> obj) """ |> withDiagnostics [ Error 10, Line 2, Col 20, Line 2, Col 21, "Unexpected symbol ')' in expression. Expected '.' or other token." Error 10, Line 3, Col 13, Line 3, Col 15, "Unexpected symbol ':>' in expression. Expected '.' or other token." - Error 583, Line 3, Col 9, Line 3, Col 10, "Unmatched '('" - Error 10, Line 4, Col 13, Line 4, Col 15, "Unexpected symbol ':>' in expression. Expected '.' or other token." - Error 583, Line 4, Col 9, Line 4, Col 10, "Unmatched '('"] + Error 10, Line 4, Col 13, Line 4, Col 15, "Unexpected symbol ':>' in expression. Expected '.' or other token."] [] let ``ToString with F# 7`` () = diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx new file mode 100644 index 00000000000..6791dc6547a --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx @@ -0,0 +1,3 @@ +let a = ( upcast _ ) : obj +let b = ( _ :> _ ) : obj +let c = ( _ :> obj) diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx.bsl new file mode 100644 index 00000000000..b65fe6bd9c6 --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Casts.fsx.bsl @@ -0,0 +1,70 @@ +ImplFile + (ParsedImplFileInput + ("/root/Expression/DotLambda - _ Recovery - Casts.fsx", true, + QualifiedNameOfFile DotLambda - _ Recovery - Casts$fsx, [], [], + [SynModuleOrNamespace + ([DotLambda - _ Recovery - Casts], false, AnonModule, + [Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((1,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None, + None), Named (SynIdent (a, None), false, None, (1,4--1,5)), + None, + Typed + (Paren + (InferredUpcast + (FromParseError (Ident _, (1,17--1,18)), (1,10--1,18)), + (1,8--1,9), Some (1,19--1,20), (1,8--1,20)), + LongIdent (SynLongIdent ([obj], [], [None])), (1,8--1,26)), + (1,4--1,5), Yes (1,0--1,26), { LeadingKeyword = Let (1,0--1,3) + InlineKeyword = None + EqualsRange = Some (1,6--1,7) })], + (1,0--1,26)); + Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((2,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None, + None), Named (SynIdent (b, None), false, None, (2,4--2,5)), + None, + Typed + (Paren + (Upcast + (FromParseError (Ident _, (2,10--2,11)), + Anon (2,15--2,16), (2,10--2,16)), (2,8--2,9), + Some (2,17--2,18), (2,8--2,18)), + LongIdent (SynLongIdent ([obj], [], [None])), (2,8--2,24)), + (2,4--2,5), Yes (2,0--2,24), { LeadingKeyword = Let (2,0--2,3) + InlineKeyword = None + EqualsRange = Some (2,6--2,7) })], + (2,0--2,24)); + Let + (false, + [SynBinding + (None, Normal, false, false, [], + PreXmlDoc ((3,0), FSharp.Compiler.Xml.XmlDocCollector), + SynValData + (None, SynValInfo ([], SynArgInfo ([], false, None)), None, + None), Named (SynIdent (c, None), false, None, (3,4--3,5)), + None, + Paren + (Upcast + (FromParseError (Ident _, (3,10--3,11)), + LongIdent (SynLongIdent ([obj], [], [None])), + (3,10--3,18)), (3,8--3,9), Some (3,18--3,19), + (3,8--3,19)), (3,4--3,5), Yes (3,0--3,19), + { LeadingKeyword = Let (3,0--3,3) + InlineKeyword = None + EqualsRange = Some (3,6--3,7) })], (3,0--3,19))], + PreXmlDocEmpty, [], None, (1,0--4,0), { LeadingKeyword = None })], + (true, true), { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(1,19)-(1,20) parse error Unexpected symbol ')' in expression. Expected '.' or other token. +(2,12)-(2,14) parse error Unexpected symbol ':>' in expression. Expected '.' or other token. +(3,12)-(3,14) parse error Unexpected symbol ':>' in expression. Expected '.' or other token. diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx new file mode 100644 index 00000000000..3454fffae8c --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx @@ -0,0 +1 @@ +1 |> _ \ No newline at end of file diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx.bsl new file mode 100644 index 00000000000..f481a08bdd5 --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery - Eof.fsx.bsl @@ -0,0 +1,23 @@ +ImplFile + (ParsedImplFileInput + ("/root/Expression/DotLambda - _ Recovery - Eof.fsx", true, + QualifiedNameOfFile DotLambda - _ Recovery - Eof$fsx, [], [], + [SynModuleOrNamespace + ([DotLambda - _ Recovery - Eof], false, AnonModule, + [Expr + (App + (NonAtomic, false, + App + (NonAtomic, true, + LongIdent + (false, + SynLongIdent + ([op_PipeRight], [], [Some (OriginalNotation "|>")]), + None, (1,2--1,4)), Const (Int32 1, (1,0--1,1)), + (1,0--1,4)), FromParseError (Ident _, (1,5--1,6)), + (1,0--1,6)), (1,0--1,6))], PreXmlDocEmpty, [], None, (1,0--1,6), + { LeadingKeyword = None })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(1,5)-(1,6) parse error Unexpected end of input in expression diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx new file mode 100644 index 00000000000..4c34cbc60d2 --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx @@ -0,0 +1 @@ +(_) diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx.bsl new file mode 100644 index 00000000000..1dfda19d13b --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _ Recovery.fsx.bsl @@ -0,0 +1,15 @@ +ImplFile + (ParsedImplFileInput + ("/root/Expression/DotLambda - _ Recovery.fsx", true, + QualifiedNameOfFile DotLambda - _ Recovery$fsx, [], [], + [SynModuleOrNamespace + ([DotLambda - _ Recovery], false, AnonModule, + [Expr + (Paren + (FromParseError (Ident _, (1,1--1,2)), (1,0--1,1), + Some (1,2--1,3), (1,0--1,3)), (1,0--1,3))], PreXmlDocEmpty, [], + None, (1,0--1,3), { LeadingKeyword = None })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(1,2)-(1,3) parse error Unexpected symbol ')' in expression. Expected '.' or other token. diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx new file mode 100644 index 00000000000..fa28bf307bf --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx @@ -0,0 +1 @@ +1 |> _. \ No newline at end of file diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl new file mode 100644 index 00000000000..f265a269f44 --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl @@ -0,0 +1,26 @@ +ImplFile + (ParsedImplFileInput + ("/root/Expression/DotLambda - _. Recovery - Eof.fsx", true, + QualifiedNameOfFile DotLambda - _. Recovery - Eof$fsx, [], [], + [SynModuleOrNamespace + ([DotLambda - _; Recovery - Eof], false, AnonModule, + [Expr + (App + (NonAtomic, false, + App + (NonAtomic, true, + LongIdent + (false, + SynLongIdent + ([op_PipeRight], [], [Some (OriginalNotation "|>")]), + None, (1,2--1,4)), Const (Int32 1, (1,0--1,1)), + (1,0--1,4)), + DotLambda + (ArbitraryAfterError ("dotLambda1", (1,7--1,7)), (1,5--1,7), + { UnderscoreRange = (1,5--1,6) + DotRange = Some (1,6--1,7) }), (1,0--1,7)), (1,0--1,7))], + PreXmlDocEmpty, [], None, (1,0--1,7), { LeadingKeyword = None })], + (true, true), { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(1,6)-(1,7) parse error Unexpected end of input in expression diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx new file mode 100644 index 00000000000..56d26b9c9d0 --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx @@ -0,0 +1 @@ +(_.) diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl new file mode 100644 index 00000000000..2e31003ce7d --- /dev/null +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl @@ -0,0 +1,18 @@ +ImplFile + (ParsedImplFileInput + ("/root/Expression/DotLambda - _. Recovery.fsx", true, + QualifiedNameOfFile DotLambda - _. Recovery$fsx, [], [], + [SynModuleOrNamespace + ([DotLambda - _; Recovery], false, AnonModule, + [Expr + (Paren + (DotLambda + (ArbitraryAfterError ("dotLambda1", (1,3--1,3)), (1,1--1,3), + { UnderscoreRange = (1,1--1,2) + DotRange = Some (1,2--1,3) }), (1,0--1,1), Some (1,3--1,4), + (1,0--1,4)), (1,0--1,4))], PreXmlDocEmpty, [], None, (1,0--1,4), + { LeadingKeyword = None })], (true, true), + { ConditionalDirectives = [] + CodeComments = [] }, set [])) + +(1,3)-(1,4) parse error Unexpected symbol ')' in expression From 6a16eaa2cac127ab547348ce6e13a68dc3a7ccab Mon Sep 17 00:00:00 2001 From: "Alexey.Berezhnykh" Date: Mon, 13 Nov 2023 22:20:36 +0300 Subject: [PATCH 2/2] wip --- .../SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl | 2 +- .../data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl index f265a269f44..878b39bfb7a 100644 --- a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery - Eof.fsx.bsl @@ -18,7 +18,7 @@ ImplFile DotLambda (ArbitraryAfterError ("dotLambda1", (1,7--1,7)), (1,5--1,7), { UnderscoreRange = (1,5--1,6) - DotRange = Some (1,6--1,7) }), (1,0--1,7)), (1,0--1,7))], + DotRange = (1,6--1,7) }), (1,0--1,7)), (1,0--1,7))], PreXmlDocEmpty, [], None, (1,0--1,7), { LeadingKeyword = None })], (true, true), { ConditionalDirectives = [] CodeComments = [] }, set [])) diff --git a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl index 2e31003ce7d..0bc367b4df3 100644 --- a/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl +++ b/tests/service/data/SyntaxTree/Expression/DotLambda - _. Recovery.fsx.bsl @@ -9,7 +9,7 @@ ImplFile (DotLambda (ArbitraryAfterError ("dotLambda1", (1,3--1,3)), (1,1--1,3), { UnderscoreRange = (1,1--1,2) - DotRange = Some (1,2--1,3) }), (1,0--1,1), Some (1,3--1,4), + DotRange = (1,2--1,3) }), (1,0--1,1), Some (1,3--1,4), (1,0--1,4)), (1,0--1,4))], PreXmlDocEmpty, [], None, (1,0--1,4), { LeadingKeyword = None })], (true, true), { ConditionalDirectives = []