summaryrefslogtreecommitdiff
path: root/compiler/nativeGen/RegAlloc/Graph
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/nativeGen/RegAlloc/Graph')
-rw-r--r--compiler/nativeGen/RegAlloc/Graph/ArchBase.hs13
-rw-r--r--compiler/nativeGen/RegAlloc/Graph/Main.hs21
-rw-r--r--compiler/nativeGen/RegAlloc/Graph/Spill.hs10
-rw-r--r--compiler/nativeGen/RegAlloc/Graph/SpillClean.hs6
-rw-r--r--compiler/nativeGen/RegAlloc/Graph/SpillCost.hs11
5 files changed, 41 insertions, 20 deletions
diff --git a/compiler/nativeGen/RegAlloc/Graph/ArchBase.hs b/compiler/nativeGen/RegAlloc/Graph/ArchBase.hs
index 787b1d2f85..c3df743454 100644
--- a/compiler/nativeGen/RegAlloc/Graph/ArchBase.hs
+++ b/compiler/nativeGen/RegAlloc/Graph/ArchBase.hs
@@ -22,6 +22,7 @@ module RegAlloc.Graph.ArchBase (
squeese
) where
import UniqSet
+import UniqFM
import Unique
@@ -88,7 +89,10 @@ worst :: (RegClass -> UniqSet Reg)
worst regsOfClass regAlias neighbors classN classC
= let regAliasS regs = unionManyUniqSets
$ map regAlias
- $ uniqSetToList regs
+ $ nonDetEltsUFM regs
+ -- This is non-deterministic but we do not
+ -- currently support deterministic code-generation.
+ -- See Note [Unique Determinism and code generation]
-- all the regs in classes N, C
regsN = regsOfClass classN
@@ -117,7 +121,8 @@ bound :: (RegClass -> UniqSet Reg)
bound regsOfClass regAlias classN classesC
= let regAliasS regs = unionManyUniqSets
$ map regAlias
- $ uniqSetToList regs
+ $ nonDetEltsUFM regs
+ -- See Note [Unique Determinism and code generation]
regsC_aliases
= unionManyUniqSets
@@ -150,5 +155,5 @@ powersetL = map concat . mapM (\x -> [[],[x]])
-- | powersetLS (list of sets)
powersetLS :: Uniquable a => UniqSet a -> [UniqSet a]
-powersetLS s = map mkUniqSet $ powersetL $ uniqSetToList s
-
+powersetLS s = map mkUniqSet $ powersetL $ nonDetEltsUFM s
+ -- See Note [Unique Determinism and code generation]
diff --git a/compiler/nativeGen/RegAlloc/Graph/Main.hs b/compiler/nativeGen/RegAlloc/Graph/Main.hs
index 52ed438f81..f7b3d0179d 100644
--- a/compiler/nativeGen/RegAlloc/Graph/Main.hs
+++ b/compiler/nativeGen/RegAlloc/Graph/Main.hs
@@ -110,8 +110,11 @@ regAlloc_spin dflags spinCount triv regsFree slotsFree debug_codeGraphs code
( text "It looks like the register allocator is stuck in an infinite loop."
$$ text "max cycles = " <> int maxSpinCount
$$ text "regsFree = " <> (hcat $ punctuate space $ map ppr
- $ uniqSetToList $ unionManyUniqSets
- $ eltsUFM regsFree)
+ $ nonDetEltsUFM $ unionManyUniqSets
+ $ nonDetEltsUFM regsFree)
+ -- This is non-deterministic but we do not
+ -- currently support deterministic code-generation.
+ -- See Note [Unique Determinism and code generation]
$$ text "slotsFree = " <> ppr (sizeUniqSet slotsFree))
-- Build the register conflict graph from the cmm code.
@@ -312,15 +315,16 @@ graphAddConflictSet
graphAddConflictSet set graph
= let virtuals = mkUniqSet
- [ vr | RegVirtual vr <- uniqSetToList set ]
+ [ vr | RegVirtual vr <- nonDetEltsUFM set ]
graph1 = Color.addConflicts virtuals classOfVirtualReg graph
graph2 = foldr (\(r1, r2) -> Color.addExclusion r1 classOfVirtualReg r2)
graph1
[ (vr, rr)
- | RegVirtual vr <- uniqSetToList set
- , RegReal rr <- uniqSetToList set]
+ | RegVirtual vr <- nonDetEltsUFM set
+ , RegReal rr <- nonDetEltsUFM set]
+ -- See Note [Unique Determinism and code generation]
in graph2
@@ -410,10 +414,11 @@ seqNode node
= seqVirtualReg (Color.nodeId node)
`seq` seqRegClass (Color.nodeClass node)
`seq` seqMaybeRealReg (Color.nodeColor node)
- `seq` (seqVirtualRegList (uniqSetToList (Color.nodeConflicts node)))
- `seq` (seqRealRegList (uniqSetToList (Color.nodeExclusions node)))
+ `seq` (seqVirtualRegList (nonDetEltsUFM (Color.nodeConflicts node)))
+ `seq` (seqRealRegList (nonDetEltsUFM (Color.nodeExclusions node)))
`seq` (seqRealRegList (Color.nodePreference node))
- `seq` (seqVirtualRegList (uniqSetToList (Color.nodeCoalesce node)))
+ `seq` (seqVirtualRegList (nonDetEltsUFM (Color.nodeCoalesce node)))
+ -- It's OK to use nonDetEltsUFM for seq
seqVirtualReg :: VirtualReg -> ()
seqVirtualReg reg = reg `seq` ()
diff --git a/compiler/nativeGen/RegAlloc/Graph/Spill.hs b/compiler/nativeGen/RegAlloc/Graph/Spill.hs
index 1ec8d1276f..9c3ccae315 100644
--- a/compiler/nativeGen/RegAlloc/Graph/Spill.hs
+++ b/compiler/nativeGen/RegAlloc/Graph/Spill.hs
@@ -62,9 +62,12 @@ regSpill platform code slotsFree regs
| otherwise
= do
-- Allocate a slot for each of the spilled regs.
- let slots = take (sizeUniqSet regs) $ uniqSetToList slotsFree
+ let slots = take (sizeUniqSet regs) $ nonDetEltsUFM slotsFree
let regSlotMap = listToUFM
- $ zip (uniqSetToList regs) slots
+ $ zip (nonDetEltsUFM regs) slots
+ -- This is non-deterministic but we do not
+ -- currently support deterministic code-generation.
+ -- See Note [Unique Determinism and code generation]
-- Grab the unique supply from the monad.
us <- getUniqueSupplyM
@@ -139,7 +142,8 @@ regSpill_top platform regSlotMap cmm
moreSlotsLive = Set.fromList
$ catMaybes
$ map (lookupUFM regSlotMap)
- $ uniqSetToList regsLive
+ $ nonDetEltsUFM regsLive
+ -- See Note [Unique Determinism and code generation]
slotMap'
= Map.insert blockId (Set.union curSlotsLive moreSlotsLive)
diff --git a/compiler/nativeGen/RegAlloc/Graph/SpillClean.hs b/compiler/nativeGen/RegAlloc/Graph/SpillClean.hs
index 2383d7bb3a..25d0ff4e80 100644
--- a/compiler/nativeGen/RegAlloc/Graph/SpillClean.hs
+++ b/compiler/nativeGen/RegAlloc/Graph/SpillClean.hs
@@ -414,7 +414,8 @@ intersects assocs = foldl1' intersectAssoc assocs
findRegOfSlot :: Assoc Store -> Int -> Maybe Reg
findRegOfSlot assoc slot
| close <- closeAssoc (SSlot slot) assoc
- , Just (SReg reg) <- find isStoreReg $ uniqSetToList close
+ , Just (SReg reg) <- find isStoreReg $ nonDetEltsUFM close
+ -- See Note [Unique Determinism and code generation]
= Just reg
| otherwise
@@ -582,7 +583,8 @@ closeAssoc a assoc
= closeAssoc' assoc emptyUniqSet (unitUniqSet a)
where
closeAssoc' assoc visited toVisit
- = case uniqSetToList toVisit of
+ = case nonDetEltsUFM toVisit of
+ -- See Note [Unique Determinism and code generation]
-- nothing else to visit, we're done
[] -> visited
diff --git a/compiler/nativeGen/RegAlloc/Graph/SpillCost.hs b/compiler/nativeGen/RegAlloc/Graph/SpillCost.hs
index 8860ebc7e0..beffde97bb 100644
--- a/compiler/nativeGen/RegAlloc/Graph/SpillCost.hs
+++ b/compiler/nativeGen/RegAlloc/Graph/SpillCost.hs
@@ -108,7 +108,10 @@ slurpSpillCostInfo platform cmm
countLIs rsLiveEntry (LiveInstr instr (Just live) : lis)
= do
-- Increment the lifetime counts for regs live on entry to this instr.
- mapM_ incLifetime $ uniqSetToList rsLiveEntry
+ mapM_ incLifetime $ nonDetEltsUFM rsLiveEntry
+ -- This is non-deterministic but we do not
+ -- currently support deterministic code-generation.
+ -- See Note [Unique Determinism and code generation]
-- Increment counts for what regs were read/written from.
let (RU read written) = regUsageOfInstr platform instr
@@ -137,7 +140,8 @@ slurpSpillCostInfo platform cmm
-- | Take all the virtual registers from this set.
takeVirtuals :: UniqSet Reg -> UniqSet VirtualReg
takeVirtuals set = mkUniqSet
- [ vr | RegVirtual vr <- uniqSetToList set ]
+ [ vr | RegVirtual vr <- nonDetEltsUFM set ]
+ -- See Note [Unique Determinism and code generation]
-- | Choose a node to spill from this graph
@@ -254,7 +258,8 @@ nodeDegree classOfVirtualReg graph reg
, virtConflicts
<- length
$ filter (\r -> classOfVirtualReg r == classOfVirtualReg reg)
- $ uniqSetToList
+ $ nonDetEltsUFM
+ -- See Note [Unique Determinism and code generation]
$ nodeConflicts node
= virtConflicts + sizeUniqSet (nodeExclusions node)