Skip to content

Commit ffc2b3d

Browse files
fendoralt-romes
authored andcommitted
Refactor mhu session initialisation to match GHCi
1 parent f8696e3 commit ffc2b3d

1 file changed

Lines changed: 47 additions & 67 deletions

File tree

haskell-debugger/GHC/Debugger/Session.hs

Lines changed: 47 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,8 @@ import qualified Data.Set as Set
7171
import Data.Maybe
7272
import GHC.Types.Target (InputFileBuffer)
7373
import GHC (SingleStep, ExecResult)
74+
import Data.Set (Set)
75+
import qualified GHC.Unit as GHC
7476

7577
-- | Throws if package flags are unsatisfiable
7678
parseHomeUnitArguments :: GhcMonad m
@@ -141,31 +143,21 @@ setupHomeUnitGraph flagsAndTargets = do
141143

142144
-- | Set up the 'HomeUnitGraph' with empty 'HomeUnitEnv's.
143145
-- The first 'DynFlags' are the 'DynFlags' for the interactive session.
144-
createUnitEnvFromFlags :: DynFlags -> [DynFlags] -> IO HomeUnitGraph
145-
createUnitEnvFromFlags initialDynFlags unitDflags = do
146-
let
147-
newInternalUnitEnv dflags hpt = mkHomeUnitEnv State.emptyUnitState Nothing dflags hpt Nothing
148-
149-
unitEnvList <- traverse (\dflags -> do
150-
emptyHpt <- emptyHomePackageTable
151-
pure (homeUnitId_ dflags, newInternalUnitEnv dflags emptyHpt)) unitDflags
152-
153-
interactiveHomeUnit <- do
154-
let interactiveDynFlags = initialDynFlags
155-
{ homeUnitId_ = interactiveGhcDebuggerUnitId
156-
, importPaths = []
157-
, packageFlags =
158-
[ ExposePackage
159-
(unitIdString unitId)
160-
(UnitIdArg $ RealUnit (Definite unitId))
161-
(ModRenaming True [])
162-
| (unitId, _) <- unitEnvList
163-
]
164-
}
165-
emptyHpt <- emptyHomePackageTable
166-
pure (homeUnitId_ interactiveDynFlags, newInternalUnitEnv interactiveDynFlags emptyHpt)
167-
168-
pure $ unitEnv_new (Map.fromList (interactiveHomeUnit : unitEnvList))
146+
createHomeUnitGraph :: GHC.Logger -> [DynFlags] -> IO HomeUnitGraph
147+
createHomeUnitGraph logger unitDflags = do
148+
let home_units = Set.fromList $ map homeUnitId_ unitDflags
149+
unitEnvList <- flip traverse unitDflags $ \ dflags -> do
150+
hue <- setupNewHomeUnitEnv logger dflags Nothing home_units
151+
pure (homeUnitId_ dflags, hue)
152+
153+
pure $ unitEnv_new (Map.fromList unitEnvList)
154+
155+
setupNewHomeUnitEnv :: GHC.Logger -> DynFlags -> Maybe [GHC.UnitDatabase UnitId] -> Set UnitId -> IO HomeUnitEnv
156+
setupNewHomeUnitEnv logger dflags cached_dbs other_home_units = do
157+
emptyHpt <- emptyHomePackageTable
158+
(dbs,unit_state,home_unit,mconstants) <- State.initUnits logger dflags cached_dbs other_home_units
159+
updated_dflags <- GHC.updatePlatformConstants dflags mconstants
160+
pure $ mkHomeUnitEnv unit_state (Just dbs) updated_dflags emptyHpt (Just home_unit)
169161

