Skip to content

Commit 22815df

Browse files
Show external metadata for enum fields in decompiled view (#18800)
1 parent 6547740 commit 22815df

File tree

5 files changed

+42
-11
lines changed

5 files changed

+42
-11
lines changed

docs/release-notes/.FSharp.Compiler.Service/10.0.100.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
* Fix active pattern typechecking regression. ([Issue #18638](https://github.com/dotnet/fsharp/issues/18638), [PR #18642](https://github.com/dotnet/fsharp/pull/18642))
1919
* Fix nullness warnings when casting non-nullable values to `IEquatable<T>` to match C# behavior. ([Issue #18759](https://github.com/dotnet/fsharp/issues/18759))
2020
* Fix IsByRefLikeAttribute types being incorrectly suppressed in completion lists. Types like `Span<T>` and `ReadOnlySpan<T>` now appear correctly in IntelliSense.
21+
* Fix Show XML doc for enum fields in external metadata ([Issue #17939](https://github.com/dotnet/fsharp/issues/17939#issuecomment-3137410105), [PR #18800](https://github.com/dotnet/fsharp/pull/18800))
2122

2223
### Changed
2324
* Use `errorR` instead of `error` in `CheckDeclarations.fs` when possible. ([PR #18645](https://github.com/dotnet/fsharp/pull/18645))

src/Compiler/Checking/NicePrint.fs

Lines changed: 23 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -305,7 +305,7 @@ module internal PrintUtilities =
305305
let layoutXmlDocOfILFieldInfo (denv: DisplayEnv) (infoReader: InfoReader) (finfo: ILFieldInfo) restL =
306306
if denv.showDocumentation then
307307
GetXmlDocSigOfILFieldInfo infoReader Range.range0 finfo
308-
|> layoutXmlDocFromSig denv infoReader true XmlDoc.Empty restL
308+
|> layoutXmlDocFromSig denv infoReader true XmlDoc.Empty restL
309309
else
310310
restL
311311

@@ -465,9 +465,11 @@ module PrintIL =
465465
| None -> WordL.equals ^^ (comment "value unavailable")
466466
| Some s -> WordL.equals ^^ wordL s
467467

468-
let layoutILEnumCase nm litVal =
468+
let layoutILEnumCase nm litVal xmlDocOpt =
469469
let nameL = ConvertLogicalNameToDisplayLayout (tagEnum >> wordL) nm
470-
WordL.bar ^^ nameL ^^ layoutILFieldInit litVal
470+
match xmlDocOpt with
471+
| Some layout -> layout @@ (WordL.bar ^^ nameL ^^ layoutILFieldInit litVal)
472+
| None -> WordL.bar ^^ nameL ^^ layoutILFieldInit litVal
471473

472474
module PrintTypes =
473475
// Note: We need nice printing of constants in order to print literals and attributes
@@ -2108,9 +2110,8 @@ module TastDefinitionPrinting =
21082110

21092111
let ilFieldsL =
21102112
ilFields
2111-
|> List.map (fun x -> (true, x.IsStatic, x.FieldName, 0, 0), layoutILFieldInfo denv infoReader m x)
2112-
|> List.sortBy fst
2113-
|> List.map snd
2113+
|> List.sortBy (fun x -> x.IsStatic, x.FieldName)
2114+
|> List.map (fun x -> layoutILFieldInfo denv infoReader m x)
21142115

21152116
let staticVals =
21162117
if isRecdTy g ty then
@@ -2225,6 +2226,14 @@ module TastDefinitionPrinting =
22252226
else
22262227
(lhsL ^^ WordL.equals) -* rhsL
22272228

2229+
let tryGetFieldXml (layoutList: Layout list) idxOpt =
2230+
match idxOpt with
2231+
| Some i when i >= 0 && i < layoutList.Length ->
2232+
match layoutList[i] with
2233+
| Node (Node (_, right, _), _, _) -> Some right
2234+
| _ -> None
2235+
| _ -> None
2236+
22282237
let typeDeclL =
22292238

22302239
match repr with
@@ -2327,9 +2336,14 @@ module TastDefinitionPrinting =
23272336
|> addLhs
23282337

23292338
| TILObjectRepr _ when tycon.ILTyconRawMetadata.IsEnum ->
2330-
infoReader.GetILFieldInfosOfType (None, ad, m, ty)
2331-
|> List.filter (fun x -> x.FieldName <> "value__")
2332-
|> List.map (fun x -> PrintIL.layoutILEnumCase x.FieldName x.LiteralValue)
2339+
let ilFieldsSorted =
2340+
ilFields
2341+
|> List.sortBy (fun x -> x.IsStatic, x.FieldName)
2342+
infoReader.GetILFieldInfosOfType (None, ad, m, ty)
2343+
|> List.filter (fun (x: ILFieldInfo) -> x.FieldName <> "value__")
2344+
|> List.map (fun (x: ILFieldInfo) ->
2345+
let xmlDocOpt = List.tryFindIndex (fun (e: ILFieldInfo) -> e.FieldName = x.FieldName) ilFieldsSorted |> tryGetFieldXml ilFieldsL
2346+
PrintIL.layoutILEnumCase x.FieldName x.LiteralValue xmlDocOpt)
23332347
|> applyMaxMembers denv.maxMembers
23342348
|> aboveListL
23352349
|> addLhs

tests/FSharp.Compiler.Service.Tests/Symbols.fs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1249,3 +1249,19 @@ module Delegates =
12491249

12501250
symbols["EventHandler"].IsDelegate |> shouldEqual true
12511251
symbols["Action"].IsDelegate |> shouldEqual true
1252+
1253+
module MetadataAsText =
1254+
[<Fact>]
1255+
let ``TryGetMetadataAsText returns metadata for external enum field`` () =
1256+
let _, checkResults = getParseAndCheckResults """
1257+
let test = System.DateTimeKind.Utc
1258+
"""
1259+
let symbolUse = checkResults |> findSymbolUseByName "DateTimeKind"
1260+
match symbolUse.Symbol with
1261+
| :? FSharpEntity as symbol ->
1262+
match symbol.TryGetMetadataText() with
1263+
| Some metadataText ->
1264+
metadataText.ToString() |> shouldContain "The time represented is UTC"
1265+
| None ->
1266+
failwith "Expected metadata text, got None"
1267+
| _ -> failwith "Expected FSharpEntity symbol"

tests/ILVerify/ilverify_FSharp.Compiler.Service_Debug_netstandard2.0.bsl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@
6060
[IL]: Error [StackUnexpected]: : FSharp.Compiler.CompilerConfig+TcConfig::.ctor([FSharp.Compiler.Service]FSharp.Compiler.CompilerConfig+TcConfigBuilder, bool)][offset 0x00000634][found Char] Unexpected type on the stack.
6161
[IL]: Error [StackUnexpected]: : FSharp.Compiler.PatternMatchCompilation::isProblematicClause([FSharp.Compiler.Service]FSharp.Compiler.PatternMatchCompilation+MatchClause)][offset 0x00000065][found Byte] Unexpected type on the stack.
6262
[IL]: Error [StackUnexpected]: : <StartupCode$FSharp-Compiler-Service>.$FSharp.Compiler.PatternMatchCompilation::.cctor()][offset 0x00000015][found Boolean] Unexpected type on the stack.
63-
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+TastDefinitionPrinting+meths@2070-3::Invoke([FSharp.Compiler.Service]FSharp.Compiler.Infos+MethInfo)][offset 0x000000BE][found Char] Unexpected type on the stack.
63+
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+TastDefinitionPrinting+meths@2072-3::Invoke([FSharp.Compiler.Service]FSharp.Compiler.Infos+MethInfo)][offset 0x000000BE][found Char] Unexpected type on the stack.
6464
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+PrintUtilities::layoutXmlDoc([FSharp.Compiler.Service]FSharp.Compiler.TypedTreeOps+DisplayEnv, bool, [FSharp.Compiler.Service]FSharp.Compiler.Xml.XmlDoc, [FSharp.Compiler.Service]FSharp.Compiler.Text.Layout)][offset 0x00000033][found Char] Unexpected type on the stack.
6565
[IL]: Error [StackUnexpected]: : FSharp.Compiler.TypeProviders::ValidateNamespaceName(string, [FSharp.Compiler.Service]FSharp.Compiler.Tainted`1<Microsoft.FSharp.Core.CompilerServices.ITypeProvider>, [FSharp.Compiler.Service]FSharp.Compiler.Text.Range, string)][offset 0x00000063][found Char] Unexpected type on the stack.
6666
[IL]: Error [StackUnexpected]: : FSharp.Compiler.TypeProviders::ValidateExpectedName([FSharp.Compiler.Service]FSharp.Compiler.Text.Range, string[], string, [FSharp.Compiler.Service]FSharp.Compiler.Tainted`1<FSharp.Compiler.TypeProviders+ProvidedType>)][offset 0x000000AD][found Char] Unexpected type on the stack.

