Marge Bot pushed to branch wip/marge_bot_batch_merge_job at Glasgow Haskell Compiler / GHC
Commits:
-
06108198
by Luite Stegeman at 2025-09-30T14:09:24-04:00
-
4bb1576e
by Luite Stegeman at 2025-09-30T14:09:24-04:00
-
9f1423b8
by Cheng Shao at 2025-09-30T14:09:25-04:00
-
583d3d53
by Cheng Shao at 2025-09-30T14:09:25-04:00
-
bb886749
by Cheng Shao at 2025-09-30T14:09:25-04:00
-
74e01719
by Matthew Pickering at 2025-09-30T14:09:26-04:00
-
51c7def9
by Cheng Shao at 2025-09-30T14:09:27-04:00
21 changed files:
- compiler/GHC.hs
- compiler/GHC/Cmm/Parser.y
- compiler/GHC/Driver/Main.hs
- compiler/GHC/Driver/Make.hs
- compiler/GHC/Driver/Session.hs
- compiler/GHC/Iface/Tidy/StaticPtrTable.hs
- compiler/GHC/Linker/Loader.hs
- compiler/GHC/Runtime/Interpreter/Types.hs
- configure.ac
- distrib/configure.ac.in
- hadrian/src/Settings/Packages.hs
- libraries/ghci/GHCi/ObjLink.hs
- m4/fp_cmm_cpp_cmd_with_args.m4
- − m4/fp_set_cflags_c99.m4
- rts/Apply.cmm
- rts/ThreadPaused.c
- + testsuite/tests/ghci-wasm/T26431.hs
- + testsuite/tests/ghci-wasm/T26431.stdout
- testsuite/tests/ghci-wasm/all.T
- utils/ghc-toolchain/src/GHC/Toolchain/Tools/Cc.hs
- utils/ghc-toolchain/src/GHC/Toolchain/Tools/Cpp.hs
Changes:
| ... | ... | @@ -716,17 +716,14 @@ setTopSessionDynFlags dflags = do |
| 716 | 716 | |
| 717 | 717 | -- see Note [Target code interpreter]
|
| 718 | 718 | interp <- if
|
| 719 | +#if !defined(wasm32_HOST_ARCH)
|
|
| 719 | 720 | -- Wasm dynamic linker
|
| 720 | 721 | | ArchWasm32 <- platformArch $ targetPlatform dflags
|
| 721 | 722 | -> do
|
| 722 | 723 | s <- liftIO $ newMVar InterpPending
|
| 723 | 724 | loader <- liftIO Loader.uninitializedLoader
|
| 724 | 725 | dyld <- liftIO $ makeAbsolute $ topDir dflags </> "dyld.mjs"
|
| 725 | -#if defined(wasm32_HOST_ARCH)
|
|
| 726 | - let libdir = sorry "cannot spawn child process on wasm"
|
|
| 727 | -#else
|
|
| 728 | 726 | libdir <- liftIO $ last <$> Loader.getGccSearchDirectory logger dflags "libraries"
|
| 729 | -#endif
|
|
| 730 | 727 | let profiled = ways dflags `hasWay` WayProf
|
| 731 | 728 | way_tag = if profiled then "_p" else ""
|
| 732 | 729 | let cfg =
|
| ... | ... | @@ -747,6 +744,7 @@ setTopSessionDynFlags dflags = do |
| 747 | 744 | wasmInterpUnitState = ue_homeUnitState $ hsc_unit_env hsc_env
|
| 748 | 745 | }
|
| 749 | 746 | pure $ Just $ Interp (ExternalInterp $ ExtWasm $ ExtInterpState cfg s) loader lookup_cache
|
| 747 | +#endif
|
|
| 750 | 748 | |
| 751 | 749 | -- JavaScript interpreter
|
| 752 | 750 | | ArchJavaScript <- platformArch (targetPlatform dflags)
|
| ... | ... | @@ -1321,6 +1321,7 @@ stmtMacros = listToUFM [ |
| 1321 | 1321 | ( fsLit "PROF_HEADER_CREATE", \[e] -> profHeaderCreate e ),
|
| 1322 | 1322 | |
| 1323 | 1323 | ( fsLit "PUSH_UPD_FRAME", \[sp,e] -> emitPushUpdateFrame sp e ),
|
| 1324 | + ( fsLit "PUSH_BH_UPD_FRAME", \[sp,e] -> emitPushBHUpdateFrame sp e ),
|
|
| 1324 | 1325 | ( fsLit "SET_HDR", \[ptr,info,ccs] ->
|
| 1325 | 1326 | emitSetDynHdr ptr info ccs ),
|
| 1326 | 1327 | ( fsLit "TICK_ALLOC_PRIM", \[hdr,goods,slop] ->
|
| ... | ... | @@ -1336,6 +1337,10 @@ emitPushUpdateFrame :: CmmExpr -> CmmExpr -> FCode () |
| 1336 | 1337 | emitPushUpdateFrame sp e = do
|
| 1337 | 1338 | emitUpdateFrame sp mkUpdInfoLabel e
|
| 1338 | 1339 | |
| 1340 | +emitPushBHUpdateFrame :: CmmExpr -> CmmExpr -> FCode ()
|
|
| 1341 | +emitPushBHUpdateFrame sp e = do
|
|
| 1342 | + emitUpdateFrame sp mkBHUpdInfoLabel e
|
|
| 1343 | + |
|
| 1339 | 1344 | pushStackFrame :: [CmmParse CmmExpr] -> CmmParse () -> CmmParse ()
|
| 1340 | 1345 | pushStackFrame fields body = do
|
| 1341 | 1346 | profile <- getProfile
|
| ... | ... | @@ -102,7 +102,6 @@ module GHC.Driver.Main |
| 102 | 102 | , dumpIfaceStats
|
| 103 | 103 | , ioMsgMaybe
|
| 104 | 104 | , showModuleIndex
|
| 105 | - , hscAddSptEntries
|
|
| 106 | 105 | , writeInterfaceOnlyMode
|
| 107 | 106 | , loadByteCode
|
| 108 | 107 | , genModDetails
|
| ... | ... | @@ -2515,9 +2514,6 @@ hscParsedDecls hsc_env decls = runInteractiveHsc hsc_env $ do |
| 2515 | 2514 | let src_span = srcLocSpan interactiveSrcLoc
|
| 2516 | 2515 | _ <- liftIO $ loadDecls interp hsc_env src_span linkable
|
| 2517 | 2516 | |
| 2518 | - {- Load static pointer table entries -}
|
|
| 2519 | - liftIO $ hscAddSptEntries hsc_env (cg_spt_entries tidy_cg)
|
|
| 2520 | - |
|
| 2521 | 2517 | let tcs = filterOut isImplicitTyCon (mg_tcs simpl_mg)
|
| 2522 | 2518 | patsyns = mg_patsyns simpl_mg
|
| 2523 | 2519 | |
| ... | ... | @@ -2539,18 +2535,6 @@ hscParsedDecls hsc_env decls = runInteractiveHsc hsc_env $ do |
| 2539 | 2535 | fam_insts defaults fix_env
|
| 2540 | 2536 | return (new_tythings, new_ictxt)
|
| 2541 | 2537 | |
| 2542 | --- | Load the given static-pointer table entries into the interpreter.
|
|
| 2543 | --- See Note [Grand plan for static forms] in "GHC.Iface.Tidy.StaticPtrTable".
|
|
| 2544 | -hscAddSptEntries :: HscEnv -> [SptEntry] -> IO ()
|
|
| 2545 | -hscAddSptEntries hsc_env entries = do
|
|
| 2546 | - let interp = hscInterp hsc_env
|
|
| 2547 | - let add_spt_entry :: SptEntry -> IO ()
|
|
| 2548 | - add_spt_entry (SptEntry n fpr) = do
|
|
| 2549 | - -- These are only names from the current module
|
|
| 2550 | - (val, _, _) <- loadName interp hsc_env n
|
|
| 2551 | - addSptEntry interp fpr val
|
|
| 2552 | - mapM_ add_spt_entry entries
|
|
| 2553 | - |
|
| 2554 | 2538 | {-
|
| 2555 | 2539 | Note [Fixity declarations in GHCi]
|
| 2556 | 2540 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| ... | ... | @@ -56,8 +56,6 @@ import GHC.Tc.Utils.Monad ( initIfaceCheck, concatMapM ) |
| 56 | 56 | |
| 57 | 57 | import GHC.Runtime.Interpreter
|
| 58 | 58 | import qualified GHC.Linker.Loader as Linker
|
| 59 | -import GHC.Linker.Types
|
|
| 60 | - |
|
| 61 | 59 | |
| 62 | 60 | import GHC.Driver.Config.Diagnostic
|
| 63 | 61 | import GHC.Driver.Pipeline
|
| ... | ... | @@ -72,8 +70,6 @@ import GHC.Driver.MakeSem |
| 72 | 70 | import GHC.Driver.Downsweep
|
| 73 | 71 | import GHC.Driver.MakeAction
|
| 74 | 72 | |
| 75 | -import GHC.ByteCode.Types
|
|
| 76 | - |
|
| 77 | 73 | import GHC.Iface.Load ( cannotFindModule, readIface )
|
| 78 | 74 | import GHC.IfaceToCore ( typecheckIface )
|
| 79 | 75 | import GHC.Iface.Recomp ( RecompileRequired(..), CompileReason(..) )
|
| ... | ... | @@ -1232,31 +1228,9 @@ upsweep_mod :: HscEnv |
| 1232 | 1228 | upsweep_mod hsc_env mHscMessage old_hmi summary mod_index nmods = do
|
| 1233 | 1229 | hmi <- compileOne' mHscMessage hsc_env summary
|
| 1234 | 1230 | mod_index nmods (hm_iface <$> old_hmi) (maybe emptyHomeModInfoLinkable hm_linkable old_hmi)
|
| 1235 | - |
|
| 1236 | - -- MP: This is a bit janky, because before you add the entries you have to extend the HPT with the module
|
|
| 1237 | - -- you just compiled. Another option, would be delay adding anything until after upsweep has finished, but I
|
|
| 1238 | - -- am unsure if this is sound (wrt running TH splices for example).
|
|
| 1239 | - -- This function only does anything if the linkable produced is a BCO, which
|
|
| 1240 | - -- used to only happen with the bytecode backend, but with
|
|
| 1241 | - -- @-fprefer-byte-code@, @HomeModInfo@ has bytecode even when generating
|
|
| 1242 | - -- object code, see #25230.
|
|
| 1243 | 1231 | hscInsertHPT hmi hsc_env
|
| 1244 | - addSptEntries (hsc_env)
|
|
| 1245 | - (homeModInfoByteCode hmi)
|
|
| 1246 | - |
|
| 1247 | 1232 | return hmi
|
| 1248 | 1233 | |
| 1249 | --- | Add the entries from a BCO linkable to the SPT table, see
|
|
| 1250 | --- See Note [Grand plan for static forms] in GHC.Iface.Tidy.StaticPtrTable.
|
|
| 1251 | -addSptEntries :: HscEnv -> Maybe Linkable -> IO ()
|
|
| 1252 | -addSptEntries hsc_env mlinkable =
|
|
| 1253 | - hscAddSptEntries hsc_env
|
|
| 1254 | - [ spt
|
|
| 1255 | - | linkable <- maybeToList mlinkable
|
|
| 1256 | - , bco <- linkableBCOs linkable
|
|
| 1257 | - , spt <- bc_spt_entries bco
|
|
| 1258 | - ]
|
|
| 1259 | - |
|
| 1260 | 1234 | |
| 1261 | 1235 | -- Note [When source is considered modified]
|
| 1262 | 1236 | -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| ... | ... | @@ -3763,12 +3763,17 @@ makeDynFlagsConsistent dflags |
| 3763 | 3763 | -- only supports dynamic code
|
| 3764 | 3764 | | LinkInMemory <- ghcLink dflags
|
| 3765 | 3765 | , sTargetRTSLinkerOnlySupportsSharedLibs $ settings dflags
|
| 3766 | +#if defined(HAVE_INTERNAL_INTERPRETER)
|
|
| 3767 | + , not (ways dflags `hasWay` WayDyn)
|
|
| 3768 | +#else
|
|
| 3766 | 3769 | , not (ways dflags `hasWay` WayDyn && gopt Opt_ExternalInterpreter dflags)
|
| 3770 | +#endif
|
|
| 3767 | 3771 | = flip loopNoWarn "Forcing dynamic way because target RTS linker only supports dynamic code" $
|
| 3768 | - -- See checkOptions, -fexternal-interpreter is
|
|
| 3769 | - -- required when using --interactive with a non-standard
|
|
| 3770 | - -- way (-prof, -static, or -dynamic).
|
|
| 3772 | +#if !defined(HAVE_INTERNAL_INTERPRETER)
|
|
| 3773 | + -- Force -fexternal-interpreter if internal-interpreter is not
|
|
| 3774 | + -- available at this stage
|
|
| 3771 | 3775 | setGeneralFlag' Opt_ExternalInterpreter $
|
| 3776 | +#endif
|
|
| 3772 | 3777 | addWay' WayDyn dflags
|
| 3773 | 3778 | |
| 3774 | 3779 | | LinkInMemory <- ghcLink dflags
|
| ... | ... | @@ -124,7 +124,7 @@ Here is a running example: |
| 124 | 124 | * If we are compiling for the byte-code interpreter, we instead explicitly add
|
| 125 | 125 | the SPT entries (recorded in CgGuts' cg_spt_entries field) to the interpreter
|
| 126 | 126 | process' SPT table using the addSptEntry interpreter message. This happens
|
| 127 | - in upsweep after we have compiled the module (see GHC.Driver.Make.upsweep').
|
|
| 127 | + when the bytecode object is linked in `dynLinkBCOs`.
|
|
| 128 | 128 | -}
|
| 129 | 129 | |
| 130 | 130 | import GHC.Prelude
|
| ... | ... | @@ -718,6 +718,7 @@ loadDecls interp hsc_env span linkable = do |
| 718 | 718 | let ce2 = extendClosureEnv (closure_env le2) nms_fhvs
|
| 719 | 719 | !pls2 = pls { linker_env = le2 { closure_env = ce2 }
|
| 720 | 720 | , linked_breaks = lb2 }
|
| 721 | + mapM_ (linkSptEntry interp ce2) (concatMap bc_spt_entries cbcs)
|
|
| 721 | 722 | return (pls2, (nms_fhvs, links_needed, units_needed))
|
| 722 | 723 | where
|
| 723 | 724 | cbcs = linkableBCOs linkable
|
| ... | ... | @@ -951,10 +952,28 @@ dynLinkBCOs interp pls bcos = do |
| 951 | 952 | -- Wrap finalizers on the ones we want to keep
|
| 952 | 953 | new_binds <- makeForeignNamedHValueRefs interp to_add
|
| 953 | 954 | |
| 955 | + |
|
| 954 | 956 | let ce2 = extendClosureEnv (closure_env le2) new_binds
|
| 957 | + |
|
| 958 | + -- Add SPT entries
|
|
| 959 | + mapM_ (linkSptEntry interp ce2) (concatMap bc_spt_entries cbcs)
|
|
| 960 | + |
|
| 955 | 961 | return $! pls1 { linker_env = le2 { closure_env = ce2 }
|
| 956 | 962 | , linked_breaks = lb2 }
|
| 957 | 963 | |
| 964 | +-- | Register SPT entries for this module in the interpreter
|
|
| 965 | +-- Assumes that the name from the SPT has already been loaded into the interpreter.
|
|
| 966 | +linkSptEntry :: Interp -> ClosureEnv -> SptEntry -> IO ()
|
|
| 967 | +linkSptEntry interp ce (SptEntry name fpr) = do
|
|
| 968 | + case lookupNameEnv ce name of
|
|
| 969 | + -- The SPT entries only point to locally defined names, which should have already been
|
|
| 970 | + -- loaded into the interpreter before this function is called.
|
|
| 971 | + Nothing -> pprPanic "linkSptEntry" (ppr name)
|
|
| 972 | + Just (_, hval) -> addSptEntry interp fpr hval
|
|
| 973 | + |
|
| 974 | + |
|
| 975 | + |
|
| 976 | + |
|
| 958 | 977 | -- Link a bunch of BCOs and return references to their values
|
| 959 | 978 | linkSomeBCOs :: Interp
|
| 960 | 979 | -> PkgsLoaded
|
| ... | ... | @@ -1614,6 +1633,9 @@ gccSearchDirCache = unsafePerformIO $ newIORef [] |
| 1614 | 1633 | -- which dominate a large percentage of startup time on Windows.
|
| 1615 | 1634 | getGccSearchDirectory :: Logger -> DynFlags -> String -> IO [FilePath]
|
| 1616 | 1635 | getGccSearchDirectory logger dflags key = do
|
| 1636 | +#if defined(wasm32_HOST_ARCH)
|
|
| 1637 | + pure []
|
|
| 1638 | +#else
|
|
| 1617 | 1639 | cache <- readIORef gccSearchDirCache
|
| 1618 | 1640 | case lookup key cache of
|
| 1619 | 1641 | Just x -> return x
|
| ... | ... | @@ -1640,6 +1662,7 @@ getGccSearchDirectory logger dflags key = do |
| 1640 | 1662 | x:_ -> case break (=='=') x of
|
| 1641 | 1663 | (_ , []) -> []
|
| 1642 | 1664 | (_, (_:xs)) -> xs
|
| 1665 | +#endif
|
|
| 1643 | 1666 | |
| 1644 | 1667 | -- | Get a list of system search directories, this to alleviate pressure on
|
| 1645 | 1668 | -- the findSysDll function.
|
| ... | ... | @@ -214,7 +214,7 @@ data JSInterpConfig = JSInterpConfig |
| 214 | 214 | |
| 215 | 215 | data WasmInterpConfig = WasmInterpConfig
|
| 216 | 216 | { wasmInterpDyLD :: !FilePath -- ^ Location of dyld.mjs script
|
| 217 | - , wasmInterpLibDir :: FilePath -- ^ wasi-sdk sysroot libdir containing libc.so, etc
|
|
| 217 | + , wasmInterpLibDir :: !FilePath -- ^ wasi-sdk sysroot libdir containing libc.so, etc
|
|
| 218 | 218 | , wasmInterpOpts :: ![String] -- ^ Additional command line arguments for iserv
|
| 219 | 219 | |
| 220 | 220 | -- wasm ghci browser mode
|
| ... | ... | @@ -448,11 +448,6 @@ AC_SUBST([CmmCPPCmd]) |
| 448 | 448 | AC_SUBST([CmmCPPArgs])
|
| 449 | 449 | AC_SUBST([CmmCPPSupportsG0])
|
| 450 | 450 | |
| 451 | -FP_SET_CFLAGS_C99([CC],[CFLAGS],[CPPFLAGS])
|
|
| 452 | -FP_SET_CFLAGS_C99([CC_STAGE0],[CONF_CC_OPTS_STAGE0],[CONF_CPP_OPTS_STAGE0])
|
|
| 453 | -FP_SET_CFLAGS_C99([CC],[CONF_CC_OPTS_STAGE1],[CONF_CPP_OPTS_STAGE1])
|
|
| 454 | -FP_SET_CFLAGS_C99([CC],[CONF_CC_OPTS_STAGE2],[CONF_CPP_OPTS_STAGE2])
|
|
| 455 | - |
|
| 456 | 451 | dnl ** Do we have a compatible emsdk version?
|
| 457 | 452 | dnl --------------------------------------------------------------
|
| 458 | 453 | EMSDK_VERSION("3.1.20", "", "")
|
| ... | ... | @@ -163,11 +163,6 @@ AC_SUBST([CmmCPPCmd]) |
| 163 | 163 | AC_SUBST([CmmCPPArgs])
|
| 164 | 164 | AC_SUBST([CmmCPPSupportsG0])
|
| 165 | 165 | |
| 166 | -FP_SET_CFLAGS_C99([CC],[CFLAGS],[CPPFLAGS])
|
|
| 167 | -dnl FP_SET_CFLAGS_C99([CC_STAGE0],[CONF_CC_OPTS_STAGE0],[CONF_CPP_OPTS_STAGE0])
|
|
| 168 | -FP_SET_CFLAGS_C99([CC],[CONF_CC_OPTS_STAGE1],[CONF_CPP_OPTS_STAGE1])
|
|
| 169 | -FP_SET_CFLAGS_C99([CC],[CONF_CC_OPTS_STAGE2],[CONF_CPP_OPTS_STAGE2])
|
|
| 170 | - |
|
| 171 | 166 | dnl ** Which ld to use?
|
| 172 | 167 | dnl --------------------------------------------------------------
|
| 173 | 168 | FIND_LD([$target],[GccUseLdOpt])
|
| ... | ... | @@ -82,15 +82,18 @@ packageArgs = do |
| 82 | 82 | ]
|
| 83 | 83 | |
| 84 | 84 | , builder (Cabal Flags) ? mconcat
|
| 85 | - -- For the ghc library, internal-interpreter only makes
|
|
| 86 | - -- sense when we're not cross compiling. For cross GHC,
|
|
| 87 | - -- external interpreter is used for loading target code
|
|
| 88 | - -- and internal interpreter is supposed to load native
|
|
| 89 | - -- code for plugins (!7377), however it's unfinished work
|
|
| 90 | - -- (#14335) and completely untested in CI for cross
|
|
| 91 | - -- backends at the moment, so we might as well disable it
|
|
| 92 | - -- for cross GHC.
|
|
| 93 | - [ andM [expr (ghcWithInterpreter stage), notCross] `cabalFlag` "internal-interpreter"
|
|
| 85 | + -- In order to enable internal-interpreter for the ghc
|
|
| 86 | + -- library:
|
|
| 87 | + --
|
|
| 88 | + -- 1. ghcWithInterpreter must be True ("Use interpreter" =
|
|
| 89 | + -- "YES")
|
|
| 90 | + -- 2. For non-cross case it can be enabled
|
|
| 91 | + -- 3. For cross case, disable for stage0 since that runs
|
|
| 92 | + -- on the host and must rely on external interpreter to
|
|
| 93 | + -- load target code, otherwise enable for stage1 since
|
|
| 94 | + -- that runs on the target and can use target's own
|
|
| 95 | + -- ghci object linker
|
|
| 96 | + [ andM [expr (ghcWithInterpreter stage), orM [notCross, stage1]] `cabalFlag` "internal-interpreter"
|
|
| 94 | 97 | , orM [ notM cross, haveCurses ] `cabalFlag` "terminfo"
|
| 95 | 98 | , arg "-build-tool-depends"
|
| 96 | 99 | , flag UseLibzstd `cabalFlag` "with-libzstd"
|
| ... | ... | @@ -113,8 +113,7 @@ foreign import javascript unsafe "__ghc_wasm_jsffi_dyld.lookupSymbol($1)" |
| 113 | 113 | js_lookupSymbol :: JSString -> IO (Ptr a)
|
| 114 | 114 | |
| 115 | 115 | lookupSymbolInDLL :: Ptr LoadedDLL -> String -> IO (Maybe (Ptr a))
|
| 116 | -lookupSymbolInDLL _ sym =
|
|
| 117 | - throwIO $ ErrorCall $ "lookupSymbolInDLL: unsupported on wasm for " <> sym
|
|
| 116 | +lookupSymbolInDLL _ _ = pure Nothing
|
|
| 118 | 117 | |
| 119 | 118 | resolveObjs :: IO Bool
|
| 120 | 119 | resolveObjs = pure True
|
| ... | ... | @@ -56,27 +56,6 @@ else |
| 56 | 56 | AC_MSG_RESULT([no])
|
| 57 | 57 | fi
|
| 58 | 58 | |
| 59 | -AC_MSG_CHECKING([the C-- preprocessor for C99 support])
|
|
| 60 | -cat > conftest.c <<EOF
|
|
| 61 | -#include <stdio.h>
|
|
| 62 | -#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 199901L
|
|
| 63 | -# error "Compiler does not advertise C99 conformance"
|
|
| 64 | -#endif
|
|
| 65 | -EOF
|
|
| 66 | -if "$CMM_CPP_CMD" $CMM_CPP_ARGS conftest.c -o conftest -g0 >/dev/null 2>&1; then
|
|
| 67 | - AC_MSG_RESULT([yes])
|
|
| 68 | -else
|
|
| 69 | - # Try -std=gnu99
|
|
| 70 | - if "$CMM_CPP_CMD" -std=gnu99 $CMM_CPP_ARGS conftest.c -o conftest -g0 >/dev/null 2>&1; then
|
|
| 71 | - $3="-std=gnu99 $$3"
|
|
| 72 | - AC_MSG_RESULT([needs -std=gnu99])
|
|
| 73 | - else
|
|
| 74 | - AC_MSG_ERROR([C99-compatible compiler needed])
|
|
| 75 | - fi
|
|
| 76 | -fi
|
|
| 77 | -rm -f conftest.c conftest.o conftest
|
|
| 78 | - |
|
| 79 | - |
|
| 80 | 59 | $2="$CMM_CPP_CMD"
|
| 81 | 60 | $3="$$3 $CMM_CPP_ARGS"
|
| 82 | 61 | |
| ... | ... | @@ -85,4 +64,3 @@ unset CMM_CPP_CMD |
| 85 | 64 | unset CMM_CPP_ARGS
|
| 86 | 65 | |
| 87 | 66 | ]) |
| 88 | - |
| 1 | -# FP_SET_CFLAGS_C99
|
|
| 2 | -# ----------------------------------
|
|
| 3 | -# figure out which CFLAGS are needed to place the compiler into C99 mode
|
|
| 4 | -# $1 is name of CC variable (unmodified)
|
|
| 5 | -# $2 is name of CC flags variable (augmented if needed)
|
|
| 6 | -# $3 is name of CPP flags variable (augmented if needed)
|
|
| 7 | -AC_DEFUN([FP_SET_CFLAGS_C99],
|
|
| 8 | -[
|
|
| 9 | - dnl save current state of AC_PROG_CC_C99
|
|
| 10 | - FP_COPY_SHELLVAR([CC],[fp_save_CC])
|
|
| 11 | - FP_COPY_SHELLVAR([CFLAGS],[fp_save_CFLAGS])
|
|
| 12 | - FP_COPY_SHELLVAR([CPPFLAGS],[fp_save_CPPFLAGS])
|
|
| 13 | - FP_COPY_SHELLVAR([ac_cv_prog_cc_c99],[fp_save_cc_c99])
|
|
| 14 | - dnl set local state
|
|
| 15 | - CC="$$1"
|
|
| 16 | - CFLAGS="$$2"
|
|
| 17 | - CPPFLAGS="$$3"
|
|
| 18 | - unset ac_cv_prog_cc_c99
|
|
| 19 | - dnl perform detection
|
|
| 20 | - AC_PROG_CC_C99
|
|
| 21 | - fp_cc_c99="$ac_cv_prog_cc_c99"
|
|
| 22 | - case "x$ac_cv_prog_cc_c99" in
|
|
| 23 | - x) ;; # noop
|
|
| 24 | - xno) AC_MSG_ERROR([C99-compatible compiler needed]) ;;
|
|
| 25 | - *) $2="$$2 $ac_cv_prog_cc_c99"
|
|
| 26 | - $3="$$3 $ac_cv_prog_cc_c99"
|
|
| 27 | - ;;
|
|
| 28 | - esac
|
|
| 29 | - dnl restore saved state
|
|
| 30 | - FP_COPY_SHELLVAR([fp_save_CC],[CC])
|
|
| 31 | - FP_COPY_SHELLVAR([fp_save_CFLAGS],[CFLAGS])
|
|
| 32 | - FP_COPY_SHELLVAR([fp_save_CPPFLAGS],[CPPFLAGS])
|
|
| 33 | - FP_COPY_SHELLVAR([fp_save_cc_c99],[ac_cv_prog_cc_c99])
|
|
| 34 | - dnl cleanup
|
|
| 35 | - unset fp_save_CC
|
|
| 36 | - unset fp_save_CFLAGS
|
|
| 37 | - unset fp_save_cc_c99
|
|
| 38 | -]) |
| ... | ... | @@ -699,7 +699,7 @@ INFO_TABLE(stg_AP_STACK,/*special layout*/0,0,AP_STACK,"AP_STACK","AP_STACK") |
| 699 | 699 | |
| 700 | 700 | /* ensure there is at least AP_STACK_SPLIM words of headroom available
|
| 701 | 701 | * after unpacking the AP_STACK. See bug #1466 */
|
| 702 | - PUSH_UPD_FRAME(Sp - SIZEOF_StgUpdateFrame, R1);
|
|
| 702 | + PUSH_BH_UPD_FRAME(Sp - SIZEOF_StgUpdateFrame, R1);
|
|
| 703 | 703 | Sp = Sp - SIZEOF_StgUpdateFrame - WDS(Words);
|
| 704 | 704 | |
| 705 | 705 | TICK_ENT_AP();
|
| ... | ... | @@ -15,6 +15,7 @@ |
| 15 | 15 | #include "RaiseAsync.h"
|
| 16 | 16 | #include "Trace.h"
|
| 17 | 17 | #include "Threads.h"
|
| 18 | +#include "Messages.h"
|
|
| 18 | 19 | #include "sm/NonMovingMark.h"
|
| 19 | 20 | |
| 20 | 21 | #include <string.h> // for memmove()
|
| ... | ... | @@ -314,52 +315,66 @@ threadPaused(Capability *cap, StgTSO *tso) |
| 314 | 315 | continue;
|
| 315 | 316 | }
|
| 316 | 317 | |
| 317 | - // an EAGER_BLACKHOLE or CAF_BLACKHOLE gets turned into a
|
|
| 318 | - // BLACKHOLE here.
|
|
| 318 | + // If we have a frame that is already eagerly blackholed, we
|
|
| 319 | + // shouldn't overwrite its payload: There may already be a blocking
|
|
| 320 | + // queue (see #26324).
|
|
| 321 | + if(frame_info == &stg_bh_upd_frame_info) {
|
|
| 322 | + // eager black hole: we do nothing
|
|
| 323 | + |
|
| 324 | + // it should be a black hole that we own
|
|
| 325 | + ASSERT(bh_info == &stg_BLACKHOLE_info ||
|
|
| 326 | + bh_info == &__stg_EAGER_BLACKHOLE_info ||
|
|
| 327 | + bh_info == &stg_CAF_BLACKHOLE_info);
|
|
| 328 | + ASSERT(blackHoleOwner(bh) == tso || blackHoleOwner(bh) == NULL);
|
|
| 329 | + } else {
|
|
| 330 | + // lazy black hole
|
|
| 331 | + |
|
| 319 | 332 | #if defined(THREADED_RTS)
|
| 320 | - // first we turn it into a WHITEHOLE to claim it, and if
|
|
| 321 | - // successful we write our TSO and then the BLACKHOLE info pointer.
|
|
| 322 | - cur_bh_info = (const StgInfoTable *)
|
|
| 323 | - cas((StgVolatilePtr)&bh->header.info,
|
|
| 324 | - (StgWord)bh_info,
|
|
| 325 | - (StgWord)&stg_WHITEHOLE_info);
|
|
| 326 | - |
|
| 327 | - if (cur_bh_info != bh_info) {
|
|
| 328 | - bh_info = cur_bh_info;
|
|
| 333 | + // first we turn it into a WHITEHOLE to claim it, and if
|
|
| 334 | + // successful we write our TSO and then the BLACKHOLE info pointer.
|
|
| 335 | + cur_bh_info = (const StgInfoTable *)
|
|
| 336 | + cas((StgVolatilePtr)&bh->header.info,
|
|
| 337 | + (StgWord)bh_info,
|
|
| 338 | + (StgWord)&stg_WHITEHOLE_info);
|
|
| 339 | + |
|
| 340 | + if (cur_bh_info != bh_info) {
|
|
| 341 | + bh_info = cur_bh_info;
|
|
| 329 | 342 | #if defined(PROF_SPIN)
|
| 330 | - NONATOMIC_ADD(&whitehole_threadPaused_spin, 1);
|
|
| 343 | + NONATOMIC_ADD(&whitehole_threadPaused_spin, 1);
|
|
| 331 | 344 | #endif
|
| 332 | - busy_wait_nop();
|
|
| 333 | - goto retry;
|
|
| 334 | - }
|
|
| 345 | + busy_wait_nop();
|
|
| 346 | + goto retry;
|
|
| 347 | + }
|
|
| 335 | 348 | #endif
|
| 336 | - |
|
| 337 | - IF_NONMOVING_WRITE_BARRIER_ENABLED {
|
|
| 338 | - if (ip_THUNK(INFO_PTR_TO_STRUCT(bh_info))) {
|
|
| 339 | - // We are about to replace a thunk with a blackhole.
|
|
| 340 | - // Add the free variables of the closure we are about to
|
|
| 341 | - // overwrite to the update remembered set.
|
|
| 342 | - // N.B. We caught the WHITEHOLE case above.
|
|
| 343 | - updateRemembSetPushThunkEager(cap,
|
|
| 344 | - THUNK_INFO_PTR_TO_STRUCT(bh_info),
|
|
| 345 | - (StgThunk *) bh);
|
|
| 349 | + ASSERT(bh_info != &stg_WHITEHOLE_info);
|
|
| 350 | + |
|
| 351 | + IF_NONMOVING_WRITE_BARRIER_ENABLED {
|
|
| 352 | + if (ip_THUNK(INFO_PTR_TO_STRUCT(bh_info))) {
|
|
| 353 | + // We are about to replace a thunk with a blackhole.
|
|
| 354 | + // Add the free variables of the closure we are about to
|
|
| 355 | + // overwrite to the update remembered set.
|
|
| 356 | + // N.B. We caught the WHITEHOLE case above.
|
|
| 357 | + updateRemembSetPushThunkEager(cap,
|
|
| 358 | + THUNK_INFO_PTR_TO_STRUCT(bh_info),
|
|
| 359 | + (StgThunk *) bh);
|
|
| 360 | + }
|
|
| 346 | 361 | }
|
| 347 | - }
|
|
| 348 | 362 | |
| 349 | - // zero out the slop so that the sanity checker can tell
|
|
| 350 | - // where the next closure is. N.B. We mustn't do this until we have
|
|
| 351 | - // pushed the free variables to the update remembered set above.
|
|
| 352 | - OVERWRITING_CLOSURE_SIZE(bh, closure_sizeW_(bh, INFO_PTR_TO_STRUCT(bh_info)));
|
|
| 363 | + // zero out the slop so that the sanity checker can tell
|
|
| 364 | + // where the next closure is. N.B. We mustn't do this until we have
|
|
| 365 | + // pushed the free variables to the update remembered set above.
|
|
| 366 | + OVERWRITING_CLOSURE_SIZE(bh, closure_sizeW_(bh, INFO_PTR_TO_STRUCT(bh_info)));
|
|
| 353 | 367 | |
| 354 | - // The payload of the BLACKHOLE points to the TSO
|
|
| 355 | - RELEASE_STORE(&((StgInd *)bh)->indirectee, (StgClosure *)tso);
|
|
| 356 | - SET_INFO_RELEASE(bh,&stg_BLACKHOLE_info);
|
|
| 368 | + // The payload of the BLACKHOLE points to the TSO
|
|
| 369 | + RELEASE_STORE(&((StgInd *)bh)->indirectee, (StgClosure *)tso);
|
|
| 370 | + SET_INFO_RELEASE(bh,&stg_BLACKHOLE_info);
|
|
| 357 | 371 | |
| 358 | - // .. and we need a write barrier, since we just mutated the closure:
|
|
| 359 | - recordClosureMutated(cap,bh);
|
|
| 372 | + // .. and we need a write barrier, since we just mutated the closure:
|
|
| 373 | + recordClosureMutated(cap,bh);
|
|
| 360 | 374 | |
| 361 | - // We pretend that bh has just been created.
|
|
| 362 | - LDV_RECORD_CREATE(bh);
|
|
| 375 | + // We pretend that bh has just been created.
|
|
| 376 | + LDV_RECORD_CREATE(bh);
|
|
| 377 | + }
|
|
| 363 | 378 | |
| 364 | 379 | frame = (StgClosure *) ((StgUpdateFrame *)frame + 1);
|
| 365 | 380 | if (prev_was_update_frame) {
|
| 1 | +import Control.Exception
|
|
| 2 | +import Control.Monad.IO.Class
|
|
| 3 | +import Data.Maybe
|
|
| 4 | +import GHC
|
|
| 5 | +import GHC.Plugins
|
|
| 6 | +import GHC.Runtime.Interpreter
|
|
| 7 | +import System.Environment.Blank
|
|
| 8 | + |
|
| 9 | +main :: IO ()
|
|
| 10 | +main = do
|
|
| 11 | + [libdir] <- getArgs
|
|
| 12 | + defaultErrorHandler defaultFatalMessager defaultFlushOut $
|
|
| 13 | + runGhc (Just libdir) $
|
|
| 14 | + do
|
|
| 15 | + dflags0 <- getSessionDynFlags
|
|
| 16 | + let dflags1 =
|
|
| 17 | + dflags0
|
|
| 18 | + { ghcMode = CompManager,
|
|
| 19 | + backend = interpreterBackend,
|
|
| 20 | + ghcLink = LinkInMemory
|
|
| 21 | + }
|
|
| 22 | + logger <- getLogger
|
|
| 23 | + (dflags2, _, _) <-
|
|
| 24 | + parseDynamicFlags logger dflags1 $
|
|
| 25 | + map noLoc ["-package", "ghc"]
|
|
| 26 | + _ <- setSessionDynFlags dflags2
|
|
| 27 | + addTarget =<< guessTarget "hello.hs" Nothing Nothing
|
|
| 28 | + _ <- load LoadAllTargets
|
|
| 29 | + setContext
|
|
| 30 | + [ IIDecl $ simpleImportDecl $ mkModuleName "Prelude",
|
|
| 31 | + IIDecl $ simpleImportDecl $ mkModuleName "Main"
|
|
| 32 | + ]
|
|
| 33 | + hsc_env <- getSession
|
|
| 34 | + fhv <- compileExprRemote "main"
|
|
| 35 | + liftIO $ evalIO (fromJust $ hsc_interp hsc_env) fhv |
| 1 | +main = putStrLn "hello world" |
| ... | ... | @@ -10,3 +10,11 @@ test('T26430', [ |
| 10 | 10 | extra_hc_opts('-L. -lT26430B')]
|
| 11 | 11 | , compile_and_run, ['']
|
| 12 | 12 | )
|
| 13 | + |
|
| 14 | +test('T26431', [
|
|
| 15 | + extra_files(['../../../.gitlab/hello.hs']),
|
|
| 16 | + extra_hc_opts('-package ghc'),
|
|
| 17 | + extra_run_opts(f'"{config.libdir}"'),
|
|
| 18 | + ignore_stderr]
|
|
| 19 | +, compile_and_run, ['']
|
|
| 20 | +) |
| ... | ... | @@ -11,7 +11,6 @@ module GHC.Toolchain.Tools.Cc |
| 11 | 11 | , compileC
|
| 12 | 12 | , compileAsm
|
| 13 | 13 | , addPlatformDepCcFlags
|
| 14 | - , checkC99Support
|
|
| 15 | 14 | ) where
|
| 16 | 15 | |
| 17 | 16 | import Control.Monad
|
| ... | ... | @@ -51,12 +50,8 @@ findCc archOs llvmTarget progOpt = do |
| 51 | 50 | cc1 <- ignoreUnusedArgs cc0
|
| 52 | 51 | cc2 <- ccSupportsTarget archOs llvmTarget cc1
|
| 53 | 52 | checking "whether Cc works" $ checkCcWorks cc2
|
| 54 | - cc3 <- oneOf "cc doesn't support C99" $ map checkC99Support
|
|
| 55 | - [ cc2
|
|
| 56 | - , cc2 & _ccFlags %++ "-std=gnu99"
|
|
| 57 | - ]
|
|
| 58 | - checkCcSupportsExtraViaCFlags cc3
|
|
| 59 | - return cc3
|
|
| 53 | + checkCcSupportsExtraViaCFlags cc2
|
|
| 54 | + return cc2
|
|
| 60 | 55 | |
| 61 | 56 | checkCcWorks :: Cc -> M ()
|
| 62 | 57 | checkCcWorks cc = withTempDir $ \dir -> do
|
| ... | ... | @@ -88,17 +83,6 @@ ccSupportsTarget archOs target cc = |
| 88 | 83 | checking "whether Cc supports --target" $
|
| 89 | 84 | supportsTarget archOs _ccProgram checkCcWorks target cc
|
| 90 | 85 | |
| 91 | -checkC99Support :: Cc -> M Cc
|
|
| 92 | -checkC99Support cc = checking "for C99 support" $ withTempDir $ \dir -> do
|
|
| 93 | - let test_o = dir </> "test.o"
|
|
| 94 | - compileC cc test_o $ unlines
|
|
| 95 | - [ "#include <stdio.h>"
|
|
| 96 | - , "#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 199901L"
|
|
| 97 | - , "# error \"Compiler does not advertise C99 conformance\""
|
|
| 98 | - , "#endif"
|
|
| 99 | - ]
|
|
| 100 | - return cc
|
|
| 101 | - |
|
| 102 | 86 | checkCcSupportsExtraViaCFlags :: Cc -> M ()
|
| 103 | 87 | checkCcSupportsExtraViaCFlags cc = checking "whether cc supports extra via-c flags" $ withTempDir $ \dir -> do
|
| 104 | 88 | let test_o = dir </> "test.o"
|
| ... | ... | @@ -19,7 +19,7 @@ import GHC.Toolchain.Prelude |
| 19 | 19 | import GHC.Toolchain.Program
|
| 20 | 20 | |
| 21 | 21 | import GHC.Toolchain.Tools.Cc
|
| 22 | -import GHC.Toolchain.Utils (withTempDir, oneOf, expectFileExists)
|
|
| 22 | +import GHC.Toolchain.Utils (withTempDir, expectFileExists)
|
|
| 23 | 23 | |
| 24 | 24 | newtype Cpp = Cpp { cppProgram :: Program
|
| 25 | 25 | }
|
| ... | ... | @@ -160,13 +160,7 @@ findJsCpp progOpt cc = checking "for JavaScript C preprocessor" $ do |
| 160 | 160 | findCmmCpp :: ProgOpt -> Cc -> M CmmCpp
|
| 161 | 161 | findCmmCpp progOpt cc = checking "for a Cmm preprocessor" $ do
|
| 162 | 162 | -- Use the specified CPP or try to use the c compiler
|
| 163 | - foundCppProg <- findProgram "Cmm preprocessor" progOpt [] <|> pure (programFromOpt progOpt (prgPath $ ccProgram cc) [])
|
|
| 164 | - -- Check whether the C preprocessor needs -std=gnu99 (only very old toolchains need this)
|
|
| 165 | - Cc cpp <- oneOf "cc doesn't support C99" $ map checkC99Support
|
|
| 166 | - [ Cc foundCppProg
|
|
| 167 | - , Cc (foundCppProg & _prgFlags %++ "-std=gnu99")
|
|
| 168 | - ]
|
|
| 169 | - |
|
| 163 | + cpp <- findProgram "Cmm preprocessor" progOpt [] <|> pure (programFromOpt progOpt (prgPath $ ccProgram cc) [])
|
|
| 170 | 164 | cmmCppSupportsG0 <- withTempDir $ \dir -> do
|
| 171 | 165 | let conftest = dir </> "conftest.c"
|
| 172 | 166 | writeFile conftest "int main(void) {}"
|
| ... | ... | @@ -181,14 +175,9 @@ findCmmCpp progOpt cc = checking "for a Cmm preprocessor" $ do |
| 181 | 175 | findCpp :: ProgOpt -> Cc -> M Cpp
|
| 182 | 176 | findCpp progOpt cc = checking "for C preprocessor" $ do
|
| 183 | 177 | -- Use the specified CPP or try to use the c compiler
|
| 184 | - foundCppProg <- findProgram "C preprocessor" progOpt [] <|> pure (programFromOpt progOpt (prgPath $ ccProgram cc) [])
|
|
| 185 | - -- Check whether the C preprocessor needs -std=gnu99 (only very old toolchains need this)
|
|
| 186 | - Cc cpp2 <- oneOf "cc doesn't support C99" $ map checkC99Support
|
|
| 187 | - [ Cc foundCppProg
|
|
| 188 | - , Cc (foundCppProg & _prgFlags %++ "-std=gnu99")
|
|
| 189 | - ]
|
|
| 178 | + cpp <- findProgram "C preprocessor" progOpt [] <|> pure (programFromOpt progOpt (prgPath $ ccProgram cc) [])
|
|
| 190 | 179 | -- Always add the -E flag to the CPP, regardless of the user options
|
| 191 | - let cppProgram = addFlagIfNew "-E" cpp2
|
|
| 180 | + let cppProgram = addFlagIfNew "-E" cpp
|
|
| 192 | 181 | return Cpp{cppProgram}
|
| 193 | 182 | |
| 194 | 183 | --------------------------------------------------------------------------------
|