@@ -175,6 +175,7 @@ let calculateStateMetrics interproceduralGraphDistanceFrom (state: IGraphTrackab
175175 let mutable notVisitedBasicBlocksInZone = 0
176176 let mutable notTouchedBasicBlocksInZone = 0
177177 let basicBlocks = HashSet<_>()
178+
178179 currentBasicBlock.OutgoingEdges.Values |> Seq.iter basicBlocks.UnionWith
179180
180181 basicBlocks
@@ -348,41 +349,47 @@ let collectStatesInfoToDump (basicBlocks: ResizeArray<BasicBlock>) =
348349
349350 statesInfoToDump
350351
351- let getFirstFreePathConditionVertexId =
352+ let getFirstFreePathConditionVertexId , resetPathConditionVertexIdCounter =
352353 let mutable count = 0 u< pathConditionVertexId>
353354
354355 fun () ->
355356 let res = count
356357 count <- count + 1 u< pathConditionVertexId>
357358 res
359+ , fun () -> count <- 0 u< pathConditionVertexId>
358360
359- let pathConditionVertices = Dictionary< Core.term, PathConditionVertex>()
360-
361- let collectPathCondition term = // TODO: Support other operations
362- let termsToVisit =
363- Stack< Core.term * uint< pathConditionVertexId>> [| ( term, getFirstFreePathConditionVertexId ()) |]
361+ let pathConditionVertices = HashSet< Core.term>()
362+ let termsWithId = Dictionary< Core.term, uint< pathConditionVertexId>>()
364363
364+ let collectPathCondition
365+ term
366+ ( termsWithId : Dictionary < Core.term , uint < pathConditionVertexId >>)
367+ ( processedPathConditionVertices : HashSet < Core.term >)
368+ = // TODO: Support other operations
369+ let termsToVisit = Stack< Core.term> [| term |]
365370 let pathConditionDelta = ResizeArray< PathConditionVertex>()
366371
372+ let getIdForTerm term =
373+ if termsWithId.ContainsKey term then
374+ termsWithId.[ term]
375+ else
376+ let newId = getFirstFreePathConditionVertexId ()
377+ termsWithId.Add( term, newId)
378+ newId
379+
380+ let handleChild term ( children : ResizeArray < _ >) =
381+ children.Add( getIdForTerm term)
382+ termsToVisit.Push term
383+
367384 while termsToVisit.Count > 0 do
368- let currentTerm , currentTermId = termsToVisit.Pop()
385+ let currentTerm = termsToVisit.Pop()
369386
370387 let markAsVisited ( vertexType : pathConditionVertexType ) children =
371- let newVertex = PathConditionVertex( currentTermId , vertexType, children)
372- pathConditionVertices .Add( currentTerm, newVertex )
388+ let newVertex = PathConditionVertex( getIdForTerm currentTerm , vertexType, children)
389+ processedPathConditionVertices .Add currentTerm |> ignore
373390 pathConditionDelta.Add newVertex
374391
375- let handleTerm term ( children : ResizeArray < _ >) =
376- let termId =
377- if not <| pathConditionVertices.ContainsKey term then
378- getFirstFreePathConditionVertexId ()
379- else
380- pathConditionVertices.[ term]. Id
381-
382- children.Add termId
383- termsToVisit.Push(( term, termId))
384-
385- if not <| pathConditionVertices.ContainsKey currentTerm then
392+ if not <| processedPathConditionVertices.Contains currentTerm then
386393 match currentTerm.term with
387394 | Nop -> markAsVisited pathConditionVertexType.Nop [||]
388395 | Concrete(_, _) -> markAsVisited pathConditionVertexType.Constant [||]
@@ -391,7 +398,7 @@ let collectPathCondition term = // TODO: Support other operations
391398 let children = ResizeArray< uint< pathConditionVertexId>>()
392399
393400 for t in termList do
394- handleTerm t children
401+ handleChild t children
395402
396403 let children = children.ToArray()
397404
@@ -443,30 +450,30 @@ let collectPathCondition term = // TODO: Support other operations
443450 let children = ResizeArray< uint< pathConditionVertexId>>()
444451
445452 for _, t in PersistentDict.toSeq fields do
446- handleTerm t children
453+ handleChild t children
447454
448455 markAsVisited pathConditionVertexType.Struct ( children.ToArray())
449456 | HeapRef(_, _) -> markAsVisited pathConditionVertexType.HeapRef [||]
450457 | Ref(_) -> markAsVisited pathConditionVertexType.Ref [||]
451458 | Ptr(_, _, t) ->
452459 let children = ResizeArray< uint< pathConditionVertexId>> [||]
453- handleTerm t children
460+ handleChild t children
454461 markAsVisited pathConditionVertexType.Ptr ( children.ToArray())
455462 | Slice( t, listOfTuples) ->
456463 let children = ResizeArray< uint< pathConditionVertexId>> [||]
457- handleTerm t children
464+ handleChild t children
458465
459466 for t1, t2, t3, _ in listOfTuples do
460- handleTerm t1 children
461- handleTerm t2 children
462- handleTerm t3 children
467+ handleChild t1 children
468+ handleChild t2 children
469+ handleChild t3 children
463470
464471 markAsVisited pathConditionVertexType.Slice ( children.ToArray())
465472 | Ite(_) -> markAsVisited pathConditionVertexType.Ite [||]
466473
467474 pathConditionDelta
468475
469- let collectGameState ( basicBlocks : ResizeArray < BasicBlock >) filterStates =
476+ let collectGameState ( basicBlocks : ResizeArray < BasicBlock >) filterStates processedPathConditionVertices termsWithId =
470477
471478 let vertices = ResizeArray<_>()
472479 let allStates = HashSet<_>()
@@ -486,13 +493,13 @@ let collectGameState (basicBlocks: ResizeArray<BasicBlock>) filterStates =
486493 let pathCondition = s.PathCondition |> PC.toSeq
487494
488495 for term in pathCondition do
489- pathConditionDelta.AddRange( collectPathCondition term)
496+ pathConditionDelta.AddRange( collectPathCondition term termsWithId processedPathConditionVertices )
490497
491498 let pathConditionRoot =
492499 PathConditionVertex(
493500 id = getFirstFreePathConditionVertexId (),
494501 pathConditionVertexType = pathConditionVertexType.PathConditionRoot,
495- children = [| for p in pathCondition -> pathConditionVertices .[ p]. Id |]
502+ children = [| for p in pathCondition -> termsWithId .[ p] |]
496503 )
497504
498505 pathConditionDelta.Add pathConditionRoot
@@ -556,7 +563,7 @@ let collectGameStateDelta () =
556563 let added = basicBlocks.Add( basicBlock)
557564 ()
558565
559- collectGameState ( ResizeArray basicBlocks) false
566+ collectGameState ( ResizeArray basicBlocks) false pathConditionVertices termsWithId
560567
561568let dumpGameState fileForResultWithoutExtension ( movedStateId : uint < stateId >) =
562569 let basicBlocks = ResizeArray<_>()
@@ -566,7 +573,9 @@ let dumpGameState fileForResultWithoutExtension (movedStateId: uint<stateId>) =
566573 basicBlock.IsGoal <- method.Key.InCoverageZone
567574 basicBlocks.Add( basicBlock)
568575
569- let gameState = collectGameState basicBlocks true
576+ let gameState =
577+ collectGameState basicBlocks true ( HashSet< Core.term>()) ( Dictionary< Core.term, uint< pathConditionVertexId>>())
578+
570579 let statesInfoToDump = collectStatesInfoToDump basicBlocks
571580 let gameStateJson = JsonSerializer.Serialize gameState
572581 let statesInfoJson = JsonSerializer.Serialize statesInfoToDump
0 commit comments