Skip to content

Commit 1c73196

Browse files
committed
try to sort out pdb
1 parent 3cd1abf commit 1c73196

File tree

1 file changed

+26
-13
lines changed

1 file changed

+26
-13
lines changed

src/Compiler/AbstractIL/ilwritepdb.fs

Lines changed: 26 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -343,9 +343,13 @@ let scopeSorter (scope1: PdbMethodScope) (scope2: PdbMethodScope) =
343343
type PortablePdbGenerator
344344
(embedAllSource: bool, embedSourceList: string list, sourceLink: string, checksumAlgorithm, info: PdbData, pathMap: PathMap) =
345345

346-
let docs = info.Documents
346+
// Deterministic: build the Document table in a stable order by mapped file path,
347+
// but preserve the original-document-index -> handle mapping by filename.
348+
let originalDocFiles = info.Documents |> Array.map (fun d -> d.File)
347349

348-
// The metadata to wite to the PortablePDB (Roslyn = _debugMetadataOpt)
350+
let docsSorted =
351+
info.Documents
352+
|> Array.sortBy (fun d -> PathMap.apply pathMap d.File)
349353

350354
let metadata = MetadataBuilder()
351355

@@ -418,15 +422,13 @@ type PortablePdbGenerator
418422

419423
Some(builder.ToImmutableArray())
420424

425+
// Build Document table in deterministic order
421426
let documentIndex =
422-
let mutable index = Dictionary<string, DocumentHandle>(docs.Length)
423-
424-
let docLength = docs.Length + if String.IsNullOrEmpty sourceLink then 1 else 0
425-
427+
let mutable index = Dictionary<string, DocumentHandle>(docsSorted.Length)
428+
let docLength = docsSorted.Length + (if String.IsNullOrWhiteSpace sourceLink then 0 else 1)
426429
metadata.SetCapacity(TableIndex.Document, docLength)
427430

428-
for doc in docs do
429-
// For F# Interactive, file name 'stdin' gets generated for interactive inputs
431+
for doc in docsSorted do
430432
let handle =
431433
match checkSum doc.File checksumAlgorithm with
432434
| Some(hashAlg, checkSum) ->
@@ -476,11 +478,12 @@ type PortablePdbGenerator
476478

477479
let mutable lastLocalVariableHandle = Unchecked.defaultof<LocalVariableHandle>
478480

481+
// IMPORTANT: map original document index -> filename -> handle
479482
let getDocumentHandle d =
480-
if docs.Length = 0 || d < 0 || d > docs.Length then
483+
if info.Documents.Length = 0 || d < 0 || d >= info.Documents.Length then
481484
Unchecked.defaultof<DocumentHandle>
482485
else
483-
match documentIndex.TryGetValue(docs[d].File) with
486+
match documentIndex.TryGetValue(originalDocFiles[d]) with
484487
| false, _ -> Unchecked.defaultof<DocumentHandle>
485488
| true, h -> h
486489

@@ -563,7 +566,16 @@ type PortablePdbGenerator
563566
let serializeImportsBlob (imports: PdbImport[]) =
564567
let writer = new BlobBuilder()
565568

566-
for import in imports do
569+
let importsSorted =
570+
imports
571+
|> Array.sortWith (fun a b ->
572+
match a, b with
573+
| ImportType t1, ImportType t2 -> compare t1 t2
574+
| ImportNamespace n1, ImportNamespace n2 -> compare n1 n2
575+
| ImportType _, ImportNamespace _ -> -1
576+
| ImportNamespace _, ImportType _ -> 1)
577+
578+
for import in importsSorted do
567579
serializeImport writer import
568580

569581
metadata.GetOrAddBlob(writer)
@@ -640,7 +652,8 @@ type PortablePdbGenerator
640652
)
641653
|> ignore
642654

643-
for localVariable in scope.Locals do
655+
// Deterministic: write locals by stable index
656+
for localVariable in scope.Locals |> Array.sortBy (fun l -> l.Index) do
644657
lastLocalVariableHandle <-
645658
metadata.AddLocalVariable(
646659
LocalVariableAttributes.None,
@@ -653,7 +666,7 @@ type PortablePdbGenerator
653666
let sps =
654667
match minfo.DebugRange with
655668
| None -> Array.empty
656-
| Some _ -> minfo.DebugPoints
669+
| Some _ -> minfo.DebugPoints |> Array.sortWith SequencePoint.orderByOffset
657670

658671
let builder = BlobBuilder()
659672
builder.WriteCompressedInteger(minfo.LocalSignatureToken)

0 commit comments

Comments
 (0)