From d492ae389be39b631bf06701276633d50a418645 Mon Sep 17 00:00:00 2001 From: Cheng Shao <terrorjack@type.dance> Date: Thu, 24 Oct 2024 20:30:13 +0200 Subject: [PATCH] driver: fix foreign stub handling logic in hscParsedDecls This patch fixes foreign stub handling logic in `hscParsedDecls`. Previously foreign stubs were simply ignored here, so any feature that involve foreign stubs would not work in ghci (e.g. CApiFFI). The patch reuses `generateByteCode` logic and eliminates a large chunk of duplicate logic that implements Core to bytecode generation pipeline here. Fixes #25414. (cherry picked from commit 677e3aa56e905524071fc9717a88ad2cd1bc2951) (cherry picked from commit 0db7ace8a69487365bc82b758fec7c6cb712d529) --- compiler/GHC/Driver/Main.hs | 54 ++++++++++++------------------ compiler/GHC/Linker/Loader.hs | 2 ++ testsuite/tests/ghci/scripts/all.T | 2 +- 3 files changed, 25 insertions(+), 33 deletions(-) diff --git a/compiler/GHC/Driver/Main.hs b/compiler/GHC/Driver/Main.hs index d7d861a7e0d..18398b70804 100644 --- a/compiler/GHC/Driver/Main.hs +++ b/compiler/GHC/Driver/Main.hs @@ -229,6 +229,7 @@ import GHC.Unit.Module.Deps import GHC.Unit.Module.Status import GHC.Unit.Home.ModInfo +import GHC.Types.Basic import GHC.Types.Id import GHC.Types.SourceError import GHC.Types.SafeHaskell @@ -2315,7 +2316,7 @@ hscParsedDecls hsc_env decls = runInteractiveHsc hsc_env $ do {- Desugar it -} -- We use a basically null location for iNTERACTIVE - let iNTERACTIVELoc = ModLocation{ ml_hs_file = Nothing, + let iNTERACTIVELoc = ModLocation{ ml_hs_file = Just "Interactive", ml_hi_file = panic "hsDeclsWithLocation:ml_hi_file", ml_obj_file = panic "hsDeclsWithLocation:ml_obj_file", ml_dyn_obj_file = panic "hsDeclsWithLocation:ml_dyn_obj_file", @@ -2332,47 +2333,36 @@ hscParsedDecls hsc_env decls = runInteractiveHsc hsc_env $ do (tidy_cg, mod_details) <- liftIO $ hscTidy hsc_env simpl_mg let !CgGuts{ cg_module = this_mod, - cg_binds = core_binds, - cg_tycons = tycons, - cg_modBreaks = mod_breaks } = tidy_cg + cg_binds = core_binds + } = tidy_cg !ModDetails { md_insts = cls_insts , md_fam_insts = fam_insts } = mod_details -- Get the *tidied* cls_insts and fam_insts - data_tycons = filter isDataTyCon tycons - - {- Prepare For Code Generation -} - -- Do saturation and convert to A-normal form - prepd_binds <- {-# SCC "CorePrep" #-} liftIO $ do - cp_cfg <- initCorePrepConfig hsc_env - corePrepPgm - (hsc_logger hsc_env) - cp_cfg - (initCorePrepPgmConfig (hsc_dflags hsc_env) (interactiveInScope $ hsc_IC hsc_env)) - this_mod iNTERACTIVELoc core_binds data_tycons - - (stg_binds_with_deps, _infotable_prov, _caf_ccs__caf_cc_stacks, _stg_cg_info) - <- {-# SCC "CoreToStg" #-} - liftIO $ myCoreToStg (hsc_logger hsc_env) - (hsc_dflags hsc_env) - (interactiveInScope (hsc_IC hsc_env)) - True - this_mod - iNTERACTIVELoc - prepd_binds - - let (stg_binds,_stg_deps) = unzip stg_binds_with_deps - - {- Generate byte code -} - cbc <- liftIO $ byteCodeGen hsc_env this_mod - stg_binds data_tycons mod_breaks + {- Generate byte code & load foreign stubs -} + (cbc, spt_entries) <- liftIO $ do + (BCOs cbc spt_entries):fos <- generateByteCode hsc_env (mkCgInteractiveGuts tidy_cg) iNTERACTIVELoc + case NE.nonEmpty fos of + Just nefos -> modifyLoaderState_ interp $ \pls -> do + mtime <- getModificationUTCTime $ nameOfObject $ NE.head nefos + (pls1, ok_flag) <- loadObjects interp hsc_env pls + [ LM + { linkableTime = mtime, + linkableModule = this_mod, + linkableUnlinked = NE.toList nefos + } ] + if succeeded ok_flag + then pure pls1 + else panic "could not load foreign stubs for interactive module" + Nothing -> pure () + pure (cbc, spt_entries) let src_span = srcLocSpan interactiveSrcLoc _ <- liftIO $ loadDecls interp hsc_env src_span cbc {- Load static pointer table entries -} - liftIO $ hscAddSptEntries hsc_env (cg_spt_entries tidy_cg) + liftIO $ hscAddSptEntries hsc_env spt_entries let tcs = filterOut isImplicitTyCon (mg_tcs simpl_mg) patsyns = mg_patsyns simpl_mg diff --git a/compiler/GHC/Linker/Loader.hs b/compiler/GHC/Linker/Loader.hs index 99e6ec02608..4cf9882e4dc 100644 --- a/compiler/GHC/Linker/Loader.hs +++ b/compiler/GHC/Linker/Loader.hs @@ -24,6 +24,7 @@ module GHC.Linker.Loader , loadModule , loadCmdLineLibs , loadName + , loadObjects , unload -- * LoadedEnv , withExtendedLoadedEnv @@ -31,6 +32,7 @@ module GHC.Linker.Loader , deleteFromLoadedEnv -- * Internals , rmDupLinkables + , modifyLoaderState_ , modifyLoaderState , initLinkDepsOpts , partitionLinkable diff --git a/testsuite/tests/ghci/scripts/all.T b/testsuite/tests/ghci/scripts/all.T index 57da4578faa..eb20009984a 100755 --- a/testsuite/tests/ghci/scripts/all.T +++ b/testsuite/tests/ghci/scripts/all.T @@ -360,7 +360,7 @@ test('T20455', normal, ghci_script, ['T20455.script']) test('shadow-bindings', normal, ghci_script, ['shadow-bindings.script']) test('T925', normal, ghci_script, ['T925.script']) test('T7388', normal, ghci_script, ['T7388.script']) -test('T25414', [expect_broken(25414)], ghci_script, ['T25414.script']) +test('T25414', normal, ghci_script, ['T25414.script']) test('T20627', normal, ghci_script, ['T20627.script']) test('T20473a', normal, ghci_script, ['T20473a.script']) test('T20473b', normal, ghci_script, ['T20473b.script']) -- GitLab