1 {-% DrIFT (Automatic class derivations for Haskell) v1.1 %-}
2 {-% DrIFT (Automatic class derivations for Haskell) v1.1 %-}
4 -- (c) The University of Glasgow 2002
6 -- Binary interface file support.
8 module BinIface ( writeBinIface, readBinIface, v_IgnoreHiVersion ) where
10 #include "HsVersions.h"
19 import HsPat ( HsConDetails(..) )
24 import RdrName ( mkRdrUnqual, mkRdrQual )
25 import Name ( Name, nameOccName, nameModule_maybe )
26 import NameEnv ( NameEnv, lookupNameEnv, nameEnvElts )
27 import Module ( moduleName )
28 import OccName ( OccName )
30 import DriverState ( v_Build_tag )
31 import CmdLineOpts ( opt_IgnoreIfacePragmas, opt_HiVersion )
38 import EXCEPTION ( throwDyn )
41 #include "HsVersions.h"
43 -- ---------------------------------------------------------------------------
44 -- We write out a ModIface, but read it in as a ParsedIface.
45 -- There are some big differences, and some subtle ones. We do most
46 -- of the conversion on the way out, so there is minimal fuss when we
47 -- read it back in again (see RnMonad.lhs)
49 -- The main difference is that all Names in a ModIface are RdrNames in
50 -- a ParsedIface, so when writing out a Name in binary we make sure it
51 -- is binary-compatible with a RdrName.
53 -- Other subtle differences:
54 -- - pi_mod is a ModuleName, but mi_mod is a Module. Hence we put
55 -- Modules as ModuleNames.
56 -- - pi_exports and pi_usages, Names have
57 -- to be converted to OccNames.
58 -- - pi_fixity is a NameEnv in ModIface,
59 -- but a list of (Name,Fixity) pairs in ParsedIface.
60 -- - versioning is totally different.
61 -- - deprecations are different.
63 writeBinIface :: FilePath -> ModIface -> IO ()
64 writeBinIface hi_path mod_iface
65 = putBinFileWithDict hi_path (mi_module mod_iface) mod_iface
67 readBinIface :: FilePath -> IO ParsedIface
68 readBinIface hi_path = getBinFileWithDict hi_path
71 -- %*********************************************************
73 -- All the Binary instances
75 -- %*********************************************************
78 {-! for IPName derive: Binary !-}
79 {-! for Fixity derive: Binary !-}
80 {-! for FixityDirection derive: Binary !-}
81 {-! for NewOrData derive: Binary !-}
82 {-! for Boxity derive: Binary !-}
83 {-! for StrictnessMark derive: Binary !-}
84 {-! for Activation derive: Binary !-}
86 instance Binary Name where
87 -- we must print these as RdrNames, because that's how they will be read in
89 = case nameModule_maybe name of
91 | this_mod == mod -> put_ bh (mkRdrUnqual occ)
92 | otherwise -> put_ bh (mkRdrQual (moduleName mod) occ)
93 _ -> put_ bh (mkRdrUnqual occ)
95 occ = nameOccName name
96 (this_mod,_,_,_) = getUserData bh
98 get bh = error "can't Binary.get a Name"
101 {-! for Demand derive: Binary !-}
102 {-! for Demands derive: Binary !-}
103 {-! for DmdResult derive: Binary !-}
104 {-! for StrictSig derive: Binary !-}
106 instance Binary DmdType where
107 -- ignore DmdEnv when spitting out the DmdType
108 put bh (DmdType _ ds dr) = do p <- put bh ds; put bh dr; return (castBin p)
109 get bh = do ds <- get bh; dr <- get bh; return (DmdType emptyVarEnv ds dr)
112 {-! for DataConDetails derive: Binary !-}
115 {-! for DefMeth derive: Binary !-}
118 {-! for HsPred derive: Binary !-}
119 {-! for HsType derive: Binary !-}
120 {-! for HsTupCon derive: Binary !-}
121 {-! for HsTyVarBndr derive: Binary !-}
124 {-! for UfExpr derive: Binary !-}
125 {-! for UfConAlt derive: Binary !-}
126 {-! for UfBinding derive: Binary !-}
127 {-! for UfBinder derive: Binary !-}
128 {-! for HsIdInfo derive: Binary !-}
129 {-! for UfNote derive: Binary !-}
132 {-! for ConDetails derive: Binary !-}
133 {-! for BangType derive: Binary !-}
135 instance (Binary name) => Binary (TyClDecl name) where
136 put_ bh (IfaceSig name ty idinfo _) = do
141 put_ bh (ForeignType ae af ag ah) =
142 error "Binary.put_(TyClDecl): ForeignType"
143 put_ bh (TyData ai aj ak al am _ (Just generics) _) = do
151 put_ bh generics -- Record whether generics needed or not
152 put_ bh (TySynonym aq ar as _) = do
157 put_ bh c@(ClassDecl ctxt nm tyvars fds sigs _ _) = do
164 -- ignore methods (there should be none)
173 let idinfo' | opt_IgnoreIfacePragmas = []
175 return (IfaceSig name ty idinfo' noSrcLoc)
176 1 -> error "Binary.get(TyClDecl): ForeignType"
184 return (TyData n_or_d ctx nm tyvars cons
185 Nothing (Just generics) noSrcLoc)
190 return (TySynonym aq ar as noSrcLoc)
197 return (ClassDecl ctxt nm tyvars fds sigs
200 instance (Binary name) => Binary (ConDecl name) where
201 put_ bh (ConDecl aa ac ad ae _) = do
212 return (ConDecl aa ac ad ae noSrcLoc)
214 instance (Binary name) => Binary (InstDecl name) where
215 put_ bh (InstDecl aa _ _ ad _) = do
224 return (InstDecl aa EmptyMonoBinds [{-no sigs-}] ad noSrcLoc)
226 instance (Binary name) => Binary (RuleDecl name) where
227 put_ bh (IfaceRule ag ah ai aj ak al _) = do
235 get bh = do ag <- get bh
241 return (IfaceRule ag ah ai aj ak al noSrcLoc)
243 instance (Binary name) => Binary (DeprecDecl name) where
244 put_ bh (Deprecation aa ab _) = do
251 return (Deprecation aa ab noSrcLoc)
254 instance Binary name => Binary (Sig name) where
255 put_ bh (ClassOpSig n def ty _) = do put_ bh n; put_ bh def; put_ bh ty
260 return (ClassOpSig n def ty noSrcLoc)
263 {-! for IsCafCC derive: Binary !-}
264 {-! for IsDupdCC derive: Binary !-}
265 {-! for CostCentre derive: Binary !-}
269 instance Binary ModIface where
271 build_tag <- readIORef v_Build_tag
272 put_ bh (show opt_HiVersion ++ build_tag)
273 p <- put_ bh (moduleName (mi_module iface))
274 put_ bh (mi_package iface)
275 put_ bh (vers_module (mi_version iface))
276 put_ bh (mi_orphan iface)
278 lazyPut bh (mi_deps iface)
279 lazyPut bh (map usageToOccName (mi_usages iface))
280 put_ bh (vers_exports (mi_version iface),
281 map exportItemToRdrExportItem (mi_exports iface))
282 put_ bh (declsToVersionedDecls (dcl_tycl (mi_decls iface))
283 (vers_decls (mi_version iface)))
285 put_ bh (collectFixities (mi_fixities iface)
286 (dcl_tycl (mi_decls iface)))
287 put_ bh (dcl_insts (mi_decls iface))
288 lazyPut bh (vers_rules (mi_version iface), dcl_rules (mi_decls iface))
289 lazyPut bh (deprecsToIfaceDeprecs (mi_deprecs iface))
291 -- Read in as a ParsedIface, not a ModIface. See above.
292 get bh = error "Binary.get: ModIface"
294 declsToVersionedDecls :: [RenamedTyClDecl] -> NameEnv Version
295 -> [(Version, RenamedTyClDecl)]
296 declsToVersionedDecls decls env
299 case lookupNameEnv env (tyClDeclName d) of
300 Nothing -> (initialVersion, d)
304 --NOT REALLY: deprecsToIfaceDeprecs :: Deprecations -> IfaceDeprecs
305 deprecsToIfaceDeprecs NoDeprecs = Nothing
306 deprecsToIfaceDeprecs (DeprecAll txt) = Just (Left txt)
307 deprecsToIfaceDeprecs (DeprecSome env) = Just (Right (nameEnvElts env))
310 {-! for GenAvailInfo derive: Binary !-}
311 {-! for WhatsImported derive: Binary !-}
313 -- For binary interfaces we need to convert the ImportVersion Names to OccNames
314 usageToOccName :: Usage Name -> Usage OccName
316 = usg { usg_entities = [ (nameOccName n, v) | (n,v) <- usg_entities usg ] }
318 exportItemToRdrExportItem (mn, avails)
319 = (mn, map availInfoToRdrAvailInfo avails)
321 availInfoToRdrAvailInfo :: AvailInfo -> RdrAvailInfo
322 availInfoToRdrAvailInfo (Avail n)
323 = Avail (nameOccName n)
324 availInfoToRdrAvailInfo (AvailTC n ns)
325 = AvailTC (nameOccName n) (map nameOccName ns)
327 -- ---------------------------------------------------------------------------
328 -- Reading a binary interface into ParsedIface
330 instance Binary ParsedIface where
332 pi_mod = module_name,
334 pi_vers = module_ver,
337 pi_exports = exports,
338 pi_decls = tycl_decls,
339 pi_fixity = fixities,
342 pi_deprecs = deprecs } = do
343 build_tag <- readIORef v_Build_tag
344 put_ bh (show opt_HiVersion ++ build_tag)
358 ignore_ver <- readIORef v_IgnoreHiVersion
359 build_tag <- readIORef v_Build_tag
360 let our_ver = show opt_HiVersion ++ build_tag
361 when (check_ver /= our_ver && not ignore_ver) $
362 -- use userError because this will be caught by readIface
363 -- which will emit an error msg containing the iface module name.
364 throwDyn (ProgramError (
365 "mismatched interface file versions: expected "
366 ++ our_ver ++ ", found " ++ check_ver))
367 module_name <- get bh -- same rep. as Module, so that's ok
372 usages <- {-# SCC "bin_usages" #-} lazyGet bh
373 exports <- {-# SCC "bin_exports" #-} get bh
374 tycl_decls <- {-# SCC "bin_tycldecls" #-} get bh
375 fixities <- {-# SCC "bin_fixities" #-} get bh
376 insts <- {-# SCC "bin_insts" #-} get bh
377 rules <- {-# SCC "bin_rules" #-} lazyGet bh
378 deprecs <- {-# SCC "bin_deprecs" #-} lazyGet bh
379 return (ParsedIface {
380 pi_mod = module_name,
382 pi_vers = module_ver,
386 pi_exports = exports,
387 pi_decls = tycl_decls,
388 pi_fixity = fixities,
389 pi_insts = reverse insts,
391 pi_deprecs = deprecs })
393 GLOBAL_VAR(v_IgnoreHiVersion, False, Bool)
395 -- ----------------------------------------------------------------------------
396 {-* Generated by DrIFT-v1.0 : Look, but Don't Touch. *-}
398 -- Imported from other files :-
400 instance Binary Dependencies where
401 put_ bh deps = do put_ bh (dep_mods deps)
402 put_ bh (dep_pkgs deps)
403 put_ bh (dep_orphs deps)
405 get bh = do ms <- get bh
408 return (Deps { dep_mods = ms, dep_pkgs = ps, dep_orphs = os })
410 instance (Binary name) => Binary (GenAvailInfo name) where
411 put_ bh (Avail aa) = do
414 put_ bh (AvailTC ab ac) = do
425 return (AvailTC ab ac)
427 instance (Binary name) => Binary (Usage name) where
429 put_ bh (usg_name usg)
430 put_ bh (usg_mod usg)
431 put_ bh (usg_exports usg)
432 put_ bh (usg_entities usg)
433 put_ bh (usg_rules usg)
441 return (Usage { usg_name = nm, usg_mod = mod,
442 usg_exports = exps, usg_entities = ents,
445 instance Binary Activation where
446 put_ bh NeverActive = do
448 put_ bh AlwaysActive = do
450 put_ bh (ActiveBefore aa) = do
453 put_ bh (ActiveAfter ab) = do
459 0 -> do return NeverActive
460 1 -> do return AlwaysActive
462 return (ActiveBefore aa)
464 return (ActiveAfter ab)
466 instance Binary StrictnessMark where
467 put_ bh MarkedUserStrict = do
469 put_ bh MarkedStrict = do
471 put_ bh MarkedUnboxed = do
473 put_ bh NotMarkedStrict = do
478 0 -> do return MarkedUserStrict
479 1 -> do return MarkedStrict
480 2 -> do return MarkedUnboxed
481 _ -> do return NotMarkedStrict
483 instance Binary Boxity where
492 _ -> do return Unboxed
494 instance Binary NewOrData where
497 put_ bh DataType = do
502 0 -> do return NewType
503 _ -> do return DataType
505 instance Binary FixityDirection where
515 0 -> do return InfixL
516 1 -> do return InfixR
517 _ -> do return InfixN
519 instance Binary Fixity where
520 put_ bh (Fixity aa ab) = do
526 return (Fixity aa ab)
528 instance (Binary name) => Binary (FixitySig name) where
529 put_ bh (FixitySig aa ab _) = do
535 return (FixitySig aa ab noSrcLoc)
537 instance (Binary name) => Binary (IPName name) where
538 put_ bh (Dupable aa) = do
541 put_ bh (Linear ab) = do
552 instance Binary Demand where
557 put_ bh (Call aa) = do
560 put_ bh (Eval ab) = do
563 put_ bh (Defer ac) = do
566 put_ bh (Box ad) = do
586 instance Binary Demands where
587 put_ bh (Poly aa) = do
590 put_ bh (Prod ab) = do
601 instance Binary DmdResult where
611 0 -> do return TopRes
612 1 -> do return RetCPR -- Really use RetCPR even if -fcpr-off
613 -- The wrapper was generated for CPR in
614 -- the imported module!
615 _ -> do return BotRes
617 instance Binary StrictSig where
618 put_ bh (StrictSig aa) = do
622 return (StrictSig aa)
624 instance (Binary name) => Binary (HsTyVarBndr name) where
625 put_ bh (UserTyVar aa) = do
628 put_ bh (IfaceTyVar ab ac) = do
636 return (UserTyVar aa)
639 return (IfaceTyVar ab ac)
641 instance Binary HsTupCon where
642 put_ bh (HsTupCon ab ac) = do
648 return (HsTupCon ab ac)
650 instance (Binary name) => Binary (HsTyOp name) where
651 put_ bh HsArrow = putByte bh 0
652 put_ bh (HsTyOp n) = do putByte bh 1
655 get bh = do h <- getByte bh
661 instance (Binary name) => Binary (HsType name) where
662 put_ bh (HsForAllTy aa ab ac) = do
667 put_ bh (HsTyVar ad) = do
670 put_ bh (HsAppTy ae af) = do
674 put_ bh (HsFunTy ag ah) = do
678 put_ bh (HsListTy ai) = do
681 put_ bh (HsPArrTy aj) = do
684 put_ bh (HsTupleTy ak al) = do
688 put_ bh (HsOpTy am an ao) = do
693 put_ bh (HsNumTy ap) = do
696 put_ bh (HsPredTy aq) = do
699 put_ bh (HsKindSig ar as) = do
709 return (HsForAllTy aa ab ac)
714 return (HsAppTy ae af)
717 return (HsFunTy ag ah)
724 return (HsTupleTy ak al)
728 return (HsOpTy am an ao)
735 return (HsKindSig ar as)
737 instance (Binary name) => Binary (HsPred name) where
738 put_ bh (HsClassP aa ab) = do
742 put_ bh (HsIParam ac ad) = do
751 return (HsClassP aa ab)
754 return (HsIParam ac ad)
756 instance (Binary name) => Binary (UfExpr name) where
757 put_ bh (UfVar aa) = do
760 put_ bh (UfType ab) = do
763 put_ bh (UfTuple ac ad) = do
767 put_ bh (UfLam ae af) = do
771 put_ bh (UfApp ag ah) = do
775 put_ bh (UfCase ai aj ak) = do
780 put_ bh (UfLet al am) = do
784 put_ bh (UfNote an ao) = do
788 put_ bh (UfLit ap) = do
791 put_ bh (UfLitLit aq ar) = do
795 put_ bh (UfFCall as at) = do
808 return (UfTuple ac ad)
818 return (UfCase ai aj ak)
824 return (UfNote an ao)
829 return (UfLitLit aq ar)
832 return (UfFCall as at)
834 instance (Binary name) => Binary (UfConAlt name) where
835 put_ bh UfDefault = do
837 put_ bh (UfDataAlt aa) = do
840 put_ bh (UfTupleAlt ab) = do
843 put_ bh (UfLitAlt ac) = do
846 put_ bh (UfLitLitAlt ad ae) = do
853 0 -> do return UfDefault
855 return (UfDataAlt aa)
857 return (UfTupleAlt ab)
862 return (UfLitLitAlt ad ae)
864 instance (Binary name) => Binary (UfBinding name) where
865 put_ bh (UfNonRec aa ab) = do
869 put_ bh (UfRec ac) = do
877 return (UfNonRec aa ab)
881 instance (Binary name) => Binary (UfBinder name) where
882 put_ bh (UfValBinder aa ab) = do
886 put_ bh (UfTyBinder ac ad) = do
895 return (UfValBinder aa ab)
898 return (UfTyBinder ac ad)
900 instance (Binary name) => Binary (HsIdInfo name) where
901 put_ bh (HsArity aa) = do
904 put_ bh (HsStrictness ab) = do
907 put_ bh (HsUnfold ac ad) = do
911 put_ bh HsNoCafRefs = do
913 put_ bh (HsWorker ae af) = do
923 return (HsStrictness ab)
926 return (HsUnfold ac ad)
927 3 -> do return HsNoCafRefs
930 return (HsWorker ae af)
932 instance (Binary name) => Binary (UfNote name) where
933 put_ bh (UfSCC aa) = do
936 put_ bh (UfCoerce ab) = do
939 put_ bh UfInlineCall = do
941 put_ bh UfInlineMe = do
943 put_ bh (UfCoreNote s) = do
953 2 -> do return UfInlineCall
954 3 -> do return UfInlineMe
956 return (UfCoreNote ac)
958 instance (Binary name) => Binary (BangType name) where
959 put_ bh (BangType aa ab) = do
965 return (BangType aa ab)
967 instance (Binary name, Binary arg) => Binary (HsConDetails name arg) where
968 put_ bh (PrefixCon aa) = do
971 put_ bh (InfixCon ab ac) = do
975 put_ bh (RecCon ad) = do
982 return (PrefixCon aa)
985 return (InfixCon ab ac)
989 instance (Binary datacon) => Binary (DataConDetails datacon) where
990 put_ bh (DataCons aa) = do
995 put_ bh (HasCons ab) = do
1001 0 -> do aa <- get bh
1002 return (DataCons aa)
1003 1 -> do return Unknown
1004 _ -> do ab <- get bh
1007 instance (Binary id) => Binary (DefMeth id) where
1008 put_ bh NoDefMeth = do
1010 put_ bh (DefMeth aa) = do
1013 put_ bh GenDefMeth = do
1018 0 -> do return NoDefMeth
1019 1 -> do aa <- get bh
1021 _ -> do return GenDefMeth
1023 instance Binary IsCafCC where
1026 put_ bh NotCafCC = do
1031 0 -> do return CafCC
1032 _ -> do return NotCafCC
1034 instance Binary IsDupdCC where
1035 put_ bh OriginalCC = do
1042 0 -> do return OriginalCC
1043 _ -> do return DupdCC
1045 instance Binary CostCentre where
1046 put_ bh NoCostCentre = do
1048 put_ bh (NormalCC aa ab ac ad) = do
1054 put_ bh (AllCafsCC ae) = do
1060 0 -> do return NoCostCentre
1061 1 -> do aa <- get bh
1065 return (NormalCC aa ab ac ad)
1066 _ -> do ae <- get bh
1067 return (AllCafsCC ae)