@@ -36,6 +36,7 @@ import Development.IDE.Import.FindImports
3636import Development.IDE.Core.FileStore
3737import Development.IDE.Types.Diagnostics
3838import Development.IDE.Types.Location
39+import Development.IDE.GHC.Util
3940import Data.Coerce
4041import Data.Either.Extra
4142import Data.Maybe
@@ -54,10 +55,12 @@ import Development.IDE.GHC.Compat
5455import UniqSupply
5556import NameCache
5657import HscTypes
58+import GHC.Generics(Generic)
5759
5860import qualified Development.IDE.Spans.AtPoint as AtPoint
5961import Development.IDE.Core.Service
6062import Development.IDE.Core.Shake
63+import Development.Shake.Classes
6164import System.Directory
6265import System.FilePath
6366import MkIface
@@ -116,7 +119,7 @@ getAtPoint file pos = fmap join $ runMaybeT $ do
116119getDefinition :: NormalizedFilePath -> Position -> Action (Maybe Location)
117120getDefinition file pos = fmap join $ runMaybeT $ do
118121 spans <- useE GetSpanInfo file
119− pkgState <- useNoFileE GhcSession
122+ pkgState <- hscEnv <$> useE GhcSession file
120123 opts <- lift getIdeOptions
121124 let getHieFile x = useNoFile (GetHieFile x)
122125 lift $ AtPoint.gotoDefinition getHieFile opts pkgState spans pos
@@ -131,8 +134,9 @@ writeIfacesAndHie ::
131134writeIfacesAndHie ifDir files =
132135 runMaybeT $ do
133136 tcms <- usesE TypeCheck files
134− session <- lift $ useNoFile_ GhcSession
135− liftIO $ concat <$> mapM (writeTcm session) tcms
137+ fmap concat $ forM (zip files tcms) $ \(file, tcm) -> do
138+ session <- lift $ hscEnv <$> use_ GhcSession file
139+ liftIO $ writeTcm session tcm
136140 where
137141 writeTcm session tcm =
138142 do
@@ -174,7 +178,7 @@ getParsedModuleRule :: Rules ()
174178getParsedModuleRule =
175179 define $ \GetParsedModule file -> do
176180 (_, contents) <- getFileContents file
177− packageState <- useNoFile_ GhcSession
181+ packageState <- hscEnv <$> use_ GhcSession file
178182 opt <- getIdeOptions
179183 liftIO $ parseModule opt packageState (fromNormalizedFilePath file) contents
180184
@@ -184,7 +188,7 @@ getLocatedImportsRule =
184188 pm <- use_ GetParsedModule file
185189 let ms = pm_mod_summary pm
186190 let imports = [(False, imp) | imp <- ms_textual_imps ms] ++ [(True, imp) | imp <- ms_srcimps ms]
187− env <- useNoFile_ GhcSession
191+ env <- hscEnv <$> useNoFile_ GhcSession
188192 let dflags = addRelativeImport pm $ hsc_dflags env
189193 opt <- getIdeOptions
190194 (diags, imports') <- fmap unzip $ forM imports $ \(isSource, (mbPkgName, modName)) -> do
@@ -295,7 +299,7 @@ getSpanInfoRule =
295299 define $ \GetSpanInfo file -> do
296300 tc <- use_ TypeCheck file
297301 (fileImports, _) <- use_ GetLocatedImports file
298− packageState <- useNoFile_ GhcSession
302+ packageState <- hscEnv <$> use_ GhcSession file
299303 x <- liftIO $ getSrcSpanInfos packageState fileImports tc
300304 return ([], Just x)
301305
@@ -307,7 +311,7 @@ typeCheckRule =
307311 deps <- use_ GetDependencies file
308312 tms <- uses_ TypeCheck (transitiveModuleDeps deps)
309313 setPriority priorityTypeCheck
310− packageState <- useNoFile_ GhcSession
314+ packageState <- hscEnv <$> use_ GhcSession file
311315 liftIO $ typecheckModule packageState tms pm
312316
313317
@@ -317,14 +321,33 @@ generateCoreRule =
317321 deps <- use_ GetDependencies file
318322 (tm:tms) <- uses_ TypeCheck (file:transitiveModuleDeps deps)
319323 setPriority priorityGenerateCore
320− packageState <- useNoFile_ GhcSession
324+ packageState <- hscEnv <$> use_ GhcSession file
321325 liftIO $ compileModule packageState tms tm
322326
327+
328+-- A local rule type to get caching. We want to use newCache, but it has
329+-- thread killed exception issues, so we lift it to a full rule.
330+-- https://github.com/digital-asset/daml/pull/2808#issuecomment-529639547
331+type instance RuleResult GhcSessionIO = GhcSessionFun
332+
333+data GhcSessionIO = GhcSessionIO deriving (Eq, Show, Typeable, Generic)
334+instance Hashable GhcSessionIO
335+instance NFData GhcSessionIO
336+
337+newtype GhcSessionFun = GhcSessionFun (FilePath -> Action HscEnvEq)
338+instance Show GhcSessionFun where show _ = "GhcSessionFun"
339+instance NFData GhcSessionFun where rnf !_ = ()
340+
341+
323342loadGhcSession :: Rules ()
324−loadGhcSession =
325− defineNoFile $ \GhcSession -> do
343+loadGhcSession = do
344+ defineNoFile $ \GhcSessionIO -> do
326345 opts <- getIdeOptions
327− optGhcSession opts
346+ liftIO $ GhcSessionFun <$> optGhcSession opts
347+ define $ \GhcSession file -> do
348+ GhcSessionFun fun <- useNoFile_ GhcSessionIO
349+ val <- fun $ fromNormalizedFilePath file
350+ return ([], Just val)
328351
329352
330353getHieFileRule :: Rules ()