Simon Peyton Jones pushed to branch wip/24279 at Glasgow Haskell Compiler / GHC
Commits:
-
b253013e
by Georgios Karachalias at 2025-11-07T17:21:57-05:00
-
ac7b737e
by Sylvain Henry at 2025-11-07T17:22:51-05:00
-
b44163d3
by Simon Peyton Jones at 2025-11-10T16:44:15+00:00
25 changed files:
- compiler/GHC/Builtin/Types/Prim.hs
- compiler/GHC/Core/Coercion.hs
- compiler/GHC/Core/Lint.hs
- compiler/GHC/Core/RoughMap.hs
- compiler/GHC/Core/Type.hs
- compiler/GHC/Core/Unify.hs
- compiler/GHC/Driver/Main.hs
- compiler/GHC/Driver/Pipeline.hs
- compiler/GHC/Linker/Deps.hs
- compiler/GHC/Linker/Types.hs
- compiler/GHC/Tc/Instance/Class.hs
- compiler/GHC/Unit/Home/ModInfo.hs
- compiler/GHC/Unit/Module/Status.hs
- compiler/GHC/Unit/Module/WholeCoreBindings.hs
- libraries/base/tests/all.T
- testsuite/driver/testlib.py
- testsuite/tests/driver/T20696/all.T
- testsuite/tests/driver/fat-iface/all.T
- testsuite/tests/indexed-types/should_fail/T21092.hs
- − testsuite/tests/indexed-types/should_fail/T21092.stderr
- testsuite/tests/indexed-types/should_fail/all.T
- testsuite/tests/splice-imports/all.T
- testsuite/tests/typecheck/should_fail/T24279.hs
- − testsuite/tests/typecheck/should_fail/T24279.stderr
- testsuite/tests/typecheck/should_fail/all.T
Changes:
| ... | ... | @@ -752,8 +752,9 @@ Specifically (a ~# b) :: CONSTRAINT (TupleRep []) |
| 752 | 752 | |
| 753 | 753 | Wrinkles
|
| 754 | 754 | |
| 755 | -(W1) Type and Constraint are considered distinct throughout GHC. But they
|
|
| 756 | - are not /apart/: see Note [Type and Constraint are not apart]
|
|
| 755 | +(W1) Type and Constraint are considered distinct throughout GHC.
|
|
| 756 | + That wasn't always the case:
|
|
| 757 | + see Historical Note [Type and Constraint are not apart]
|
|
| 757 | 758 | |
| 758 | 759 | (W2) We need two absent-error Ids, aBSENT_ERROR_ID for types of kind Type, and
|
| 759 | 760 | aBSENT_CONSTRAINT_ERROR_ID for types of kind Constraint.
|
| ... | ... | @@ -768,8 +769,24 @@ Wrinkles |
| 768 | 769 | of type TYPE rr. See (CPR2) in Note [Which types are unboxed?] in
|
| 769 | 770 | GHC.Core.Opt.WorkWrap.Utils.
|
| 770 | 771 | |
| 771 | -Note [Type and Constraint are not apart]
|
|
| 772 | -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
| 772 | +-------------------------------------------------------------
|
|
| 773 | +Historical Note [Type and Constraint are not apart]
|
|
| 774 | +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
| 775 | +Nov 2025:
|
|
| 776 | + In the past, Type and Constraint were carefully coonsiderd to be
|
|
| 777 | + not /apart/. But the necessity for that vanished with unary classes
|
|
| 778 | + (see Note [Unary class magic]), done in
|
|
| 779 | + |
|
| 780 | + commit 9bd7fcc518111a1549c98720c222cdbabd32ed46
|
|
| 781 | + Author: Simon Peyton Jones <simon.peytonjones@gmail.com>
|
|
| 782 | + Date: Tue Apr 15 17:43:46 2025 +0100
|
|
| 783 | + Implement unary classes
|
|
| 784 | + |
|
| 785 | + So now Type and Constraint are simply distinct type constructors, just as
|
|
| 786 | + much as Int and Bool.
|
|
| 787 | + |
|
| 788 | + The rest of this Note is preserved for historical interest.
|
|
| 789 | + |
|
| 773 | 790 | Type and Constraint are not equal (eqType) but they are not /apart/
|
| 774 | 791 | either. Reason (c.f. #7451):
|
| 775 | 792 | |
| ... | ... | @@ -841,6 +858,9 @@ Wrinkles |
| 841 | 858 | So in GHC.Tc.Instance.Class.matchTypeable, Type and Constraint are
|
| 842 | 859 | treated as separate TyCons; i.e. given no special treatment.
|
| 843 | 860 | |
| 861 | +End of Historical Note
|
|
| 862 | +-------------------------------------------------------------
|
|
| 863 | + |
|
| 844 | 864 | Note [RuntimeRep polymorphism]
|
| 845 | 865 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| 846 | 866 | Generally speaking, you can't be polymorphic in `RuntimeRep`. E.g
|
| ... | ... | @@ -641,11 +641,6 @@ eqTyConRole tc |
| 641 | 641 | |
| 642 | 642 | -- | Given a coercion `co :: (t1 :: TYPE r1) ~ (t2 :: TYPE r2)`
|
| 643 | 643 | -- produce a coercion `rep_co :: r1 ~ r2`
|
| 644 | --- But actually it is possible that
|
|
| 645 | --- co :: (t1 :: CONSTRAINT r1) ~ (t2 :: CONSTRAINT r2)
|
|
| 646 | --- or co :: (t1 :: TYPE r1) ~ (t2 :: CONSTRAINT r2)
|
|
| 647 | --- or co :: (t1 :: CONSTRAINT r1) ~ (t2 :: TYPE r2)
|
|
| 648 | --- See Note [mkRuntimeRepCo]
|
|
| 649 | 644 | mkRuntimeRepCo :: HasDebugCallStack => Coercion -> Coercion
|
| 650 | 645 | mkRuntimeRepCo co
|
| 651 | 646 | = assert (isTYPEorCONSTRAINT k1 && isTYPEorCONSTRAINT k2) $
|
| ... | ... | @@ -654,26 +649,6 @@ mkRuntimeRepCo co |
| 654 | 649 | kind_co = mkKindCo co -- kind_co :: TYPE r1 ~ TYPE r2
|
| 655 | 650 | Pair k1 k2 = coercionKind kind_co
|
| 656 | 651 | |
| 657 | -{- Note [mkRuntimeRepCo]
|
|
| 658 | -~~~~~~~~~~~~~~~~~~~~~~~~
|
|
| 659 | -Given
|
|
| 660 | - class C a where { op :: Maybe a }
|
|
| 661 | -we will get an axiom
|
|
| 662 | - axC a :: (C a :: CONSTRAINT r1) ~ (Maybe a :: TYPE r2)
|
|
| 663 | -(See Note [Type and Constraint are not apart] in GHC.Builtin.Types.Prim.)
|
|
| 664 | - |
|
| 665 | -Then we may call mkRuntimeRepCo on (axC ty), and that will return
|
|
| 666 | - mkSelCo (SelTyCon 0 Nominal) (Kind (axC ty)) :: r1 ~ r2
|
|
| 667 | - |
|
| 668 | -So mkSelCo needs to be happy with decomposing a coercion of kind
|
|
| 669 | - CONSTRAINT r1 ~ TYPE r2
|
|
| 670 | - |
|
| 671 | -Hence the use of `tyConIsTYPEorCONSTRAINT` in the assertion `good_call`
|
|
| 672 | -in `mkSelCo`. See #23018 for a concrete example. (In this context it's
|
|
| 673 | -important that TYPE and CONSTRAINT have the same arity and kind, not
|
|
| 674 | -merely that they are not-apart; otherwise SelCo would not make sense.)
|
|
| 675 | --}
|
|
| 676 | - |
|
| 677 | 652 | isReflCoVar_maybe :: Var -> Maybe Coercion
|
| 678 | 653 | -- If cv :: t~t then isReflCoVar_maybe cv = Just (Refl t)
|
| 679 | 654 | -- Works on all kinds of Vars, not just CoVars
|
| ... | ... | @@ -1305,8 +1280,7 @@ mkSelCo_maybe cs co |
| 1305 | 1280 | , Just (tc2, tys2) <- splitTyConApp_maybe ty2
|
| 1306 | 1281 | , let { len1 = length tys1
|
| 1307 | 1282 | ; len2 = length tys2 }
|
| 1308 | - = (tc1 == tc2 || (tyConIsTYPEorCONSTRAINT tc1 && tyConIsTYPEorCONSTRAINT tc2))
|
|
| 1309 | - -- tyConIsTYPEorCONSTRAINT: see Note [mkRuntimeRepCo]
|
|
| 1283 | + = tc1 == tc2
|
|
| 1310 | 1284 | && len1 == len2
|
| 1311 | 1285 | && n < len1
|
| 1312 | 1286 | && r == tyConRole (coercionRole co) tc1 n
|
| ... | ... | @@ -2891,13 +2891,9 @@ lint_branch ax_tc (CoAxBranch { cab_tvs = tvs, cab_cvs = cvs |
| 2891 | 2891 | hang (text "Inhomogeneous axiom")
|
| 2892 | 2892 | 2 (text "lhs:" <+> ppr lhs <+> dcolon <+> ppr lhs_kind $$
|
| 2893 | 2893 | text "rhs:" <+> ppr rhs <+> dcolon <+> ppr rhs_kind) }
|
| 2894 | - -- Type and Constraint are not Apart, so this test allows
|
|
| 2895 | - -- the newtype axiom for a single-method class. Indeed the
|
|
| 2896 | - -- whole reason Type and Constraint are not Apart is to allow
|
|
| 2897 | - -- such axioms!
|
|
| 2898 | 2894 | |
| 2899 | --- these checks do not apply to newtype axioms
|
|
| 2900 | 2895 | lint_family_branch :: TyCon -> CoAxBranch -> LintM ()
|
| 2896 | +-- These checks do not apply to newtype axioms
|
|
| 2901 | 2897 | lint_family_branch fam_tc br@(CoAxBranch { cab_tvs = tvs
|
| 2902 | 2898 | , cab_eta_tvs = eta_tvs
|
| 2903 | 2899 | , cab_cvs = cvs
|
| ... | ... | @@ -36,7 +36,6 @@ import GHC.Core.Type |
| 36 | 36 | import GHC.Utils.Outputable
|
| 37 | 37 | import GHC.Types.Name
|
| 38 | 38 | import GHC.Types.Name.Env
|
| 39 | -import GHC.Builtin.Types.Prim( cONSTRAINTTyConName, tYPETyConName )
|
|
| 40 | 39 | |
| 41 | 40 | import Control.Monad (join)
|
| 42 | 41 | import Data.Data (Data)
|
| ... | ... | @@ -347,16 +346,7 @@ typeToRoughMatchTc ty |
| 347 | 346 | |
| 348 | 347 | roughMatchTyConName :: TyCon -> Name
|
| 349 | 348 | roughMatchTyConName tc
|
| 350 | - | tc_name == cONSTRAINTTyConName
|
|
| 351 | - = tYPETyConName -- TYPE and CONSTRAINT are not apart, so they must use
|
|
| 352 | - -- the same rough-map key. We arbitrarily use TYPE.
|
|
| 353 | - -- See Note [Type and Constraint are not apart]
|
|
| 354 | - -- wrinkle (W1) in GHC.Builtin.Types.Prim
|
|
| 355 | - | otherwise
|
|
| 356 | - = assertPpr (isGenerativeTyCon tc Nominal) (ppr tc) tc_name
|
|
| 357 | - where
|
|
| 358 | - tc_name = tyConName tc
|
|
| 359 | - |
|
| 349 | + = assertPpr (isGenerativeTyCon tc Nominal) (ppr tc) (tyConName tc)
|
|
| 360 | 350 | |
| 361 | 351 | -- | Trie of @[RoughMatchTc]@
|
| 362 | 352 | --
|
| ... | ... | @@ -1421,8 +1421,6 @@ piResultTy ty arg = case piResultTy_maybe ty arg of |
| 1421 | 1421 | Nothing -> pprPanic "piResultTy" (ppr ty $$ ppr arg)
|
| 1422 | 1422 | |
| 1423 | 1423 | piResultTy_maybe :: Type -> Type -> Maybe Type
|
| 1424 | --- We don't need a 'tc' version, because
|
|
| 1425 | --- this function behaves the same for Type and Constraint
|
|
| 1426 | 1424 | piResultTy_maybe ty arg = case coreFullView ty of
|
| 1427 | 1425 | FunTy { ft_res = res } -> Just res
|
| 1428 | 1426 |
| ... | ... | @@ -27,7 +27,6 @@ import GHC.Prelude |
| 27 | 27 | import GHC.Types.Var
|
| 28 | 28 | import GHC.Types.Var.Env
|
| 29 | 29 | import GHC.Types.Var.Set
|
| 30 | -import GHC.Builtin.Names( tYPETyConKey, cONSTRAINTTyConKey )
|
|
| 31 | 30 | import GHC.Core.Type hiding ( getTvSubstEnv )
|
| 32 | 31 | import GHC.Core.Coercion hiding ( getCvSubstEnv )
|
| 33 | 32 | import GHC.Core.Predicate( scopedSort )
|
| ... | ... | @@ -98,8 +97,6 @@ of ways. Here we summarise, but see Note [Specification of unification]. |
| 98 | 97 | See Note [Apartness and type families]
|
| 99 | 98 | * MARInfinite (occurs check):
|
| 100 | 99 | See Note [Infinitary substitutions]
|
| 101 | - * MARTypeVsConstraint:
|
|
| 102 | - See Note [Type and Constraint are not apart] in GHC.Builtin.Types.Prim
|
|
| 103 | 100 | * MARCast (obscure):
|
| 104 | 101 | See (KCU2) in Note [Kind coercions in Unify]
|
| 105 | 102 | |
| ... | ... | @@ -997,16 +994,12 @@ data UnifyResultM a = Unifiable a -- the subst that unifies the types |
| 997 | 994 | |
| 998 | 995 | -- | Why are two types 'MaybeApart'? 'MARInfinite' takes precedence:
|
| 999 | 996 | -- This is used (only) in Note [Infinitary substitution in lookup] in GHC.Core.InstEnv
|
| 1000 | --- As of Feb 2022, we never differentiate between MARTypeFamily and MARTypeVsConstraint;
|
|
| 1001 | --- it's really only MARInfinite that's interesting here.
|
|
| 997 | +-- It's really only MARInfinite that's interesting here.
|
|
| 1002 | 998 | data MaybeApartReason
|
| 1003 | 999 | = MARTypeFamily -- ^ matching e.g. F Int ~? Bool
|
| 1004 | 1000 | |
| 1005 | 1001 | | MARInfinite -- ^ matching e.g. a ~? Maybe a
|
| 1006 | 1002 | |
| 1007 | - | MARTypeVsConstraint -- ^ matching Type ~? Constraint or the arrow types
|
|
| 1008 | - -- See Note [Type and Constraint are not apart] in GHC.Builtin.Types.Prim
|
|
| 1009 | - |
|
| 1010 | 1003 | | MARCast -- ^ Very obscure.
|
| 1011 | 1004 | -- See (KCU2) in Note [Kind coercions in Unify]
|
| 1012 | 1005 | |
| ... | ... | @@ -1015,13 +1008,11 @@ combineMAR :: MaybeApartReason -> MaybeApartReason -> MaybeApartReason |
| 1015 | 1008 | -- See (UR1) in Note [Unification result] for why MARInfinite wins
|
| 1016 | 1009 | combineMAR MARInfinite _ = MARInfinite -- MARInfinite wins
|
| 1017 | 1010 | combineMAR MARTypeFamily r = r -- Otherwise it doesn't really matter
|
| 1018 | -combineMAR MARTypeVsConstraint r = r
|
|
| 1019 | 1011 | combineMAR MARCast r = r
|
| 1020 | 1012 | |
| 1021 | 1013 | instance Outputable MaybeApartReason where
|
| 1022 | 1014 | ppr MARTypeFamily = text "MARTypeFamily"
|
| 1023 | 1015 | ppr MARInfinite = text "MARInfinite"
|
| 1024 | - ppr MARTypeVsConstraint = text "MARTypeVsConstraint"
|
|
| 1025 | 1016 | ppr MARCast = text "MARCast"
|
| 1026 | 1017 | |
| 1027 | 1018 | instance Semigroup MaybeApartReason where
|
| ... | ... | @@ -1729,30 +1720,6 @@ unify_ty env ty1 ty2 kco |
| 1729 | 1720 | ; unify_tc_app env tc1 tys1 tys2
|
| 1730 | 1721 | }
|
| 1731 | 1722 | |
| 1732 | - -- TYPE and CONSTRAINT are not Apart
|
|
| 1733 | - -- See Note [Type and Constraint are not apart] in GHC.Builtin.Types.Prim
|
|
| 1734 | - -- NB: at this point we know that the two TyCons do not match
|
|
| 1735 | - | Just (tc1,_) <- mb_tc_app1, let u1 = tyConUnique tc1
|
|
| 1736 | - , Just (tc2,_) <- mb_tc_app2, let u2 = tyConUnique tc2
|
|
| 1737 | - , (u1 == tYPETyConKey && u2 == cONSTRAINTTyConKey) ||
|
|
| 1738 | - (u2 == tYPETyConKey && u1 == cONSTRAINTTyConKey)
|
|
| 1739 | - = maybeApart MARTypeVsConstraint
|
|
| 1740 | - -- We don't bother to look inside; wrinkle (W3) in GHC.Builtin.Types.Prim
|
|
| 1741 | - -- Note [Type and Constraint are not apart]
|
|
| 1742 | - |
|
| 1743 | - -- The arrow types are not Apart
|
|
| 1744 | - -- See Note [Type and Constraint are not apart] in GHC.Builtin.Types.Prim
|
|
| 1745 | - -- wrinkle (W2)
|
|
| 1746 | - -- NB1: at this point we know that the two TyCons do not match
|
|
| 1747 | - -- NB2: In the common FunTy/FunTy case you might wonder if we want to go via
|
|
| 1748 | - -- splitTyConApp_maybe. But yes we do: we need to look at those implied
|
|
| 1749 | - -- kind argument in order to satisfy (Unification Kind Invariant)
|
|
| 1750 | - | FunTy {} <- ty1
|
|
| 1751 | - , FunTy {} <- ty2
|
|
| 1752 | - = maybeApart MARTypeVsConstraint
|
|
| 1753 | - -- We don't bother to look inside; wrinkle (W3) in GHC.Builtin.Types.Prim
|
|
| 1754 | - -- Note [Type and Constraint are not apart]
|
|
| 1755 | - |
|
| 1756 | 1723 | where
|
| 1757 | 1724 | mb_tc_app1 = splitTyConApp_maybe ty1
|
| 1758 | 1725 | mb_tc_app2 = splitTyConApp_maybe ty2
|
| ... | ... | @@ -277,6 +277,7 @@ import Data.Data hiding (Fixity, TyCon) |
| 277 | 277 | import Data.Functor ((<&>))
|
| 278 | 278 | import Data.List ( nub, isPrefixOf, partition )
|
| 279 | 279 | import qualified Data.List.NonEmpty as NE
|
| 280 | +import Data.Traversable (for)
|
|
| 280 | 281 | import Control.Monad
|
| 281 | 282 | import Data.IORef
|
| 282 | 283 | import System.FilePath as FilePath
|
| ... | ... | @@ -850,11 +851,11 @@ hscRecompStatus |
| 850 | 851 | if | not (backendGeneratesCode (backend lcl_dflags)) -> do
|
| 851 | 852 | -- No need for a linkable, we're good to go
|
| 852 | 853 | msg UpToDate
|
| 853 | - return $ HscUpToDate checked_iface emptyHomeModInfoLinkable
|
|
| 854 | + return $ HscUpToDate checked_iface emptyRecompLinkables
|
|
| 854 | 855 | | not (backendGeneratesCodeForHsBoot (backend lcl_dflags))
|
| 855 | 856 | , IsBoot <- isBootSummary mod_summary -> do
|
| 856 | 857 | msg UpToDate
|
| 857 | - return $ HscUpToDate checked_iface emptyHomeModInfoLinkable
|
|
| 858 | + return $ HscUpToDate checked_iface emptyRecompLinkables
|
|
| 858 | 859 | |
| 859 | 860 | -- Always recompile with the JS backend when TH is enabled until
|
| 860 | 861 | -- #23013 is fixed.
|
| ... | ... | @@ -883,7 +884,7 @@ hscRecompStatus |
| 883 | 884 | let just_o = justObjects <$> obj_linkable
|
| 884 | 885 | |
| 885 | 886 | bytecode_or_object_code
|
| 886 | - | gopt Opt_WriteByteCode lcl_dflags = justBytecode <$> definitely_bc
|
|
| 887 | + | gopt Opt_WriteByteCode lcl_dflags = justBytecode . Left <$> definitely_bc
|
|
| 887 | 888 | | otherwise = (justBytecode <$> maybe_bc) `choose` just_o
|
| 888 | 889 | |
| 889 | 890 | |
| ... | ... | @@ -900,13 +901,13 @@ hscRecompStatus |
| 900 | 901 | definitely_bc = bc_obj_linkable `prefer` bc_in_memory_linkable
|
| 901 | 902 | |
| 902 | 903 | -- If not -fwrite-byte-code, then we could use core bindings or object code if that's available.
|
| 903 | - maybe_bc = bc_in_memory_linkable `choose`
|
|
| 904 | - bc_obj_linkable `choose`
|
|
| 905 | - bc_core_linkable
|
|
| 904 | + maybe_bc = (Left <$> bc_in_memory_linkable) `choose`
|
|
| 905 | + (Left <$> bc_obj_linkable) `choose`
|
|
| 906 | + (Right <$> bc_core_linkable)
|
|
| 906 | 907 | |
| 907 | 908 | bc_result = if gopt Opt_WriteByteCode lcl_dflags
|
| 908 | 909 | -- If the byte-code artifact needs to be produced, then we certainly need bytecode.
|
| 909 | - then definitely_bc
|
|
| 910 | + then Left <$> definitely_bc
|
|
| 910 | 911 | else maybe_bc
|
| 911 | 912 | |
| 912 | 913 | trace_if (hsc_logger hsc_env)
|
| ... | ... | @@ -1021,14 +1022,13 @@ checkByteCodeFromObject hsc_env mod_sum = do |
| 1021 | 1022 | |
| 1022 | 1023 | -- | Attempt to load bytecode from whole core bindings in the interface if they exist.
|
| 1023 | 1024 | -- This is a legacy code-path, these days it should be preferred to use the bytecode object linkable.
|
| 1024 | -checkByteCodeFromIfaceCoreBindings :: HscEnv -> ModIface -> ModSummary -> IO (MaybeValidated Linkable)
|
|
| 1025 | +checkByteCodeFromIfaceCoreBindings :: HscEnv -> ModIface -> ModSummary -> IO (MaybeValidated WholeCoreBindingsLinkable)
|
|
| 1025 | 1026 | checkByteCodeFromIfaceCoreBindings _hsc_env iface mod_sum = do
|
| 1026 | 1027 | let
|
| 1027 | 1028 | this_mod = ms_mod mod_sum
|
| 1028 | 1029 | if_date = fromJust $ ms_iface_date mod_sum
|
| 1029 | 1030 | case iface_core_bindings iface (ms_location mod_sum) of
|
| 1030 | - Just fi -> do
|
|
| 1031 | - return (UpToDateItem (Linkable if_date this_mod (NE.singleton (CoreBindings fi))))
|
|
| 1031 | + Just fi -> return $ UpToDateItem (Linkable if_date this_mod fi)
|
|
| 1032 | 1032 | _ -> return $ outOfDateItemBecause MissingBytecode Nothing
|
| 1033 | 1033 | |
| 1034 | 1034 | --------------------------------------------------------------
|
| ... | ... | @@ -1142,20 +1142,22 @@ initWholeCoreBindings :: |
| 1142 | 1142 | HscEnv ->
|
| 1143 | 1143 | ModIface ->
|
| 1144 | 1144 | ModDetails ->
|
| 1145 | - Linkable ->
|
|
| 1146 | - IO Linkable
|
|
| 1147 | -initWholeCoreBindings hsc_env iface details (Linkable utc_time this_mod uls) = do
|
|
| 1148 | - Linkable utc_time this_mod <$> mapM (go hsc_env) uls
|
|
| 1145 | + RecompLinkables ->
|
|
| 1146 | + IO HomeModLinkable
|
|
| 1147 | +initWholeCoreBindings hsc_env iface details (RecompLinkables bc o) = do
|
|
| 1148 | + bc' <- go bc
|
|
| 1149 | + pure $ HomeModLinkable bc' o
|
|
| 1149 | 1150 | where
|
| 1150 | - go hsc_env' = \case
|
|
| 1151 | - CoreBindings wcb -> do
|
|
| 1151 | + type_env = md_types details
|
|
| 1152 | + |
|
| 1153 | + go :: RecompBytecodeLinkable -> IO (Maybe Linkable)
|
|
| 1154 | + go (NormalLinkable l) = pure l
|
|
| 1155 | + go (WholeCoreBindingsLinkable wcbl) =
|
|
| 1156 | + fmap Just $ for wcbl $ \wcb -> do
|
|
| 1152 | 1157 | add_iface_to_hpt iface details hsc_env
|
| 1153 | 1158 | bco <- unsafeInterleaveIO $
|
| 1154 | - compileWholeCoreBindings hsc_env' type_env wcb
|
|
| 1155 | - pure (DotGBC bco)
|
|
| 1156 | - l -> pure l
|
|
| 1157 | - |
|
| 1158 | - type_env = md_types details
|
|
| 1159 | + compileWholeCoreBindings hsc_env type_env wcb
|
|
| 1160 | + pure $ NE.singleton (DotGBC bco)
|
|
| 1159 | 1161 | |
| 1160 | 1162 | -- | Hydrate interface Core bindings and compile them to bytecode.
|
| 1161 | 1163 | --
|
| ... | ... | @@ -109,6 +109,7 @@ import GHC.Unit.Env |
| 109 | 109 | import GHC.Unit.Finder
|
| 110 | 110 | import GHC.Unit.Module.ModSummary
|
| 111 | 111 | import GHC.Unit.Module.ModIface
|
| 112 | +import GHC.Unit.Module.Status
|
|
| 112 | 113 | import GHC.Unit.Home.ModInfo
|
| 113 | 114 | import GHC.Unit.Home.PackageTable
|
| 114 | 115 | |
| ... | ... | @@ -249,8 +250,8 @@ compileOne' mHscMessage |
| 249 | 250 | (iface, linkable) <- runPipeline (hsc_hooks plugin_hsc_env) pipeline
|
| 250 | 251 | -- See Note [ModDetails and --make mode]
|
| 251 | 252 | details <- initModDetails plugin_hsc_env iface
|
| 252 | - linkable' <- traverse (initWholeCoreBindings plugin_hsc_env iface details) (homeMod_bytecode linkable)
|
|
| 253 | - return $! HomeModInfo iface details (linkable { homeMod_bytecode = linkable' })
|
|
| 253 | + linkable' <- initWholeCoreBindings plugin_hsc_env iface details linkable
|
|
| 254 | + return $! HomeModInfo iface details linkable'
|
|
| 254 | 255 | |
| 255 | 256 | where lcl_dflags = ms_hspp_opts summary
|
| 256 | 257 | location = ms_location summary
|
| ... | ... | @@ -759,7 +760,7 @@ preprocessPipeline pipe_env hsc_env input_fn = do |
| 759 | 760 | $ phaseIfFlag hsc_env flag def action
|
| 760 | 761 | |
| 761 | 762 | -- | The complete compilation pipeline, from start to finish
|
| 762 | -fullPipeline :: P m => PipeEnv -> HscEnv -> FilePath -> HscSource -> m (ModIface, HomeModLinkable)
|
|
| 763 | +fullPipeline :: P m => PipeEnv -> HscEnv -> FilePath -> HscSource -> m (ModIface, RecompLinkables)
|
|
| 763 | 764 | fullPipeline pipe_env hsc_env pp_fn src_flavour = do
|
| 764 | 765 | (dflags, input_fn) <- preprocessPipeline pipe_env hsc_env pp_fn
|
| 765 | 766 | let hsc_env' = hscSetFlags dflags hsc_env
|
| ... | ... | @@ -768,7 +769,7 @@ fullPipeline pipe_env hsc_env pp_fn src_flavour = do |
| 768 | 769 | hscPipeline pipe_env (hsc_env_with_plugins, mod_sum, hsc_recomp_status)
|
| 769 | 770 | |
| 770 | 771 | -- | Everything after preprocess
|
| 771 | -hscPipeline :: P m => PipeEnv -> ((HscEnv, ModSummary, HscRecompStatus)) -> m (ModIface, HomeModLinkable)
|
|
| 772 | +hscPipeline :: P m => PipeEnv -> (HscEnv, ModSummary, HscRecompStatus) -> m (ModIface, RecompLinkables)
|
|
| 772 | 773 | hscPipeline pipe_env (hsc_env_with_plugins, mod_sum, hsc_recomp_status) = do
|
| 773 | 774 | case hsc_recomp_status of
|
| 774 | 775 | HscUpToDate iface mb_linkable -> return (iface, mb_linkable)
|
| ... | ... | @@ -777,7 +778,7 @@ hscPipeline pipe_env (hsc_env_with_plugins, mod_sum, hsc_recomp_status) = do |
| 777 | 778 | hscBackendAction <- use (T_HscPostTc hsc_env_with_plugins mod_sum tc_result warnings mb_old_hash )
|
| 778 | 779 | hscBackendPipeline pipe_env hsc_env_with_plugins mod_sum hscBackendAction
|
| 779 | 780 | |
| 780 | -hscBackendPipeline :: P m => PipeEnv -> HscEnv -> ModSummary -> HscBackendAction -> m (ModIface, HomeModLinkable)
|
|
| 781 | +hscBackendPipeline :: P m => PipeEnv -> HscEnv -> ModSummary -> HscBackendAction -> m (ModIface, RecompLinkables)
|
|
| 781 | 782 | hscBackendPipeline pipe_env hsc_env mod_sum result =
|
| 782 | 783 | if backendGeneratesCode (backend (hsc_dflags hsc_env)) then
|
| 783 | 784 | do
|
| ... | ... | @@ -796,15 +797,15 @@ hscBackendPipeline pipe_env hsc_env mod_sum result = |
| 796 | 797 | return res
|
| 797 | 798 | else
|
| 798 | 799 | case result of
|
| 799 | - HscUpdate iface -> return (iface, emptyHomeModInfoLinkable)
|
|
| 800 | - HscRecomp {} -> (,) <$> liftIO (mkFullIface hsc_env (hscs_partial_iface result) Nothing Nothing NoStubs []) <*> pure emptyHomeModInfoLinkable
|
|
| 800 | + HscUpdate iface -> return (iface, emptyRecompLinkables)
|
|
| 801 | + HscRecomp {} -> (,) <$> liftIO (mkFullIface hsc_env (hscs_partial_iface result) Nothing Nothing NoStubs []) <*> pure emptyRecompLinkables
|
|
| 801 | 802 | |
| 802 | 803 | hscGenBackendPipeline :: P m
|
| 803 | 804 | => PipeEnv
|
| 804 | 805 | -> HscEnv
|
| 805 | 806 | -> ModSummary
|
| 806 | 807 | -> HscBackendAction
|
| 807 | - -> m (ModIface, HomeModLinkable)
|
|
| 808 | + -> m (ModIface, RecompLinkables)
|
|
| 808 | 809 | hscGenBackendPipeline pipe_env hsc_env mod_sum result = do
|
| 809 | 810 | let mod_name = moduleName (ms_mod mod_sum)
|
| 810 | 811 | src_flavour = (ms_hsc_src mod_sum)
|
| ... | ... | @@ -812,7 +813,7 @@ hscGenBackendPipeline pipe_env hsc_env mod_sum result = do |
| 812 | 813 | (fos, miface, mlinkable, o_file) <- use (T_HscBackend pipe_env hsc_env mod_name src_flavour location result)
|
| 813 | 814 | final_fp <- hscPostBackendPipeline pipe_env hsc_env (ms_hsc_src mod_sum) (backend (hsc_dflags hsc_env)) (Just location) o_file
|
| 814 | 815 | final_linkable <-
|
| 815 | - case final_fp of
|
|
| 816 | + safeCastHomeModLinkable <$> case final_fp of
|
|
| 816 | 817 | -- No object file produced, bytecode or NoBackend
|
| 817 | 818 | Nothing -> return mlinkable
|
| 818 | 819 | Just o_fp -> do
|
| ... | ... | @@ -936,7 +937,7 @@ pipelineStart pipe_env hsc_env input_fn mb_phase = |
| 936 | 937 | as :: P m => Bool -> m (Maybe FilePath)
|
| 937 | 938 | as use_cpp = asPipeline use_cpp pipe_env hsc_env Nothing input_fn
|
| 938 | 939 | |
| 939 | - objFromLinkable (_, homeMod_object -> Just (Linkable _ _ (DotO lnk _ :| []))) = Just lnk
|
|
| 940 | + objFromLinkable (_, recompLinkables_object -> Just (Linkable _ _ (DotO lnk _ :| []))) = Just lnk
|
|
| 940 | 941 | objFromLinkable _ = Nothing
|
| 941 | 942 | |
| 942 | 943 | fromPhase :: P m => Phase -> m (Maybe FilePath)
|
| ... | ... | @@ -33,7 +33,6 @@ import GHC.Utils.Error |
| 33 | 33 | import GHC.Unit.Env
|
| 34 | 34 | import GHC.Unit.Finder
|
| 35 | 35 | import GHC.Unit.Module
|
| 36 | -import GHC.Unit.Module.WholeCoreBindings
|
|
| 37 | 36 | import GHC.Unit.Home.ModInfo
|
| 38 | 37 | |
| 39 | 38 | import GHC.Iface.Errors.Types
|
| ... | ... | @@ -206,10 +205,7 @@ get_link_deps opts pls maybe_normal_osuf span mods = do |
| 206 | 205 | DotO file ForeignObject -> pure (DotO file ForeignObject)
|
| 207 | 206 | DotA fp -> panic ("adjust_ul DotA " ++ show fp)
|
| 208 | 207 | DotDLL fp -> panic ("adjust_ul DotDLL " ++ show fp)
|
| 209 | - DotGBC {} -> pure part
|
|
| 210 | - CoreBindings WholeCoreBindings {wcb_module} ->
|
|
| 211 | - pprPanic "Unhydrated core bindings" (ppr wcb_module)
|
|
| 212 | - |
|
| 208 | + DotGBC {} -> pure part
|
|
| 213 | 209 | |
| 214 | 210 | |
| 215 | 211 | {-
|
| 1 | 1 | {-# LANGUAGE TypeApplications #-}
|
| 2 | 2 | {-# LANGUAGE LambdaCase #-}
|
| 3 | +{-# LANGUAGE DeriveTraversable #-}
|
|
| 3 | 4 | |
| 4 | 5 | -----------------------------------------------------------------------------
|
| 5 | 6 | --
|
| ... | ... | @@ -30,7 +31,9 @@ module GHC.Linker.Types |
| 30 | 31 | , PkgsLoaded
|
| 31 | 32 | |
| 32 | 33 | -- * Linkable
|
| 33 | - , Linkable(..)
|
|
| 34 | + , Linkable
|
|
| 35 | + , WholeCoreBindingsLinkable
|
|
| 36 | + , LinkableWith(..)
|
|
| 34 | 37 | , mkModuleByteCodeLinkable
|
| 35 | 38 | , LinkablePart(..)
|
| 36 | 39 | , LinkableObjectSort (..)
|
| ... | ... | @@ -254,7 +257,7 @@ instance Outputable LoadedPkgInfo where |
| 254 | 257 | |
| 255 | 258 | |
| 256 | 259 | -- | Information we can use to dynamically link modules into the compiler
|
| 257 | -data Linkable = Linkable
|
|
| 260 | +data LinkableWith parts = Linkable
|
|
| 258 | 261 | { linkableTime :: !UTCTime
|
| 259 | 262 | -- ^ Time at which this linkable was built
|
| 260 | 263 | -- (i.e. when the bytecodes were produced,
|
| ... | ... | @@ -263,9 +266,13 @@ data Linkable = Linkable |
| 263 | 266 | , linkableModule :: !Module
|
| 264 | 267 | -- ^ The linkable module itself
|
| 265 | 268 | |
| 266 | - , linkableParts :: NonEmpty LinkablePart
|
|
| 269 | + , linkableParts :: parts
|
|
| 267 | 270 | -- ^ Files and chunks of code to link.
|
| 268 | - }
|
|
| 271 | + } deriving (Functor, Traversable, Foldable)
|
|
| 272 | + |
|
| 273 | +type Linkable = LinkableWith (NonEmpty LinkablePart)
|
|
| 274 | + |
|
| 275 | +type WholeCoreBindingsLinkable = LinkableWith WholeCoreBindings
|
|
| 269 | 276 | |
| 270 | 277 | type LinkableSet = ModuleEnv Linkable
|
| 271 | 278 | |
| ... | ... | @@ -282,7 +289,7 @@ unionLinkableSet = plusModuleEnv_C go |
| 282 | 289 | | linkableTime l1 > linkableTime l2 = l1
|
| 283 | 290 | | otherwise = l2
|
| 284 | 291 | |
| 285 | -instance Outputable Linkable where
|
|
| 292 | +instance Outputable a => Outputable (LinkableWith a) where
|
|
| 286 | 293 | ppr (Linkable when_made mod parts)
|
| 287 | 294 | = (text "Linkable" <+> parens (text (show when_made)) <+> ppr mod)
|
| 288 | 295 | $$ nest 3 (ppr parts)
|
| ... | ... | @@ -318,11 +325,6 @@ data LinkablePart |
| 318 | 325 | | DotDLL FilePath
|
| 319 | 326 | -- ^ Dynamically linked library file (.so, .dll, .dylib)
|
| 320 | 327 | |
| 321 | - | CoreBindings WholeCoreBindings
|
|
| 322 | - -- ^ Serialised core which we can turn into BCOs (or object files), or
|
|
| 323 | - -- used by some other backend See Note [Interface Files with Core
|
|
| 324 | - -- Definitions]
|
|
| 325 | - |
|
| 326 | 328 | | DotGBC ModuleByteCode
|
| 327 | 329 | -- ^ A byte-code object, lives only in memory.
|
| 328 | 330 | |
| ... | ... | @@ -350,7 +352,6 @@ instance Outputable LinkablePart where |
| 350 | 352 | ppr (DotA path) = text "DotA" <+> text path
|
| 351 | 353 | ppr (DotDLL path) = text "DotDLL" <+> text path
|
| 352 | 354 | ppr (DotGBC bco) = text "DotGBC" <+> ppr bco
|
| 353 | - ppr (CoreBindings {}) = text "CoreBindings"
|
|
| 354 | 355 | |
| 355 | 356 | -- | Return true if the linkable only consists of native code (no BCO)
|
| 356 | 357 | linkableIsNativeCodeOnly :: Linkable -> Bool
|
| ... | ... | @@ -391,7 +392,6 @@ isNativeCode = \case |
| 391 | 392 | DotA {} -> True
|
| 392 | 393 | DotDLL {} -> True
|
| 393 | 394 | DotGBC {} -> False
|
| 394 | - CoreBindings {} -> False
|
|
| 395 | 395 | |
| 396 | 396 | -- | Is the part a native library? (.so/.dll)
|
| 397 | 397 | isNativeLib :: LinkablePart -> Bool
|
| ... | ... | @@ -400,7 +400,6 @@ isNativeLib = \case |
| 400 | 400 | DotA {} -> True
|
| 401 | 401 | DotDLL {} -> True
|
| 402 | 402 | DotGBC {} -> False
|
| 403 | - CoreBindings {} -> False
|
|
| 404 | 403 | |
| 405 | 404 | -- | Get the FilePath of linkable part (if applicable)
|
| 406 | 405 | linkablePartPath :: LinkablePart -> Maybe FilePath
|
| ... | ... | @@ -408,7 +407,6 @@ linkablePartPath = \case |
| 408 | 407 | DotO fn _ -> Just fn
|
| 409 | 408 | DotA fn -> Just fn
|
| 410 | 409 | DotDLL fn -> Just fn
|
| 411 | - CoreBindings {} -> Nothing
|
|
| 412 | 410 | DotGBC {} -> Nothing
|
| 413 | 411 | |
| 414 | 412 | -- | Return the paths of all object code files (.o, .a, .so) contained in this
|
| ... | ... | @@ -418,7 +416,6 @@ linkablePartNativePaths = \case |
| 418 | 416 | DotO fn _ -> [fn]
|
| 419 | 417 | DotA fn -> [fn]
|
| 420 | 418 | DotDLL fn -> [fn]
|
| 421 | - CoreBindings {} -> []
|
|
| 422 | 419 | DotGBC {} -> []
|
| 423 | 420 | |
| 424 | 421 | -- | Return the paths of all object files (.o) contained in this 'LinkablePart'.
|
| ... | ... | @@ -427,7 +424,6 @@ linkablePartObjectPaths = \case |
| 427 | 424 | DotO fn _ -> [fn]
|
| 428 | 425 | DotA _ -> []
|
| 429 | 426 | DotDLL _ -> []
|
| 430 | - CoreBindings {} -> []
|
|
| 431 | 427 | DotGBC bco -> gbc_foreign_files bco
|
| 432 | 428 | |
| 433 | 429 | -- | Retrieve the compiled byte-code from the linkable part.
|
| ... | ... | @@ -444,12 +440,11 @@ linkableFilter f linkable = do |
| 444 | 440 | Just linkable {linkableParts = new}
|
| 445 | 441 | |
| 446 | 442 | linkablePartNative :: LinkablePart -> [LinkablePart]
|
| 447 | -linkablePartNative = \case
|
|
| 448 | - u@DotO {} -> [u]
|
|
| 449 | - u@DotA {} -> [u]
|
|
| 450 | - u@DotDLL {} -> [u]
|
|
| 443 | +linkablePartNative u = case u of
|
|
| 444 | + DotO {} -> [u]
|
|
| 445 | + DotA {} -> [u]
|
|
| 446 | + DotDLL {} -> [u]
|
|
| 451 | 447 | DotGBC bco -> [DotO f ForeignObject | f <- gbc_foreign_files bco]
|
| 452 | - _ -> []
|
|
| 453 | 448 | |
| 454 | 449 | linkablePartByteCode :: LinkablePart -> [LinkablePart]
|
| 455 | 450 | linkablePartByteCode = \case
|
| ... | ... | @@ -963,11 +963,6 @@ matchTypeable clas [k,t] -- clas = Typeable |
| 963 | 963 | | k `eqType` naturalTy = doTyLit knownNatClassName t
|
| 964 | 964 | | k `eqType` typeSymbolKind = doTyLit knownSymbolClassName t
|
| 965 | 965 | | k `eqType` charTy = doTyLit knownCharClassName t
|
| 966 | - |
|
| 967 | - -- TyCon applied to its kind args
|
|
| 968 | - -- No special treatment of Type and Constraint; they get distinct TypeReps
|
|
| 969 | - -- see wrinkle (W4) of Note [Type and Constraint are not apart]
|
|
| 970 | - -- in GHC.Builtin.Types.Prim.
|
|
| 971 | 966 | | Just (tc, ks) <- splitTyConApp_maybe t -- See Note [Typeable (T a b c)]
|
| 972 | 967 | , onlyNamedBndrsApplied tc ks = doTyConApp clas t tc ks
|
| 973 | 968 |
| ... | ... | @@ -3,13 +3,10 @@ |
| 3 | 3 | module GHC.Unit.Home.ModInfo
|
| 4 | 4 | (
|
| 5 | 5 | HomeModInfo (..)
|
| 6 | - , HomeModLinkable(..)
|
|
| 6 | + , HomeModLinkable (..)
|
|
| 7 | 7 | , homeModInfoObject
|
| 8 | 8 | , homeModInfoByteCode
|
| 9 | 9 | , emptyHomeModInfoLinkable
|
| 10 | - , justBytecode
|
|
| 11 | - , justObjects
|
|
| 12 | - , bytecodeAndObjects
|
|
| 13 | 10 | )
|
| 14 | 11 | where
|
| 15 | 12 | |
| ... | ... | @@ -18,11 +15,9 @@ import GHC.Prelude |
| 18 | 15 | import GHC.Unit.Module.ModIface
|
| 19 | 16 | import GHC.Unit.Module.ModDetails
|
| 20 | 17 | |
| 21 | -import GHC.Linker.Types ( Linkable(..), linkableIsNativeCodeOnly )
|
|
| 18 | +import GHC.Linker.Types ( Linkable )
|
|
| 22 | 19 | |
| 23 | 20 | import GHC.Utils.Outputable
|
| 24 | -import GHC.Utils.Panic
|
|
| 25 | - |
|
| 26 | 21 | |
| 27 | 22 | -- | Information about modules in the package being compiled
|
| 28 | 23 | data HomeModInfo = HomeModInfo
|
| ... | ... | @@ -68,22 +63,6 @@ data HomeModLinkable = HomeModLinkable { homeMod_bytecode :: !(Maybe Linkable) |
| 68 | 63 | instance Outputable HomeModLinkable where
|
| 69 | 64 | ppr (HomeModLinkable l1 l2) = ppr l1 $$ ppr l2
|
| 70 | 65 | |
| 71 | -justBytecode :: Linkable -> HomeModLinkable
|
|
| 72 | -justBytecode lm =
|
|
| 73 | - assertPpr (not (linkableIsNativeCodeOnly lm)) (ppr lm)
|
|
| 74 | - $ emptyHomeModInfoLinkable { homeMod_bytecode = Just lm }
|
|
| 75 | - |
|
| 76 | -justObjects :: Linkable -> HomeModLinkable
|
|
| 77 | -justObjects lm =
|
|
| 78 | - assertPpr (linkableIsNativeCodeOnly lm) (ppr lm)
|
|
| 79 | - $ emptyHomeModInfoLinkable { homeMod_object = Just lm }
|
|
| 80 | - |
|
| 81 | -bytecodeAndObjects :: Linkable -> Linkable -> HomeModLinkable
|
|
| 82 | -bytecodeAndObjects bc o =
|
|
| 83 | - assertPpr (not (linkableIsNativeCodeOnly bc) && linkableIsNativeCodeOnly o) (ppr bc $$ ppr o)
|
|
| 84 | - (HomeModLinkable (Just bc) (Just o))
|
|
| 85 | - |
|
| 86 | - |
|
| 87 | 66 | {-
|
| 88 | 67 | Note [Home module build products]
|
| 89 | 68 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| 1 | +{-# LANGUAGE LambdaCase #-}
|
|
| 2 | + |
|
| 1 | 3 | module GHC.Unit.Module.Status
|
| 2 | - ( HscBackendAction(..), HscRecompStatus (..)
|
|
| 4 | + ( HscBackendAction(..)
|
|
| 5 | + , HscRecompStatus (..)
|
|
| 6 | + , RecompLinkables (..)
|
|
| 7 | + , RecompBytecodeLinkable (..)
|
|
| 8 | + , emptyRecompLinkables
|
|
| 9 | + , justBytecode
|
|
| 10 | + , justObjects
|
|
| 11 | + , bytecodeAndObjects
|
|
| 12 | + , safeCastHomeModLinkable
|
|
| 3 | 13 | )
|
| 4 | 14 | where
|
| 5 | 15 | |
| 6 | 16 | import GHC.Prelude
|
| 7 | 17 | |
| 8 | 18 | import GHC.Unit
|
| 19 | +import GHC.Unit.Home.ModInfo
|
|
| 9 | 20 | import GHC.Unit.Module.ModGuts
|
| 10 | 21 | import GHC.Unit.Module.ModIface
|
| 11 | 22 | |
| 23 | +import GHC.Linker.Types ( Linkable, WholeCoreBindingsLinkable, linkableIsNativeCodeOnly )
|
|
| 24 | + |
|
| 12 | 25 | import GHC.Utils.Fingerprint
|
| 13 | 26 | import GHC.Utils.Outputable
|
| 14 | -import GHC.Unit.Home.ModInfo
|
|
| 27 | +import GHC.Utils.Panic
|
|
| 15 | 28 | |
| 16 | 29 | -- | Status of a module in incremental compilation
|
| 17 | 30 | data HscRecompStatus
|
| 18 | 31 | -- | Nothing to do because code already exists.
|
| 19 | - = HscUpToDate ModIface HomeModLinkable
|
|
| 32 | + = HscUpToDate ModIface RecompLinkables
|
|
| 20 | 33 | -- | Recompilation of module, or update of interface is required. Optionally
|
| 21 | 34 | -- pass the old interface hash to avoid updating the existing interface when
|
| 22 | 35 | -- it has not changed.
|
| ... | ... | @@ -41,6 +54,16 @@ data HscBackendAction |
| 41 | 54 | -- changed.
|
| 42 | 55 | }
|
| 43 | 56 | |
| 57 | +-- | Linkables produced by @hscRecompStatus@. Might contain serialized core
|
|
| 58 | +-- which can be turned into BCOs (or object files), or used by some other
|
|
| 59 | +-- backend. See Note [Interface Files with Core Definitions].
|
|
| 60 | +data RecompLinkables = RecompLinkables { recompLinkables_bytecode :: !RecompBytecodeLinkable
|
|
| 61 | + , recompLinkables_object :: !(Maybe Linkable) }
|
|
| 62 | + |
|
| 63 | +data RecompBytecodeLinkable
|
|
| 64 | + = NormalLinkable !(Maybe Linkable)
|
|
| 65 | + | WholeCoreBindingsLinkable !WholeCoreBindingsLinkable
|
|
| 66 | + |
|
| 44 | 67 | instance Outputable HscRecompStatus where
|
| 45 | 68 | ppr HscUpToDate{} = text "HscUpToDate"
|
| 46 | 69 | ppr HscRecompNeeded{} = text "HscRecompNeeded"
|
| ... | ... | @@ -48,3 +71,37 @@ instance Outputable HscRecompStatus where |
| 48 | 71 | instance Outputable HscBackendAction where
|
| 49 | 72 | ppr (HscUpdate mi) = text "Update:" <+> (ppr (mi_module mi))
|
| 50 | 73 | ppr (HscRecomp _ ml _mi _mf) = text "Recomp:" <+> ppr ml
|
| 74 | + |
|
| 75 | +instance Outputable RecompLinkables where
|
|
| 76 | + ppr (RecompLinkables l1 l2) = ppr l1 $$ ppr l2
|
|
| 77 | + |
|
| 78 | +instance Outputable RecompBytecodeLinkable where
|
|
| 79 | + ppr (NormalLinkable lm) = text "NormalLinkable:" <+> ppr lm
|
|
| 80 | + ppr (WholeCoreBindingsLinkable lm) = text "WholeCoreBindingsLinkable:" <+> ppr lm
|
|
| 81 | + |
|
| 82 | +emptyRecompLinkables :: RecompLinkables
|
|
| 83 | +emptyRecompLinkables = RecompLinkables (NormalLinkable Nothing) Nothing
|
|
| 84 | + |
|
| 85 | +safeCastHomeModLinkable :: HomeModLinkable -> RecompLinkables
|
|
| 86 | +safeCastHomeModLinkable (HomeModLinkable bc o) = RecompLinkables (NormalLinkable bc) o
|
|
| 87 | + |
|
| 88 | +justBytecode :: Either Linkable WholeCoreBindingsLinkable -> RecompLinkables
|
|
| 89 | +justBytecode = \case
|
|
| 90 | + Left lm ->
|
|
| 91 | + assertPpr (not (linkableIsNativeCodeOnly lm)) (ppr lm)
|
|
| 92 | + $ emptyRecompLinkables { recompLinkables_bytecode = NormalLinkable (Just lm) }
|
|
| 93 | + Right lm -> emptyRecompLinkables { recompLinkables_bytecode = WholeCoreBindingsLinkable lm }
|
|
| 94 | + |
|
| 95 | +justObjects :: Linkable -> RecompLinkables
|
|
| 96 | +justObjects lm =
|
|
| 97 | + assertPpr (linkableIsNativeCodeOnly lm) (ppr lm)
|
|
| 98 | + $ emptyRecompLinkables { recompLinkables_object = Just lm }
|
|
| 99 | + |
|
| 100 | +bytecodeAndObjects :: Either Linkable WholeCoreBindingsLinkable -> Linkable -> RecompLinkables
|
|
| 101 | +bytecodeAndObjects either_bc o = case either_bc of
|
|
| 102 | + Left bc ->
|
|
| 103 | + assertPpr (not (linkableIsNativeCodeOnly bc) && linkableIsNativeCodeOnly o) (ppr bc $$ ppr o)
|
|
| 104 | + $ RecompLinkables (NormalLinkable (Just bc)) (Just o)
|
|
| 105 | + Right bc ->
|
|
| 106 | + assertPpr (linkableIsNativeCodeOnly o) (ppr o)
|
|
| 107 | + $ RecompLinkables (WholeCoreBindingsLinkable bc) (Just o) |
| ... | ... | @@ -130,6 +130,9 @@ data WholeCoreBindings = WholeCoreBindings |
| 130 | 130 | , wcb_foreign :: IfaceForeign
|
| 131 | 131 | }
|
| 132 | 132 | |
| 133 | +instance Outputable WholeCoreBindings where
|
|
| 134 | + ppr (WholeCoreBindings {}) = text "WholeCoreBindings"
|
|
| 135 | + |
|
| 133 | 136 | {-
|
| 134 | 137 | Note [Foreign stubs and TH bytecode linking]
|
| 135 | 138 | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| ... | ... | @@ -80,7 +80,7 @@ test('length001', |
| 80 | 80 | # excessive amounts of stack space. So we specifically set a low
|
| 81 | 81 | # stack limit and mark it as failing under a few conditions.
|
| 82 | 82 | [extra_run_opts('+RTS -K8m -RTS'),
|
| 83 | - expect_fail_for(['normal', 'threaded1', 'llvm', 'nonmoving', 'nonmoving_thr', 'nonmoving_thr_ghc']),
|
|
| 83 | + expect_fail_for(['normal', 'threaded1', 'llvm', 'nonmoving', 'nonmoving_thr', 'nonmoving_thr_ghc', 'ext-interp']),
|
|
| 84 | 84 | # JS doesn't support stack limit so the test sometimes passes just fine. Therefore the test is
|
| 85 | 85 | # marked as fragile.
|
| 86 | 86 | when(js_arch(), fragile(22921))],
|
| ... | ... | @@ -352,6 +352,9 @@ def req_plugins( name, opts ): |
| 352 | 352 | """
|
| 353 | 353 | req_interp(name, opts)
|
| 354 | 354 | |
| 355 | + # Plugins aren't supported with the external interpreter (#14335)
|
|
| 356 | + expect_broken_for(14335,['ext-interp'])(name,opts)
|
|
| 357 | + |
|
| 355 | 358 | if config.cross:
|
| 356 | 359 | opts.skip = True
|
| 357 | 360 |
| 1 | 1 | test('T20696', [extra_files(['A.hs', 'B.hs', 'C.hs'])
|
| 2 | + , expect_broken_for(26552, ['ext-interp'])
|
|
| 2 | 3 | , unless(ghc_dynamic(), skip)], multimod_compile, ['A', ''])
|
| 3 | 4 | test('T20696-static', [extra_files(['A.hs', 'B.hs', 'C.hs'])
|
| 4 | 5 | , when(ghc_dynamic(), skip)], multimod_compile, ['A', '']) |
| ... | ... | @@ -9,12 +9,12 @@ test('fat010', [req_th,extra_files(['THA.hs', 'THB.hs', 'THC.hs']), copy_files], |
| 9 | 9 | # Check linking works when using -fbyte-code-and-object-code
|
| 10 | 10 | test('fat011', [req_th, extra_files(['FatMain.hs', 'FatTH.hs', 'FatQuote.hs'])], multimod_compile, ['FatMain', '-fbyte-code-and-object-code -fprefer-byte-code'])
|
| 11 | 11 | # Check that we use interpreter rather than enable dynamic-too if needed for TH
|
| 12 | -test('fat012', [req_th, unless(ghc_dynamic(), skip), extra_files(['FatTH.hs', 'FatQuote.hs'])], multimod_compile, ['FatTH', '-fprefer-byte-code'])
|
|
| 12 | +test('fat012', [req_th, expect_broken_for(26552, ['ext-interp']), unless(ghc_dynamic(), skip), extra_files(['FatTH.hs', 'FatQuote.hs'])], multimod_compile, ['FatTH', '-fprefer-byte-code'])
|
|
| 13 | 13 | # Check that no objects are generated if using -fno-code and -fprefer-byte-code
|
| 14 | 14 | test('fat013', [req_th, req_bco, extra_files(['FatTH.hs', 'FatQuote.hs'])], multimod_compile, ['FatTH', '-fno-code -fprefer-byte-code'])
|
| 15 | 15 | # When using interpreter should not produce objects
|
| 16 | 16 | test('fat014', [req_th, extra_files(['FatTH.hs', 'FatQuote.hs']), extra_run_opts('-fno-code')], ghci_script, ['fat014.script'])
|
| 17 | -test('fat015', [req_th, unless(ghc_dynamic(), skip), extra_files(['FatQuote.hs', 'FatQuote1.hs', 'FatQuote2.hs', 'FatTH1.hs', 'FatTH2.hs', 'FatTHTop.hs'])], multimod_compile, ['FatTHTop', '-fno-code -fwrite-interface'])
|
|
| 17 | +test('fat015', [req_th, expect_broken_for(26552, ['ext-interp']), unless(ghc_dynamic(), skip), extra_files(['FatQuote.hs', 'FatQuote1.hs', 'FatQuote2.hs', 'FatTH1.hs', 'FatTH2.hs', 'FatTHTop.hs'])], multimod_compile, ['FatTHTop', '-fno-code -fwrite-interface'])
|
|
| 18 | 18 | test('T22807', [req_th, unless(ghc_dynamic(), skip), extra_files(['T22807A.hs', 'T22807B.hs'])]
|
| 19 | 19 | , makefile_test, ['T22807'])
|
| 20 | 20 | test('T22807_ghci', [req_th, unless(ghc_dynamic(), skip), extra_files(['T22807_ghci.hs'])]
|
| ... | ... | @@ -7,3 +7,5 @@ type family F a |
| 7 | 7 | |
| 8 | 8 | type instance F Type = Int
|
| 9 | 9 | type instance F Constraint = Bool
|
| 10 | + |
|
| 11 | +-- Nov 2025: Type and Constraint are now Apart (#24279) |
| 1 | - |
|
| 2 | -T21092.hs:8:15: error: [GHC-34447]
|
|
| 3 | - Conflicting family instance declarations:
|
|
| 4 | - F (*) = Int -- Defined at T21092.hs:8:15
|
|
| 5 | - F Constraint = Bool -- Defined at T21092.hs:9:15 |
| ... | ... | @@ -107,7 +107,7 @@ test('T8368', normal, compile_fail, ['']) |
| 107 | 107 | test('T8368a', normal, compile_fail, [''])
|
| 108 | 108 | test('T8518', normal, compile_fail, [''])
|
| 109 | 109 | test('T9036', normal, compile_fail, [''])
|
| 110 | -test('T21092', normal, compile_fail, [''])
|
|
| 110 | +test('T21092', normal, compile, ['']) # Now compiles fine
|
|
| 111 | 111 | test('T9167', normal, compile_fail, [''])
|
| 112 | 112 | test('T9171', normal, compile_fail, [''])
|
| 113 | 113 | test('T9097', normal, compile_fail, [''])
|
| ... | ... | @@ -9,7 +9,7 @@ test('SI03', [extra_files(["SI01A.hs"])], multimod_compile_fail, ['SI03', '-v0'] |
| 9 | 9 | test('SI04', [extra_files(["SI01A.hs"])], multimod_compile, ['SI04', '-v0'])
|
| 10 | 10 | test('SI05', [extra_files(["SI01A.hs"])], multimod_compile_fail, ['SI05', '-v0'])
|
| 11 | 11 | test('SI06', [extra_files(["SI01A.hs"])], multimod_compile, ['SI06', '-v0'])
|
| 12 | -test('SI07', [unless(ghc_dynamic(), skip), extra_files(["SI05A.hs"])], multimod_compile, ['SI07', '-fwrite-interface -fno-code'])
|
|
| 12 | +test('SI07', [expect_broken_for(26552, ['ext-interp']), unless(ghc_dynamic(), skip), extra_files(["SI05A.hs"])], multimod_compile, ['SI07', '-fwrite-interface -fno-code'])
|
|
| 13 | 13 | # Instance tests
|
| 14 | 14 | test('SI08', [extra_files(["ClassA.hs", "InstanceA.hs"])], multimod_compile_fail, ['SI08', '-v0'])
|
| 15 | 15 | test('SI09', [extra_files(["ClassA.hs", "InstanceA.hs"])], multimod_compile, ['SI09', '-v0'])
|
| ... | ... | @@ -13,7 +13,7 @@ type G :: Type -> RuntimeRep -> Type |
| 13 | 13 | type family G a where
|
| 14 | 14 | G (a b) = a
|
| 15 | 15 | |
| 16 | --- Should be rejected
|
|
| 16 | +-- Now (Nov 2025) accepted
|
|
| 17 | 17 | foo :: (F (G Constraint)) -> Bool
|
| 18 | 18 | foo x = x
|
| 19 | 19 | |
| ... | ... | @@ -22,10 +22,10 @@ type family H a b where |
| 22 | 22 | H a a = Int
|
| 23 | 23 | H a b = Bool
|
| 24 | 24 | |
| 25 | --- Should be rejected
|
|
| 26 | -bar1 :: H TYPE CONSTRAINT -> Int
|
|
| 25 | +-- Now (Nov 2025) accepted
|
|
| 26 | +bar1 :: H TYPE CONSTRAINT -> Bool
|
|
| 27 | 27 | bar1 x = x
|
| 28 | 28 | |
| 29 | --- Should be rejected
|
|
| 30 | -bar2 :: H Type Constraint -> Int
|
|
| 29 | +-- Now (Nov 2025) accepted
|
|
| 30 | +bar2 :: H Type Constraint -> Bool
|
|
| 31 | 31 | bar2 x = x |
| 1 | - |
|
| 2 | -T24279.hs:18:9: error: [GHC-83865]
|
|
| 3 | - • Couldn't match type ‘F CONSTRAINT’ with ‘Bool’
|
|
| 4 | - Expected: Bool
|
|
| 5 | - Actual: F (G Constraint)
|
|
| 6 | - • In the expression: x
|
|
| 7 | - In an equation for ‘foo’: foo x = x
|
|
| 8 | - |
|
| 9 | -T24279.hs:27:10: error: [GHC-83865]
|
|
| 10 | - • Couldn't match expected type ‘Int’
|
|
| 11 | - with actual type ‘H TYPE CONSTRAINT’
|
|
| 12 | - • In the expression: x
|
|
| 13 | - In an equation for ‘bar1’: bar1 x = x
|
|
| 14 | - |
|
| 15 | -T24279.hs:31:10: error: [GHC-83865]
|
|
| 16 | - • Couldn't match expected type ‘Int’
|
|
| 17 | - with actual type ‘H (*) Constraint’
|
|
| 18 | - • In the expression: x
|
|
| 19 | - In an equation for ‘bar2’: bar2 x = x |
| ... | ... | @@ -718,7 +718,7 @@ test('T24064', normal, compile_fail, ['']) |
| 718 | 718 | test('T24090a', normal, compile_fail, [''])
|
| 719 | 719 | test('T24090b', normal, compile, ['']) # scheduled to become an actual error in GHC 9.16
|
| 720 | 720 | test('T24298', normal, compile_fail, [''])
|
| 721 | -test('T24279', normal, compile_fail, [''])
|
|
| 721 | +test('T24279', normal, compile, ['']) # Now accepted (Nov 2025)
|
|
| 722 | 722 | test('T24318', normal, compile_fail, [''])
|
| 723 | 723 | |
| 724 | 724 | # all the various do expansion fail messages
|