tests/ILVerify/ilverify_FSharp.Compiler.Service_Release_netstandard2.0.bsl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@
6565
[IL]: Error [StackUnexpected]: : FSharp.Compiler.IlxGen::HashRangeSorted([S.P.CoreLib]System.Collections.Generic.IDictionary`2<!!0,System.Tuple`2<int32,!!1>>)][offset 0x00000012][found ref '[FSharp.Compiler.Service]FSharp.Compiler.IlxGen+HashRangeSorted@1875<T1>'][expected ref '[FSharp.Core]Microsoft.FSharp.Core.FSharpFunc`2<System.Tuple`2<int32,T0>,T0>'] Unexpected type on the stack.
6666
[IL]: Error [StackUnexpected]: : FSharp.Compiler.PatternMatchCompilation::isProblematicClause([FSharp.Compiler.Service]FSharp.Compiler.PatternMatchCompilation+MatchClause)][offset 0x00000040][found Byte] Unexpected type on the stack.
6767
[IL]: Error [StackUnexpected]: : <StartupCode$FSharp-Compiler-Service>.$FSharp.Compiler.PatternMatchCompilation::.cctor()][offset 0x0000000B][found Boolean] Unexpected type on the stack.
68-
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+TastDefinitionPrinting+meths@2070-3::Invoke([FSharp.Compiler.Service]FSharp.Compiler.Infos+MethInfo)][offset 0x000000B3][found Char] Unexpected type on the stack.
68+
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+TastDefinitionPrinting+meths@2072-3::Invoke([FSharp.Compiler.Service]FSharp.Compiler.Infos+MethInfo)][offset 0x000000B3][found Char] Unexpected type on the stack.
6969
[IL]: Error [StackUnexpected]: : FSharp.Compiler.NicePrint+PrintUtilities::layoutXmlDoc([FSharp.Compiler.Service]FSharp.Compiler.TypedTreeOps+DisplayEnv, bool, [FSharp.Compiler.Service]FSharp.Compiler.Xml.XmlDoc, [FSharp.Compiler.Service]FSharp.Compiler.Text.Layout)][offset 0x00000034][found Char] Unexpected type on the stack.
7070
[IL]: Error [StackUnexpected]: : FSharp.Compiler.TypeProviders::ValidateNamespaceName(string, [FSharp.Compiler.Service]FSharp.Compiler.Tainted`1<Microsoft.FSharp.Core.CompilerServices.ITypeProvider>, [FSharp.Compiler.Service]FSharp.Compiler.Text.Range, string)][offset 0x00000074][found Char] Unexpected type on the stack.
7171
[IL]: Error [StackUnexpected]: : FSharp.Compiler.TypeProviders::ValidateExpectedName([FSharp.Compiler.Service]FSharp.Compiler.Text.Range, string[], string, [FSharp.Compiler.Service]FSharp.Compiler.Tainted`1<FSharp.Compiler.TypeProviders+ProvidedType>)][offset 0x000000A8][found Char] Unexpected type on the stack.

0 commit comments

Comments
 (0)