From 204bf4e1ffc80b3a9412911a2aaa9fd796d7675f Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Sat, 24 Feb 2024 23:23:01 +0000 Subject: [PATCH 1/9] Error when property has same name as DU case --- src/Compiler/Checking/CheckExpressions.fs | 11 ++++++- .../Language/DotLambdaTests.fs | 29 ++++++++++++++++++- 2 files changed, 38 insertions(+), 2 deletions(-) diff --git a/src/Compiler/Checking/CheckExpressions.fs b/src/Compiler/Checking/CheckExpressions.fs index 3466b162c3a..9c43c731e8b 100644 --- a/src/Compiler/Checking/CheckExpressions.fs +++ b/src/Compiler/Checking/CheckExpressions.fs @@ -9416,6 +9416,16 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed TcTraitItemThen cenv overallTy env (Some objExpr) traitInfo tpenv mItem delayed | Item.DelegateCtor _ -> error (Error (FSComp.SR.tcConstructorsCannotBeFirstClassValues(), mItem)) + + | Item.UnionCase(info, _) -> + let clashingName = + info.TyconRef.MembersOfFSharpTyconSorted |> List.tryFind (fun mem -> mem.DisplayNameCore = info.DisplayNameCore) + + match clashingName with + | None -> PropagateThenTcDelayed cenv overallTy env tpenv mExprAndItem (MakeApplicableExprWithFlex cenv env objExpr) objExprTy ExprAtomicFlag.Atomic delayed + | Some value -> + let kind = (if value.IsMember then "member" else "value") + error(NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) // These items are not expected here - they can't be the result of a instance member dot-lookup "expr.Ident" | Item.ActivePatternResult _ @@ -9426,7 +9436,6 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed | Item.ModuleOrNamespaces _ | Item.TypeVar _ | Item.Types _ - | Item.UnionCase _ | Item.UnionCaseField _ | Item.UnqualifiedType _ | Item.Value _ diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index 6dff28ab6a7..356189a4006 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -290,4 +290,31 @@ let _ = asQ.Select _.Length """ |> withLangVersion80 |> typecheck - |> shouldSucceed \ No newline at end of file + |> shouldSucceed + +[] + let ``Error when property has same name as DU case`` () = + Fsx """ +type MyId = + | IdA of int + | IdB of string + + member this.IdA = + match this with + | IdA x -> Some x + | _ -> None + + member this.IdX = + match this with + | IdB x -> Some x + | _ -> None + +let onlyIdX (ids: MyId list) = ids |> List.choose _.IdX +let onlyIdA (ids: MyId list) = ids |> List.choose _.IdA + """ + |> ignoreWarnings + |> compile + |> shouldFail + |> withDiagnostics [ + (Error 23, Line 17, Col 51, Line 17, Col 56, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") + ] \ No newline at end of file From 4ffef239c9a949033634b78014271280b4dba348 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Sun, 25 Feb 2024 15:18:17 +0000 Subject: [PATCH 2/9] Update tests --- .../NameResolution/Misc/E_ClashingIdentifiersDU02.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs index 90b8cc0d3dd..c1744d434f7 100644 --- a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs +++ b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs @@ -2,7 +2,7 @@ // Regression test for FSHARP1.0:2364 // Clashing union case label and property //The member 'ClashingID' can not be defined because the name 'ClashingID' clashes with the union case 'ClashingID' in this type or module -//The syntax 'expr\.id' may only be used with record labels, properties and fields +//The member 'ClashingID' can not be defined because the name 'ClashingID' clashes with the union case 'ClashingID' in this type or module module M= type Suit = From 3f0f6b63d869b5f45a38f4c66430ca01b8b95eee Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Sun, 25 Feb 2024 21:01:27 +0000 Subject: [PATCH 3/9] fix test --- .../NameResolution/Misc/E_ClashingIdentifiersDU02.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs index c1744d434f7..90b8cc0d3dd 100644 --- a/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs +++ b/tests/fsharpqa/Source/Conformance/InferenceProcedures/NameResolution/Misc/E_ClashingIdentifiersDU02.fs @@ -2,7 +2,7 @@ // Regression test for FSHARP1.0:2364 // Clashing union case label and property //The member 'ClashingID' can not be defined because the name 'ClashingID' clashes with the union case 'ClashingID' in this type or module -//The member 'ClashingID' can not be defined because the name 'ClashingID' clashes with the union case 'ClashingID' in this type or module +//The syntax 'expr\.id' may only be used with record labels, properties and fields module M= type Suit = From 115c17f954aa18bdccaf6c0b2b10e070b47778e5 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Mon, 26 Feb 2024 20:29:51 +0000 Subject: [PATCH 4/9] update condition --- src/Compiler/Checking/CheckExpressions.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Compiler/Checking/CheckExpressions.fs b/src/Compiler/Checking/CheckExpressions.fs index 9c43c731e8b..692b7a2ec5f 100644 --- a/src/Compiler/Checking/CheckExpressions.fs +++ b/src/Compiler/Checking/CheckExpressions.fs @@ -9422,7 +9422,7 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed info.TyconRef.MembersOfFSharpTyconSorted |> List.tryFind (fun mem -> mem.DisplayNameCore = info.DisplayNameCore) match clashingName with - | None -> PropagateThenTcDelayed cenv overallTy env tpenv mExprAndItem (MakeApplicableExprWithFlex cenv env objExpr) objExprTy ExprAtomicFlag.Atomic delayed + | None -> error (Error (FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) | Some value -> let kind = (if value.IsMember then "member" else "value") error(NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) From e5e8c1a627af9ddd33c41489ad0a649ef90dd43a Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Thu, 25 Apr 2024 17:20:57 +0100 Subject: [PATCH 5/9] Three is better than one --- src/Compiler/Checking/CheckExpressions.fs | 18 +++++++++--------- .../Language/DotLambdaTests.fs | 5 +++-- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/src/Compiler/Checking/CheckExpressions.fs b/src/Compiler/Checking/CheckExpressions.fs index 692b7a2ec5f..8d6a358e042 100644 --- a/src/Compiler/Checking/CheckExpressions.fs +++ b/src/Compiler/Checking/CheckExpressions.fs @@ -9418,15 +9418,15 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed | Item.DelegateCtor _ -> error (Error (FSComp.SR.tcConstructorsCannotBeFirstClassValues(), mItem)) | Item.UnionCase(info, _) -> - let clashingName = - info.TyconRef.MembersOfFSharpTyconSorted |> List.tryFind (fun mem -> mem.DisplayNameCore = info.DisplayNameCore) - - match clashingName with - | None -> error (Error (FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) - | Some value -> - let kind = (if value.IsMember then "member" else "value") - error(NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) - + let clashingNames = info.Tycon.MembersOfFSharpTyconSorted + for value in clashingNames do + if value.DisplayNameCore = info.DisplayNameCore then + let kind = (if value.IsMember then "member" else "value") + errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, value.Range, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, value.Range)) + errorR(NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) + error (Error(FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) + + PropagateThenTcDelayed cenv overallTy env tpenv mExprAndItem (MakeApplicableExprWithFlex cenv env objExpr) objExprTy ExprAtomicFlag.Atomic delayed // These items are not expected here - they can't be the result of a instance member dot-lookup "expr.Ident" | Item.ActivePatternResult _ | Item.CustomOperation _ diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index 356189a4006..d5989f7af2b 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -312,9 +312,10 @@ type MyId = let onlyIdX (ids: MyId list) = ids |> List.choose _.IdX let onlyIdA (ids: MyId list) = ids |> List.choose _.IdA """ - |> ignoreWarnings - |> compile + |> typecheck |> shouldFail |> withDiagnostics [ + (Error 23, Line 6, Col 17, Line 6, Col 20, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") (Error 23, Line 17, Col 51, Line 17, Col 56, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") + (Error 812, Line 17, Col 51, Line 17, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields") ] \ No newline at end of file From 56b1fe620ce4bb394405bb763628bff990de5938 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Thu, 25 Apr 2024 20:41:24 +0100 Subject: [PATCH 6/9] More tests --- src/Compiler/Checking/CheckExpressions.fs | 18 +++++------ .../Types/UnionTypes/UnionTypes.fs | 30 +++++++++++++++++++ .../Language/DotLambdaTests.fs | 18 ++++++++--- 3 files changed, 53 insertions(+), 13 deletions(-) diff --git a/src/Compiler/Checking/CheckExpressions.fs b/src/Compiler/Checking/CheckExpressions.fs index 2ba1ec964db..813299e3c21 100644 --- a/src/Compiler/Checking/CheckExpressions.fs +++ b/src/Compiler/Checking/CheckExpressions.fs @@ -9413,15 +9413,15 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed | Item.DelegateCtor _ -> error (Error (FSComp.SR.tcConstructorsCannotBeFirstClassValues(), mItem)) | Item.UnionCase(info, _) -> - let clashingNames = info.Tycon.MembersOfFSharpTyconSorted - for value in clashingNames do - if value.DisplayNameCore = info.DisplayNameCore then - let kind = (if value.IsMember then "member" else "value") - errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, value.Range, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, value.Range)) - errorR(NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) - error (Error(FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) - - PropagateThenTcDelayed cenv overallTy env tpenv mExprAndItem (MakeApplicableExprWithFlex cenv env objExpr) objExprTy ExprAtomicFlag.Atomic delayed + let clashingNames = info.Tycon.MembersOfFSharpTyconSorted |> List.tryFind(fun mem -> mem.DisplayNameCore = info.DisplayNameCore) + match clashingNames with + | None -> () + | Some value -> + let kind = if value.IsMember then "member" else "value" + errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, value.Range, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, value.Range)) + errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) + + error (Error (FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) // These items are not expected here - they can't be the result of a instance member dot-lookup "expr.Ident" | Item.ActivePatternResult _ | Item.CustomOperation _ diff --git a/tests/FSharp.Compiler.ComponentTests/Conformance/Types/UnionTypes/UnionTypes.fs b/tests/FSharp.Compiler.ComponentTests/Conformance/Types/UnionTypes/UnionTypes.fs index 75ee664d938..fb11a41005d 100644 --- a/tests/FSharp.Compiler.ComponentTests/Conformance/Types/UnionTypes/UnionTypes.fs +++ b/tests/FSharp.Compiler.ComponentTests/Conformance/Types/UnionTypes/UnionTypes.fs @@ -721,3 +721,33 @@ type U = |> shouldFail |> withSingleDiagnostic (Error 912, Line 4, Col 3, Line 4, Col 28, "This declaration element is not permitted in an augmentation") + + [] + let ``Error when property has same name as DU case`` () = + Fsx """ +type MyId = + | IdA of int + | IdB of string + | IdC of float + + member this.IdA = + match this with + | IdA x -> Some x + | _ -> None + + member this.IdX = + match this with + | IdB x -> Some x + | _ -> None + + member this.IdC = + match this with + | IdC x -> Some x + | _ -> None + """ + |> typecheck + |> shouldFail + |> withDiagnostics [ + (Error 23, Line 7, Col 17, Line 7, Col 20, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") + (Error 23, Line 17, Col 17, Line 17, Col 20, "The member 'IdC' can not be defined because the name 'IdC' clashes with the union case 'IdC' in this type or module") + ] diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index d5989f7af2b..5b0be285edb 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -298,6 +298,7 @@ let _ = asQ.Select _.Length type MyId = | IdA of int | IdB of string + | IdC of float member this.IdA = match this with @@ -309,13 +310,22 @@ type MyId = | IdB x -> Some x | _ -> None -let onlyIdX (ids: MyId list) = ids |> List.choose _.IdX + member this.IdC = + match this with + | IdC x -> Some x + | _ -> None + let onlyIdA (ids: MyId list) = ids |> List.choose _.IdA +let onlyIdX (ids: MyId list) = ids |> List.choose _.IdX +let onlyIdD (ids: MyId list) = ids |> List.choose _.IdC """ |> typecheck |> shouldFail |> withDiagnostics [ - (Error 23, Line 6, Col 17, Line 6, Col 20, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") - (Error 23, Line 17, Col 51, Line 17, Col 56, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module") - (Error 812, Line 17, Col 51, Line 17, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields") + (Error 23, Line 7, Col 17, Line 7, Col 20, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module"); + (Error 23, Line 22, Col 51, Line 22, Col 56, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module"); + (Error 812, Line 22, Col 51, Line 22, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields"); + (Error 23, Line 17, Col 17, Line 17, Col 20, "The member 'IdC' can not be defined because the name 'IdC' clashes with the union case 'IdC' in this type or module"); + (Error 23, Line 24, Col 51, Line 24, Col 56, "The member 'IdC' can not be defined because the name 'IdC' clashes with the union case 'IdC' in this type or module"); + (Error 812, Line 24, Col 51, Line 24, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields") ] \ No newline at end of file From 8487420898a6203efd963bfc05a110bda33f3503 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Fri, 26 Apr 2024 09:10:56 +0100 Subject: [PATCH 7/9] release notes --- docs/release-notes/.FSharp.Compiler.Service/8.0.400.md | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/release-notes/.FSharp.Compiler.Service/8.0.400.md b/docs/release-notes/.FSharp.Compiler.Service/8.0.400.md index 16ead61175e..5927f702531 100644 --- a/docs/release-notes/.FSharp.Compiler.Service/8.0.400.md +++ b/docs/release-notes/.FSharp.Compiler.Service/8.0.400.md @@ -1,6 +1,7 @@ ### Fixed * Improve error reporting for abstract members when used in classes. ([PR #17063](https://github.com/dotnet/fsharp/pull/17063)) +* Improve error reporting when property has same name as DU case. ([Issue #16646](https://github.com/dotnet/fsharp/issues/16646), [PR #17088](https://github.com/dotnet/fsharp/pull/17088)) * Make typechecking of indexed setters with tuples on the right more consistent. ([Issue #16987](https://github.com/dotnet/fsharp/issues/16987), [PR #17017](https://github.com/dotnet/fsharp/pull/17017)) * Static abstract method on classes no longer yields internal error. ([Issue #17044](https://github.com/dotnet/fsharp/issues/17044), [PR #17055](https://github.com/dotnet/fsharp/pull/17055)) * Disallow calling abstract methods directly on interfaces. ([Issue #14012](https://github.com/dotnet/fsharp/issues/14012), [Issue #16299](https://github.com/dotnet/fsharp/issues/16299), [PR #17021](https://github.com/dotnet/fsharp/pull/17021)) From d787f946fd77ec8508a6fc22a0d580f5215bfaa2 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Fri, 26 Apr 2024 13:17:45 +0100 Subject: [PATCH 8/9] Update tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs Co-authored-by: Petr --- tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index 5b0be285edb..30d189acd24 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -317,7 +317,7 @@ type MyId = let onlyIdA (ids: MyId list) = ids |> List.choose _.IdA let onlyIdX (ids: MyId list) = ids |> List.choose _.IdX -let onlyIdD (ids: MyId list) = ids |> List.choose _.IdC +let onlyIdC (ids: MyId list) = ids |> List.choose _.IdC """ |> typecheck |> shouldFail From 64db6ca872e7f402e238ef1956d3394c82b62515 Mon Sep 17 00:00:00 2001 From: Edgar Gonzalez Date: Fri, 26 Apr 2024 15:45:29 +0100 Subject: [PATCH 9/9] one less error --- src/Compiler/Checking/CheckExpressions.fs | 1 - tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs | 2 -- 2 files changed, 3 deletions(-) diff --git a/src/Compiler/Checking/CheckExpressions.fs b/src/Compiler/Checking/CheckExpressions.fs index 813299e3c21..f19f328eff3 100644 --- a/src/Compiler/Checking/CheckExpressions.fs +++ b/src/Compiler/Checking/CheckExpressions.fs @@ -9419,7 +9419,6 @@ and TcLookupItemThen cenv overallTy env tpenv mObjExpr objExpr objExprTy delayed | Some value -> let kind = if value.IsMember then "member" else "value" errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, value.Range, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, value.Range)) - errorR (NameClash(info.DisplayNameCore, kind, info.DisplayNameCore, mItem, FSComp.SR.typeInfoUnionCase(), info.DisplayNameCore, mItem)) error (Error (FSComp.SR.tcSyntaxFormUsedOnlyWithRecordLabelsPropertiesAndFields(), mItem)) // These items are not expected here - they can't be the result of a instance member dot-lookup "expr.Ident" diff --git a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs index 30d189acd24..3d2333ec9a4 100644 --- a/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs +++ b/tests/FSharp.Compiler.ComponentTests/Language/DotLambdaTests.fs @@ -323,9 +323,7 @@ let onlyIdC (ids: MyId list) = ids |> List.choose _.IdC |> shouldFail |> withDiagnostics [ (Error 23, Line 7, Col 17, Line 7, Col 20, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module"); - (Error 23, Line 22, Col 51, Line 22, Col 56, "The member 'IdA' can not be defined because the name 'IdA' clashes with the union case 'IdA' in this type or module"); (Error 812, Line 22, Col 51, Line 22, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields"); (Error 23, Line 17, Col 17, Line 17, Col 20, "The member 'IdC' can not be defined because the name 'IdC' clashes with the union case 'IdC' in this type or module"); - (Error 23, Line 24, Col 51, Line 24, Col 56, "The member 'IdC' can not be defined because the name 'IdC' clashes with the union case 'IdC' in this type or module"); (Error 812, Line 24, Col 51, Line 24, Col 56, "The syntax 'expr.id' may only be used with record labels, properties and fields") ] \ No newline at end of file