170162
-- | Given a set of 'DynFlags', set up the 'UnitEnv' and 'HomeUnitEnv' for this
171163
-- 'HscEnv'.
@@ -174,50 +166,38 @@ createUnitEnvFromFlags initialDynFlags unitDflags = do
174166
initHomeUnitEnv :: [DynFlags] -> HscEnv -> IO HscEnv
175167
initHomeUnitEnv unitDflags env = do
176168
let dflags0 = hsc_dflags env
177-
-- additionally, set checked dflags so we don't lose fixes
178-
initial_home_graph <- createUnitEnvFromFlags dflags0 unitDflags
179-
let home_units = unitEnv_keys initial_home_graph
180-
init_home_unit_graph <- forM initial_home_graph $ \homeUnitEnv -> do
181-
let dflags = homeUnitEnv_dflags homeUnitEnv
182-
old_hpt = homeUnitEnv_hpt homeUnitEnv
183-
(dbs,unit_state,home_unit,mconstants) <- State.initUnits (hsc_logger env) dflags Nothing home_units
184-
updated_dflags <- GHC.updatePlatformConstants dflags mconstants
185-
pure HomeUnitEnv
186-
{ homeUnitEnv_units = unit_state
187-
, homeUnitEnv_unit_dbs = Just dbs
188-
, homeUnitEnv_dflags = updated_dflags
189-
, homeUnitEnv_hpt = old_hpt
190-
, homeUnitEnv_home_unit = Just home_unit
191-
}
192-
193-
let cached_unit_dbs = concat . catMaybes . fmap homeUnitEnv_unit_dbs $ Foldable.toList init_home_unit_graph
194-
195-
let homeUnitEnv = fromJust $ HUG.unitEnv_lookup_maybe interactiveGhcDebuggerUnitId init_home_unit_graph
196-
dflags = homeUnitEnv_dflags homeUnitEnv
197-
old_hpt = homeUnitEnv_hpt homeUnitEnv
198-
(dbs,unit_state,home_unit,mconstants) <- State.initUnits (hsc_logger env) dflags (Just cached_unit_dbs) home_units
199169

200-
updated_dflags <- GHC.updatePlatformConstants dflags mconstants
201-
let ie = HomeUnitEnv
202-
{ homeUnitEnv_units = unit_state
203-
, homeUnitEnv_unit_dbs = Just dbs
204-
, homeUnitEnv_dflags = updated_dflags
205-
, homeUnitEnv_hpt = old_hpt
206-
, homeUnitEnv_home_unit = Just home_unit
207-
}
208-
209-
let home_unit_graph = HUG.unitEnv_insert interactiveGhcDebuggerUnitId ie init_home_unit_graph
210-
211-
let dflags1 = homeUnitEnv_dflags $ unitEnv_lookup interactiveGhcDebuggerUnitId home_unit_graph
212-
let unit_env = UnitEnv
213-
{ ue_platform = targetPlatform dflags1
214-
, ue_namever = GHC.ghcNameVersion dflags1
215-
, ue_home_unit_graph = home_unit_graph
216-
, ue_current_unit = interactiveGhcDebuggerUnitId
217-
, ue_module_graph = ue_module_graph (hsc_unit_env env)
218-
, ue_eps = ue_eps (hsc_unit_env env)
170+
initial_home_graph <- createHomeUnitGraph (hsc_logger env) unitDflags
171+
172+
-- We set up the interactive debugger home unit after the other home units
173+
-- have been initialised.
174+
-- This allows us to reuse the package databases and their respective visibilities.
175+
interactiveHomeUnit <- do
176+
let
177+
home_units = unitEnv_keys initial_home_graph
178+
179+
interactiveDynFlags = dflags0
180+
{ homeUnitId_ = interactiveGhcDebuggerUnitId
181+
, importPaths = []
182+
, packageFlags =
183+
[ ExposePackage
184+
(unitIdString home_unit_id)
185+
(UnitIdArg $ RealUnit (Definite home_unit_id))
186+
(ModRenaming True [])
187+
| home_unit_id <- Set.toList home_units
188+
]
219189
}
220-
pure $ hscSetFlags dflags1 $ hscSetUnitEnv unit_env env
190+
191+
let cached_unit_dbs = concat . catMaybes . fmap homeUnitEnv_unit_dbs $ Foldable.toList initial_home_graph
192+
setupNewHomeUnitEnv (hsc_logger env) interactiveDynFlags (Just cached_unit_dbs) home_units
193+
194+
let home_unit_graph =
195+
HUG.unitEnv_insert interactiveGhcDebuggerUnitId interactiveHomeUnit initial_home_graph
196+
197+
let interactiveDFlags = homeUnitEnv_dflags interactiveHomeUnit
198+
unit_env <-
199+
initUnitEnv interactiveGhcDebuggerUnitId home_unit_graph (GHC.ghcNameVersion interactiveDFlags) (targetPlatform interactiveDFlags)
200+
pure $ hscSetFlags interactiveDFlags $ hscSetUnitEnv unit_env env
221201

222202

223203
-- | Setup the given 'HscEnv' to hold a 'UnitEnv'

0 commit comments

Comments
 (0)