Merge remote branch 'working/master'
authorSimon Marlow <marlowsd@gmail.com>
Mon, 6 Jun 2011 10:39:00 +0000 (11:39 +0100)
committerSimon Marlow <marlowsd@gmail.com>
Mon, 6 Jun 2011 10:39:00 +0000 (11:39 +0100)
70 files changed:
.gitignore
compiler/cmm/CmmMachOp.hs
compiler/cmm/CmmOpt.hs
compiler/cmm/CmmParse.y
compiler/codeGen/CgUtils.hs
compiler/iface/BinIface.hs
compiler/iface/LoadIface.lhs
compiler/iface/MkIface.lhs
compiler/iface/TcIface.lhs
compiler/llvmGen/Llvm/AbsSyn.hs
compiler/llvmGen/Llvm/PpLlvm.hs
compiler/llvmGen/LlvmCodeGen.hs
compiler/llvmGen/LlvmCodeGen/Base.hs
compiler/llvmGen/LlvmCodeGen/CodeGen.hs
compiler/main/CodeOutput.lhs
compiler/main/DriverPipeline.hs
compiler/main/DynFlags.hs
compiler/main/ErrUtils.lhs
compiler/main/HscMain.lhs
compiler/main/HscTypes.lhs
compiler/main/SysTools.lhs
compiler/main/TidyPgm.lhs
compiler/nativeGen/AsmCodeGen.lhs
compiler/nativeGen/NCG.h
compiler/nativeGen/PPC/CodeGen.hs
compiler/nativeGen/PPC/Ppr.hs
compiler/nativeGen/PPC/RegInfo.hs
compiler/nativeGen/RegAlloc/Graph/TrivColorable.hs
compiler/nativeGen/RegAlloc/Linear/Base.hs
compiler/nativeGen/RegAlloc/Linear/FreeRegs.hs
compiler/nativeGen/RegAlloc/Linear/JoinToTargets.hs
compiler/nativeGen/RegAlloc/Linear/Main.hs
compiler/nativeGen/RegAlloc/Linear/State.hs
compiler/nativeGen/SPARC/CodeGen/CCall.hs
compiler/nativeGen/SPARC/Ppr.hs
compiler/nativeGen/SPARC/ShortcutJump.hs
compiler/nativeGen/TargetReg.hs
compiler/nativeGen/X86/CodeGen.hs
compiler/nativeGen/X86/Instr.hs
compiler/nativeGen/X86/Ppr.hs
compiler/nativeGen/X86/RegInfo.hs
compiler/prelude/PrelNames.lhs
compiler/utils/Platform.hs
compiler/vectorise/Vectorise/Env.hs
compiler/vectorise/Vectorise/Monad.hs
compiler/vectorise/Vectorise/Monad/Global.hs
configure.ac
docs/users_guide/7.0.1-notes.xml
docs/users_guide/bugs.xml
docs/users_guide/debugging.xml
docs/users_guide/ffi-chap.xml
docs/users_guide/flags.xml
docs/users_guide/ghci.xml
docs/users_guide/glasgow_exts.xml
docs/users_guide/intro.xml
docs/users_guide/license.xml
docs/users_guide/packages.xml
docs/users_guide/parallel.xml
docs/users_guide/phases.xml
docs/users_guide/profiling.xml
docs/users_guide/runtime_control.xml
docs/users_guide/separate_compilation.xml
docs/users_guide/shared_libs.xml
docs/users_guide/using.xml
docs/users_guide/win32-dlls.xml
rts/RtsFlags.c
rts/ThreadPaused.c
rts/Trace.c
rts/eventlog/EventLog.c
rts/win32/GetEnv.c

index 3e2e7f4..ac8c70e 100644 (file)
@@ -232,3 +232,5 @@ _darcs/
 /utils/runstdtest/runstdtest
 /utils/unlit/unlit
 
+
+/extra-gcc-opts
\ No newline at end of file
index 5e1ac16..6e89035 100644 (file)
@@ -459,7 +459,15 @@ data CallishMachOp
   | MO_F32_Sqrt
   | MO_WriteBarrier
   | MO_Touch         -- Keep variables live (when using interior pointers)
+  
+  -- Note that these three MachOps all take 1 extra parameter than the
+  -- standard C lib versions. The extra (last) parameter contains
+  -- alignment of the pointers. Used for optimisation in backends.
+  | MO_Memcpy
+  | MO_Memset
+  | MO_Memmove
   deriving (Eq, Show)
 
 pprCallishMachOp :: CallishMachOp -> SDoc
 pprCallishMachOp mo = text (show mo)
+
index a2eecd5..69df4fb 100644 (file)
@@ -99,11 +99,13 @@ cmmEliminateDeadBlocks blocks@(BasicBlock base_id _:_) =
 -- The mini-inliner
 
 {-
-This pass inlines assignments to temporaries that are used just
-once.  It works as follows:
+This pass inlines assignments to temporaries.  Temporaries that are
+only used once are unconditionally inlined.  Temporaries that are used
+two or more times are only inlined if they are assigned a literal.  It
+works as follows:
 
   - count uses of each temporary
-  - for each temporary that occurs just once:
+  - for each temporary:
        - attempt to push it forward to the statement that uses it
         - only push forward past assignments to other temporaries
          (assumes that temporaries are single-assignment)
@@ -159,11 +161,37 @@ cmmMiniInline blocks = map do_inline blocks
 cmmMiniInlineStmts :: UniqFM Int -> [CmmStmt] -> [CmmStmt]
 cmmMiniInlineStmts uses [] = []
 cmmMiniInlineStmts uses (stmt@(CmmAssign (CmmLocal (LocalReg u _)) expr) : stmts)
-        -- not used at all: just discard this assignment
+        -- not used: just discard this assignment
   | Nothing <- lookupUFM uses u
   = cmmMiniInlineStmts uses stmts
 
-        -- used once: try to inline at the use site
+        -- used (literal): try to inline at all the use sites
+  | Just n <- lookupUFM uses u, isLit expr
+  =
+#ifdef NCG_DEBUG
+     trace ("nativeGen: inlining " ++ showSDoc (pprStmt stmt)) $
+#endif
+     case lookForInlineLit u expr stmts of
+         (m, stmts')
+             | n == m -> cmmMiniInlineStmts (delFromUFM uses u) stmts'
+             | otherwise ->
+                 stmt : cmmMiniInlineStmts (adjustUFM (\x -> x - m) uses u) stmts'
+
+        -- used (foldable to literal): try to inline at all the use sites
+  | Just n <- lookupUFM uses u,
+    CmmMachOp op es <- expr,
+    e@(CmmLit _) <- cmmMachOpFold op es
+  =
+#ifdef NCG_DEBUG
+     trace ("nativeGen: inlining " ++ showSDoc (pprStmt stmt)) $
+#endif
+     case lookForInlineLit u e stmts of
+         (m, stmts')
+             | n == m -> cmmMiniInlineStmts (delFromUFM uses u) stmts'
+             | otherwise ->
+                 stmt : cmmMiniInlineStmts (adjustUFM (\x -> x - m) uses u) stmts'
+
+        -- used once (non-literal): try to inline at the use site
   | Just 1 <- lookupUFM uses u,
     Just stmts' <- lookForInline u expr stmts
   = 
@@ -175,6 +203,31 @@ cmmMiniInlineStmts uses (stmt@(CmmAssign (CmmLocal (LocalReg u _)) expr) : stmts
 cmmMiniInlineStmts uses (stmt:stmts)
   = stmt : cmmMiniInlineStmts uses stmts
 
+-- | Takes a register, a 'CmmLit' expression assigned to that
+-- register, and a list of statements.  Inlines the expression at all
+-- use sites of the register.  Returns the number of substituations
+-- made and the, possibly modified, list of statements.
+lookForInlineLit :: Unique -> CmmExpr -> [CmmStmt] -> (Int, [CmmStmt])
+lookForInlineLit _ _ [] = (0, [])
+lookForInlineLit u expr stmts@(stmt : rest)
+  | Just n <- lookupUFM (countUses stmt) u
+  = case lookForInlineLit u expr rest of
+      (m, stmts) -> let z = n + m
+                    in z `seq` (z, inlineStmt u expr stmt : stmts)
+
+  | ok_to_skip
+  = case lookForInlineLit u expr rest of
+      (n, stmts) -> (n, stmt : stmts)
+
+  | otherwise
+  = (0, stmts)
+  where
+    -- We skip over assignments to registers, unless the register
+    -- being assigned to is the one we're inlining.
+    ok_to_skip = case stmt of
+        CmmAssign (CmmLocal r@(LocalReg u' _)) _ | u' == u -> False
+        _other -> True
+
 lookForInline u expr stmts = lookForInline' u expr regset stmts
     where regset = foldRegsUsed extendRegSet emptyRegSet expr
 
index 0ee429d..6d14be2 100644 (file)
@@ -735,7 +735,10 @@ machOps = listToUFM $
 
 callishMachOps = listToUFM $
        map (\(x, y) -> (mkFastString x, y)) [
-        ( "write_barrier", MO_WriteBarrier )
+        ( "write_barrier", MO_WriteBarrier ),
+        ( "memcpy", MO_Memcpy ),
+        ( "memset", MO_Memset ),
+        ( "memmove", MO_Memmove )
         -- ToDo: the rest, maybe
     ]
 
index 4df7c77..63d99a6 100644 (file)
@@ -601,13 +601,17 @@ assignTemp e
                            ; stmtC (CmmAssign (CmmLocal reg) e)
                            ; return (CmmReg (CmmLocal reg)) }
 
--- | Assign the expression to a temporary register and return an
--- expression referring to this register.
+-- | If the expression is trivial and doesn't refer to a global
+-- register, return it.  Otherwise, assign the expression to a
+-- temporary register and return an expression referring to this
+-- register.
 assignTemp_ :: CmmExpr -> FCode CmmExpr
-assignTemp_ e = do
-    reg <- newTemp (cmmExprType e)
-    stmtC (CmmAssign (CmmLocal reg) e)
-    return (CmmReg (CmmLocal reg))
+assignTemp_ e
+    | isTrivialCmmExpr e && hasNoGlobalRegs e = return e
+    | otherwise = do
+        reg <- newTemp (cmmExprType e)
+        stmtC (CmmAssign (CmmLocal reg) e)
+        return (CmmReg (CmmLocal reg))
 
 newTemp :: CmmType -> FCode LocalReg
 newTemp rep = do { uniq <- newUnique; return (LocalReg uniq rep) }
index c80628b..502eefa 100644 (file)
@@ -1508,14 +1508,18 @@ instance Binary name => Binary (AnnTarget name) where
                   return (ModuleTarget a)
 
 instance Binary IfaceVectInfo where
-    put_ bh (IfaceVectInfo a1 a2 a3) = do
+    put_ bh (IfaceVectInfo a1 a2 a3 a4 a5) = do
            put_ bh a1
            put_ bh a2
            put_ bh a3
+           put_ bh a4
+           put_ bh a5
     get bh = do
            a1 <- get bh
            a2 <- get bh
            a3 <- get bh
-           return (IfaceVectInfo a1 a2 a3)
+           a4 <- get bh
+           a5 <- get bh
+           return (IfaceVectInfo a1 a2 a3 a4 a5)
 
 
index e92a160..97acc52 100644 (file)
@@ -729,14 +729,18 @@ pprFixities fixes = ptext (sLit "fixities") <+> pprWithCommas pprFix fixes
                    pprFix (occ,fix) = ppr fix <+> ppr occ 
 
 pprVectInfo :: IfaceVectInfo -> SDoc
-pprVectInfo (IfaceVectInfo { ifaceVectInfoVar        = vars
-                           , ifaceVectInfoTyCon      = tycons
-                           , ifaceVectInfoTyConReuse = tyconsReuse
+pprVectInfo (IfaceVectInfo { ifaceVectInfoVar          = vars
+                           , ifaceVectInfoTyCon        = tycons
+                           , ifaceVectInfoTyConReuse   = tyconsReuse
+                           , ifaceVectInfoScalarVars   = scalarVars
+                           , ifaceVectInfoScalarTyCons = scalarTyCons
                            }) = 
   vcat 
   [ ptext (sLit "vectorised variables:") <+> hsep (map ppr vars)
   , ptext (sLit "vectorised tycons:") <+> hsep (map ppr tycons)
   , ptext (sLit "vectorised reused tycons:") <+> hsep (map ppr tyconsReuse)
+  , ptext (sLit "scalar variables:") <+> hsep (map ppr scalarVars)
+  , ptext (sLit "scalar tycons:") <+> hsep (map ppr scalarTyCons)
   ]
 
 instance Outputable Warnings where
index 5c58a80..0bce56b 100644 (file)
@@ -7,23 +7,23 @@
 module MkIface ( 
         mkUsedNames,
         mkDependencies,
-       mkIface,        -- Build a ModIface from a ModGuts, 
-                       -- including computing version information
+        mkIface,        -- Build a ModIface from a ModGuts, 
+                        -- including computing version information
 
         mkIfaceTc,
 
-       writeIfaceFile, -- Write the interface file
+        writeIfaceFile, -- Write the interface file
 
-       checkOldIface,  -- See if recompilation is required, by
-                       -- comparing version information
+        checkOldIface,  -- See if recompilation is required, by
+                        -- comparing version information
 
         tyThingToIfaceDecl -- Converting things to their Iface equivalents
  ) where
 \end{code}
 
-       -----------------------------------------------
-               Recompilation checking
-       -----------------------------------------------
+  -----------------------------------------------
+          Recompilation checking
+  -----------------------------------------------
 
 A complete description of how recompilation checking works can be
 found in the wiki commentary:
@@ -72,6 +72,7 @@ import HscTypes
 import Finder
 import DynFlags
 import VarEnv
+import VarSet
 import Var
 import Name
 import RdrName
@@ -325,18 +326,17 @@ mkIface_ hsc_env maybe_old_fingerprint
 
      ifFamInstTcName = ifaceTyConName . ifFamInstTyCon
 
-     flattenVectInfo (VectInfo { vectInfoVar   = vVar
-                               , vectInfoTyCon = vTyCon
+     flattenVectInfo (VectInfo { vectInfoVar          = vVar
+                               , vectInfoTyCon        = vTyCon
+                               , vectInfoScalarVars   = vScalarVars
+                               , vectInfoScalarTyCons = vScalarTyCons
                                }) = 
-       IfaceVectInfo { 
-         ifaceVectInfoVar        = [ Var.varName v 
-                                   | (v, _) <- varEnvElts vVar],
-         ifaceVectInfoTyCon      = [ tyConName t 
-                                   | (t, t_v) <- nameEnvElts vTyCon
-                                   , t /= t_v],
-         ifaceVectInfoTyConReuse = [ tyConName t
-                                   | (t, t_v) <- nameEnvElts vTyCon
-                                   , t == t_v]
+       IfaceVectInfo
+       { ifaceVectInfoVar          = [Var.varName v | (v, _  ) <- varEnvElts  vVar]
+       , ifaceVectInfoTyCon        = [tyConName t   | (t, t_v) <- nameEnvElts vTyCon, t /= t_v]
+       , ifaceVectInfoTyConReuse   = [tyConName t   | (t, t_v) <- nameEnvElts vTyCon, t == t_v]
+       , ifaceVectInfoScalarVars   = [Var.varName v | v <- varSetElems vScalarVars]
+       , ifaceVectInfoScalarTyCons = nameSetToList vScalarTyCons
        } 
 
 -----------------------------
index 7ac95b1..5bfb406 100644 (file)
@@ -39,14 +39,16 @@ import Class
 import TyCon
 import DataCon
 import TysWiredIn
-import TysPrim         ( anyTyConOfKind )
-import BasicTypes      ( Arity, nonRuleLoopBreaker )
+import TysPrim          ( anyTyConOfKind )
+import BasicTypes       ( Arity, nonRuleLoopBreaker )
 import qualified Var
 import VarEnv
+import VarSet
 import Name
 import NameEnv
-import OccurAnal       ( occurAnalyseExpr )
-import Demand          ( isBottomingSig )
+import NameSet
+import OccurAnal        ( occurAnalyseExpr )
+import Demand           ( isBottomingSig )
 import Module
 import UniqFM
 import UniqSupply
@@ -689,28 +691,32 @@ tcIfaceAnnTarget (ModuleTarget mod) = do
 
 
 %************************************************************************
-%*                                                                     *
-               Vectorisation information
-%*                                                                     *
+%*                                                                      *
+                Vectorisation information
+%*                                                                      *
 %************************************************************************
 
 \begin{code}
 tcIfaceVectInfo :: Module -> TypeEnv  -> IfaceVectInfo -> IfL VectInfo
 tcIfaceVectInfo mod typeEnv (IfaceVectInfo 
-                             { ifaceVectInfoVar        = vars
-                             , ifaceVectInfoTyCon      = tycons
-                             , ifaceVectInfoTyConReuse = tyconsReuse
+                             { ifaceVectInfoVar          = vars
+                             , ifaceVectInfoTyCon        = tycons
+                             , ifaceVectInfoTyConReuse   = tyconsReuse
+                             , ifaceVectInfoScalarVars   = scalarVars
+                             , ifaceVectInfoScalarTyCons = scalarTyCons
                              })
   = do { vVars     <- mapM vectVarMapping vars
        ; tyConRes1 <- mapM vectTyConMapping      tycons
        ; tyConRes2 <- mapM vectTyConReuseMapping tyconsReuse
        ; let (vTyCons, vDataCons, vPAs, vIsos) = unzip4 (tyConRes1 ++ tyConRes2)
        ; return $ VectInfo 
-                  { vectInfoVar     = mkVarEnv  vVars
-                  , vectInfoTyCon   = mkNameEnv vTyCons
-                  , vectInfoDataCon = mkNameEnv (concat vDataCons)
-                  , vectInfoPADFun  = mkNameEnv vPAs
-                  , vectInfoIso     = mkNameEnv vIsos
+                  { vectInfoVar          = mkVarEnv     vVars
+                  , vectInfoTyCon        = mkNameEnv    vTyCons
+                  , vectInfoDataCon      = mkNameEnv    (concat vDataCons)
+                  , vectInfoPADFun       = mkNameEnv    vPAs
+                  , vectInfoIso          = mkNameEnv    vIsos
+                  , vectInfoScalarVars   = mkVarSet  (map lookupVar scalarVars)
+                  , vectInfoScalarTyCons = mkNameSet scalarTyCons
                   }
        }
   where
@@ -778,9 +784,9 @@ tcIfaceVectInfo mod typeEnv (IfaceVectInfo
 \end{code}
 
 %************************************************************************
-%*                                                                     *
-                       Types
-%*                                                                     *
+%*                                                                      *
+                        Types
+%*                                                                      *
 %************************************************************************
 
 \begin{code}
index e25f5be..93bc62c 100644 (file)
@@ -132,6 +132,12 @@ data LlvmStatement
   -}
   | Expr LlvmExpression
 
+  {- |
+    A nop LLVM statement. Useful as its often more efficient to use this
+    then to wrap LLvmStatement in a Just or [].
+  -}
+  | Nop
+
   deriving (Show, Eq)
 
 
index 1a972e7..82c6bfa 100644 (file)
@@ -161,6 +161,7 @@ ppLlvmStatement stmt
         Return      result        -> ppReturn result
         Expr        expr          -> ppLlvmExpression expr
         Unreachable               -> text "unreachable"
+        Nop                       -> empty
 
 
 -- | Print out an LLVM expression.
index ba5c1ec..56d8386 100644 (file)
@@ -28,7 +28,9 @@ import Outputable
 import qualified Pretty as Prt
 import UniqSupply
 import Util
+import SysTools ( figureLlvmVersion )
 
+import Data.Maybe ( fromMaybe )
 import System.IO
 
 -- -----------------------------------------------------------------------------
@@ -48,8 +50,9 @@ llvmCodeGen dflags h us cmms
     in do
         bufh <- newBufHandle h
         Prt.bufLeftRender bufh $ pprLlvmHeader
-
-        env' <- cmmDataLlvmGens dflags bufh env cdata []
+        ver <- (fromMaybe defaultLlvmVersion) `fmap` figureLlvmVersion dflags
+        
+        env' <- cmmDataLlvmGens dflags bufh (setLlvmVer ver env) cdata []
         cmmProcLlvmGens dflags bufh us env' cmm 1 []
 
         bFlush bufh
index 80d88e6..221106a 100644 (file)
@@ -9,8 +9,10 @@ module LlvmCodeGen.Base (
         LlvmCmmTop, LlvmBasicBlock,
         LlvmUnresData, LlvmData, UnresLabel, UnresStatic,
 
+        LlvmVersion, defaultLlvmVersion,
+
         LlvmEnv, initLlvmEnv, clearVars, varLookup, varInsert,
-        funLookup, funInsert,
+        funLookup, funInsert, getLlvmVer, setLlvmVer,
 
         cmmToLlvmType, widthToLlvmFloat, widthToLlvmInt, llvmFunTy,
         llvmFunSig, llvmStdFunAttrs, llvmFunAlign, llvmInfAlign,
@@ -128,33 +130,50 @@ tysToParams = map (\ty -> (ty, []))
 llvmPtrBits :: Int
 llvmPtrBits = widthInBits $ typeWidth gcWord
 
+-- ----------------------------------------------------------------------------
+-- * Llvm Version
+--
+
+-- | LLVM Version Number
+type LlvmVersion = Int
+
+-- | The LLVM Version we assume if we don't know
+defaultLlvmVersion :: LlvmVersion
+defaultLlvmVersion = 28
 
 -- ----------------------------------------------------------------------------
 -- * Environment Handling
 --
 
-type LlvmEnvMap = UniqFM LlvmType
 -- two maps, one for functions and one for local vars.
-type LlvmEnv = (LlvmEnvMap, LlvmEnvMap)
+newtype LlvmEnv = LlvmEnv (LlvmEnvMap, LlvmEnvMap, LlvmVersion)
+type LlvmEnvMap = UniqFM LlvmType
 
 -- | Get initial Llvm environment.
 initLlvmEnv :: LlvmEnv
-initLlvmEnv = (emptyUFM, emptyUFM)
+initLlvmEnv = LlvmEnv (emptyUFM, emptyUFM, defaultLlvmVersion)
 
 -- | Clear variables from the environment.
 clearVars :: LlvmEnv -> LlvmEnv
-clearVars (e1, _) = (e1, emptyUFM)
+clearVars (LlvmEnv (e1, _, n)) = LlvmEnv (e1, emptyUFM, n)
 
 -- | Insert functions into the environment.
 varInsert, funInsert :: Uniquable key => key -> LlvmType -> LlvmEnv -> LlvmEnv
-varInsert s t (e1, e2) = (e1, addToUFM e2 s t)
-funInsert s t (e1, e2) = (addToUFM e1 s t, e2)
+varInsert s t (LlvmEnv (e1, e2, n)) = LlvmEnv (e1, addToUFM e2 s t, n)
+funInsert s t (LlvmEnv (e1, e2, n)) = LlvmEnv (addToUFM e1 s t, e2, n)
 
 -- | Lookup functions in the environment.
 varLookup, funLookup :: Uniquable key => key -> LlvmEnv -> Maybe LlvmType
-varLookup s (_, e2) = lookupUFM e2 s
-funLookup s (e1, _) = lookupUFM e1 s
+varLookup s (LlvmEnv (_, e2, _)) = lookupUFM e2 s
+funLookup s (LlvmEnv (e1, _, _)) = lookupUFM e1 s
+
+-- | Get the LLVM version we are generating code for
+getLlvmVer :: LlvmEnv -> LlvmVersion
+getLlvmVer (LlvmEnv (_, _, n)) = n
 
+-- | Set the LLVM version we are generating code for
+setLlvmVer :: LlvmVersion -> LlvmEnv -> LlvmEnv
+setLlvmVer n (LlvmEnv (e1, e2, _)) = LlvmEnv (e1, e2, n)
 
 -- ----------------------------------------------------------------------------
 -- * Label handling
index f5dd3bb..c55da14 100644 (file)
@@ -1,3 +1,4 @@
+{-# OPTIONS -fno-warn-type-defaults #-}
 -- ----------------------------------------------------------------------------
 -- | Handle conversion of CmmProc to LLVM code.
 --
@@ -17,7 +18,6 @@ import OldCmm
 import qualified OldPprCmm as PprCmm
 import OrdList
 
-import BasicTypes
 import FastString
 import ForeignCall
 import Outputable hiding ( panic, pprPanic )
@@ -175,9 +175,31 @@ genCall env (CmmPrim MO_WriteBarrier) _ _ _ = do
 
     where
         lmTrue :: LlvmVar
-        lmTrue  = LMLitVar $ LMIntLit (-1) i1
+        lmTrue  = mkIntLit i1 (-1)
 #endif
 
+-- Handle memcpy function specifically since llvm's intrinsic version takes
+-- some extra parameters.
+genCall env t@(CmmPrim op) [] args CmmMayReturn | op == MO_Memcpy ||
+                                                  op == MO_Memset ||
+                                                  op == MO_Memmove = do
+    let (isVolTy, isVolVal) = if getLlvmVer env >= 28
+                                 then ([i1], [mkIntLit i1 0]) else ([], [])
+        argTy | op == MO_Memset = [i8Ptr, i8,    llvmWord, i32] ++ isVolTy
+              | otherwise       = [i8Ptr, i8Ptr, llvmWord, i32] ++ isVolTy
+        funTy = \name -> LMFunction $ LlvmFunctionDecl name ExternallyVisible
+                             CC_Ccc LMVoid FixedArgs (tysToParams argTy) Nothing
+
+    (env1, argVars, stmts1, top1) <- arg_vars env args ([], nilOL, [])
+    (env2, fptr, stmts2, top2)    <- getFunPtr env1 funTy t
+    (argVars', stmts3)            <- castVars $ zip argVars argTy
+
+    let arguments = argVars' ++ isVolVal
+        call = Expr $ Call StdCall fptr arguments []
+        stmts = stmts1 `appOL` stmts2 `appOL` stmts3
+                `appOL` trashStmts `snocOL` call
+    return (env2, stmts, top1 ++ top2)
+
 -- Handle all other foreign calls and prim ops.
 genCall env target res args ret = do
 
@@ -225,91 +247,17 @@ genCall env target res args ret = do
     let ccTy  = StdCall -- tail calls should be done through CmmJump
     let retTy = ret_type res
     let argTy = tysToParams $ map arg_type args
-    let funTy name = LMFunction $ LlvmFunctionDecl name ExternallyVisible
-                        lmconv retTy FixedArgs argTy llvmFunAlign
+    let funTy = \name -> LMFunction $ LlvmFunctionDecl name ExternallyVisible
+                             lmconv retTy FixedArgs argTy llvmFunAlign
 
-    -- get parameter values
-    (env1, argVars, stmts1, top1) <- arg_vars env args ([], nilOL, [])
 
-    -- get the return register
-    let ret_reg ([CmmHinted reg hint]) = (reg, hint)
-        ret_reg t = panic $ "genCall: Bad number of registers! Can only handle"
-                        ++ " 1, given " ++ show (length t) ++ "."
-
-    -- deal with call types
-    let getFunPtr :: CmmCallTarget -> UniqSM ExprData
-        getFunPtr targ = case targ of
-            CmmCallee (CmmLit (CmmLabel lbl)) _ -> do
-                let name = strCLabel_llvm lbl
-                case funLookup name env1 of
-                    Just ty'@(LMFunction sig) -> do
-                        -- Function in module in right form
-                        let fun = LMGlobalVar name ty' (funcLinkage sig)
-                                        Nothing Nothing False
-                        return (env1, fun, nilOL, [])
-
-                    Just ty' -> do
-                        -- label in module but not function pointer, convert
-                        let fty@(LMFunction sig) = funTy name
-                        let fun = LMGlobalVar name (pLift ty') (funcLinkage sig)
-                                        Nothing Nothing False
-                        (v1, s1) <- doExpr (pLift fty)
-                                        $ Cast LM_Bitcast fun (pLift fty)
-                        return  (env1, v1, unitOL s1, [])
-
-                    Nothing -> do
-                        -- label not in module, create external reference
-                        let fty@(LMFunction sig) = funTy name
-                        let fun = LMGlobalVar name fty (funcLinkage sig)
-                                        Nothing Nothing False
-                        let top = CmmData Data [([],[fty])]
-                        let env' = funInsert name fty env1
-                        return (env', fun, nilOL, [top])
-
-            CmmCallee expr _ -> do
-                (env', v1, stmts, top) <- exprToVar env1 expr
-                let fty = funTy $ fsLit "dynamic"
-                let cast = case getVarType v1 of
-                     ty | isPointer ty -> LM_Bitcast
-                     ty | isInt ty     -> LM_Inttoptr
-
-                     ty -> panic $ "genCall: Expr is of bad type for function"
-                                ++ " call! (" ++ show (ty) ++ ")"
-
-                (v2,s1) <- doExpr (pLift fty) $ Cast cast v1 (pLift fty)
-                return (env', v2, stmts `snocOL` s1, top)
-
-            CmmPrim mop -> do
-                let name = cmmPrimOpFunctions mop
-                let lbl  = mkForeignLabel name Nothing
-                                    ForeignLabelInExternalPackage IsFunction
-                getFunPtr $ CmmCallee (CmmLit (CmmLabel lbl)) CCallConv
-
-    (env2, fptr, stmts2, top2) <- getFunPtr target
+    (env1, argVars, stmts1, top1) <- arg_vars env args ([], nilOL, [])
+    (env2, fptr, stmts2, top2)    <- getFunPtr env1 funTy target
 
     let retStmt | ccTy == TailCall       = unitOL $ Return Nothing
                 | ret == CmmNeverReturns = unitOL $ Unreachable
                 | otherwise              = nilOL
 
-    {- In LLVM we pass the STG registers around everywhere in function calls.
-       So this means LLVM considers them live across the entire function, when
-       in reality they usually aren't. For Caller save registers across C calls
-       the saving and restoring of them is done by the Cmm code generator,
-       using Cmm local vars. So to stop LLVM saving them as well (and saving
-       all of them since it thinks they're always live, we trash them just
-       before the call by assigning the 'undef' value to them. The ones we
-       need are restored from the Cmm local var and the ones we don't need
-       are fine to be trashed.
-    -}
-    let trashStmts = concatOL $ map trashReg activeStgRegs
-            where trashReg r =
-                    let reg   = lmGlobalRegVar r
-                        ty    = (pLower . getVarType) reg
-                        trash = unitOL $ Store (LMLitVar $ LMUndefLit ty) reg
-                    in case callerSaves r of
-                              True  -> trash
-                              False -> nilOL
-
     let stmts = stmts1 `appOL` stmts2 `appOL` trashStmts
 
     -- make the actual call
@@ -321,6 +269,10 @@ genCall env target res args ret = do
 
         _ -> do
             (v1, s1) <- doExpr retTy $ Call ccTy fptr argVars fnAttrs
+            -- get the return register
+            let ret_reg ([CmmHinted reg hint]) = (reg, hint)
+                ret_reg t = panic $ "genCall: Bad number of registers! Can only handle"
+                                ++ " 1, given " ++ show (length t) ++ "."
             let (creg, _) = ret_reg res
             let (env3, vreg, stmts3, top3) = getCmmReg env2 (CmmLocal creg)
             let allStmts = stmts `snocOL` s1 `appOL` stmts3
@@ -344,6 +296,55 @@ genCall env target res args ret = do
                                 `appOL` retStmt, top1 ++ top2 ++ top3)
 
 
+-- | Create a function pointer from a target.
+getFunPtr :: LlvmEnv -> (LMString -> LlvmType) -> CmmCallTarget
+          -> UniqSM ExprData
+getFunPtr env funTy targ = case targ of
+    CmmCallee (CmmLit (CmmLabel lbl)) _ -> litCase $ strCLabel_llvm lbl
+
+    CmmCallee expr _ -> do
+        (env', v1, stmts, top) <- exprToVar env expr
+        let fty = funTy $ fsLit "dynamic"
+            cast = case getVarType v1 of
+                ty | isPointer ty -> LM_Bitcast
+                ty | isInt ty     -> LM_Inttoptr
+
+                ty -> panic $ "genCall: Expr is of bad type for function"
+                              ++ " call! (" ++ show (ty) ++ ")"
+
+        (v2,s1) <- doExpr (pLift fty) $ Cast cast v1 (pLift fty)
+        return (env', v2, stmts `snocOL` s1, top)
+
+    CmmPrim mop -> litCase $ cmmPrimOpFunctions env mop
+
+    where
+        litCase name = do
+            case funLookup name env of
+                Just ty'@(LMFunction sig) -> do
+                    -- Function in module in right form
+                    let fun = LMGlobalVar name ty' (funcLinkage sig)
+                                    Nothing Nothing False
+                    return (env, fun, nilOL, [])
+
+                Just ty' -> do
+                    -- label in module but not function pointer, convert
+                    let fty@(LMFunction sig) = funTy name
+                        fun = LMGlobalVar name (pLift ty') (funcLinkage sig)
+                                    Nothing Nothing False
+                    (v1, s1) <- doExpr (pLift fty)
+                                    $ Cast LM_Bitcast fun (pLift fty)
+                    return  (env, v1, unitOL s1, [])
+
+                Nothing -> do
+                    -- label not in module, create external reference
+                    let fty@(LMFunction sig) = funTy name
+                        fun = LMGlobalVar name fty (funcLinkage sig)
+                                    Nothing Nothing False
+                        top = [CmmData Data [([],[fty])]]
+                        env' = funInsert name fty env
+                    return (env', fun, nilOL, top)
+
+
 -- | Conversion of call arguments.
 arg_vars :: LlvmEnv
          -> HintedCmmActuals
@@ -370,9 +371,41 @@ arg_vars env (CmmHinted e _:rest) (vars, stmts, tops)
   = do (env', v1, stmts', top') <- exprToVar env e
        arg_vars env' rest (vars ++ [v1], stmts `appOL` stmts', tops ++ top')
 
+
+-- | Cast a collection of LLVM variables to specific types.
+castVars :: [(LlvmVar, LlvmType)]
+         -> UniqSM ([LlvmVar], LlvmStatements)
+castVars vars = do
+                done <- mapM (uncurry castVar) vars
+                let (vars', stmts) = unzip done
+                return (vars', toOL stmts)
+
+-- | Cast an LLVM variable to a specific type, panicing if it can't be done.
+castVar :: LlvmVar -> LlvmType -> UniqSM (LlvmVar, LlvmStatement)
+castVar v t | getVarType v == t
+            = return (v, Nop)
+
+            | otherwise
+            = let op = case (getVarType v, t) of
+                      (LMInt n, LMInt m)
+                          -> if n < m then LM_Sext else LM_Trunc
+                      (vt, _) | isFloat vt && isFloat t
+                          -> if llvmWidthInBits vt < llvmWidthInBits t
+                                then LM_Fpext else LM_Fptrunc
+                      (vt, _) | isInt vt && isFloat t       -> LM_Sitofp
+                      (vt, _) | isFloat vt && isInt t       -> LM_Fptosi
+                      (vt, _) | isInt vt && isPointer t     -> LM_Inttoptr
+                      (vt, _) | isPointer vt && isInt t     -> LM_Ptrtoint
+                      (vt, _) | isPointer vt && isPointer t -> LM_Bitcast
+
+                      (vt, _) -> panic $ "castVars: Can't cast this type ("
+                                  ++ show vt ++ ") to (" ++ show t ++ ")"
+              in doExpr t $ Cast op v t
+
+
 -- | Decide what C function to use to implement a CallishMachOp
-cmmPrimOpFunctions :: CallishMachOp -> FastString
-cmmPrimOpFunctions mop
+cmmPrimOpFunctions :: LlvmEnv -> CallishMachOp -> LMString
+cmmPrimOpFunctions env mop
  = case mop of
     MO_F32_Exp    -> fsLit "expf"
     MO_F32_Log    -> fsLit "logf"
@@ -408,8 +441,18 @@ cmmPrimOpFunctions mop
     MO_F64_Cosh   -> fsLit "cosh"
     MO_F64_Tanh   -> fsLit "tanh"
 
+    MO_Memcpy     -> fsLit $ "llvm.memcpy."  ++ intrinTy1
+    MO_Memmove    -> fsLit $ "llvm.memmove." ++ intrinTy1
+    MO_Memset     -> fsLit $ "llvm.memset."  ++ intrinTy2
+
     a -> panic $ "cmmPrimOpFunctions: Unknown callish op! (" ++ show a ++ ")"
 
+    where
+        intrinTy1 = (if getLlvmVer env >= 28
+                       then "p0i8.p0i8." else "") ++ show llvmWord
+        intrinTy2 = (if getLlvmVer env >= 28
+                       then "p0i8." else "") ++ show llvmWord
+    
 
 -- | Tail function calls
 genJump :: LlvmEnv -> CmmExpr -> UniqSM StmtData
@@ -594,7 +637,7 @@ genSwitch env cond maybe_ids = do
     (env', vc, stmts, top) <- exprToVar env cond
     let ty = getVarType vc
 
-    let pairs = [ (ix, id) | (ix,Just id) <- zip ([0..]::[Integer]) maybe_ids ]
+    let pairs = [ (ix, id) | (ix,Just id) <- zip [0..] maybe_ids ]
     let labels = map (\(ix, b) -> (mkIntLit ty ix, blockIdToLlvm b)) pairs
     -- out of range is undefied, so lets just branch to first label
     let (_, defLbl) = head labels
@@ -675,11 +718,11 @@ genMachOp :: LlvmEnv -> EOption -> MachOp -> [CmmExpr] -> UniqSM ExprData
 genMachOp env _ op [x] = case op of
 
     MO_Not w ->
-        let all1 = mkIntLit (widthToLlvmInt w) (-1::Int)
+        let all1 = mkIntLit (widthToLlvmInt w) (-1)
         in negate (widthToLlvmInt w) all1 LM_MO_Xor
 
     MO_S_Neg w ->
-        let all0 = mkIntLit (widthToLlvmInt w) (0::Int)
+        let all0 = mkIntLit (widthToLlvmInt w) 0
         in negate (widthToLlvmInt w) all0 LM_MO_Sub
 
     MO_F_Neg w ->
@@ -1107,6 +1150,28 @@ funEpilogue = do
     return (vars, concatOL stmts)
 
 
+-- | A serries of statements to trash all the STG registers.
+--
+-- In LLVM we pass the STG registers around everywhere in function calls.
+-- So this means LLVM considers them live across the entire function, when
+-- in reality they usually aren't. For Caller save registers across C calls
+-- the saving and restoring of them is done by the Cmm code generator,
+-- using Cmm local vars. So to stop LLVM saving them as well (and saving
+-- all of them since it thinks they're always live, we trash them just
+-- before the call by assigning the 'undef' value to them. The ones we
+-- need are restored from the Cmm local var and the ones we don't need
+-- are fine to be trashed.
+trashStmts :: LlvmStatements
+trashStmts = concatOL $ map trashReg activeStgRegs
+    where trashReg r =
+            let reg   = lmGlobalRegVar r
+                ty    = (pLower . getVarType) reg
+                trash = unitOL $ Store (LMLitVar $ LMUndefLit ty) reg
+            in case callerSaves r of
+                      True  -> trash
+                      False -> nilOL
+
+
 -- | Get a function pointer to the CLabel specified.
 --
 -- This is for Haskell functions, function type is assumed, so doesn't work
index f5e3394..b58b7cd 100644 (file)
@@ -13,12 +13,6 @@ import LlvmCodeGen ( llvmCodeGen )
 
 import UniqSupply      ( mkSplitUniqSupply )
 
-#ifdef JAVA
-import JavaGen         ( javaGen )
-import qualified PrintJava
-import OccurAnal       ( occurAnalyseBinds )
-#endif
-
 import Finder          ( mkStubPaths )
 import PprC            ( writeCs )
 import CmmLint         ( cmmLint )
@@ -83,12 +77,6 @@ codeOutput dflags this_mod location foreign_stubs pkg_deps flat_abstractC
              HscAsm         -> outputAsm dflags filenm flat_abstractC;
              HscC           -> outputC dflags filenm flat_abstractC pkg_deps;
              HscLlvm        -> outputLlvm dflags filenm flat_abstractC;
-             HscJava        -> 
-#ifdef JAVA
-                              outputJava dflags filenm mod_name tycons core_binds;
-#else
-                               panic "Java support not compiled into this ghc";
-#endif
              HscNothing     -> panic "codeOutput: HscNothing"
          }
        ; return stubs_exist
@@ -176,26 +164,6 @@ outputLlvm dflags filenm flat_absC
 
 %************************************************************************
 %*                                                                     *
-\subsection{Java}
-%*                                                                     *
-%************************************************************************
-
-\begin{code}
-#ifdef JAVA
-outputJava dflags filenm mod tycons core_binds
-  = doOutput filenm (\ f -> printForUser f alwaysQualify pp_java)
-       -- User style printing for now to keep indentation
-  where
-    occ_anal_binds = occurAnalyseBinds core_binds
-       -- Make sure we have up to date dead-var information
-    java_code = javaGen mod [{- Should be imports-}] tycons occ_anal_binds
-    pp_java   = PrintJava.compilationUnit java_code
-#endif
-\end{code}
-
-
-%************************************************************************
-%*                                                                     *
 \subsection{Foreign import/export}
 %*                                                                     *
 %************************************************************************
index 2719470..afbd03e 100644 (file)
@@ -2007,5 +2007,4 @@ hscNextPhase dflags _ hsc_lang =
         HscLlvm        -> LlvmOpt
         HscNothing     -> StopLn
         HscInterpreted -> StopLn
-        _other         -> StopLn
 
index d9f3246..b49b860 100644 (file)
@@ -644,7 +644,6 @@ data HscTarget
   = HscC           -- ^ Generate C code.
   | HscAsm         -- ^ Generate assembly using the native code generator.
   | HscLlvm        -- ^ Generate assembly using the llvm code generator.
-  | HscJava        -- ^ Generate Java bytecode.
   | HscInterpreted -- ^ Generate bytecode.  (Requires 'LinkInMemory')
   | HscNothing     -- ^ Don't generate any code.  See notes above.
   deriving (Eq, Show)
@@ -653,7 +652,6 @@ showHscTargetFlag :: HscTarget -> String
 showHscTargetFlag HscC           = "-fvia-c"
 showHscTargetFlag HscAsm         = "-fasm"
 showHscTargetFlag HscLlvm        = "-fllvm"
-showHscTargetFlag HscJava        = panic "No flag for HscJava"
 showHscTargetFlag HscInterpreted = "-fbyte-code"
 showHscTargetFlag HscNothing     = "-fno-code"
 
index 1c7a389..a0a9f0e 100644 (file)
@@ -190,11 +190,11 @@ dumpIfSet_dyn dflags flag hdr doc
   = return ()
 
 dumpIfSet_dyn_or :: DynFlags -> [DynFlag] -> String -> SDoc -> IO ()
-dumpIfSet_dyn_or dflags flags hdr doc
-  | or [dopt flag dflags | flag <- flags]
-  || verbosity dflags >= 4 
-  = printDump (mkDumpDoc hdr doc)
-  | otherwise = return ()
+dumpIfSet_dyn_or _ [] _ _ = return ()
+dumpIfSet_dyn_or dflags (flag : flags) hdr doc
+    = if dopt flag dflags || verbosity dflags >= 4
+      then dumpSDoc dflags flag hdr doc
+      else dumpIfSet_dyn_or dflags flags hdr doc
 
 mkDumpDoc :: String -> SDoc -> SDoc
 mkDumpDoc hdr doc 
index 6a5552f..3e37f5b 100644 (file)
@@ -430,7 +430,7 @@ makeSimpleDetails hsc_env tc_result = mkBootModDetailsTc hsc_env tc_result
 
 
 It's the task of the compilation proper to compile Haskell, hs-boot and
-core files to either byte-code, hard-code (C, asm, Java, ect) or to
+core files to either byte-code, hard-code (C, asm, LLVM, ect) or to
 nothing at all (the module is still parsed and type-checked. This
 feature is mostly used by IDE's and the likes).
 Compilation can happen in either 'one-shot', 'batch', 'nothing',
index 77e69fd..f3e569b 100644 (file)
@@ -100,7 +100,7 @@ module HscTypes (
 #include "HsVersions.h"
 
 #ifdef GHCI
-import ByteCodeAsm     ( CompiledByteCode )
+import ByteCodeAsm      ( CompiledByteCode )
 import {-# SOURCE #-}  InteractiveEval ( Resume )
 #endif
 
@@ -108,16 +108,17 @@ import HsSyn
 import RdrName
 import Name
 import NameEnv
-import NameSet 
+import NameSet  
 import Module
-import InstEnv         ( InstEnv, Instance )
-import FamInstEnv      ( FamInstEnv, FamInst )
-import Rules           ( RuleBase )
-import CoreSyn         ( CoreBind )
+import InstEnv          ( InstEnv, Instance )
+import FamInstEnv       ( FamInstEnv, FamInst )
+import Rules            ( RuleBase )
+import CoreSyn          ( CoreBind )
 import VarEnv
+import VarSet
 import Var
 import Id
-import Type            
+import Type             
 
 import Annotations
 import Class           ( Class, classAllSelIds, classATs, classTyCon )
@@ -1722,9 +1723,9 @@ isHpcUsed (NoHpcInfo { hpcUsed = used }) = used
 \end{code}
 
 %************************************************************************
-%*                                                                     *
+%*                                                                      *
 \subsection{Vectorisation Support}
-%*                                                                     *
+%*                                                                      *
 %************************************************************************
 
 The following information is generated and consumed by the vectorisation
@@ -1737,49 +1738,58 @@ vectorisation, we need to know `f_v', whose `Var' we cannot lookup based
 on just the OccName easily in a Core pass.
 
 \begin{code}
--- | Vectorisation information for 'ModGuts', 'ModDetails' and 'ExternalPackageState'.
+-- |Vectorisation information for 'ModGuts', 'ModDetails' and 'ExternalPackageState'; see also
+-- documentation at 'Vectorise.Env.GlobalEnv'.
 data VectInfo      
-  = VectInfo {
-      vectInfoVar     :: VarEnv  (Var    , Var  ),   -- ^ @(f, f_v)@ keyed on @f@
-      vectInfoTyCon   :: NameEnv (TyCon  , TyCon),   -- ^ @(T, T_v)@ keyed on @T@
-      vectInfoDataCon :: NameEnv (DataCon, DataCon), -- ^ @(C, C_v)@ keyed on @C@
-      vectInfoPADFun  :: NameEnv (TyCon  , Var),     -- ^ @(T_v, paT)@ keyed on @T_v@
-      vectInfoIso     :: NameEnv (TyCon  , Var)      -- ^ @(T, isoT)@ keyed on @T@
+  = VectInfo
+    { vectInfoVar          :: VarEnv  (Var    , Var  )    -- ^ @(f, f_v)@ keyed on @f@
+    , vectInfoTyCon        :: NameEnv (TyCon  , TyCon)    -- ^ @(T, T_v)@ keyed on @T@
+    , vectInfoDataCon      :: NameEnv (DataCon, DataCon)  -- ^ @(C, C_v)@ keyed on @C@
+    , vectInfoPADFun       :: NameEnv (TyCon  , Var)      -- ^ @(T_v, paT)@ keyed on @T_v@
+    , vectInfoIso          :: NameEnv (TyCon  , Var)      -- ^ @(T, isoT)@ keyed on @T@
+    , vectInfoScalarVars   :: VarSet                      -- ^ set of purely scalar variables
+    , vectInfoScalarTyCons :: NameSet                     -- ^ set of scalar type constructors
     }
 
--- | Vectorisation information for 'ModIface': a slightly less low-level view
+-- |Vectorisation information for 'ModIface'; i.e, the vectorisation information propagated 
+-- across module boundaries.
+--
 data IfaceVectInfo 
-  = IfaceVectInfo {
-      ifaceVectInfoVar        :: [Name],
-        -- ^ All variables in here have a vectorised variant
-      ifaceVectInfoTyCon      :: [Name],
-        -- ^ All 'TyCon's in here have a vectorised variant;
-        -- the name of the vectorised variant and those of its
-        -- data constructors are determined by 'OccName.mkVectTyConOcc'
-        -- and 'OccName.mkVectDataConOcc'; the names of
-        -- the isomorphisms are determined by 'OccName.mkVectIsoOcc'
-      ifaceVectInfoTyConReuse :: [Name]              
-        -- ^ The vectorised form of all the 'TyCon's in here coincides with
-        -- the unconverted form; the name of the isomorphisms is determined
-        -- by 'OccName.mkVectIsoOcc'
+  = IfaceVectInfo 
+    { ifaceVectInfoVar          :: [Name]  -- ^ All variables in here have a vectorised variant
+    , ifaceVectInfoTyCon        :: [Name]  -- ^ All 'TyCon's in here have a vectorised variant;
+                                           -- the name of the vectorised variant and those of its
+                                           -- data constructors are determined by
+                                           -- 'OccName.mkVectTyConOcc' and 
+                                           -- 'OccName.mkVectDataConOcc'; the names of the
+                                           -- isomorphisms are determined by 'OccName.mkVectIsoOcc'
+    , ifaceVectInfoTyConReuse   :: [Name]  -- ^ The vectorised form of all the 'TyCon's in here
+                                           -- coincides with the unconverted form; the name of the
+                                           -- isomorphisms is determined by 'OccName.mkVectIsoOcc'
+    , ifaceVectInfoScalarVars   :: [Name]  -- iface version of 'vectInfoScalarVar'
+    , ifaceVectInfoScalarTyCons :: [Name]  -- iface version of 'vectInfoScalarTyCon'
     }
 
 noVectInfo :: VectInfo
-noVectInfo = VectInfo emptyVarEnv emptyNameEnv emptyNameEnv emptyNameEnv emptyNameEnv
+noVectInfo 
+  = VectInfo emptyVarEnv emptyNameEnv emptyNameEnv emptyNameEnv emptyNameEnv emptyVarSet
+             emptyNameSet
 
 plusVectInfo :: VectInfo -> VectInfo -> VectInfo
 plusVectInfo vi1 vi2 = 
-  VectInfo (vectInfoVar     vi1 `plusVarEnv`  vectInfoVar     vi2)
-           (vectInfoTyCon   vi1 `plusNameEnv` vectInfoTyCon   vi2)
-           (vectInfoDataCon vi1 `plusNameEnv` vectInfoDataCon vi2)
-           (vectInfoPADFun  vi1 `plusNameEnv` vectInfoPADFun  vi2)
-           (vectInfoIso     vi1 `plusNameEnv` vectInfoIso     vi2)
+  VectInfo (vectInfoVar          vi1 `plusVarEnv`    vectInfoVar          vi2)
+           (vectInfoTyCon        vi1 `plusNameEnv`   vectInfoTyCon        vi2)
+           (vectInfoDataCon      vi1 `plusNameEnv`   vectInfoDataCon      vi2)
+           (vectInfoPADFun       vi1 `plusNameEnv`   vectInfoPADFun       vi2)
+           (vectInfoIso          vi1 `plusNameEnv`   vectInfoIso          vi2)
+           (vectInfoScalarVars   vi1 `unionVarSet`   vectInfoScalarVars   vi2)
+           (vectInfoScalarTyCons vi1 `unionNameSets` vectInfoScalarTyCons vi2)
 
 concatVectInfo :: [VectInfo] -> VectInfo
 concatVectInfo = foldr plusVectInfo noVectInfo
 
 noIfaceVectInfo :: IfaceVectInfo
-noIfaceVectInfo = IfaceVectInfo [] [] []
+noIfaceVectInfo = IfaceVectInfo [] [] [] [] []
 \end{code}
 
 %************************************************************************
index 9c086cc..e40312c 100644 (file)
@@ -21,6 +21,7 @@ module SysTools (
         runWindres,
         runLlvmOpt,
         runLlvmLlc,
+        figureLlvmVersion,
         readElfSection,
 
         touch,                  -- String -> String -> IO ()
@@ -416,16 +417,54 @@ runAs dflags args = do
   mb_env <- getGccEnv args1
   runSomethingFiltered dflags id "Assembler" p args1 mb_env
 
+-- | Run the LLVM Optimiser
 runLlvmOpt :: DynFlags -> [Option] -> IO ()
 runLlvmOpt dflags args = do
   let (p,args0) = pgm_lo dflags
   runSomething dflags "LLVM Optimiser" p (args0++args)
 
+-- | Run the LLVM Compiler
 runLlvmLlc :: DynFlags -> [Option] -> IO ()
 runLlvmLlc dflags args = do
   let (p,args0) = pgm_lc dflags
   runSomething dflags "LLVM Compiler" p (args0++args)
 
+-- | Figure out which version of LLVM we are running this session
+figureLlvmVersion :: DynFlags -> IO (Maybe Int)
+figureLlvmVersion dflags = do
+  let (pgm,opts) = pgm_lc dflags
+      args = filter notNull (map showOpt opts)
+      -- we grab the args even though they should be useless just in
+      -- case the user is using a customised 'llc' that requires some
+      -- of the options they've specified. llc doesn't care what other
+      -- options are specified when '-version' is used.
+      args' = args ++ ["-version"]
+  ver <- catchIO (do
+             (pin, pout, perr, _) <- runInteractiveProcess pgm args'
+                                             Nothing Nothing
+             {- > llc -version
+                  Low Level Virtual Machine (http://llvm.org/):
+                    llvm version 2.8 (Ubuntu 2.8-0Ubuntu1)
+                    ...
+             -}
+             hSetBinaryMode pout False
+             _     <- hGetLine pout
+             vline <- hGetLine pout
+             v     <- case filter isDigit vline of
+                            []      -> fail "no digits!"
+                            [x]     -> fail $ "only 1 digit! (" ++ show x ++ ")"
+                            (x:y:_) -> return ((read [x,y]) :: Int)
+             hClose pin
+             hClose pout
+             hClose perr
+             return $ Just v
+            )
+            (\err -> do
+                putMsg dflags $ text $ "Warning: " ++ show err
+                return Nothing)
+  return ver
+  
+
 runLink :: DynFlags -> [Option] -> IO ()
 runLink dflags args = do
   let (p,args0) = pgm_l dflags
index b4296cb..b3f1a06 100644 (file)
@@ -487,12 +487,16 @@ tidyInstances tidy_dfun ispecs
 
 \begin{code}
 tidyVectInfo :: TidyEnv -> VectInfo -> VectInfo
-tidyVectInfo (_, var_env) info@(VectInfo { vectInfoVar     = vars
-                                         , vectInfoPADFun  = pas
-                                         , vectInfoIso     = isos })
-  = info { vectInfoVar    = tidy_vars
-         , vectInfoPADFun = tidy_pas
-         , vectInfoIso    = tidy_isos }
+tidyVectInfo (_, var_env) info@(VectInfo { vectInfoVar          = vars
+                                         , vectInfoPADFun       = pas
+                                         , vectInfoIso          = isos
+                                         , vectInfoScalarVars   = scalarVars
+                                         })
+  = info { vectInfoVar          = tidy_vars
+         , vectInfoPADFun       = tidy_pas
+         , vectInfoIso          = tidy_isos 
+         , vectInfoScalarVars   = tidy_scalarVars
+         }
   where
     tidy_vars = mkVarEnv
               $ map tidy_var_mapping
@@ -504,6 +508,10 @@ tidyVectInfo (_, var_env) info@(VectInfo { vectInfoVar     = vars
     tidy_var_mapping (from, to) = (from', (from', lookup_var to))
       where from' = lookup_var from
     tidy_snd_var (x, var) = (x, lookup_var var)
+
+    tidy_scalarVars = mkVarSet
+                    $ map lookup_var
+                    $ varSetElems scalarVars
       
     lookup_var var = lookupWithDefaultVarEnv var_env var var
 \end{code}
index 57faa6f..ae91b62 100644 (file)
@@ -13,32 +13,24 @@ module AsmCodeGen ( nativeCodeGen ) where
 #include "nativeGen/NCG.h"
 
 
-#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
-import X86.CodeGen
-import X86.Regs
-import X86.Instr
-import X86.Ppr
-
-#elif sparc_TARGET_ARCH
-import SPARC.CodeGen
-import SPARC.CodeGen.Expand
-import SPARC.Regs
-import SPARC.Instr
-import SPARC.Ppr
-import SPARC.ShortcutJump
-
-#elif powerpc_TARGET_ARCH
-import PPC.CodeGen
-import PPC.Cond
-import PPC.Regs
-import PPC.RegInfo
-import PPC.Instr
-import PPC.Ppr
-
-#else
-#error "AsmCodeGen: unknown architecture"
-
-#endif
+import qualified X86.CodeGen
+import qualified X86.Regs
+import qualified X86.Instr
+import qualified X86.Ppr
+
+import qualified SPARC.CodeGen
+import qualified SPARC.Regs
+import qualified SPARC.Instr
+import qualified SPARC.Ppr
+import qualified SPARC.ShortcutJump
+import qualified SPARC.CodeGen.Expand
+
+import qualified PPC.CodeGen
+import qualified PPC.Cond
+import qualified PPC.Regs
+import qualified PPC.RegInfo
+import qualified PPC.Instr
+import qualified PPC.Ppr
 
 import RegAlloc.Liveness
 import qualified RegAlloc.Linear.Main          as Linear
@@ -71,6 +63,7 @@ import StaticFlags
 import Util
 
 import Digraph
+import Pretty (Doc)
 import qualified Pretty
 import BufWrite
 import Outputable
@@ -138,17 +131,89 @@ The machine-dependent bits break down as follows:
 -- -----------------------------------------------------------------------------
 -- Top-level of the native codegen
 
+data NcgImpl instr jumpDest = NcgImpl {
+    cmmTopCodeGen             :: DynFlags -> RawCmmTop -> NatM [NatCmmTop instr],
+    generateJumpTableForInstr :: instr -> Maybe (NatCmmTop instr),
+    getJumpDestBlockId        :: jumpDest -> Maybe BlockId,
+    canShortcut               :: instr -> Maybe jumpDest,
+    shortcutStatic            :: (BlockId -> Maybe jumpDest) -> CmmStatic -> CmmStatic,
+    shortcutJump              :: (BlockId -> Maybe jumpDest) -> instr -> instr,
+    pprNatCmmTop              :: NatCmmTop instr -> Doc,
+    maxSpillSlots             :: Int,
+    allocatableRegs           :: [RealReg],
+    ncg_x86fp_kludge          :: [NatCmmTop instr] -> [NatCmmTop instr],
+    ncgExpandTop              :: [NatCmmTop instr] -> [NatCmmTop instr],
+    ncgMakeFarBranches        :: [NatBasicBlock instr] -> [NatBasicBlock instr]
+    }
+
 --------------------
 nativeCodeGen :: DynFlags -> Handle -> UniqSupply -> [RawCmm] -> IO ()
 nativeCodeGen dflags h us cmms
+ = let nCG' ncgImpl = nativeCodeGen' dflags ncgImpl h us cmms
+       x86NcgImpl = NcgImpl {
+                         cmmTopCodeGen             = X86.CodeGen.cmmTopCodeGen
+                        ,generateJumpTableForInstr = X86.CodeGen.generateJumpTableForInstr
+                        ,getJumpDestBlockId        = X86.Instr.getJumpDestBlockId
+                        ,canShortcut               = X86.Instr.canShortcut
+                        ,shortcutStatic            = X86.Instr.shortcutStatic
+                        ,shortcutJump              = X86.Instr.shortcutJump
+                        ,pprNatCmmTop              = X86.Ppr.pprNatCmmTop
+                        ,maxSpillSlots             = X86.Instr.maxSpillSlots
+                        ,allocatableRegs           = X86.Regs.allocatableRegs
+                        ,ncg_x86fp_kludge          = id
+                        ,ncgExpandTop              = id
+                        ,ncgMakeFarBranches        = id
+                    }
+   in case platformArch $ targetPlatform dflags of
+                 ArchX86    -> nCG' (x86NcgImpl { ncg_x86fp_kludge = map x86fp_kludge })
+                 ArchX86_64 -> nCG' x86NcgImpl
+                 ArchPPC ->
+                     nCG' $ NcgImpl {
+                          cmmTopCodeGen             = PPC.CodeGen.cmmTopCodeGen
+                         ,generateJumpTableForInstr = PPC.CodeGen.generateJumpTableForInstr
+                         ,getJumpDestBlockId        = PPC.RegInfo.getJumpDestBlockId
+                         ,canShortcut               = PPC.RegInfo.canShortcut
+                         ,shortcutStatic            = PPC.RegInfo.shortcutStatic
+                         ,shortcutJump              = PPC.RegInfo.shortcutJump
+                         ,pprNatCmmTop              = PPC.Ppr.pprNatCmmTop
+                         ,maxSpillSlots             = PPC.Instr.maxSpillSlots
+                         ,allocatableRegs           = PPC.Regs.allocatableRegs
+                         ,ncg_x86fp_kludge          = id
+                         ,ncgExpandTop              = id
+                         ,ncgMakeFarBranches        = makeFarBranches
+                     }
+                 ArchSPARC ->
+                     nCG' $ NcgImpl {
+                          cmmTopCodeGen             = SPARC.CodeGen.cmmTopCodeGen
+                         ,generateJumpTableForInstr = SPARC.CodeGen.generateJumpTableForInstr
+                         ,getJumpDestBlockId        = SPARC.ShortcutJump.getJumpDestBlockId
+                         ,canShortcut               = SPARC.ShortcutJump.canShortcut
+                         ,shortcutStatic            = SPARC.ShortcutJump.shortcutStatic
+                         ,shortcutJump              = SPARC.ShortcutJump.shortcutJump
+                         ,pprNatCmmTop              = SPARC.Ppr.pprNatCmmTop
+                         ,maxSpillSlots             = SPARC.Instr.maxSpillSlots
+                         ,allocatableRegs           = SPARC.Regs.allocatableRegs
+                         ,ncg_x86fp_kludge          = id
+                         ,ncgExpandTop              = map SPARC.CodeGen.Expand.expandTop
+                         ,ncgMakeFarBranches        = id
+                     }
+                 ArchPPC_64 ->
+                     panic "nativeCodeGen: No NCG for PPC 64"
+                 ArchUnknown ->
+                     panic "nativeCodeGen: No NCG for unknown arch"
+
+nativeCodeGen' :: (Instruction instr, Outputable instr)
+               => DynFlags
+               -> NcgImpl instr jumpDest
+               -> Handle -> UniqSupply -> [RawCmm] -> IO ()
+nativeCodeGen' dflags ncgImpl h us cmms
  = do
        let split_cmms  = concat $ map add_split cmms
-
         -- BufHandle is a performance hack.  We could hide it inside
         -- Pretty if it weren't for the fact that we do lots of little
         -- printDocs here (in order to do codegen in constant space).
         bufh <- newBufHandle h
-       (imports, prof) <- cmmNativeGens dflags bufh us split_cmms [] [] 0
+       (imports, prof) <- cmmNativeGens dflags ncgImpl bufh us split_cmms [] [] 0
         bFlush bufh
 
        let (native, colorStats, linearStats)
@@ -157,7 +222,7 @@ nativeCodeGen dflags h us cmms
        -- dump native code
        dumpIfSet_dyn dflags
                Opt_D_dump_asm "Asm code"
-               (vcat $ map (docToSDoc . pprNatCmmTop) $ concat native)
+               (vcat $ map (docToSDoc . pprNatCmmTop ncgImpl) $ concat native)
 
        -- dump global NCG stats for graph coloring allocator
        (case concat $ catMaybes colorStats of
@@ -203,30 +268,32 @@ nativeCodeGen dflags h us cmms
 
 -- | Do native code generation on all these cmms.
 --
-cmmNativeGens :: DynFlags
+cmmNativeGens :: (Instruction instr, Outputable instr)
+              => DynFlags
+              -> NcgImpl instr jumpDest
               -> BufHandle
               -> UniqSupply
               -> [RawCmmTop]
               -> [[CLabel]]
-              -> [ ([NatCmmTop Instr],
-                   Maybe [Color.RegAllocStats Instr],
+              -> [ ([NatCmmTop instr],
+                   Maybe [Color.RegAllocStats instr],
                    Maybe [Linear.RegAllocStats]) ]
               -> Int
               -> IO ( [[CLabel]],
-                      [([NatCmmTop Instr],
-                      Maybe [Color.RegAllocStats Instr],
+                      [([NatCmmTop instr],
+                      Maybe [Color.RegAllocStats instr],
                       Maybe [Linear.RegAllocStats])] )
 
-cmmNativeGens _ _ _ [] impAcc profAcc _
+cmmNativeGens _ _ _ _ [] impAcc profAcc _
        = return (reverse impAcc, reverse profAcc)
 
-cmmNativeGens dflags h us (cmm : cmms) impAcc profAcc count
+cmmNativeGens dflags ncgImpl h us (cmm : cmms) impAcc profAcc count
  = do
        (us', native, imports, colorStats, linearStats)
-               <- cmmNativeGen dflags us cmm count
+               <- cmmNativeGen dflags ncgImpl us cmm count
 
        Pretty.bufLeftRender h
-               $ {-# SCC "pprNativeCode" #-} Pretty.vcat $ map pprNatCmmTop native
+               $ {-# SCC "pprNativeCode" #-} Pretty.vcat $ map (pprNatCmmTop ncgImpl) native
 
            -- carefully evaluate this strictly.  Binding it with 'let'
            -- and then using 'seq' doesn't work, because the let
@@ -242,7 +309,8 @@ cmmNativeGens dflags h us (cmm : cmms) impAcc profAcc count
        -- force evaulation all this stuff to avoid space leaks
        seqString (showSDoc $ vcat $ map ppr imports) `seq` return ()
 
-       cmmNativeGens dflags h us' cmms
+       cmmNativeGens dflags ncgImpl
+            h us' cmms
                        (imports : impAcc)
                        ((lsPprNative, colorStats, linearStats) : profAcc)
                        count'
@@ -254,18 +322,20 @@ cmmNativeGens dflags h us (cmm : cmms) impAcc profAcc count
 -- | Complete native code generation phase for a single top-level chunk of Cmm.
 --     Dumping the output of each stage along the way.
 --     Global conflict graph and NGC stats
-cmmNativeGen 
-       :: DynFlags
+cmmNativeGen
+       :: (Instruction instr, Outputable instr)
+    => DynFlags
+    -> NcgImpl instr jumpDest
        -> UniqSupply
        -> RawCmmTop                                    -- ^ the cmm to generate code for
        -> Int                                          -- ^ sequence number of this top thing
        -> IO   ( UniqSupply
-               , [NatCmmTop Instr]                     -- native code
+               , [NatCmmTop instr]                     -- native code
                , [CLabel]                              -- things imported by this cmm
-               , Maybe [Color.RegAllocStats Instr]     -- stats for the coloring register allocator
+               , Maybe [Color.RegAllocStats instr]     -- stats for the coloring register allocator
                , Maybe [Linear.RegAllocStats])         -- stats for the linear register allocators
 
-cmmNativeGen dflags us cmm count
+cmmNativeGen dflags ncgImpl us cmm count
  = do
 
        -- rewrite assignments to global regs
@@ -285,11 +355,11 @@ cmmNativeGen dflags us cmm count
        -- generate native code from cmm
        let ((native, lastMinuteImports), usGen) =
                {-# SCC "genMachCode" #-}
-               initUs us $ genMachCode dflags opt_cmm
+               initUs us $ genMachCode dflags (cmmTopCodeGen ncgImpl) opt_cmm
 
        dumpIfSet_dyn dflags
                Opt_D_dump_asm_native "Native code"
-               (vcat $ map (docToSDoc . pprNatCmmTop) native)
+               (vcat $ map (docToSDoc . pprNatCmmTop ncgImpl) native)
 
        -- tag instructions with register liveness information
        let (withLiveness, usLive) =
@@ -312,7 +382,7 @@ cmmNativeGen dflags us cmm count
                        = foldr (\r -> plusUFM_C unionUniqSets
                                        $ unitUFM (targetClassOfRealReg r) (unitUniqSet r))
                                emptyUFM
-                       $ allocatableRegs
+                       $ allocatableRegs ncgImpl
 
                -- do the graph coloring register allocation
                let ((alloced, regAllocStats), usAlloc)
@@ -321,13 +391,13 @@ cmmNativeGen dflags us cmm count
                          $ Color.regAlloc
                                dflags
                                alloc_regs
-                               (mkUniqSet [0..maxSpillSlots])
+                               (mkUniqSet [0 .. maxSpillSlots ncgImpl])
                                withLiveness
 
                -- dump out what happened during register allocation
                dumpIfSet_dyn dflags
                        Opt_D_dump_asm_regalloc "Registers allocated"
-                       (vcat $ map (docToSDoc . pprNatCmmTop) alloced)
+                       (vcat $ map (docToSDoc . pprNatCmmTop ncgImpl) alloced)
 
                dumpIfSet_dyn dflags
                        Opt_D_dump_asm_regalloc_stages "Build/spill stages"
@@ -354,11 +424,11 @@ cmmNativeGen dflags us cmm count
                        = {-# SCC "RegAlloc" #-}
                          initUs usLive
                          $ liftM unzip
-                         $ mapUs Linear.regAlloc withLiveness
+                         $ mapUs (Linear.regAlloc dflags) withLiveness
 
                dumpIfSet_dyn dflags
                        Opt_D_dump_asm_regalloc "Registers allocated"
-                       (vcat $ map (docToSDoc . pprNatCmmTop) alloced)
+                       (vcat $ map (docToSDoc . pprNatCmmTop ncgImpl) alloced)
 
                let mPprStats =
                        if dopt Opt_D_dump_asm_stats dflags
@@ -378,42 +448,31 @@ cmmNativeGen dflags us cmm count
         ----
         ---- NB. must happen before shortcutBranches, because that
         ---- generates JXX_GBLs which we can't fix up in x86fp_kludge.
-        let kludged =
-#if i386_TARGET_ARCH
-               {-# SCC "x86fp_kludge" #-}
-                map x86fp_kludge alloced
-#else
-                alloced
-#endif
+        let kludged = {-# SCC "x86fp_kludge" #-} ncg_x86fp_kludge ncgImpl alloced
 
         ---- generate jump tables
        let tabled      =
                {-# SCC "generateJumpTables" #-}
-                generateJumpTables kludged
+                generateJumpTables ncgImpl kludged
 
        ---- shortcut branches
        let shorted     =
                {-# SCC "shortcutBranches" #-}
-               shortcutBranches dflags tabled
+               shortcutBranches dflags ncgImpl tabled
 
        ---- sequence blocks
        let sequenced   =
                {-# SCC "sequenceBlocks" #-}
-               map sequenceTop shorted
+               map (sequenceTop ncgImpl) shorted
 
         ---- expansion of SPARC synthetic instrs
-#if sparc_TARGET_ARCH
        let expanded = 
                {-# SCC "sparc_expand" #-}
-                map expandTop sequenced
+                ncgExpandTop ncgImpl sequenced
 
        dumpIfSet_dyn dflags
                Opt_D_dump_asm_expanded "Synthetic instructions expanded"
-               (vcat $ map (docToSDoc . pprNatCmmTop) expanded)
-#else
-       let expanded = 
-                sequenced
-#endif
+               (vcat $ map (docToSDoc . pprNatCmmTop ncgImpl) expanded)
 
        return  ( usAlloc
                , expanded
@@ -422,12 +481,10 @@ cmmNativeGen dflags us cmm count
                , ppr_raStatsLinear)
 
 
-#if i386_TARGET_ARCH
-x86fp_kludge :: NatCmmTop Instr -> NatCmmTop Instr
+x86fp_kludge :: NatCmmTop X86.Instr.Instr -> NatCmmTop X86.Instr.Instr
 x86fp_kludge top@(CmmData _ _) = top
 x86fp_kludge (CmmProc info lbl (ListGraph code)) = 
-       CmmProc info lbl (ListGraph $ i386_insert_ffrees code)
-#endif
+       CmmProc info lbl (ListGraph $ X86.Instr.i386_insert_ffrees code)
 
 
 -- | Build a doc for all the imports.
@@ -496,12 +553,12 @@ makeImportsDoc dflags imports
 -- fallthroughs.
 
 sequenceTop 
-       :: NatCmmTop Instr
-       -> NatCmmTop Instr
+       :: Instruction instr
+    => NcgImpl instr jumpDest -> NatCmmTop instr -> NatCmmTop instr
 
-sequenceTop top@(CmmData _ _) = top
-sequenceTop (CmmProc info lbl (ListGraph blocks)) = 
-  CmmProc info lbl (ListGraph $ makeFarBranches $ sequenceBlocks blocks)
+sequenceTop _       top@(CmmData _ _) = top
+sequenceTop ncgImpl (CmmProc info lbl (ListGraph blocks)) = 
+  CmmProc info lbl (ListGraph $ ncgMakeFarBranches ncgImpl $ sequenceBlocks blocks)
 
 -- The algorithm is very simple (and stupid): we make a graph out of
 -- the blocks where there is an edge from one block to another iff the
@@ -575,11 +632,9 @@ reorder id accum (b@(block,id',out) : rest)
 -- Conditional branches on PowerPC are limited to +-32KB; if our Procs get too
 -- big, we have to work around this limitation.
 
-makeFarBranches 
-       :: [NatBasicBlock Instr] 
-       -> [NatBasicBlock Instr]
-
-#if powerpc_TARGET_ARCH
+makeFarBranches
+       :: [NatBasicBlock PPC.Instr.Instr] 
+       -> [NatBasicBlock PPC.Instr.Instr]
 makeFarBranches blocks
     | last blockAddresses < nearLimit = blocks
     | otherwise = zipWith handleBlock blockAddresses blocks
@@ -590,12 +645,12 @@ makeFarBranches blocks
         handleBlock addr (BasicBlock id instrs)
                 = BasicBlock id (zipWith makeFar [addr..] instrs)
         
-        makeFar _ (BCC ALWAYS tgt) = BCC ALWAYS tgt
-        makeFar addr (BCC cond tgt)
+        makeFar _ (PPC.Instr.BCC PPC.Cond.ALWAYS tgt) = PPC.Instr.BCC PPC.Cond.ALWAYS tgt
+        makeFar addr (PPC.Instr.BCC cond tgt)
             | abs (addr - targetAddr) >= nearLimit
-            = BCCFAR cond tgt
+            = PPC.Instr.BCCFAR cond tgt
             | otherwise
-            = BCC cond tgt
+            = PPC.Instr.BCC cond tgt
             where Just targetAddr = lookupUFM blockAddressMap tgt
         makeFar _ other            = other
         
@@ -606,9 +661,6 @@ makeFarBranches blocks
                          -- things exactly
         
         blockAddressMap = listToUFM $ zip (map blockId blocks) blockAddresses
-#else
-makeFarBranches = id
-#endif
 
 -- -----------------------------------------------------------------------------
 -- Generate jump tables
@@ -616,33 +668,36 @@ makeFarBranches = id
 -- Analyzes all native code and generates data sections for all jump
 -- table instructions.
 generateJumpTables
-       :: [NatCmmTop Instr] -> [NatCmmTop Instr]
-generateJumpTables xs = concatMap f xs
+       :: NcgImpl instr jumpDest
+    -> [NatCmmTop instr] -> [NatCmmTop instr]
+generateJumpTables ncgImpl xs = concatMap f xs
     where f p@(CmmProc _ _ (ListGraph xs)) = p : concatMap g xs
           f p = [p]
-          g (BasicBlock _ xs) = catMaybes (map generateJumpTableForInstr xs)
+          g (BasicBlock _ xs) = catMaybes (map (generateJumpTableForInstr ncgImpl) xs)
 
 -- -----------------------------------------------------------------------------
 -- Shortcut branches
 
-shortcutBranches 
-       :: DynFlags 
-       -> [NatCmmTop Instr] 
-       -> [NatCmmTop Instr]
+shortcutBranches
+       :: DynFlags
+    -> NcgImpl instr jumpDest
+       -> [NatCmmTop instr] 
+       -> [NatCmmTop instr]
 
-shortcutBranches dflags tops
+shortcutBranches dflags ncgImpl tops
   | optLevel dflags < 1 = tops    -- only with -O or higher
-  | otherwise           = map (apply_mapping mapping) tops'
+  | otherwise           = map (apply_mapping ncgImpl mapping) tops'
   where
-    (tops', mappings) = mapAndUnzip build_mapping tops
+    (tops', mappings) = mapAndUnzip (build_mapping ncgImpl) tops
     mapping = foldr plusUFM emptyUFM mappings
 
-build_mapping :: GenCmmTop d t (ListGraph Instr)
-              -> (GenCmmTop d t (ListGraph Instr), UniqFM JumpDest)
-build_mapping top@(CmmData _ _) = (top, emptyUFM)
-build_mapping (CmmProc info lbl (ListGraph []))
+build_mapping :: NcgImpl instr jumpDest
+              -> GenCmmTop d t (ListGraph instr)
+              -> (GenCmmTop d t (ListGraph instr), UniqFM jumpDest)
+build_mapping _ top@(CmmData _ _) = (top, emptyUFM)
+build_mapping _ (CmmProc info lbl (ListGraph []))
   = (CmmProc info lbl (ListGraph []), emptyUFM)
-build_mapping (CmmProc info lbl (ListGraph (head:blocks)))
+build_mapping ncgImpl (CmmProc info lbl (ListGraph (head:blocks)))
   = (CmmProc info lbl (ListGraph (head:others)), mapping)
         -- drop the shorted blocks, but don't ever drop the first one,
         -- because it is pointed to by a global label.
@@ -652,11 +707,12 @@ build_mapping (CmmProc info lbl (ListGraph (head:blocks)))
     -- Don't completely eliminate loops here -- that can leave a dangling jump!
     (_, shortcut_blocks, others) = foldl split (emptyBlockSet, [], []) blocks
     split (s, shortcut_blocks, others) b@(BasicBlock id [insn])
-        | Just (DestBlockId dest) <- canShortcut insn,
+        | Just jd <- canShortcut ncgImpl insn,
+          Just dest <- getJumpDestBlockId ncgImpl jd,
           (setMember dest s) || dest == id -- loop checks
         = (s, shortcut_blocks, b : others)
     split (s, shortcut_blocks, others) (BasicBlock id [insn])
-        | Just dest <- canShortcut insn
+        | Just dest <- canShortcut ncgImpl insn
         = (setInsert id s, (id,dest) : shortcut_blocks, others)
     split (s, shortcut_blocks, others) other = (s, shortcut_blocks, other : others)
 
@@ -665,18 +721,19 @@ build_mapping (CmmProc info lbl (ListGraph (head:blocks)))
     mapping = foldl add emptyUFM shortcut_blocks
     add ufm (id,dest) = addToUFM ufm id dest
     
-apply_mapping :: UniqFM JumpDest
-              -> GenCmmTop CmmStatic h (ListGraph Instr)
-              -> GenCmmTop CmmStatic h (ListGraph Instr)
-apply_mapping ufm (CmmData sec statics) 
-  = CmmData sec (map (shortcutStatic (lookupUFM ufm)) statics)
+apply_mapping :: NcgImpl instr jumpDest
+              -> UniqFM jumpDest
+              -> GenCmmTop CmmStatic h (ListGraph instr)
+              -> GenCmmTop CmmStatic h (ListGraph instr)
+apply_mapping ncgImpl ufm (CmmData sec statics)
+  = CmmData sec (map (shortcutStatic ncgImpl (lookupUFM ufm)) statics)
   -- we need to get the jump tables, so apply the mapping to the entries
   -- of a CmmData too.
-apply_mapping ufm (CmmProc info lbl (ListGraph blocks))
+apply_mapping ncgImpl ufm (CmmProc info lbl (ListGraph blocks))
   = CmmProc info lbl (ListGraph $ map short_bb blocks)
   where
     short_bb (BasicBlock id insns) = BasicBlock id $! map short_insn insns
-    short_insn i = shortcutJump (lookupUFM ufm) i
+    short_insn i = shortcutJump ncgImpl (lookupUFM ufm) i
                  -- shortcutJump should apply the mapping repeatedly,
                  -- just in case we can short multiple branches.
 
@@ -702,12 +759,13 @@ apply_mapping ufm (CmmProc info lbl (ListGraph blocks))
 
 genMachCode 
        :: DynFlags 
+        -> (DynFlags -> RawCmmTop -> NatM [NatCmmTop instr])
        -> RawCmmTop 
        -> UniqSM 
-               ( [NatCmmTop Instr]
+               ( [NatCmmTop instr]
                , [CLabel])
 
-genMachCode dflags cmm_top
+genMachCode dflags cmmTopCodeGen cmm_top
   = do { initial_us <- getUs
        ; let initial_st           = mkNatM_State initial_us 0 dflags
              (new_tops, final_st) = initNat initial_st (cmmTopCodeGen dflags cmm_top)
index 6771b75..81cbf61 100644 (file)
 #define COMMA ,
 
 -- - - - - - - - - - - - - - - - - - - - - - 
-#if alpha_TARGET_ARCH
-# define IF_ARCH_alpha(x,y) x
-#else
-# define IF_ARCH_alpha(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
 #if i386_TARGET_ARCH
 # define IF_ARCH_i386(x,y) x
 #else
 # define IF_ARCH_i386(x,y) y
 #endif
 -- - - - - - - - - - - - - - - - - - - - - - 
-#if x86_64_TARGET_ARCH
-# define IF_ARCH_x86_64(x,y) x
-#else
-# define IF_ARCH_x86_64(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if freebsd_TARGET_OS
-# define IF_OS_freebsd(x,y) x
-#else
-# define IF_OS_freebsd(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if dragonfly_TARGET_OS
-# define IF_OS_dragonfly(x,y) x
-#else
-# define IF_OS_dragonfly(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if netbsd_TARGET_OS
-# define IF_OS_netbsd(x,y) x
-#else
-# define IF_OS_netbsd(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if openbsd_TARGET_OS
-# define IF_OS_openbsd(x,y) x
-#else
-# define IF_OS_openbsd(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
 #if linux_TARGET_OS
 # define IF_OS_linux(x,y) x
 #else
 # define IF_OS_linux(x,y) y
 #endif
 -- - - - - - - - - - - - - - - - - - - - - - 
-#if linuxaout_TARGET_OS
-# define IF_OS_linuxaout(x,y) x
-#else
-# define IF_OS_linuxaout(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if bsdi_TARGET_OS
-# define IF_OS_bsdi(x,y) x
-#else
-# define IF_OS_bsdi(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if cygwin32_TARGET_OS
-# define IF_OS_cygwin32(x,y) x
-#else
-# define IF_OS_cygwin32(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if sparc_TARGET_ARCH
-# define IF_ARCH_sparc(x,y) x
-#else
-# define IF_ARCH_sparc(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if sunos4_TARGET_OS
-# define IF_OS_sunos4(x,y) x
-#else
-# define IF_OS_sunos4(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
--- NB: this will catch i386-*-solaris2, too
-#if solaris2_TARGET_OS
-# define IF_OS_solaris2(x,y) x
-#else
-# define IF_OS_solaris2(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
-#if powerpc_TARGET_ARCH
-# define IF_ARCH_powerpc(x,y) x
-#else
-# define IF_ARCH_powerpc(x,y) y
-#endif
--- - - - - - - - - - - - - - - - - - - - - - 
 #if darwin_TARGET_OS
 # define IF_OS_darwin(x,y) x
 #else
index c96badd..736d564 100644 (file)
@@ -910,7 +910,7 @@ genCCall target dest_regs argsAndHints
         (labelOrExpr, reduceToFF32) <- case target of
             CmmCallee (CmmLit (CmmLabel lbl)) conv -> return (Left lbl, False)
             CmmCallee expr conv -> return  (Right expr, False)
-            CmmPrim mop -> outOfLineFloatOp mop
+            CmmPrim mop -> outOfLineMachOp mop
                                                         
         let codeBefore = move_sp_down finalStack `appOL` passArgumentsCode
             codeAfter = move_sp_up finalStack `appOL` moveResult reduceToFF32
@@ -937,7 +937,17 @@ genCCall target dest_regs argsAndHints
         initialStackOffset = 8
         stackDelta finalStack = roundTo 16 finalStack
 #endif
-       args = map hintlessCmm argsAndHints
+        -- need to remove alignment information
+        argsAndHints' | (CmmPrim mop) <- target,
+                        (mop == MO_Memcpy ||
+                         mop == MO_Memset ||
+                         mop == MO_Memmove)
+                      = init argsAndHints
+
+                      | otherwise
+                      = argsAndHints
+
+       args = map hintlessCmm argsAndHints'
        argReps = map cmmExprType args
 
        roundTo a x | x `mod` a == 0 = x
@@ -1062,7 +1072,7 @@ genCCall target dest_regs argsAndHints
                     where rep = cmmRegType (CmmLocal dest)
                           r_dest = getRegisterReg (CmmLocal dest)
                           
-        outOfLineFloatOp mop =
+        outOfLineMachOp mop =
             do
                 dflags <- getDynFlagsNat
                 mopExpr <- cmmMakeDynamicReference dflags addImportNat CallReference $
@@ -1106,6 +1116,11 @@ genCCall target dest_regs argsAndHints
                     MO_F64_Cosh  -> (fsLit "cosh", False)
                     MO_F64_Tanh  -> (fsLit "tanh", False)
                     MO_F64_Pwr   -> (fsLit "pow", False)
+
+                    MO_Memcpy    -> (fsLit "memcpy", False)
+                    MO_Memset    -> (fsLit "memset", False)
+                    MO_Memmove   -> (fsLit "memmove", False)
+
                     other -> pprPanic "genCCall(ppc): unknown callish op"
                                     (pprCallishMachOp other)
 
index 8d8b16a..bd12a81 100644 (file)
@@ -109,9 +109,7 @@ pprData (CmmStaticLit lit)       = pprDataItem lit
 pprGloblDecl :: CLabel -> Doc
 pprGloblDecl lbl
   | not (externallyVisibleCLabel lbl) = empty
-  | otherwise = ptext IF_ARCH_sparc((sLit ".global "), 
-                                   (sLit ".globl ")) <>
-               pprCLabel_asm lbl
+  | otherwise = ptext (sLit ".globl ") <> pprCLabel_asm lbl
 
 pprTypeAndSizeDecl :: CLabel -> Doc
 #if linux_TARGET_OS
@@ -352,14 +350,9 @@ pprInstr :: Instr -> Doc
 pprInstr (COMMENT _) = empty -- nuke 'em
 {-
 pprInstr (COMMENT s)
-   =  IF_ARCH_alpha( ((<>) (ptext (sLit "\t# ")) (ftext s))
-     ,IF_ARCH_sparc( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_i386( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_x86_64( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_powerpc( IF_OS_linux(
+     IF_OS_linux(
         ((<>) (ptext (sLit "# ")) (ftext s)),
         ((<>) (ptext (sLit "; ")) (ftext s)))
-     ,)))))
 -}
 pprInstr (DELTA d)
    = pprInstr (COMMENT (mkFastString ("\tdelta = " ++ show d)))
index 91c9e15..bfc712a 100644 (file)
@@ -7,7 +7,7 @@
 -----------------------------------------------------------------------------
 
 module PPC.RegInfo (
-        JumpDest( DestBlockId ), 
+        JumpDest( DestBlockId ), getJumpDestBlockId,
        canShortcut, 
        shortcutJump, 
 
@@ -31,6 +31,10 @@ import Unique
 
 data JumpDest = DestBlockId BlockId | DestImm Imm
 
+getJumpDestBlockId :: JumpDest -> Maybe BlockId
+getJumpDestBlockId (DestBlockId bid) = Just bid
+getJumpDestBlockId _                 = Nothing
+
 canShortcut :: Instr -> Maybe JumpDest
 canShortcut _ = Nothing
 
index 4c05860..848b266 100644 (file)
@@ -1,7 +1,7 @@
-{-# OPTIONS -fno-warn-unused-binds #-}
+{-# LANGUAGE BangPatterns #-}
 
 module RegAlloc.Graph.TrivColorable (
-       trivColorable,
+        trivColorable,
 )
 
 where
@@ -15,78 +15,51 @@ import GraphBase
 
 import UniqFM
 import FastTypes
+import Platform
+import Panic
 
 
 -- trivColorable ---------------------------------------------------------------
 
 -- trivColorable function for the graph coloring allocator
 --
---     This gets hammered by scanGraph during register allocation,
---     so needs to be fairly efficient.
+--      This gets hammered by scanGraph during register allocation,
+--      so needs to be fairly efficient.
 --
---     NOTE:   This only works for arcitectures with just RcInteger and RcDouble
---             (which are disjoint) ie. x86, x86_64 and ppc
+--      NOTE:   This only works for arcitectures with just RcInteger and RcDouble
+--              (which are disjoint) ie. x86, x86_64 and ppc
 --
---     The number of allocatable regs is hard coded here so we can do a fast
---             comparision in trivColorable. 
+--      The number of allocatable regs is hard coded in here so we can do
+--              a fast comparision in trivColorable.
 --
---     It's ok if these numbers are _less_ than the actual number of free regs, 
---             but they can't be more or the register conflict graph won't color.
+--      It's ok if these numbers are _less_ than the actual number of free
+--              regs, but they can't be more or the register conflict
+--              graph won't color.
 --
---     If the graph doesn't color then the allocator will panic, but it won't 
---             generate bad object code or anything nasty like that.
+--      If the graph doesn't color then the allocator will panic, but it won't
+--              generate bad object code or anything nasty like that.
 --
---     There is an allocatableRegsInClass :: RegClass -> Int, but doing the unboxing
---     is too slow for us here.
+--      There is an allocatableRegsInClass :: RegClass -> Int, but doing
+--      the unboxing is too slow for us here.
+--      TODO: Is that still true? Could we use allocatableRegsInClass
+--      without losing performance now?
 --
---     Look at includes/stg/MachRegs.h to get these numbers.
+--      Look at includes/stg/MachRegs.h to get the numbers.
 --
 
-#if i386_TARGET_ARCH
-#define ALLOCATABLE_REGS_INTEGER (_ILIT(3))
-#define ALLOCATABLE_REGS_DOUBLE  (_ILIT(6))
-#define ALLOCATABLE_REGS_FLOAT   (_ILIT(0))
-#define ALLOCATABLE_REGS_SSE     (_ILIT(8))
-
-
-#elif x86_64_TARGET_ARCH
-#define ALLOCATABLE_REGS_INTEGER (_ILIT(5))
-#define ALLOCATABLE_REGS_DOUBLE  (_ILIT(0))
-#define ALLOCATABLE_REGS_FLOAT   (_ILIT(0))
-#define ALLOCATABLE_REGS_SSE     (_ILIT(10))
-
-#elif powerpc_TARGET_ARCH
-#define ALLOCATABLE_REGS_INTEGER (_ILIT(16))
-#define ALLOCATABLE_REGS_DOUBLE  (_ILIT(26))
-#define ALLOCATABLE_REGS_FLOAT   (_ILIT(0))
-#define ALLOCATABLE_REGS_SSE     (_ILIT(0))
-
-
-#elif sparc_TARGET_ARCH
-#define ALLOCATABLE_REGS_INTEGER (_ILIT(14))
-#define ALLOCATABLE_REGS_DOUBLE  (_ILIT(11))
-#define ALLOCATABLE_REGS_FLOAT   (_ILIT(22))
-#define ALLOCATABLE_REGS_SSE     (_ILIT(0))
-
-
-#else
-#error ToDo: choose which trivColorable function to use for this architecture.
-#endif
-
-
 
 -- Disjoint registers ----------------------------------------------------------
---     
---     The definition has been unfolded into individual cases for speed.
---     Each architecture has a different register setup, so we use a
---     different regSqueeze function for each.
 --
-accSqueeze 
-       :: FastInt 
-       -> FastInt
-       -> (reg -> FastInt) 
-       -> UniqFM reg
-       -> FastInt
+--      The definition has been unfolded into individual cases for speed.
+--      Each architecture has a different register setup, so we use a
+--      different regSqueeze function for each.
+--
+accSqueeze
+        :: FastInt
+        -> FastInt
+        -> (reg -> FastInt)
+        -> UniqFM reg
+        -> FastInt
 
 accSqueeze count maxCount squeeze ufm = acc count (eltsUFM ufm)
   where acc count [] = count
@@ -125,60 +98,96 @@ the most efficient variant tried. Benchmark compiling 10-times SHA1.lhs follows.
                                  100.00%   166.23%   94.18%    100.95%
 -}
 
+-- TODO: We shouldn't be using defaultTargetPlatform here.
+--       We should be passing DynFlags in instead, and looking at
+--       its targetPlatform.
+
 trivColorable
-       :: (RegClass -> VirtualReg -> FastInt)
-       -> (RegClass -> RealReg    -> FastInt)
-       -> Triv VirtualReg RegClass RealReg
+        :: (RegClass -> VirtualReg -> FastInt)
+        -> (RegClass -> RealReg    -> FastInt)
+        -> Triv VirtualReg RegClass RealReg
 
 trivColorable virtualRegSqueeze realRegSqueeze RcInteger conflicts exclusions
-       | count2        <- accSqueeze (_ILIT(0)) ALLOCATABLE_REGS_INTEGER 
-                               (virtualRegSqueeze RcInteger)
-                               conflicts
-                               
-       , count3        <- accSqueeze  count2    ALLOCATABLE_REGS_INTEGER
-                               (realRegSqueeze   RcInteger)
-                               exclusions
-
-       = count3 <# ALLOCATABLE_REGS_INTEGER
+        | let !cALLOCATABLE_REGS_INTEGER
+                  = iUnbox (case platformArch defaultTargetPlatform of
+                            ArchX86     -> 3
+                            ArchX86_64  -> 5
+                            ArchPPC     -> 16
+                            ArchSPARC   -> 14
+                            ArchPPC_64  -> panic "trivColorable ArchPPC_64"
+                            ArchUnknown -> panic "trivColorable ArchUnknown")
+        , count2        <- accSqueeze (_ILIT(0)) cALLOCATABLE_REGS_INTEGER
+                                (virtualRegSqueeze RcInteger)
+                                conflicts
+
+        , count3        <- accSqueeze  count2    cALLOCATABLE_REGS_INTEGER
+                                (realRegSqueeze   RcInteger)
+                                exclusions
+
+        = count3 <# cALLOCATABLE_REGS_INTEGER
 
 trivColorable virtualRegSqueeze realRegSqueeze RcFloat conflicts exclusions
-       | count2        <- accSqueeze (_ILIT(0)) ALLOCATABLE_REGS_FLOAT
-                               (virtualRegSqueeze RcFloat)
-                               conflicts
-                               
-       , count3        <- accSqueeze  count2    ALLOCATABLE_REGS_FLOAT
-                               (realRegSqueeze   RcFloat)
-                               exclusions
-
-       = count3 <# ALLOCATABLE_REGS_FLOAT
+        | let !cALLOCATABLE_REGS_FLOAT
+                  = iUnbox (case platformArch defaultTargetPlatform of
+                            ArchX86     -> 0
+                            ArchX86_64  -> 0
+                            ArchPPC     -> 0
+                            ArchSPARC   -> 22
+                            ArchPPC_64  -> panic "trivColorable ArchPPC_64"
+                            ArchUnknown -> panic "trivColorable ArchUnknown")
+        , count2        <- accSqueeze (_ILIT(0)) cALLOCATABLE_REGS_FLOAT
+                                (virtualRegSqueeze RcFloat)
+                                conflicts
+
+        , count3        <- accSqueeze  count2    cALLOCATABLE_REGS_FLOAT
+                                (realRegSqueeze   RcFloat)
+                                exclusions
+
+        = count3 <# cALLOCATABLE_REGS_FLOAT
 
 trivColorable virtualRegSqueeze realRegSqueeze RcDouble conflicts exclusions
-       | count2        <- accSqueeze (_ILIT(0)) ALLOCATABLE_REGS_DOUBLE
-                               (virtualRegSqueeze RcDouble)
-                               conflicts
-                               
-       , count3        <- accSqueeze  count2    ALLOCATABLE_REGS_DOUBLE
-                               (realRegSqueeze   RcDouble)
-                               exclusions
-
-       = count3 <# ALLOCATABLE_REGS_DOUBLE
+        | let !cALLOCATABLE_REGS_DOUBLE
+                  = iUnbox (case platformArch defaultTargetPlatform of
+                            ArchX86     -> 6
+                            ArchX86_64  -> 0
+                            ArchPPC     -> 26
+                            ArchSPARC   -> 11
+                            ArchPPC_64  -> panic "trivColorable ArchPPC_64"
+                            ArchUnknown -> panic "trivColorable ArchUnknown")
+        , count2        <- accSqueeze (_ILIT(0)) cALLOCATABLE_REGS_DOUBLE
+                                (virtualRegSqueeze RcDouble)
+                                conflicts
+
+        , count3        <- accSqueeze  count2    cALLOCATABLE_REGS_DOUBLE
+                                (realRegSqueeze   RcDouble)
+                                exclusions
+
+        = count3 <# cALLOCATABLE_REGS_DOUBLE
 
 trivColorable virtualRegSqueeze realRegSqueeze RcDoubleSSE conflicts exclusions
-       | count2        <- accSqueeze (_ILIT(0)) ALLOCATABLE_REGS_SSE
-                               (virtualRegSqueeze RcDoubleSSE)
-                               conflicts
-                               
-       , count3        <- accSqueeze  count2    ALLOCATABLE_REGS_SSE
-                               (realRegSqueeze   RcDoubleSSE)
-                               exclusions
+        | let !cALLOCATABLE_REGS_SSE
+                  = iUnbox (case platformArch defaultTargetPlatform of
+                            ArchX86     -> 8
+                            ArchX86_64  -> 10
+                            ArchPPC     -> 0
+                            ArchSPARC   -> 0
+                            ArchPPC_64  -> panic "trivColorable ArchPPC_64"
+                            ArchUnknown -> panic "trivColorable ArchUnknown")
+        , count2        <- accSqueeze (_ILIT(0)) cALLOCATABLE_REGS_SSE
+                                (virtualRegSqueeze RcDoubleSSE)
+                                conflicts
 
-       = count3 <# ALLOCATABLE_REGS_SSE
+        , count3        <- accSqueeze  count2    cALLOCATABLE_REGS_SSE
+                                (realRegSqueeze   RcDoubleSSE)
+                                exclusions
+
+        = count3 <# cALLOCATABLE_REGS_SSE
 
 
 -- Specification Code ----------------------------------------------------------
 --
---     The trivColorable function for each particular architecture should
---     implement the following function, but faster.
+--      The trivColorable function for each particular architecture should
+--      implement the following function, but faster.
 --
 
 {-
@@ -186,39 +195,39 @@ trivColorable :: RegClass -> UniqSet Reg -> UniqSet Reg -> Bool
 trivColorable classN conflicts exclusions
  = let
 
-       acc :: Reg -> (Int, Int) -> (Int, Int)
-       acc r (cd, cf)  
-        = case regClass r of
-               RcInteger       -> (cd+1, cf)
-               RcFloat         -> (cd,   cf+1)
-               _               -> panic "Regs.trivColorable: reg class not handled"
+        acc :: Reg -> (Int, Int) -> (Int, Int)
+        acc r (cd, cf)
+         = case regClass r of
+                RcInteger       -> (cd+1, cf)
+                RcFloat         -> (cd,   cf+1)
+                _               -> panic "Regs.trivColorable: reg class not handled"
 
-       tmp                     = foldUniqSet acc (0, 0) conflicts
-       (countInt,  countFloat) = foldUniqSet acc tmp    exclusions
+        tmp                     = foldUniqSet acc (0, 0) conflicts
+        (countInt,  countFloat) = foldUniqSet acc tmp    exclusions
 
-       squeese         = worst countInt   classN RcInteger
-                       + worst countFloat classN RcFloat
+        squeese         = worst countInt   classN RcInteger
+                        + worst countFloat classN RcFloat
 
-   in  squeese < allocatableRegsInClass classN
+   in   squeese < allocatableRegsInClass classN
 
 -- | Worst case displacement
---     node N of classN has n neighbors of class C.
+--      node N of classN has n neighbors of class C.
 --
---     We currently only have RcInteger and RcDouble, which don't conflict at all.
---     This is a bit boring compared to what's in RegArchX86.
+--      We currently only have RcInteger and RcDouble, which don't conflict at all.
+--      This is a bit boring compared to what's in RegArchX86.
 --
 worst :: Int -> RegClass -> RegClass -> Int
 worst n classN classC
  = case classN of
-       RcInteger
-        -> case classC of
-               RcInteger       -> min n (allocatableRegsInClass RcInteger)
-               RcFloat         -> 0
-               
-       RcDouble
-        -> case classC of
-               RcFloat         -> min n (allocatableRegsInClass RcFloat)
-               RcInteger       -> 0
+        RcInteger
+         -> case classC of
+                RcInteger       -> min n (allocatableRegsInClass RcInteger)
+                RcFloat         -> 0
+
+        RcDouble
+         -> case classC of
+                RcFloat         -> min n (allocatableRegsInClass RcFloat)
+                RcInteger       -> 0
 
 -- allocatableRegs is allMachRegNos with the fixed-use regs removed.
 -- i.e., these are the regs for which we are prepared to allow the
@@ -230,21 +239,21 @@ allocatableRegs
 
 
 -- | The number of regs in each class.
---     We go via top level CAFs to ensure that we're not recomputing
---     the length of these lists each time the fn is called.
+--      We go via top level CAFs to ensure that we're not recomputing
+--      the length of these lists each time the fn is called.
 allocatableRegsInClass :: RegClass -> Int
 allocatableRegsInClass cls
  = case cls of
-       RcInteger       -> allocatableRegsInteger
-       RcFloat         -> allocatableRegsDouble
+        RcInteger       -> allocatableRegsInteger
+        RcFloat         -> allocatableRegsDouble
 
 allocatableRegsInteger :: Int
-allocatableRegsInteger 
-       = length $ filter (\r -> regClass r == RcInteger) 
-                $ map RealReg allocatableRegs
+allocatableRegsInteger
+        = length $ filter (\r -> regClass r == RcInteger)
+                 $ map RealReg allocatableRegs
 
 allocatableRegsFloat :: Int
 allocatableRegsFloat
-       = length $ filter (\r -> regClass r == RcFloat 
-                $ map RealReg allocatableRegs
+        = length $ filter (\r -> regClass r == RcFloat
+                 $ map RealReg allocatableRegs
 -}
index 9fd090c..432acdf 100644 (file)
@@ -2,23 +2,22 @@
 -- | Put common type definitions here to break recursive module dependencies.
 
 module RegAlloc.Linear.Base (
-       BlockAssignment,
-
-       Loc(..),
-       regsOfLoc,
-
-       -- for stats
-       SpillReason(..),
-       RegAllocStats(..),
-       
-       -- the allocator monad
-       RA_State(..),
-       RegM(..)
+        BlockAssignment,
+
+        Loc(..),
+        regsOfLoc,
+
+        -- for stats
+        SpillReason(..),
+        RegAllocStats(..),
+
+        -- the allocator monad
+        RA_State(..),
+        RegM(..)
 )
 
 where
 
-import RegAlloc.Linear.FreeRegs
 import RegAlloc.Linear.StackMap
 import RegAlloc.Liveness
 import Reg
@@ -30,40 +29,40 @@ import UniqSupply
 
 
 -- | Used to store the register assignment on entry to a basic block.
---     We use this to handle join points, where multiple branch instructions
---     target a particular label. We have to insert fixup code to make
---     the register assignments from the different sources match up.
+--      We use this to handle join points, where multiple branch instructions
+--      target a particular label. We have to insert fixup code to make
+--      the register assignments from the different sources match up.
 --
-type BlockAssignment 
-       = BlockMap (FreeRegs, RegMap Loc)
+type BlockAssignment freeRegs
+        = BlockMap (freeRegs, RegMap Loc)
 
 
 -- | Where a vreg is currently stored
---     A temporary can be marked as living in both a register and memory
---     (InBoth), for example if it was recently loaded from a spill location.
---     This makes it cheap to spill (no save instruction required), but we
---     have to be careful to turn this into InReg if the value in the
---     register is changed.
-
---     This is also useful when a temporary is about to be clobbered.  We
---     save it in a spill location, but mark it as InBoth because the current
---     instruction might still want to read it.
+--      A temporary can be marked as living in both a register and memory
+--      (InBoth), for example if it was recently loaded from a spill location.
+--      This makes it cheap to spill (no save instruction required), but we
+--      have to be careful to turn this into InReg if the value in the
+--      register is changed.
+
+--      This is also useful when a temporary is about to be clobbered.  We
+--      save it in a spill location, but mark it as InBoth because the current
+--      instruction might still want to read it.
 --
-data Loc 
-       -- | vreg is in a register
-       = InReg   !RealReg
+data Loc
+        -- | vreg is in a register
+        = InReg   !RealReg
 
-       -- | vreg is held in a stack slot
-       | InMem   {-# UNPACK #-}  !StackSlot
+        -- | vreg is held in a stack slot
+        | InMem   {-# UNPACK #-}  !StackSlot
 
 
-       -- | vreg is held in both a register and a stack slot
-       | InBoth   !RealReg
-                  {-# UNPACK #-} !StackSlot
-       deriving (Eq, Show, Ord)
+        -- | vreg is held in both a register and a stack slot
+        | InBoth   !RealReg
+                   {-# UNPACK #-} !StackSlot
+        deriving (Eq, Show, Ord)
 
 instance Outputable Loc where
-       ppr l = text (show l)
+        ppr l = text (show l)
 
 
 -- | Get the reg numbers stored in this Loc.
@@ -74,64 +73,64 @@ regsOfLoc (InMem _)    = []
 
 
 -- | Reasons why instructions might be inserted by the spiller.
---     Used when generating stats for -ddrop-asm-stats.
+--      Used when generating stats for -ddrop-asm-stats.
 --
 data SpillReason
-       -- | vreg was spilled to a slot so we could use its
-       --      current hreg for another vreg
-       = SpillAlloc    !Unique 
+        -- | vreg was spilled to a slot so we could use its
+        --      current hreg for another vreg
+        = SpillAlloc    !Unique
 
-       -- | vreg was moved because its hreg was clobbered
-       | SpillClobber  !Unique 
+        -- | vreg was moved because its hreg was clobbered
+        | SpillClobber  !Unique
 
-       -- | vreg was loaded from a spill slot
-       | SpillLoad     !Unique 
+        -- | vreg was loaded from a spill slot
+        | SpillLoad     !Unique
 
-       -- | reg-reg move inserted during join to targets
-       | SpillJoinRR   !Unique 
+        -- | reg-reg move inserted during join to targets
+        | SpillJoinRR   !Unique
 
-       -- | reg-mem move inserted during join to targets
-       | SpillJoinRM   !Unique 
+        -- | reg-mem move inserted during join to targets
+        | SpillJoinRM   !Unique
 
 
 -- | Used to carry interesting stats out of the register allocator.
 data RegAllocStats
-       = RegAllocStats
-       { ra_spillInstrs        :: UniqFM [Int] }
+        = RegAllocStats
+        { ra_spillInstrs        :: UniqFM [Int] }
 
 
 -- | The register alloctor state
-data RA_State 
-       = RA_State 
+data RA_State freeRegs
+        = RA_State
+
+        {
+        -- | the current mapping from basic blocks to
+        --      the register assignments at the beginning of that block.
+          ra_blockassig :: BlockAssignment freeRegs
 
-       { 
-       -- | the current mapping from basic blocks to 
-       --      the register assignments at the beginning of that block.
-         ra_blockassig :: BlockAssignment
-       
-       -- | free machine registers
-       , ra_freeregs   :: {-#UNPACK#-}!FreeRegs
+        -- | free machine registers
+        , ra_freeregs   :: !freeRegs
 
-       -- | assignment of temps to locations
-       , ra_assig      :: RegMap Loc
+        -- | assignment of temps to locations
+        , ra_assig      :: RegMap Loc
 
-       -- | current stack delta
-       , ra_delta      :: Int
+        -- | current stack delta
+        , ra_delta      :: Int
 
-       -- | free stack slots for spilling
-       , ra_stack      :: StackMap
+        -- | free stack slots for spilling
+        , ra_stack      :: StackMap
 
-       -- | unique supply for generating names for join point fixup blocks.
-       , ra_us         :: UniqSupply
+        -- | unique supply for generating names for join point fixup blocks.
+        , ra_us         :: UniqSupply
 
-       -- | Record why things were spilled, for -ddrop-asm-stats.
-       --      Just keep a list here instead of a map of regs -> reasons.
-       --      We don't want to slow down the allocator if we're not going to emit the stats.
-       , ra_spills     :: [SpillReason] }
+        -- | Record why things were spilled, for -ddrop-asm-stats.
+        --      Just keep a list here instead of a map of regs -> reasons.
+        --      We don't want to slow down the allocator if we're not going to emit the stats.
+        , ra_spills     :: [SpillReason] }
 
 
 -- | The register allocator monad type.
-newtype RegM a 
-       = RegM { unReg :: RA_State -> (# RA_State, a #) }
+newtype RegM freeRegs a
+        = RegM { unReg :: RA_State freeRegs -> (# RA_State freeRegs, a #) }
 
 
index b357160..b442d06 100644 (file)
@@ -1,18 +1,19 @@
 
 module RegAlloc.Linear.FreeRegs (
-       FreeRegs(),
-       noFreeRegs,
-       releaseReg,
-       initFreeRegs,
-       getFreeRegs,
-       allocateReg,
-       maxSpillSlots
+    FR(..),
+    maxSpillSlots
 )
 
 #include "HsVersions.h"
 
 where
 
+import Reg
+import RegClass
+
+import Panic
+import Platform
+
 -- -----------------------------------------------------------------------------
 -- The free register set
 -- This needs to be *efficient*
@@ -25,21 +26,48 @@ where
 --     getFreeRegs cls f = filter ( (==cls) . regClass . RealReg ) f
 --     allocateReg f r = filter (/= r) f
 
+import qualified RegAlloc.Linear.PPC.FreeRegs   as PPC
+import qualified RegAlloc.Linear.SPARC.FreeRegs as SPARC
+import qualified RegAlloc.Linear.X86.FreeRegs   as X86
+
+import qualified PPC.Instr
+import qualified SPARC.Instr
+import qualified X86.Instr
+
+class Show freeRegs => FR freeRegs where
+    frAllocateReg :: RealReg -> freeRegs -> freeRegs
+    frGetFreeRegs :: RegClass -> freeRegs -> [RealReg]
+    frInitFreeRegs :: freeRegs
+    frReleaseReg :: RealReg -> freeRegs -> freeRegs
 
-#if   defined(powerpc_TARGET_ARCH) 
-import RegAlloc.Linear.PPC.FreeRegs
-import PPC.Instr       (maxSpillSlots)
+instance FR X86.FreeRegs where
+    frAllocateReg  = X86.allocateReg
+    frGetFreeRegs  = X86.getFreeRegs
+    frInitFreeRegs = X86.initFreeRegs
+    frReleaseReg   = X86.releaseReg
 
-#elif defined(sparc_TARGET_ARCH)
-import RegAlloc.Linear.SPARC.FreeRegs
-import SPARC.Instr     (maxSpillSlots)
+instance FR PPC.FreeRegs where
+    frAllocateReg  = PPC.allocateReg
+    frGetFreeRegs  = PPC.getFreeRegs
+    frInitFreeRegs = PPC.initFreeRegs
+    frReleaseReg   = PPC.releaseReg
 
-#elif defined(i386_TARGET_ARCH) || defined(x86_64_TARGET_ARCH)
-import RegAlloc.Linear.X86.FreeRegs
-import X86.Instr       (maxSpillSlots)
+instance FR SPARC.FreeRegs where
+    frAllocateReg  = SPARC.allocateReg
+    frGetFreeRegs  = SPARC.getFreeRegs
+    frInitFreeRegs = SPARC.initFreeRegs
+    frReleaseReg   = SPARC.releaseReg
 
-#else
-#error "RegAlloc.Linear.FreeRegs not defined for this architecture."
+-- TODO: We shouldn't be using defaultTargetPlatform here.
+--       We should be passing DynFlags in instead, and looking at
+--       its targetPlatform.
 
-#endif
+maxSpillSlots :: Int
+maxSpillSlots = case platformArch defaultTargetPlatform of
+                ArchX86     -> X86.Instr.maxSpillSlots
+                ArchX86_64  -> X86.Instr.maxSpillSlots
+                ArchPPC     -> PPC.Instr.maxSpillSlots
+                ArchSPARC   -> SPARC.Instr.maxSpillSlots
+                ArchPPC_64  -> panic "maxSpillSlots ArchPPC_64"
+                ArchUnknown -> panic "maxSpillSlots ArchUnknown"
 
index ef6ae9b..e6a078a 100644 (file)
@@ -1,5 +1,3 @@
-{-# OPTIONS -fno-warn-missing-signatures #-}
-
 
 -- | Handles joining of a jump instruction to its targets.
 
@@ -35,14 +33,14 @@ import UniqSet
 --     vregs are in the correct regs for its destination.
 --
 joinToTargets
-       :: Instruction instr
+       :: (FR freeRegs, Instruction instr)
        => BlockMap RegSet              -- ^ maps the unique of the blockid to the set of vregs 
                                        --      that are known to be live on the entry to each block.
 
        -> BlockId                      -- ^ id of the current block
        -> instr                        -- ^ branch instr on the end of the source block.
 
-       -> RegM ([NatBasicBlock instr]  --   fresh blocks of fixup code.
+       -> RegM freeRegs ([NatBasicBlock instr] --   fresh blocks of fixup code.
                , instr)                --   the original branch instruction, but maybe patched to jump
                                        --      to a fixup block first.
 
@@ -57,7 +55,7 @@ joinToTargets block_live id instr
 
 -----
 joinToTargets'
-       :: Instruction instr
+       :: (FR freeRegs, Instruction instr)
        => BlockMap RegSet              -- ^ maps the unique of the blockid to the set of vregs 
                                        --      that are known to be live on the entry to each block.
 
@@ -68,7 +66,7 @@ joinToTargets'
 
        -> [BlockId]                    -- ^ branch destinations still to consider.
 
-       -> RegM ( [NatBasicBlock instr]
+       -> RegM freeRegs ( [NatBasicBlock instr]
                , instr)
 
 -- no more targets to consider. all done.
@@ -109,13 +107,24 @@ joinToTargets' block_live new_blocks block_id instr (dest:dests)
 
 
 -- this is the first time we jumped to this block.
+joinToTargets_first :: (FR freeRegs, Instruction instr)
+                    => BlockMap RegSet
+                    -> [NatBasicBlock instr]
+                    -> BlockId
+                    -> instr
+                    -> BlockId
+                    -> [BlockId]
+                    -> BlockAssignment freeRegs
+                    -> RegMap Loc
+                    -> [RealReg]
+                    -> RegM freeRegs ([NatBasicBlock instr], instr)
 joinToTargets_first block_live new_blocks block_id instr dest dests
        block_assig src_assig 
-       (to_free :: [RealReg])
+       to_free
 
  = do  -- free up the regs that are not live on entry to this block.
        freeregs        <- getFreeRegsR
-       let freeregs'   = foldr releaseReg freeregs to_free 
+       let freeregs'   = foldr frReleaseReg freeregs to_free 
        
        -- remember the current assignment on entry to this block.
        setBlockAssigR (mapInsert dest (freeregs', src_assig) block_assig)
@@ -124,6 +133,16 @@ joinToTargets_first block_live new_blocks block_id instr dest dests
 
 
 -- we've jumped to this block before
+joinToTargets_again :: (Instruction instr, FR freeRegs)
+                    => BlockMap RegSet
+                    -> [NatBasicBlock instr]
+                    -> BlockId
+                    -> instr
+                    -> BlockId
+                    -> [BlockId]
+                    -> UniqFM Loc
+                    -> UniqFM Loc
+                    -> RegM freeRegs ([NatBasicBlock instr], instr)
 joinToTargets_again 
        block_live new_blocks block_id instr dest dests
        src_assig dest_assig
@@ -262,7 +281,7 @@ expandNode vreg src dst
 --
 handleComponent 
        :: Instruction instr
-       => Int -> instr -> SCC (Unique, Loc, [Loc]) -> RegM [instr]
+       => Int -> instr -> SCC (Unique, Loc, [Loc]) -> RegM freeRegs [instr]
 
 -- If the graph is acyclic then we won't get the swapping problem below.
 --     In this case we can just do the moves directly, and avoid having to
@@ -317,7 +336,7 @@ makeMove
        -> Unique       -- ^ unique of the vreg that we're moving.
        -> Loc          -- ^ source location.
        -> Loc          -- ^ destination location.
-       -> RegM instr   -- ^ move instruction.
+       -> RegM freeRegs instr  -- ^ move instruction.
 
 makeMove _     vreg (InReg src) (InReg dst)
  = do  recordSpill (SpillJoinRR vreg)
index 473b549..b91c2d0 100644 (file)
@@ -1,4 +1,3 @@
-{-# OPTIONS -fno-warn-missing-signatures #-}
 -----------------------------------------------------------------------------
 --
 -- The register allocator
@@ -9,82 +8,82 @@
 
 {-
 The algorithm is roughly:
+
   1) Compute strongly connected components of the basic block list.
 
   2) Compute liveness (mapping from pseudo register to
      point(s) of death?).
 
   3) Walk instructions in each basic block.  We keep track of
-       (a) Free real registers (a bitmap?)
-       (b) Current assignment of temporaries to machine registers and/or
-           spill slots (call this the "assignment").
-       (c) Partial mapping from basic block ids to a virt-to-loc mapping.
-           When we first encounter a branch to a basic block,
-           we fill in its entry in this table with the current mapping.
+        (a) Free real registers (a bitmap?)
+        (b) Current assignment of temporaries to machine registers and/or
+            spill slots (call this the "assignment").
+        (c) Partial mapping from basic block ids to a virt-to-loc mapping.
+            When we first encounter a branch to a basic block,
+            we fill in its entry in this table with the current mapping.
 
      For each instruction:
-       (a) For each real register clobbered by this instruction:
-           If a temporary resides in it,
-               If the temporary is live after this instruction,
-                   Move the temporary to another (non-clobbered & free) reg,
-                   or spill it to memory.  Mark the temporary as residing
-                   in both memory and a register if it was spilled (it might
-                   need to be read by this instruction).
-           (ToDo: this is wrong for jump instructions?)
-
-       (b) For each temporary *read* by the instruction:
-           If the temporary does not have a real register allocation:
-               - Allocate a real register from the free list.  If
-                 the list is empty:
-                 - Find a temporary to spill.  Pick one that is
-                   not used in this instruction (ToDo: not
-                   used for a while...)
-                 - generate a spill instruction
-               - If the temporary was previously spilled,
-                 generate an instruction to read the temp from its spill loc.
-           (optimisation: if we can see that a real register is going to
+        (a) For each real register clobbered by this instruction:
+            If a temporary resides in it,
+                If the temporary is live after this instruction,
+                    Move the temporary to another (non-clobbered & free) reg,
+                    or spill it to memory.  Mark the temporary as residing
+                    in both memory and a register if it was spilled (it might
+                    need to be read by this instruction).
+            (ToDo: this is wrong for jump instructions?)
+
+        (b) For each temporary *read* by the instruction:
+            If the temporary does not have a real register allocation:
+                - Allocate a real register from the free list.  If
+                  the list is empty:
+                  - Find a temporary to spill.  Pick one that is
+                    not used in this instruction (ToDo: not
+                    used for a while...)
+                  - generate a spill instruction
+                - If the temporary was previously spilled,
+                  generate an instruction to read the temp from its spill loc.
+            (optimisation: if we can see that a real register is going to
             be used soon, then don't use it for allocation).
 
-       (c) Update the current assignment
+        (c) Update the current assignment
 
-       (d) If the instruction is a branch:
-             if the destination block already has a register assignment,
-               Generate a new block with fixup code and redirect the
-               jump to the new block.
-             else,
-               Update the block id->assignment mapping with the current
-               assignment.
+        (d) If the instruction is a branch:
+              if the destination block already has a register assignment,
+                Generate a new block with fixup code and redirect the
+                jump to the new block.
+              else,
+                Update the block id->assignment mapping with the current
+                assignment.
 
-       (e) Delete all register assignments for temps which are read
-           (only) and die here.  Update the free register list.
+        (e) Delete all register assignments for temps which are read
+            (only) and die here.  Update the free register list.
 
-       (f) Mark all registers clobbered by this instruction as not free,
-           and mark temporaries which have been spilled due to clobbering
-           as in memory (step (a) marks then as in both mem & reg).
+        (f) Mark all registers clobbered by this instruction as not free,
+            and mark temporaries which have been spilled due to clobbering
+            as in memory (step (a) marks then as in both mem & reg).
 
-       (g) For each temporary *written* by this instruction:
-           Allocate a real register as for (b), spilling something
-           else if necessary.
-               - except when updating the assignment, drop any memory
-                 locations that the temporary was previously in, since
-                 they will be no longer valid after this instruction.
+        (g) For each temporary *written* by this instruction:
+            Allocate a real register as for (b), spilling something
+            else if necessary.
+                - except when updating the assignment, drop any memory
+                  locations that the temporary was previously in, since
+                  they will be no longer valid after this instruction.
 
-       (h) Delete all register assignments for temps which are
-           written and die here (there should rarely be any).  Update
-           the free register list.
+        (h) Delete all register assignments for temps which are
+            written and die here (there should rarely be any).  Update
+            the free register list.
 
-       (i) Rewrite the instruction with the new mapping.
+        (i) Rewrite the instruction with the new mapping.
 
-       (j) For each spilled reg known to be now dead, re-add its stack slot
-           to the free list.
+        (j) For each spilled reg known to be now dead, re-add its stack slot
+            to the free list.
 
 -}
 
 module RegAlloc.Linear.Main (
-       regAlloc,
-       module  RegAlloc.Linear.Base,
-       module  RegAlloc.Linear.Stats
+        regAlloc,
+        module  RegAlloc.Linear.Base,
+        module  RegAlloc.Linear.Stats
   ) where
 
 #include "HsVersions.h"
@@ -96,6 +95,9 @@ import RegAlloc.Linear.StackMap
 import RegAlloc.Linear.FreeRegs
 import RegAlloc.Linear.Stats
 import RegAlloc.Linear.JoinToTargets
+import qualified RegAlloc.Linear.PPC.FreeRegs   as PPC
+import qualified RegAlloc.Linear.SPARC.FreeRegs as SPARC
+import qualified RegAlloc.Linear.X86.FreeRegs   as X86
 import TargetReg
 import RegAlloc.Liveness
 import Instruction
@@ -105,11 +107,13 @@ import BlockId
 import OldCmm hiding (RegSet)
 
 import Digraph
+import DynFlags
 import Unique
 import UniqSet
 import UniqFM
 import UniqSupply
 import Outputable
+import Platform
 
 import Data.Maybe
 import Data.List
@@ -122,38 +126,39 @@ import Control.Monad
 -- Top level of the register allocator
 
 -- Allocate registers
-regAlloc 
-       :: (Outputable instr, Instruction instr)
-       => LiveCmmTop instr
-       -> UniqSM (NatCmmTop instr, Maybe RegAllocStats)
-
-regAlloc (CmmData sec d) 
-       = return
-               ( CmmData sec d
-               , Nothing )
-       
-regAlloc (CmmProc (LiveInfo info _ _ _) lbl [])
-       = return ( CmmProc info lbl (ListGraph [])
-                , Nothing )
-       
-regAlloc (CmmProc static lbl sccs)
-       | LiveInfo info (Just first_id) (Just block_live) _     <- static
-       = do    
-               -- do register allocation on each component.
-               (final_blocks, stats)
-                       <- linearRegAlloc first_id block_live sccs
-
-               -- make sure the block that was first in the input list
-               --      stays at the front of the output
-               let ((first':_), rest')
-                               = partition ((== first_id) . blockId) final_blocks
-
-               return  ( CmmProc info lbl (ListGraph (first' : rest'))
-                       , Just stats)
-       
+regAlloc
+        :: (Outputable instr, Instruction instr)
+        => DynFlags
+        -> LiveCmmTop instr
+        -> UniqSM (NatCmmTop instr, Maybe RegAllocStats)
+
+regAlloc _ (CmmData sec d)
+        = return
+                ( CmmData sec d
+                , Nothing )
+
+regAlloc _ (CmmProc (LiveInfo info _ _ _) lbl [])
+        = return ( CmmProc info lbl (ListGraph [])
+                 , Nothing )
+
+regAlloc dflags (CmmProc static lbl sccs)
+        | LiveInfo info (Just first_id) (Just block_live) _     <- static
+        = do
+                -- do register allocation on each component.
+                (final_blocks, stats)
+                        <- linearRegAlloc dflags first_id block_live sccs
+
+                -- make sure the block that was first in the input list
+                --      stays at the front of the output
+                let ((first':_), rest')
+                                = partition ((== first_id) . blockId) final_blocks
+
+                return  ( CmmProc info lbl (ListGraph (first' : rest'))
+                        , Just stats)
+
 -- bogus. to make non-exhaustive match warning go away.
-regAlloc (CmmProc _ _ _)
-       = panic "RegAllocLinear.regAlloc: no match"
+regAlloc _ (CmmProc _ _ _)
+        = panic "RegAllocLinear.regAlloc: no match"
 
 
 -- -----------------------------------------------------------------------------
@@ -165,161 +170,196 @@ regAlloc (CmmProc _ _ _)
 --   an entry in the block map or it is the first block.
 --
 linearRegAlloc
-       :: (Outputable instr, Instruction instr)
-       => BlockId                      -- ^ the first block
-        -> BlockMap RegSet             -- ^ live regs on entry to each basic block
-       -> [SCC (LiveBasicBlock instr)] -- ^ instructions annotated with "deaths"
-       -> UniqSM ([NatBasicBlock instr], RegAllocStats)
-
-linearRegAlloc first_id block_live sccs
- = do  us      <- getUs
-       let (_, _, stats, blocks) =
-               runR emptyBlockMap initFreeRegs emptyRegMap emptyStackMap us
-                       $ linearRA_SCCs first_id block_live [] sccs
-
-       return  (blocks, stats)
+        :: (Outputable instr, Instruction instr)
+        => DynFlags
+        -> BlockId                      -- ^ the first block
+        -> BlockMap RegSet              -- ^ live regs on entry to each basic block
+        -> [SCC (LiveBasicBlock instr)] -- ^ instructions annotated with "deaths"
+        -> UniqSM ([NatBasicBlock instr], RegAllocStats)
+
+linearRegAlloc dflags first_id block_live sccs
+ = case platformArch $ targetPlatform dflags of
+   ArchX86     -> linearRegAlloc' (frInitFreeRegs :: X86.FreeRegs)   first_id block_live sccs
+   ArchX86_64  -> linearRegAlloc' (frInitFreeRegs :: X86.FreeRegs)   first_id block_live sccs
+   ArchSPARC   -> linearRegAlloc' (frInitFreeRegs :: SPARC.FreeRegs) first_id block_live sccs
+   ArchPPC     -> linearRegAlloc' (frInitFreeRegs :: PPC.FreeRegs)   first_id block_live sccs
+   ArchPPC_64  -> panic "linearRegAlloc ArchPPC_64"
+   ArchUnknown -> panic "linearRegAlloc ArchUnknown"
+
+linearRegAlloc'
+        :: (FR freeRegs, Outputable instr, Instruction instr)
+        => freeRegs
+        -> BlockId                      -- ^ the first block
+        -> BlockMap RegSet              -- ^ live regs on entry to each basic block
+        -> [SCC (LiveBasicBlock instr)] -- ^ instructions annotated with "deaths"
+        -> UniqSM ([NatBasicBlock instr], RegAllocStats)
+
+linearRegAlloc' initFreeRegs first_id block_live sccs
+ = do   us      <- getUs
+        let (_, _, stats, blocks) =
+                runR emptyBlockMap initFreeRegs emptyRegMap emptyStackMap us
+                    $ linearRA_SCCs first_id block_live [] sccs
+        return  (blocks, stats)
+
+
+linearRA_SCCs :: (FR freeRegs, Instruction instr, Outputable instr)
+              => BlockId
+              -> BlockMap RegSet
+              -> [NatBasicBlock instr]
+              -> [SCC (LiveBasicBlock instr)]
+              -> RegM freeRegs [NatBasicBlock instr]
 
 linearRA_SCCs _ _ blocksAcc []
-       = return $ reverse blocksAcc
+        = return $ reverse blocksAcc
 
-linearRA_SCCs first_id block_live blocksAcc (AcyclicSCC block : sccs) 
- = do  blocks' <- processBlock block_live block
-       linearRA_SCCs first_id block_live 
-               ((reverse blocks') ++ blocksAcc)
-               sccs
+linearRA_SCCs first_id block_live blocksAcc (AcyclicSCC block : sccs)
+ = do   blocks' <- processBlock block_live block
+        linearRA_SCCs first_id block_live
+                ((reverse blocks') ++ blocksAcc)
+                sccs
 
-linearRA_SCCs first_id block_live blocksAcc (CyclicSCC blocks : sccs) 
+linearRA_SCCs first_id block_live blocksAcc (CyclicSCC blocks : sccs)
  = do
         blockss' <- process first_id block_live blocks [] (return []) False
-       linearRA_SCCs first_id block_live
-               (reverse (concat blockss') ++ blocksAcc)
-               sccs
+        linearRA_SCCs first_id block_live
+                (reverse (concat blockss') ++ blocksAcc)
+                sccs
 
 {- from John Dias's patch 2008/10/16:
    The linear-scan allocator sometimes allocates a block
-   before allocating one of its predecessors, which could lead to 
+   before allocating one of its predecessors, which could lead to
    inconsistent allocations. Make it so a block is only allocated
    if a predecessor has set the "incoming" assignments for the block, or
    if it's the procedure's entry block.
 
    BL 2009/02: Careful. If the assignment for a block doesn't get set for
-   some reason then this function will loop. We should probably do some 
+   some reason then this function will loop. We should probably do some
    more sanity checking to guard against this eventuality.
 -}
 
+process :: (FR freeRegs, Instruction instr, Outputable instr)
+        => BlockId
+        -> BlockMap RegSet
+        -> [GenBasicBlock (LiveInstr instr)]
+        -> [GenBasicBlock (LiveInstr instr)]
+        -> [[NatBasicBlock instr]]
+        -> Bool
+        -> RegM freeRegs [[NatBasicBlock instr]]
+
 process _ _ [] []         accum _
-       = return $ reverse accum
+        = return $ reverse accum
 
 process first_id block_live [] next_round accum madeProgress
-       | not madeProgress
-       
-         {- BUGS: There are so many unreachable blocks in the code the warnings are overwhelming.
-            pprTrace "RegAlloc.Linear.Main.process: no progress made, bailing out." 
-               (  text "Unreachable blocks:"
-               $$ vcat (map ppr next_round)) -}
-       = return $ reverse accum
-       
-       | otherwise
-       = process first_id block_live 
-                 next_round [] accum False
-
-process first_id block_live (b@(BasicBlock id _) : blocks) 
-       next_round accum madeProgress
- = do  
-       block_assig <- getBlockAssigR
-
-       if isJust (mapLookup id block_assig) 
+        | not madeProgress
+
+          {- BUGS: There are so many unreachable blocks in the code the warnings are overwhelming.
+             pprTrace "RegAlloc.Linear.Main.process: no progress made, bailing out."
+                (  text "Unreachable blocks:"
+                $$ vcat (map ppr next_round)) -}
+        = return $ reverse accum
+
+        | otherwise
+        = process first_id block_live
+                  next_round [] accum False
+
+process first_id block_live (b@(BasicBlock id _) : blocks)
+        next_round accum madeProgress
+ = do
+        block_assig <- getBlockAssigR
+
+        if isJust (mapLookup id block_assig)
              || id == first_id
-         then do 
-               b'  <- processBlock block_live b
-                process first_id block_live blocks 
-                       next_round (b' : accum) True
+         then do
+                b'  <- processBlock block_live b
+                process first_id block_live blocks
+                        next_round (b' : accum) True
 
-         else  process first_id block_live blocks 
-                       (b : next_round) accum madeProgress
+         else   process first_id block_live blocks
+                        (b : next_round) accum madeProgress
 
 
 -- | Do register allocation on this basic block
 --
 processBlock
-       :: (Outputable instr, Instruction instr)
-       => BlockMap RegSet              -- ^ live regs on entry to each basic block
-       -> LiveBasicBlock instr         -- ^ block to do register allocation on
-       -> RegM [NatBasicBlock instr]   -- ^ block with registers allocated
+        :: (FR freeRegs, Outputable instr, Instruction instr)
+        => BlockMap RegSet              -- ^ live regs on entry to each basic block
+        -> LiveBasicBlock instr         -- ^ block to do register allocation on
+        -> RegM freeRegs [NatBasicBlock instr]   -- ^ block with registers allocated
 
 processBlock block_live (BasicBlock id instrs)
- = do  initBlock id
-       (instrs', fixups)
-               <- linearRA block_live [] [] id instrs
-       return  $ BasicBlock id instrs' : fixups
+ = do   initBlock id
+        (instrs', fixups)
+                <- linearRA block_live [] [] id instrs
+        return  $ BasicBlock id instrs' : fixups
 
 
 -- | Load the freeregs and current reg assignment into the RegM state
---     for the basic block with this BlockId.
-initBlock :: BlockId -> RegM ()
+--      for the basic block with this BlockId.
+initBlock :: FR freeRegs => BlockId -> RegM freeRegs ()
 initBlock id
- = do  block_assig     <- getBlockAssigR
-       case mapLookup id block_assig of
-               -- no prior info about this block: assume everything is
-               -- free and the assignment is empty.
-               Nothing
-                -> do  -- pprTrace "initFreeRegs" (text $ show initFreeRegs) (return ())
-                
-                       setFreeRegsR    initFreeRegs
-                       setAssigR       emptyRegMap
-
-               -- load info about register assignments leading into this block.
-               Just (freeregs, assig)
-                -> do  setFreeRegsR    freeregs
-                       setAssigR       assig
+ = do   block_assig     <- getBlockAssigR
+        case mapLookup id block_assig of
+                -- no prior info about this block: assume everything is
+                -- free and the assignment is empty.
+                Nothing
+                 -> do  -- pprTrace "initFreeRegs" (text $ show initFreeRegs) (return ())
+
+                        setFreeRegsR    frInitFreeRegs
+                        setAssigR       emptyRegMap
+
+                -- load info about register assignments leading into this block.
+                Just (freeregs, assig)
+                 -> do  setFreeRegsR    freeregs
+                        setAssigR       assig
 
 
 -- | Do allocation for a sequence of instructions.
 linearRA
-       :: (Outputable instr, Instruction instr)
-       => BlockMap RegSet                      -- ^ map of what vregs are live on entry to each block.
-       -> [instr]                              -- ^ accumulator for instructions already processed.
-       -> [NatBasicBlock instr]                -- ^ accumulator for blocks of fixup code.
-       -> BlockId                              -- ^ id of the current block, for debugging.
-       -> [LiveInstr instr]                    -- ^ liveness annotated instructions in this block.
+        :: (FR freeRegs, Outputable instr, Instruction instr)
+        => BlockMap RegSet                      -- ^ map of what vregs are live on entry to each block.
+        -> [instr]                              -- ^ accumulator for instructions already processed.
+        -> [NatBasicBlock instr]                -- ^ accumulator for blocks of fixup code.
+        -> BlockId                              -- ^ id of the current block, for debugging.
+        -> [LiveInstr instr]                    -- ^ liveness annotated instructions in this block.
 
-       -> RegM ( [instr]                       --   instructions after register allocation
-               , [NatBasicBlock instr])        --   fresh blocks of fixup code.
+        -> RegM freeRegs
+                ( [instr]                       --   instructions after register allocation
+                , [NatBasicBlock instr])        --   fresh blocks of fixup code.
 
 
 linearRA _          accInstr accFixup _ []
-       = return 
-               ( reverse accInstr              -- instrs need to be returned in the correct order.
-               , accFixup)                     -- it doesn't matter what order the fixup blocks are returned in.
+        = return
+                ( reverse accInstr              -- instrs need to be returned in the correct order.
+                , accFixup)                     -- it doesn't matter what order the fixup blocks are returned in.
 
 
 linearRA block_live accInstr accFixups id (instr:instrs)
  = do
-       (accInstr', new_fixups) 
-               <- raInsn block_live accInstr id instr
+        (accInstr', new_fixups)
+                <- raInsn block_live accInstr id instr
 
-       linearRA block_live accInstr' (new_fixups ++ accFixups) id instrs
+        linearRA block_live accInstr' (new_fixups ++ accFixups) id instrs
 
 
 -- | Do allocation for a single instruction.
-raInsn  
-       :: (Outputable instr, Instruction instr)
-       => BlockMap RegSet                      -- ^ map of what vregs are love on entry to each block.
-       -> [instr]                              -- ^ accumulator for instructions already processed.
-       -> BlockId                              -- ^ the id of the current block, for debugging
-       -> LiveInstr instr                      -- ^ the instr to have its regs allocated, with liveness info.
-       -> RegM 
-               ( [instr]                       -- new instructions
-               , [NatBasicBlock instr])        -- extra fixup blocks
-
-raInsn _     new_instrs _ (LiveInstr ii Nothing)  
-       | Just n        <- takeDeltaInstr ii
-       = do    setDeltaR n
-               return (new_instrs, [])
+raInsn
+        :: (FR freeRegs, Outputable instr, Instruction instr)
+        => BlockMap RegSet                      -- ^ map of what vregs are love on entry to each block.
+        -> [instr]                              -- ^ accumulator for instructions already processed.
+        -> BlockId                              -- ^ the id of the current block, for debugging
+        -> LiveInstr instr                      -- ^ the instr to have its regs allocated, with liveness info.
+        -> RegM freeRegs
+                ( [instr]                       -- new instructions
+                , [NatBasicBlock instr])        -- extra fixup blocks
 
 raInsn _     new_instrs _ (LiveInstr ii Nothing)
-       | isMetaInstr ii
-       = return (new_instrs, [])
+        | Just n        <- takeDeltaInstr ii
+        = do    setDeltaR n
+                return (new_instrs, [])
+
+raInsn _     new_instrs _ (LiveInstr ii Nothing)
+        | isMetaInstr ii
+        = return (new_instrs, [])
 
 
 raInsn block_live new_instrs id (LiveInstr (Instr instr) (Just live))
@@ -334,78 +374,85 @@ raInsn block_live new_instrs id (LiveInstr (Instr instr) (Just live))
     -- (we can't eliminate it if the source register is on the stack, because
     --  we do not want to use one spill slot for different virtual registers)
     case takeRegRegMoveInstr instr of
-       Just (src,dst)  | src `elementOfUniqSet` (liveDieRead live), 
-                         isVirtualReg dst,
-                         not (dst `elemUFM` assig),
-                         Just (InReg _) <- (lookupUFM assig src) -> do
-          case src of
-             (RegReal rr) -> setAssigR (addToUFM assig dst (InReg rr))
-               -- if src is a fixed reg, then we just map dest to this
-               -- reg in the assignment.  src must be an allocatable reg,
-               -- otherwise it wouldn't be in r_dying.
-             _virt -> case lookupUFM assig src of
-                        Nothing -> panic "raInsn"
-                        Just loc ->
-                          setAssigR (addToUFM (delFromUFM assig src) dst loc)
-
-          -- we have eliminated this instruction
+        Just (src,dst)  | src `elementOfUniqSet` (liveDieRead live),
+                          isVirtualReg dst,
+                          not (dst `elemUFM` assig),
+                          Just (InReg _) <- (lookupUFM assig src) -> do
+           case src of
+              (RegReal rr) -> setAssigR (addToUFM assig dst (InReg rr))
+                -- if src is a fixed reg, then we just map dest to this
+                -- reg in the assignment.  src must be an allocatable reg,
+                -- otherwise it wouldn't be in r_dying.
+              _virt -> case lookupUFM assig src of
+                         Nothing -> panic "raInsn"
+                         Just loc ->
+                           setAssigR (addToUFM (delFromUFM assig src) dst loc)
+
+           -- we have eliminated this instruction
           {-
-         freeregs <- getFreeRegsR
-         assig <- getAssigR
-          pprTrace "raInsn" (text "ELIMINATED: " <> docToSDoc (pprInstr instr) 
-                       $$ ppr r_dying <+> ppr w_dying $$ text (show freeregs) $$ ppr assig) $ do
+          freeregs <- getFreeRegsR
+          assig <- getAssigR
+          pprTrace "raInsn" (text "ELIMINATED: " <> docToSDoc (pprInstr instr)
+                        $$ ppr r_dying <+> ppr w_dying $$ text (show freeregs) $$ ppr assig) $ do
           -}
-          return (new_instrs, [])
+           return (new_instrs, [])
 
-       _ -> genRaInsn block_live new_instrs id instr 
-                       (uniqSetToList $ liveDieRead live) 
-                       (uniqSetToList $ liveDieWrite live)
+        _ -> genRaInsn block_live new_instrs id instr
+                        (uniqSetToList $ liveDieRead live)
+                        (uniqSetToList $ liveDieWrite live)
 
 
 raInsn _ _ _ instr
-       = pprPanic "raInsn" (text "no match for:" <> ppr instr)
-
+        = pprPanic "raInsn" (text "no match for:" <> ppr instr)
 
 
+genRaInsn :: (FR freeRegs, Instruction instr, Outputable instr)
+          => BlockMap RegSet
+          -> [instr]
+          -> BlockId
+          -> instr
+          -> [Reg]
+          -> [Reg]
+          -> RegM freeRegs ([instr], [NatBasicBlock instr])
 
 genRaInsn block_live new_instrs block_id instr r_dying w_dying =
     case regUsageOfInstr instr              of { RU read written ->
     do
-    let        real_written    = [ rr  | (RegReal     rr) <- written ]
-    let virt_written   = [ vr  | (RegVirtual  vr) <- written ]
+    let real_written    = [ rr  | (RegReal     rr) <- written ]
+    let virt_written    = [ vr  | (RegVirtual  vr) <- written ]
 
     -- we don't need to do anything with real registers that are
     -- only read by this instr.  (the list is typically ~2 elements,
     -- so using nub isn't a problem).
-    let virt_read      = nub [ vr      | (RegVirtual vr) <- read ]
+    let virt_read       = nub [ vr      | (RegVirtual vr) <- read ]
 
     -- (a) save any temporaries which will be clobbered by this instruction
-    clobber_saves      <- saveClobberedTemps real_written r_dying
+    clobber_saves       <- saveClobberedTemps real_written r_dying
 
     -- debugging
 {-    freeregs <- getFreeRegsR
     assig    <- getAssigR
-    pprTrace "genRaInsn" 
-       (ppr instr 
-               $$ text "r_dying      = " <+> ppr r_dying 
-               $$ text "w_dying      = " <+> ppr w_dying 
-               $$ text "virt_read    = " <+> ppr virt_read 
-               $$ text "virt_written = " <+> ppr virt_written 
-               $$ text "freeregs     = " <+> text (show freeregs)
-               $$ text "assig        = " <+> ppr assig)
-       $ do
+    pprTrace "genRaInsn"
+        (ppr instr
+                $$ text "r_dying      = " <+> ppr r_dying
+                $$ text "w_dying      = " <+> ppr w_dying
+                $$ text "virt_read    = " <+> ppr virt_read
+                $$ text "virt_written = " <+> ppr virt_written
+                $$ text "freeregs     = " <+> text (show freeregs)
+                $$ text "assig        = " <+> ppr assig)
+        $ do
 -}
 
     -- (b), (c) allocate real regs for all regs read by this instruction.
-    (r_spills, r_allocd) <- 
-       allocateRegsAndSpill True{-reading-} virt_read [] [] virt_read
+    (r_spills, r_allocd) <-
+        allocateRegsAndSpill True{-reading-} virt_read [] [] virt_read
 
     -- (d) Update block map for new destinations
     -- NB. do this before removing dead regs from the assignment, because
     -- these dead regs might in fact be live in the jump targets (they're
     -- only dead in the code that follows in the current basic block).
     (fixup_blocks, adjusted_instr)
-       <- joinToTargets block_live block_id instr
+        <- joinToTargets block_live block_id instr
 
     -- (e) Delete all register assignments for temps which are read
     --     (only) and die here.  Update the free register list.
@@ -415,43 +462,43 @@ genRaInsn block_live new_instrs block_id instr r_dying w_dying =
     clobberRegs real_written
 
     -- (g) Allocate registers for temporaries *written* (only)
-    (w_spills, w_allocd) <- 
-       allocateRegsAndSpill False{-writing-} virt_written [] [] virt_written
+    (w_spills, w_allocd) <-
+        allocateRegsAndSpill False{-writing-} virt_written [] [] virt_written
 
     -- (h) Release registers for temps which are written here and not
     -- used again.
     releaseRegs w_dying
 
     let
-       -- (i) Patch the instruction
-       patch_map 
-               = listToUFM
-                       [ (t, RegReal r) 
-                               | (t, r) <- zip virt_read    r_allocd
-                                        ++ zip virt_written w_allocd ]
+        -- (i) Patch the instruction
+        patch_map
+                = listToUFM
+                        [ (t, RegReal r)
+                                | (t, r) <- zip virt_read    r_allocd
+                                         ++ zip virt_written w_allocd ]
 
-       patched_instr 
-               = patchRegsOfInstr adjusted_instr patchLookup
+        patched_instr
+                = patchRegsOfInstr adjusted_instr patchLookup
 
-       patchLookup x 
-               = case lookupUFM patch_map x of
-                       Nothing -> x
-                       Just y  -> y
+        patchLookup x
+                = case lookupUFM patch_map x of
+                        Nothing -> x
+                        Just y  -> y
 
 
     -- (j) free up stack slots for dead spilled regs
     -- TODO (can't be bothered right now)
 
     -- erase reg->reg moves where the source and destination are the same.
-    -- If the src temp didn't die in this instr but happened to be allocated
-    -- to the same real reg as the destination, then we can erase the move anyway.
-    let        squashed_instr  = case takeRegRegMoveInstr patched_instr of
-                               Just (src, dst)
-                                | src == dst   -> []
-                               _               -> [patched_instr]
+    --  If the src temp didn't die in this instr but happened to be allocated
+    --  to the same real reg as the destination, then we can erase the move anyway.
+    let squashed_instr  = case takeRegRegMoveInstr patched_instr of
+                                Just (src, dst)
+                                 | src == dst   -> []
+                                _               -> [patched_instr]
 
     let code = squashed_instr ++ w_spills ++ reverse r_spills
-               ++ clobber_saves ++ new_instrs
+                ++ clobber_saves ++ new_instrs
 
 --    pprTrace "patched-code" ((vcat $ map (docToSDoc . pprInstr) code)) $ do
 --    pprTrace "pached-fixup" ((ppr fixup_blocks)) $ do
@@ -463,110 +510,111 @@ genRaInsn block_live new_instrs block_id instr r_dying w_dying =
 -- -----------------------------------------------------------------------------
 -- releaseRegs
 
+releaseRegs :: FR freeRegs => [Reg] -> RegM freeRegs ()
 releaseRegs regs = do
   assig <- getAssigR
   free <- getFreeRegsR
-  loop assig free regs 
+  loop assig free regs
  where
   loop _     free _ | free `seq` False = undefined
   loop assig free [] = do setAssigR assig; setFreeRegsR free; return ()
-  loop assig free (RegReal rr : rs) = loop assig (releaseReg rr free) rs
-  loop assig free (r:rs) = 
+  loop assig free (RegReal rr : rs) = loop assig (frReleaseReg rr free) rs
+  loop assig free (r:rs) =
      case lookupUFM assig r of
-       Just (InBoth real _) -> loop (delFromUFM assig r) (releaseReg real free) rs
-       Just (InReg real) -> loop (delFromUFM assig r) (releaseReg real free) rs
-       _other            -> loop (delFromUFM assig r) free rs
+        Just (InBoth real _) -> loop (delFromUFM assig r) (frReleaseReg real free) rs
+        Just (InReg real) -> loop (delFromUFM assig r) (frReleaseReg real free) rs
+        _other            -> loop (delFromUFM assig r) free rs
 
 
 -- -----------------------------------------------------------------------------
 -- Clobber real registers
 
 -- For each temp in a register that is going to be clobbered:
---     - if the temp dies after this instruction, do nothing
---     - otherwise, put it somewhere safe (another reg if possible,
---             otherwise spill and record InBoth in the assignment).
---     - for allocateRegs on the temps *read*,
---     - clobbered regs are allocatable.
+--      - if the temp dies after this instruction, do nothing
+--      - otherwise, put it somewhere safe (another reg if possible,
+--              otherwise spill and record InBoth in the assignment).
+--      - for allocateRegs on the temps *read*,
+--      - clobbered regs are allocatable.
 --
---     for allocateRegs on the temps *written*, 
---       - clobbered regs are not allocatable.
+--      for allocateRegs on the temps *written*,
+--        - clobbered regs are not allocatable.
 --
---     TODO:   instead of spilling, try to copy clobbered
---             temps to another register if possible.
+--      TODO:   instead of spilling, try to copy clobbered
+--              temps to another register if possible.
 --
 
 
 saveClobberedTemps
-       :: (Outputable instr, Instruction instr)
-       => [RealReg]            -- real registers clobbered by this instruction
-       -> [Reg]                -- registers which are no longer live after this insn
-       -> RegM [instr]         -- return: instructions to spill any temps that will
-                               -- be clobbered.
+        :: (Outputable instr, Instruction instr)
+        => [RealReg]            -- real registers clobbered by this instruction
+        -> [Reg]                -- registers which are no longer live after this insn
+        -> RegM freeRegs [instr]         -- return: instructions to spill any temps that will
+                                -- be clobbered.
 
-saveClobberedTemps [] _ 
-       = return []
+saveClobberedTemps [] _
+        = return []
 
-saveClobberedTemps clobbered dying 
+saveClobberedTemps clobbered dying
  = do
-       assig   <- getAssigR
-       let to_spill  
-               = [ (temp,reg) 
-                       | (temp, InReg reg) <- ufmToList assig
-                       , any (realRegsAlias reg) clobbered
-                       , temp `notElem` map getUnique dying  ]
+        assig   <- getAssigR
+        let to_spill
+                = [ (temp,reg)
+                        | (temp, InReg reg) <- ufmToList assig
+                        , any (realRegsAlias reg) clobbered
+                        , temp `notElem` map getUnique dying  ]
 
-       (instrs,assig') <- clobber assig [] to_spill
-       setAssigR assig'
-       return instrs
+        (instrs,assig') <- clobber assig [] to_spill
+        setAssigR assig'
+        return instrs
 
    where
-       clobber assig instrs [] 
-               = return (instrs, assig)
+        clobber assig instrs []
+                = return (instrs, assig)
 
-       clobber assig instrs ((temp, reg) : rest)
-        = do
-               (spill, slot)   <- spillR (RegReal reg) temp
+        clobber assig instrs ((temp, reg) : rest)
+         = do
+                (spill, slot)   <- spillR (RegReal reg) temp
 
-               -- record why this reg was spilled for profiling
-               recordSpill (SpillClobber temp)
+                -- record why this reg was spilled for profiling
+                recordSpill (SpillClobber temp)
 
-               let new_assign  = addToUFM assig temp (InBoth reg slot)
+                let new_assign  = addToUFM assig temp (InBoth reg slot)
 
-               clobber new_assign (spill : instrs) rest
+                clobber new_assign (spill : instrs) rest
 
 
 
 -- | Mark all these real regs as allocated,
---     and kick out their vreg assignments.
+--      and kick out their vreg assignments.
 --
-clobberRegs :: [RealReg] -> RegM ()
-clobberRegs []         
-       = return ()
+clobberRegs :: FR freeRegs => [RealReg] -> RegM freeRegs ()
+clobberRegs []
+        = return ()
 
-clobberRegs clobbered 
+clobberRegs clobbered
  = do
-       freeregs        <- getFreeRegsR
-       setFreeRegsR $! foldr allocateReg freeregs clobbered
+        freeregs        <- getFreeRegsR
+        setFreeRegsR $! foldr frAllocateReg freeregs clobbered
 
-       assig           <- getAssigR
-       setAssigR $! clobber assig (ufmToList assig)
+        assig           <- getAssigR
+        setAssigR $! clobber assig (ufmToList assig)
 
    where
-       -- if the temp was InReg and clobbered, then we will have
-       -- saved it in saveClobberedTemps above.  So the only case
-       -- we have to worry about here is InBoth.  Note that this
-       -- also catches temps which were loaded up during allocation
-       -- of read registers, not just those saved in saveClobberedTemps.
-
-       clobber assig [] 
-               = assig
-
-       clobber assig ((temp, InBoth reg slot) : rest)
-               | any (realRegsAlias reg) clobbered
-               = clobber (addToUFM assig temp (InMem slot)) rest
-       clobber assig (_:rest)
-               = clobber assig rest 
+        -- if the temp was InReg and clobbered, then we will have
+        -- saved it in saveClobberedTemps above.  So the only case
+        -- we have to worry about here is InBoth.  Note that this
+        -- also catches temps which were loaded up during allocation
+        -- of read registers, not just those saved in saveClobberedTemps.
+
+        clobber assig []
+                = assig
+
+        clobber assig ((temp, InBoth reg slot) : rest)
+                | any (realRegsAlias reg) clobbered
+                = clobber (addToUFM assig temp (InMem slot)) rest
+
+        clobber assig (_:rest)
+                = clobber assig rest
 
 -- -----------------------------------------------------------------------------
 -- allocateRegsAndSpill
@@ -589,38 +637,37 @@ data SpillLoc = ReadMem StackSlot  -- reading from register only in memory
 --   the list of free registers and free stack slots.
 
 allocateRegsAndSpill
-       :: (Outputable instr, Instruction instr)
-       => Bool                 -- True <=> reading (load up spilled regs)
-       -> [VirtualReg]         -- don't push these out
-       -> [instr]              -- spill insns
-       -> [RealReg]            -- real registers allocated (accum.)
-       -> [VirtualReg]         -- temps to allocate
-       -> RegM ( [instr]
-               , [RealReg])
+        :: (FR freeRegs, Outputable instr, Instruction instr)
+        => Bool                 -- True <=> reading (load up spilled regs)
+        -> [VirtualReg]         -- don't push these out
+        -> [instr]              -- spill insns
+        -> [RealReg]            -- real registers allocated (accum.)
+        -> [VirtualReg]         -- temps to allocate
+        -> RegM freeRegs ( [instr] , [RealReg])
 
 allocateRegsAndSpill _       _    spills alloc []
-       = return (spills, reverse alloc)
-
-allocateRegsAndSpill reading keep spills alloc (r:rs) 
- = do  assig <- getAssigR
-       let doSpill = allocRegsAndSpill_spill reading keep spills alloc r rs assig
-       case lookupUFM assig r of
-               -- case (1a): already in a register
-               Just (InReg my_reg) ->
-                       allocateRegsAndSpill reading keep spills (my_reg:alloc) rs
-
-               -- case (1b): already in a register (and memory)
-               -- NB1. if we're writing this register, update its assignment to be
-               -- InReg, because the memory value is no longer valid.
-               -- NB2. This is why we must process written registers here, even if they
-               -- are also read by the same instruction.
-               Just (InBoth my_reg _) 
-                -> do  when (not reading) (setAssigR (addToUFM assig r (InReg my_reg)))
-                       allocateRegsAndSpill reading keep spills (my_reg:alloc) rs
-
-               -- Not already in a register, so we need to find a free one...
-               Just (InMem slot) | reading   -> doSpill (ReadMem slot)
-                                 | otherwise -> doSpill WriteMem
+        = return (spills, reverse alloc)
+
+allocateRegsAndSpill reading keep spills alloc (r:rs)
+ = do   assig <- getAssigR
+        let doSpill = allocRegsAndSpill_spill reading keep spills alloc r rs assig
+        case lookupUFM assig r of
+                -- case (1a): already in a register
+                Just (InReg my_reg) ->
+                        allocateRegsAndSpill reading keep spills (my_reg:alloc) rs
+
+                -- case (1b): already in a register (and memory)
+                -- NB1. if we're writing this register, update its assignment to be
+                -- InReg, because the memory value is no longer valid.
+                -- NB2. This is why we must process written registers here, even if they
+                -- are also read by the same instruction.
+                Just (InBoth my_reg _)
+                 -> do  when (not reading) (setAssigR (addToUFM assig r (InReg my_reg)))
+                        allocateRegsAndSpill reading keep spills (my_reg:alloc) rs
+
+                -- Not already in a register, so we need to find a free one...
+                Just (InMem slot) | reading   -> doSpill (ReadMem slot)
+                                  | otherwise -> doSpill WriteMem
                 Nothing | reading   ->
                    -- pprPanic "allocateRegsAndSpill: Cannot read from uninitialized register" (ppr r)
                    -- ToDo: This case should be a panic, but we
@@ -629,96 +676,106 @@ allocateRegsAndSpill reading keep spills alloc (r:rs)
                    -- will start with an empty assignment.
                    doSpill WriteNew
 
-                       | otherwise -> doSpill WriteNew
-       
+                        | otherwise -> doSpill WriteNew
+
 
 -- reading is redundant with reason, but we keep it around because it's
 -- convenient and it maintains the recursive structure of the allocator. -- EZY
+allocRegsAndSpill_spill :: (FR freeRegs, Instruction instr, Outputable instr)
+                        => Bool
+                        -> [VirtualReg]
+                        -> [instr]
+                        -> [RealReg]
+                        -> VirtualReg
+                        -> [VirtualReg]
+                        -> UniqFM Loc
+                        -> SpillLoc
+                        -> RegM freeRegs ([instr], [RealReg])
 allocRegsAndSpill_spill reading keep spills alloc r rs assig spill_loc
  = do
-       freeRegs                <- getFreeRegsR
-       let freeRegs_thisClass  = getFreeRegs (classOfVirtualReg r) freeRegs
+        freeRegs                <- getFreeRegsR
+        let freeRegs_thisClass  = frGetFreeRegs (classOfVirtualReg r) freeRegs
 
         case freeRegs_thisClass of
 
-        -- case (2): we have a free register
-        (my_reg : _) -> 
-          do   spills'   <- loadTemp r spill_loc my_reg spills
-
-               setAssigR       (addToUFM assig r $! newLocation spill_loc my_reg)
-               setFreeRegsR $  allocateReg my_reg freeRegs
-
-               allocateRegsAndSpill reading keep spills' (my_reg : alloc) rs
-
-
-         -- case (3): we need to push something out to free up a register
-        [] -> 
-          do   let keep' = map getUnique keep
-
-               -- the vregs we could kick out that are already in a slot
-               let candidates_inBoth
-                       = [ (temp, reg, mem)
-                               | (temp, InBoth reg mem) <- ufmToList assig
-                               , temp `notElem` keep'
-                               , targetClassOfRealReg reg == classOfVirtualReg r ]
-
-               -- the vregs we could kick out that are only in a reg
-               --      this would require writing the reg to a new slot before using it.
-               let candidates_inReg
-                       = [ (temp, reg)
-                               | (temp, InReg reg)     <- ufmToList assig
-                               , temp `notElem` keep'
-                               , targetClassOfRealReg reg == classOfVirtualReg r ]
-
-               let result
-
-                       -- we have a temporary that is in both register and mem,
-                       -- just free up its register for use.
-                       | (temp, my_reg, slot) : _      <- candidates_inBoth
-                       = do    spills' <- loadTemp r spill_loc my_reg spills
-                               let assig1  = addToUFM assig temp (InMem slot)
-                               let assig2  = addToUFM assig1 r $! newLocation spill_loc my_reg
-
-                               setAssigR assig2
-                               allocateRegsAndSpill reading keep spills' (my_reg:alloc) rs
-
-                       -- otherwise, we need to spill a temporary that currently
-                       -- resides in a register.
-                       | (temp_to_push_out, (my_reg :: RealReg)) : _
-                                       <- candidates_inReg
-                       = do
-                               (spill_insn, slot) <- spillR (RegReal my_reg) temp_to_push_out
-                               let spill_store  = (if reading then id else reverse)
-                                                       [ -- COMMENT (fsLit "spill alloc") 
-                                                          spill_insn ]
-
-                               -- record that this temp was spilled
-                               recordSpill (SpillAlloc temp_to_push_out)
-
-                               -- update the register assignment
-                               let assig1  = addToUFM assig temp_to_push_out   (InMem slot)
-                               let assig2  = addToUFM assig1 r                 $! newLocation spill_loc my_reg
-                               setAssigR assig2
-
-                               -- if need be, load up a spilled temp into the reg we've just freed up.
-                               spills' <- loadTemp r spill_loc my_reg spills
-
-                               allocateRegsAndSpill reading keep
-                                       (spill_store ++ spills')
-                                       (my_reg:alloc) rs
-
-
-                       -- there wasn't anything to spill, so we're screwed.
-                       | otherwise
-                       = pprPanic ("RegAllocLinear.allocRegsAndSpill: no spill candidates\n")
-                       $ vcat 
-                               [ text "allocating vreg:  " <> text (show r)
-                               , text "assignment:       " <> text (show $ ufmToList assig) 
-                               , text "freeRegs:         " <> text (show freeRegs) 
-                               , text "initFreeRegs:     " <> text (show initFreeRegs) ]
-
-               result
-               
+         -- case (2): we have a free register
+         (my_reg : _) ->
+           do   spills'   <- loadTemp r spill_loc my_reg spills
+
+                setAssigR       (addToUFM assig r $! newLocation spill_loc my_reg)
+                setFreeRegsR $  frAllocateReg my_reg freeRegs
+
+                allocateRegsAndSpill reading keep spills' (my_reg : alloc) rs
+
+
+          -- case (3): we need to push something out to free up a register
+         [] ->
+           do   let keep' = map getUnique keep
+
+                -- the vregs we could kick out that are already in a slot
+                let candidates_inBoth
+                        = [ (temp, reg, mem)
+                                | (temp, InBoth reg mem) <- ufmToList assig
+                                , temp `notElem` keep'
+                                , targetClassOfRealReg reg == classOfVirtualReg r ]
+
+                -- the vregs we could kick out that are only in a reg
+                --      this would require writing the reg to a new slot before using it.
+                let candidates_inReg
+                        = [ (temp, reg)
+                                | (temp, InReg reg)     <- ufmToList assig
+                                , temp `notElem` keep'
+                                , targetClassOfRealReg reg == classOfVirtualReg r ]
+
+                let result
+
+                        -- we have a temporary that is in both register and mem,
+                        -- just free up its register for use.
+                        | (temp, my_reg, slot) : _      <- candidates_inBoth
+                        = do    spills' <- loadTemp r spill_loc my_reg spills
+                                let assig1  = addToUFM assig temp (InMem slot)
+                                let assig2  = addToUFM assig1 r $! newLocation spill_loc my_reg
+
+                                setAssigR assig2
+                                allocateRegsAndSpill reading keep spills' (my_reg:alloc) rs
+
+                        -- otherwise, we need to spill a temporary that currently
+                        -- resides in a register.
+                        | (temp_to_push_out, (my_reg :: RealReg)) : _
+                                        <- candidates_inReg
+                        = do
+                                (spill_insn, slot) <- spillR (RegReal my_reg) temp_to_push_out
+                                let spill_store  = (if reading then id else reverse)
+                                                        [ -- COMMENT (fsLit "spill alloc")
+                                                           spill_insn ]
+
+                                -- record that this temp was spilled
+                                recordSpill (SpillAlloc temp_to_push_out)
+
+                                -- update the register assignment
+                                let assig1  = addToUFM assig temp_to_push_out   (InMem slot)
+                                let assig2  = addToUFM assig1 r                 $! newLocation spill_loc my_reg
+                                setAssigR assig2
+
+                                -- if need be, load up a spilled temp into the reg we've just freed up.
+                                spills' <- loadTemp r spill_loc my_reg spills
+
+                                allocateRegsAndSpill reading keep
+                                        (spill_store ++ spills')
+                                        (my_reg:alloc) rs
+
+
+                        -- there wasn't anything to spill, so we're screwed.
+                        | otherwise
+                        = pprPanic ("RegAllocLinear.allocRegsAndSpill: no spill candidates\n")
+                        $ vcat
+                                [ text "allocating vreg:  " <> text (show r)
+                                , text "assignment:       " <> text (show $ ufmToList assig)
+                                , text "freeRegs:         " <> text (show freeRegs)
+                                , text "initFreeRegs:     " <> text (show (frInitFreeRegs `asTypeOf` freeRegs)) ]
+
+                result
+
 
 -- | Calculate a new location after a register has been loaded.
 newLocation :: SpillLoc -> RealReg -> Loc
@@ -729,18 +786,18 @@ newLocation _ my_reg = InReg my_reg
 
 -- | Load up a spilled temporary if we need to (read from memory).
 loadTemp
-       :: (Outputable instr, Instruction instr)
-       => VirtualReg   -- the temp being loaded
-       -> SpillLoc     -- the current location of this temp
-       -> RealReg      -- the hreg to load the temp into
-       -> [instr]
-       -> RegM [instr]
+        :: (Outputable instr, Instruction instr)
+        => VirtualReg   -- the temp being loaded
+        -> SpillLoc     -- the current location of this temp
+        -> RealReg      -- the hreg to load the temp into
+        -> [instr]
+        -> RegM freeRegs [instr]
 
 loadTemp vreg (ReadMem slot) hreg spills
  = do
-       insn <- loadR (RegReal hreg) slot
-       recordSpill (SpillLoad $ getUnique vreg)
-       return  $  {- COMMENT (fsLit "spill load") : -} insn : spills
+        insn <- loadR (RegReal hreg) slot
+        recordSpill (SpillLoad $ getUnique vreg)
+        return  $  {- COMMENT (fsLit "spill load") : -} insn : spills
 
 loadTemp _ _ _ spills =
    return spills
index 234701c..05db9de 100644 (file)
@@ -32,7 +32,6 @@ where
 import RegAlloc.Linear.Stats
 import RegAlloc.Linear.StackMap
 import RegAlloc.Linear.Base
-import RegAlloc.Linear.FreeRegs
 import RegAlloc.Liveness
 import Instruction
 import Reg
@@ -42,19 +41,19 @@ import UniqSupply
 
 
 -- | The RegM Monad
-instance Monad RegM where
+instance Monad (RegM freeRegs) where
   m >>= k   =  RegM $ \s -> case unReg m s of { (# s, a #) -> unReg (k a) s }
   return a  =  RegM $ \s -> (# s, a #)
 
 
 -- | Run a computation in the RegM register allocator monad.
-runR   :: BlockAssignment 
-       -> FreeRegs 
+runR   :: BlockAssignment freeRegs
+       -> freeRegs 
        -> RegMap Loc
        -> StackMap 
        -> UniqSupply
-       -> RegM a 
-       -> (BlockAssignment, StackMap, RegAllocStats, a)
+       -> RegM freeRegs a 
+       -> (BlockAssignment freeRegs, StackMap, RegAllocStats, a)
 
 runR block_assig freeregs assig stack us thing =
   case unReg thing 
@@ -76,14 +75,14 @@ runR block_assig freeregs assig stack us thing =
 
 
 -- | Make register allocator stats from its final state.
-makeRAStats :: RA_State -> RegAllocStats
+makeRAStats :: RA_State freeRegs -> RegAllocStats
 makeRAStats state
        = RegAllocStats
        { ra_spillInstrs        = binSpillReasons (ra_spills state) }
 
 
 spillR         :: Instruction instr
-       => Reg -> Unique -> RegM (instr, Int)
+       => Reg -> Unique -> RegM freeRegs (instr, Int)
 
 spillR reg temp = RegM $ \ s@RA_State{ra_delta=delta, ra_stack=stack} ->
   let (stack',slot) = getStackSlotFor stack temp
@@ -93,49 +92,49 @@ spillR reg temp = RegM $ \ s@RA_State{ra_delta=delta, ra_stack=stack} ->
 
 
 loadR  :: Instruction instr
-       => Reg -> Int -> RegM instr
+       => Reg -> Int -> RegM freeRegs instr
 
 loadR reg slot = RegM $ \ s@RA_State{ra_delta=delta} ->
   (# s, mkLoadInstr reg delta slot #)
 
-getFreeRegsR :: RegM FreeRegs
+getFreeRegsR :: RegM freeRegs freeRegs
 getFreeRegsR = RegM $ \ s@RA_State{ra_freeregs = freeregs} ->
   (# s, freeregs #)
 
-setFreeRegsR :: FreeRegs -> RegM ()
+setFreeRegsR :: freeRegs -> RegM freeRegs ()
 setFreeRegsR regs = RegM $ \ s ->
   (# s{ra_freeregs = regs}, () #)
 
-getAssigR :: RegM (RegMap Loc)
+getAssigR :: RegM freeRegs (RegMap Loc)
 getAssigR = RegM $ \ s@RA_State{ra_assig = assig} ->
   (# s, assig #)
 
-setAssigR :: RegMap Loc -> RegM ()
+setAssigR :: RegMap Loc -> RegM freeRegs ()
 setAssigR assig = RegM $ \ s ->
   (# s{ra_assig=assig}, () #)
 
-getBlockAssigR :: RegM BlockAssignment
+getBlockAssigR :: RegM freeRegs (BlockAssignment freeRegs)
 getBlockAssigR = RegM $ \ s@RA_State{ra_blockassig = assig} ->
   (# s, assig #)
 
-setBlockAssigR :: BlockAssignment -> RegM ()
+setBlockAssigR :: BlockAssignment freeRegs -> RegM freeRegs ()
 setBlockAssigR assig = RegM $ \ s ->
   (# s{ra_blockassig = assig}, () #)
 
-setDeltaR :: Int -> RegM ()
+setDeltaR :: Int -> RegM freeRegs ()
 setDeltaR n = RegM $ \ s ->
   (# s{ra_delta = n}, () #)
 
-getDeltaR :: RegM Int
+getDeltaR :: RegM freeRegs Int
 getDeltaR = RegM $ \s -> (# s, ra_delta s #)
 
-getUniqueR :: RegM Unique
+getUniqueR :: RegM freeRegs Unique
 getUniqueR = RegM $ \s ->
   case takeUniqFromSupply (ra_us s) of
     (uniq, us) -> (# s{ra_us = us}, uniq #)
 
 
 -- | Record that a spill instruction was inserted, for profiling.
-recordSpill :: SpillReason -> RegM ()
+recordSpill :: SpillReason -> RegM freeRegs ()
 recordSpill spill
        = RegM $ \s -> (# s { ra_spills = spill : ra_spills s}, () #)
index 106b673..0a26c23 100644 (file)
@@ -80,9 +80,19 @@ genCCall (CmmPrim (MO_WriteBarrier)) _ _
 
 genCCall target dest_regs argsAndHints 
  = do          
+        -- need to remove alignment information
+        let argsAndHints' | (CmmPrim mop) <- target,
+                            (mop == MO_Memcpy ||
+                             mop == MO_Memset ||
+                             mop == MO_Memmove)
+                          = init argsAndHints
+
+                          | otherwise
+                          = argsAndHints
+                
        -- strip hints from the arg regs
        let args :: [CmmExpr]
-           args  = map hintlessCmm argsAndHints
+           args  = map hintlessCmm argsAndHints'
 
 
        -- work out the arguments, and assign them to integer regs
@@ -104,7 +114,7 @@ genCCall target dest_regs argsAndHints
                        return (dyn_c `snocOL` CALL (Right dyn_r) n_argRegs_used False)
 
                CmmPrim mop 
-                -> do  res     <- outOfLineFloatOp mop
+                -> do  res     <- outOfLineMachOp mop
                        lblOrMopExpr <- case res of
                                Left lbl -> do
                                        return (unitOL (CALL (Left (litToImm (CmmLabel lbl))) n_argRegs_used False))
@@ -253,13 +263,13 @@ assign_code _
 
 
 -- | Generate a call to implement an out-of-line floating point operation
-outOfLineFloatOp 
+outOfLineMachOp
        :: CallishMachOp 
        -> NatM (Either CLabel CmmExpr)
 
-outOfLineFloatOp mop 
+outOfLineMachOp mop 
  = do  let functionName
-               = outOfLineFloatOp_table mop
+               = outOfLineMachOp_table mop
        
        dflags  <- getDynFlagsNat
        mopExpr <- cmmMakeDynamicReference dflags addImportNat CallReference 
@@ -275,11 +285,11 @@ outOfLineFloatOp mop
 
 -- | Decide what C function to use to implement a CallishMachOp
 --
-outOfLineFloatOp_table 
+outOfLineMachOp_table 
        :: CallishMachOp
        -> FastString
        
-outOfLineFloatOp_table mop
+outOfLineMachOp_table mop
  = case mop of
        MO_F32_Exp    -> fsLit "expf"
        MO_F32_Log    -> fsLit "logf"
@@ -315,5 +325,9 @@ outOfLineFloatOp_table mop
        MO_F64_Cosh   -> fsLit "cosh"
        MO_F64_Tanh   -> fsLit "tanh"
 
-       _ -> pprPanic "outOfLineFloatOp(sparc): Unknown callish mach op "
+        MO_Memcpy    -> fsLit "memcpy"
+        MO_Memset    -> fsLit "memset"
+        MO_Memmove   -> fsLit "memmove"
+
+       _ -> pprPanic "outOfLineMachOp(sparc): Unknown callish mach op "
                        (pprCallishMachOp mop)
index c5a3314..d78d1a7 100644 (file)
@@ -101,9 +101,7 @@ pprData (CmmStaticLit lit)       = pprDataItem lit
 pprGloblDecl :: CLabel -> Doc
 pprGloblDecl lbl
   | not (externallyVisibleCLabel lbl) = empty
-  | otherwise = ptext IF_ARCH_sparc((sLit ".global "), 
-                                   (sLit ".globl ")) <>
-               pprCLabel_asm lbl
+  | otherwise = ptext (sLit ".global ") <> pprCLabel_asm lbl
 
 pprTypeAndSizeDecl :: CLabel -> Doc
 #if linux_TARGET_OS
index c0c3343..30e48bb 100644 (file)
@@ -1,6 +1,6 @@
 
 module SPARC.ShortcutJump (
-       JumpDest(..),
+       JumpDest(..), getJumpDestBlockId,
        canShortcut,
        shortcutJump,
        shortcutStatic,
@@ -25,6 +25,10 @@ data JumpDest
        = DestBlockId BlockId 
        | DestImm Imm
 
+getJumpDestBlockId :: JumpDest -> Maybe BlockId
+getJumpDestBlockId (DestBlockId bid) = Just bid
+getJumpDestBlockId _                 = Nothing
+
 
 canShortcut :: Instr -> Maybe JumpDest
 canShortcut _ = Nothing
index 35b49d1..b357675 100644 (file)
@@ -31,60 +31,72 @@ import CmmType      (wordWidth)
 import Outputable
 import Unique
 import FastTypes
+import Platform
 
+import qualified X86.Regs       as X86
+import qualified X86.RegInfo    as X86
 
-#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
-import qualified X86.Regs      as X86
-import qualified X86.RegInfo   as X86
+import qualified PPC.Regs       as PPC
 
-#elif powerpc_TARGET_ARCH
-import qualified PPC.Regs      as PPC
+import qualified SPARC.Regs     as SPARC
 
-#elif sparc_TARGET_ARCH        
-import qualified SPARC.Regs    as SPARC
-
-#else
-#error "RegAlloc.Graph.TargetReg: not defined"
-#endif
+-- TODO: We shouldn't be using defaultTargetPlatform here.
+--       We should be passing DynFlags in instead, and looking at
+--       its targetPlatform.
 
 targetVirtualRegSqueeze :: RegClass -> VirtualReg -> FastInt
-targetRealRegSqueeze   :: RegClass -> RealReg -> FastInt
-targetClassOfRealReg   :: RealReg -> RegClass
-targetWordSize                 :: Size
-targetMkVirtualReg     :: Unique -> Size -> VirtualReg
-targetRegDotColor      :: RealReg -> SDoc
-
--- x86 -------------------------------------------------------------------------
-#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
-targetVirtualRegSqueeze = X86.virtualRegSqueeze
-targetRealRegSqueeze   = X86.realRegSqueeze
-targetClassOfRealReg   = X86.classOfRealReg
-targetWordSize                 = intSize wordWidth
-targetMkVirtualReg     = X86.mkVirtualReg
-targetRegDotColor      = X86.regDotColor
-
--- ppc -------------------------------------------------------------------------
-#elif powerpc_TARGET_ARCH
-targetVirtualRegSqueeze = PPC.virtualRegSqueeze
-targetRealRegSqueeze   = PPC.realRegSqueeze
-targetClassOfRealReg   = PPC.classOfRealReg
-targetWordSize                 = intSize wordWidth
-targetMkVirtualReg     = PPC.mkVirtualReg
-targetRegDotColor      = PPC.regDotColor
-
--- sparc -----------------------------------------------------------------------
-#elif sparc_TARGET_ARCH
-targetVirtualRegSqueeze = SPARC.virtualRegSqueeze
-targetRealRegSqueeze   = SPARC.realRegSqueeze
-targetClassOfRealReg   = SPARC.classOfRealReg
-targetWordSize                 = intSize wordWidth
-targetMkVirtualReg     = SPARC.mkVirtualReg
-targetRegDotColor      = SPARC.regDotColor
-
---------------------------------------------------------------------------------
-#else
-#error "RegAlloc.Graph.TargetReg: not defined"
-#endif
+targetVirtualRegSqueeze
+    = case platformArch defaultTargetPlatform of
+      ArchX86     -> X86.virtualRegSqueeze
+      ArchX86_64  -> X86.virtualRegSqueeze
+      ArchPPC     -> PPC.virtualRegSqueeze
+      ArchSPARC   -> SPARC.virtualRegSqueeze
+      ArchPPC_64  -> panic "targetVirtualRegSqueeze ArchPPC_64"
+      ArchUnknown -> panic "targetVirtualRegSqueeze ArchUnknown"
+
+targetRealRegSqueeze :: RegClass -> RealReg -> FastInt
+targetRealRegSqueeze
+    = case platformArch defaultTargetPlatform of
+      ArchX86     -> X86.realRegSqueeze
+      ArchX86_64  -> X86.realRegSqueeze
+      ArchPPC     -> PPC.realRegSqueeze
+      ArchSPARC   -> SPARC.realRegSqueeze
+      ArchPPC_64  -> panic "targetRealRegSqueeze ArchPPC_64"
+      ArchUnknown -> panic "targetRealRegSqueeze ArchUnknown"
+
+targetClassOfRealReg :: RealReg -> RegClass
+targetClassOfRealReg
+    = case platformArch defaultTargetPlatform of
+      ArchX86     -> X86.classOfRealReg
+      ArchX86_64  -> X86.classOfRealReg
+      ArchPPC     -> PPC.classOfRealReg
+      ArchSPARC   -> SPARC.classOfRealReg
+      ArchPPC_64  -> panic "targetClassOfRealReg ArchPPC_64"
+      ArchUnknown -> panic "targetClassOfRealReg ArchUnknown"
+
+-- TODO: This should look at targetPlatform too
+targetWordSize :: Size
+targetWordSize = intSize wordWidth
+
+targetMkVirtualReg :: Unique -> Size -> VirtualReg
+targetMkVirtualReg
+    = case platformArch defaultTargetPlatform of
+      ArchX86     -> X86.mkVirtualReg
+      ArchX86_64  -> X86.mkVirtualReg
+      ArchPPC     -> PPC.mkVirtualReg
+      ArchSPARC   -> SPARC.mkVirtualReg
+      ArchPPC_64  -> panic "targetMkVirtualReg ArchPPC_64"
+      ArchUnknown -> panic "targetMkVirtualReg ArchUnknown"
+
+targetRegDotColor :: RealReg -> SDoc
+targetRegDotColor
+    = case platformArch defaultTargetPlatform of
+      ArchX86     -> X86.regDotColor
+      ArchX86_64  -> X86.regDotColor
+      ArchPPC     -> PPC.regDotColor
+      ArchSPARC   -> SPARC.regDotColor
+      ArchPPC_64  -> panic "targetRegDotColor ArchPPC_64"
+      ArchUnknown -> panic "targetRegDotColor ArchUnknown"
 
 
 targetClassOfReg :: Reg -> RegClass
index a6cc36f..2f3e139 100644 (file)
@@ -1,10 +1,3 @@
-{-# OPTIONS -w #-}
--- The above warning supression flag is a temporary kludge.
--- While working on this module you are encouraged to remove it and fix
--- any warnings in the module. See
---     http://hackage.haskell.org/trac/ghc/wiki/Commentary/CodingStyle#Warnings
--- for details
-
 -----------------------------------------------------------------------------
 --
 -- Generating machine code (instruction selection)
@@ -35,30 +28,25 @@ import X86.Instr
 import X86.Cond
 import X86.Regs
 import X86.RegInfo
-import X86.Ppr
 import Instruction
 import PIC
 import NCGMonad
 import Size
 import Reg
-import RegClass
 import Platform
 
 -- Our intermediate code:
 import BasicTypes
 import BlockId
-import PprCmm          ( pprExpr )
+import PprCmm          ()
 import OldCmm
-import OldPprCmm
+import OldPprCmm        ()
 import CLabel
-import ClosureInfo     ( C_SRT(..) )
 
 -- The rest:
 import StaticFlags     ( opt_PIC )
 import ForeignCall     ( CCallConv(..) )
 import OrdList
-import Pretty
-import qualified Outputable as O
 import Outputable
 import Unique
 import FastString
@@ -66,13 +54,15 @@ import FastBool             ( isFastTrue )
 import Constants       ( wORD_SIZE )
 import DynFlags
 
-import Debug.Trace     ( trace )
+import Control.Monad    ( mapAndUnzipM )
+import Data.Maybe       ( catMaybes )
+import Data.Int
 
-import Control.Monad   ( mapAndUnzipM )
-import Data.Maybe      ( fromJust )
-import Data.Bits
+#if WORD_SIZE_IN_BITS==32
+import Data.Maybe       ( fromJust )
 import Data.Word
-import Data.Int
+import Data.Bits
+#endif
 
 sse2Enabled :: NatM Bool
 #if x86_64_TARGET_ARCH
@@ -170,8 +160,8 @@ stmtToInstrs stmt = case stmt of
     CmmBranch id         -> genBranch id
     CmmCondBranch arg id  -> genCondJump id arg
     CmmSwitch arg ids     -> genSwitch arg ids
-    CmmJump arg params   -> genJump arg
-    CmmReturn params     ->
+    CmmJump arg _         -> genJump arg
+    CmmReturn _           ->
       panic "stmtToInstrs: return statement should have been cps'd away"
 
 
@@ -190,6 +180,7 @@ data CondCode
        = CondCode Bool Cond InstrBlock
 
 
+#if WORD_SIZE_IN_BITS==32
 -- | a.k.a "Register64"
 --     Reg is the lower 32-bit temporary which contains the result. 
 --     Use getHiVRegFromLo to find the other VRegUnique.  
@@ -201,6 +192,7 @@ data ChildCode64
    = ChildCode64 
         InstrBlock
         Reg            
+#endif
 
 
 -- | Register's passed up the tree.  If the stix code forces the register
@@ -282,8 +274,8 @@ jumpTableEntry (Just blockid) = CmmStaticLit (CmmLabel blockLabel)
 
 -- Expand CmmRegOff.  ToDo: should we do it this way around, or convert
 -- CmmExprs into CmmRegOff?
-mangleIndexTree :: CmmExpr -> CmmExpr
-mangleIndexTree (CmmRegOff reg off)
+mangleIndexTree :: CmmReg -> Int -> CmmExpr
+mangleIndexTree reg off
   = CmmMachOp (MO_Add width) [CmmReg reg, CmmLit (CmmInt (fromIntegral off) width)]
   where width = typeWidth (cmmRegType reg)
 
@@ -300,9 +292,7 @@ getSomeReg expr = do
        return (reg, code)
 
 
-
-
-
+#if WORD_SIZE_IN_BITS==32
 assignMem_I64Code :: CmmExpr -> CmmExpr -> NatM InstrBlock
 assignMem_I64Code addrTree valueTree = do
   Amode addr addr_code <- getAmode addrTree
@@ -318,7 +308,7 @@ assignMem_I64Code addrTree valueTree = do
 
 
 assignReg_I64Code :: CmmReg  -> CmmExpr -> NatM InstrBlock
-assignReg_I64Code (CmmLocal (LocalReg u_dst pk)) valueTree = do
+assignReg_I64Code (CmmLocal (LocalReg u_dst _)) valueTree = do
    ChildCode64 vcode r_src_lo <- iselExpr64 valueTree
    let 
          r_dst_lo = RegVirtual $ mkVirtualReg u_dst II32
@@ -331,12 +321,10 @@ assignReg_I64Code (CmmLocal (LocalReg u_dst pk)) valueTree = do
         vcode `snocOL` mov_lo `snocOL` mov_hi
      )
 
-assignReg_I64Code lvalue valueTree
+assignReg_I64Code _ _
    = panic "assignReg_I64Code(i386): invalid lvalue"
 
 
-
-
 iselExpr64        :: CmmExpr -> NatM ChildCode64
 iselExpr64 (CmmLit (CmmInt i _)) = do
   (rlo,rhi) <- getNewRegPairNat II32
@@ -410,7 +398,7 @@ iselExpr64 (CmmMachOp (MO_UU_Conv _ W64) [expr]) = do
 
 iselExpr64 expr
    = pprPanic "iselExpr64(i386)" (ppr expr)
-
+#endif
 
 
 --------------------------------------------------------------------------------
@@ -435,8 +423,8 @@ getRegister (CmmReg reg)
        return (Fixed size (getRegisterReg use_sse2 reg) nilOL)
   
 
-getRegister tree@(CmmRegOff _ _) 
-  = getRegister (mangleIndexTree tree)
+getRegister (CmmRegOff r n) 
+  = getRegister $ mangleIndexTree r n
 
 
 #if WORD_SIZE_IN_BITS==32
@@ -611,7 +599,7 @@ getRegister (CmmMachOp mop [x]) = do -- unary MachOps
       MO_FS_Conv from to -> coerceFP2Int from to x
       MO_SF_Conv from to -> coerceInt2FP from to x
 
-      other -> pprPanic "getRegister" (pprMachOp mop)
+      _other -> pprPanic "getRegister" (pprMachOp mop)
    where
        triv_ucode :: (Size -> Operand -> Instr) -> Size -> NatM Register
        triv_ucode instr size = trivialUCode size (instr size) x
@@ -648,37 +636,37 @@ getRegister (CmmMachOp mop [x]) = do -- unary MachOps
                  return (swizzleRegisterRep e_code new_size)
 
 
-getRegister e@(CmmMachOp mop [x, y]) = do -- dyadic MachOps
+getRegister (CmmMachOp mop [x, y]) = do -- dyadic MachOps
   sse2 <- sse2Enabled
   case mop of
-      MO_F_Eq w -> condFltReg EQQ x y
-      MO_F_Ne w -> condFltReg NE x y
-      MO_F_Gt w -> condFltReg GTT x y
-      MO_F_Ge w -> condFltReg GE x y
-      MO_F_Lt w -> condFltReg LTT x y
-      MO_F_Le w -> condFltReg LE x y
-
-      MO_Eq rep   -> condIntReg EQQ x y
-      MO_Ne rep   -> condIntReg NE x y
-
-      MO_S_Gt rep -> condIntReg GTT x y
-      MO_S_Ge rep -> condIntReg GE x y
-      MO_S_Lt rep -> condIntReg LTT x y
-      MO_S_Le rep -> condIntReg LE x y
-
-      MO_U_Gt rep -> condIntReg GU  x y
-      MO_U_Ge rep -> condIntReg GEU x y
-      MO_U_Lt rep -> condIntReg LU  x y
-      MO_U_Le rep -> condIntReg LEU x y
+      MO_F_Eq _ -> condFltReg EQQ x y
+      MO_F_Ne _ -> condFltReg NE  x y
+      MO_F_Gt _ -> condFltReg GTT x y
+      MO_F_Ge _ -> condFltReg GE  x y
+      MO_F_Lt _ -> condFltReg LTT x y
+      MO_F_Le _ -> condFltReg LE  x y
+
+      MO_Eq _   -> condIntReg EQQ x y
+      MO_Ne _   -> condIntReg NE  x y
+
+      MO_S_Gt _ -> condIntReg GTT x y
+      MO_S_Ge _ -> condIntReg GE  x y
+      MO_S_Lt _ -> condIntReg LTT x y
+      MO_S_Le _ -> condIntReg LE  x y
+
+      MO_U_Gt _ -> condIntReg GU  x y
+      MO_U_Ge _ -> condIntReg GEU x y
+      MO_U_Lt _ -> condIntReg LU  x y
+      MO_U_Le _ -> condIntReg LEU x y
 
       MO_F_Add w  | sse2      -> trivialFCode_sse2 w ADD  x y
-                  | otherwise -> trivialFCode_x87  w GADD x y
+                  | otherwise -> trivialFCode_x87    GADD x y
       MO_F_Sub w  | sse2      -> trivialFCode_sse2 w SUB  x y
-                  | otherwise -> trivialFCode_x87  w GSUB x y
+                  | otherwise -> trivialFCode_x87    GSUB x y
       MO_F_Quot w | sse2      -> trivialFCode_sse2 w FDIV x y
-                  | otherwise -> trivialFCode_x87  w GDIV x y
+                  | otherwise -> trivialFCode_x87    GDIV x y
       MO_F_Mul w  | sse2      -> trivialFCode_sse2 w MUL x y
-                  | otherwise -> trivialFCode_x87  w GMUL x y
+                  | otherwise -> trivialFCode_x87    GMUL x y
 
       MO_Add rep -> add_code rep x y
       MO_Sub rep -> sub_code rep x y
@@ -703,7 +691,7 @@ getRegister e@(CmmMachOp mop [x, y]) = do -- dyadic MachOps
       MO_U_Shr rep -> shift_code rep SHR x y {-False-}
       MO_S_Shr rep -> shift_code rep SAR x y {-False-}
 
-      other -> pprPanic "getRegister(x86) - binary CmmMachOp (1)" (pprMachOp mop)
+      _other -> pprPanic "getRegister(x86) - binary CmmMachOp (1)" (pprMachOp mop)
   where
     --------------------
     triv_op width instr = trivialCode width op (Just op) x y
@@ -740,7 +728,7 @@ getRegister e@(CmmMachOp mop [x, y]) = do -- dyadic MachOps
               -> NatM Register
 
     {- Case1: shift length as immediate -}
-    shift_code width instr x y@(CmmLit lit) = do
+    shift_code width instr x (CmmLit lit) = do
          x_code <- getAnyReg x
          let
               size = intSize width
@@ -866,8 +854,7 @@ getRegister (CmmLit (CmmInt 0 width))
        size = intSize width
 
        -- x86_64: 32-bit xor is one byte shorter, and zero-extends to 64 bits
-       adj_size = case size of II64 -> II32; _ -> size
-       size1 = IF_ARCH_i386( size, adj_size ) 
+       size1 = IF_ARCH_i386( size, case size of II64 -> II32; _ -> size )
        code dst 
            = unitOL (XOR size1 (OpReg dst) (OpReg dst))
     in
@@ -971,7 +958,7 @@ reg2reg size src dst
 
 --------------------------------------------------------------------------------
 getAmode :: CmmExpr -> NatM Amode
-getAmode tree@(CmmRegOff _ _) = getAmode (mangleIndexTree tree)
+getAmode (CmmRegOff r n) = getAmode $ mangleIndexTree r n
 
 #if x86_64_TARGET_ARCH
 
@@ -984,14 +971,14 @@ getAmode (CmmMachOp (MO_Add W64) [CmmReg (CmmGlobal PicBaseReg),
 
 -- This is all just ridiculous, since it carefully undoes 
 -- what mangleIndexTree has just done.
-getAmode (CmmMachOp (MO_Sub rep) [x, CmmLit lit@(CmmInt i _)])
+getAmode (CmmMachOp (MO_Sub _rep) [x, CmmLit lit@(CmmInt i _)])
   | is32BitLit lit
   -- ASSERT(rep == II32)???
   = do (x_reg, x_code) <- getSomeReg x
        let off = ImmInt (-(fromInteger i))
        return (Amode (AddrBaseIndex (EABaseReg x_reg) EAIndexNone off) x_code)
   
-getAmode (CmmMachOp (MO_Add rep) [x, CmmLit lit])
+getAmode (CmmMachOp (MO_Add _rep) [x, CmmLit lit])
   | is32BitLit lit
   -- ASSERT(rep == II32)???
   = do (x_reg, x_code) <- getSomeReg x
@@ -1004,12 +991,12 @@ getAmode (CmmMachOp (MO_Add rep) [a@(CmmMachOp (MO_Shl _) _),
                                  b@(CmmLit _)])
   = getAmode (CmmMachOp (MO_Add rep) [b,a])
 
-getAmode (CmmMachOp (MO_Add rep) [x, CmmMachOp (MO_Shl _) 
+getAmode (CmmMachOp (MO_Add _) [x, CmmMachOp (MO_Shl _) 
                                        [y, CmmLit (CmmInt shift _)]])
   | shift == 0 || shift == 1 || shift == 2 || shift == 3
   = x86_complex_amode x y shift 0
 
-getAmode (CmmMachOp (MO_Add rep) 
+getAmode (CmmMachOp (MO_Add _) 
                 [x, CmmMachOp (MO_Add _)
                         [CmmMachOp (MO_Shl _) [y, CmmLit (CmmInt shift _)],
                          CmmLit (CmmInt offset _)]])
@@ -1017,7 +1004,7 @@ getAmode (CmmMachOp (MO_Add rep)
   && is32BitInteger offset
   = x86_complex_amode x y shift offset
 
-getAmode (CmmMachOp (MO_Add rep) [x,y])
+getAmode (CmmMachOp (MO_Add _) [x,y])
   = x86_complex_amode x y 0 0
 
 getAmode (CmmLit lit) | is32BitLit lit
@@ -1036,7 +1023,8 @@ x86_complex_amode base index shift offset
        (y_reg, y_code) <- getSomeReg index
        let
           code = x_code `appOL` y_code
-           base = case shift of 0 -> 1; 1 -> 2; 2 -> 4; 3 -> 8
+           base = case shift of 0 -> 1; 1 -> 2; 2 -> 4; 3 -> 8;
+                                n -> panic $ "x86_complex_amode: unhandled shift! (" ++ show n ++ ")"
        return (Amode (AddrBaseIndex (EABaseReg x_reg) (EAIndex y_reg base) (ImmInt (fromIntegral offset)))
                code)
 
@@ -1093,6 +1081,7 @@ getNonClobberedOperand_generic e = do
 amodeCouldBeClobbered :: AddrMode -> Bool
 amodeCouldBeClobbered amode = any regClobbered (addrModeRegs amode)
 
+regClobbered :: Reg -> Bool
 regClobbered (RegReal (RealRegSingle rr)) = isFastTrue (freeReg rr)
 regClobbered _ = False
 
@@ -1124,6 +1113,7 @@ getOperand (CmmLoad mem pk) = do
 
 getOperand e = getOperand_generic e
 
+getOperand_generic :: CmmExpr -> NatM (Operand, InstrBlock)
 getOperand_generic e = do
     (reg, code) <- getSomeReg e
     return (OpReg reg, code)
@@ -1170,6 +1160,7 @@ loadFloatAmode use_sse2 w addr addr_code = do
 -- use it directly from memory.  However, if the literal is
 -- zero, we're better off generating it into a register using
 -- xor.
+isSuitableFloatingPointLit :: CmmLit -> Bool
 isSuitableFloatingPointLit (CmmFloat f _) = f /= 0.0
 isSuitableFloatingPointLit _ = False
 
@@ -1187,12 +1178,13 @@ getRegOrMem e = do
     (reg, code) <- getNonClobberedReg e
     return (OpReg reg, code)
 
+is32BitLit :: CmmLit -> Bool
 #if x86_64_TARGET_ARCH
 is32BitLit (CmmInt i W64) = is32BitInteger i
    -- assume that labels are in the range 0-2^31-1: this assumes the
    -- small memory model (see gcc docs, -mcmodel=small).
 #endif
-is32BitLit x = True
+is32BitLit _ = True
 
 
 
@@ -1220,20 +1212,20 @@ getCondCode (CmmMachOp mop [x, y])
       MO_F_Lt W64 -> condFltCode LTT x y
       MO_F_Le W64 -> condFltCode LE  x y
 
-      MO_Eq rep -> condIntCode EQQ  x y
-      MO_Ne rep -> condIntCode NE   x y
+      MO_Eq _ -> condIntCode EQQ x y
+      MO_Ne _ -> condIntCode NE  x y
 
-      MO_S_Gt rep -> condIntCode GTT  x y
-      MO_S_Ge rep -> condIntCode GE   x y
-      MO_S_Lt rep -> condIntCode LTT  x y
-      MO_S_Le rep -> condIntCode LE   x y
+      MO_S_Gt _ -> condIntCode GTT x y
+      MO_S_Ge _ -> condIntCode GE  x y
+      MO_S_Lt _ -> condIntCode LTT x y
+      MO_S_Le _ -> condIntCode LE  x y
 
-      MO_U_Gt rep -> condIntCode GU   x y
-      MO_U_Ge rep -> condIntCode GEU  x y
-      MO_U_Lt rep -> condIntCode LU   x y
-      MO_U_Le rep -> condIntCode LEU  x y
+      MO_U_Gt _ -> condIntCode GU  x y
+      MO_U_Ge _ -> condIntCode GEU x y
+      MO_U_Lt _ -> condIntCode LU  x y
+      MO_U_Le _ -> condIntCode LEU x y
 
-      other -> pprPanic "getCondCode(x86,x86_64,sparc)" (ppr (CmmMachOp mop [x,y]))
+      _other -> pprPanic "getCondCode(x86,x86_64,sparc)" (ppr (CmmMachOp mop [x,y]))
 
 getCondCode other =  pprPanic "getCondCode(2)(x86,sparc)" (ppr other)
 
@@ -1257,8 +1249,8 @@ condIntCode cond (CmmLoad x pk) (CmmLit lit) | is32BitLit lit = do
 
 -- anything vs zero, using a mask
 -- TODO: Add some sanity checking!!!!
-condIntCode cond (CmmMachOp (MO_And rep) [x,o2]) (CmmLit (CmmInt 0 pk))
-    | (CmmLit lit@(CmmInt mask pk2)) <- o2, is32BitLit lit
+condIntCode cond (CmmMachOp (MO_And _) [x,o2]) (CmmLit (CmmInt 0 pk))
+    | (CmmLit lit@(CmmInt mask _)) <- o2, is32BitLit lit
     = do
       (x_reg, x_code) <- getSomeReg x
       let
@@ -1310,7 +1302,6 @@ condFltCode cond x y
     = ASSERT(cond `elem` ([EQQ, NE, LE, LTT, GE, GTT])) do
     (x_reg, x_code) <- getNonClobberedReg x
     (y_reg, y_code) <- getSomeReg y
-    use_sse2 <- sse2Enabled
     let
        code = x_code `appOL` y_code `snocOL`
                GCMP cond x_reg y_reg
@@ -1400,7 +1391,7 @@ assignReg_IntCode pk reg (CmmLoad src _) = do
   return (load_code (getRegisterReg False{-no sse2-} reg))
 
 -- dst is a reg, but src could be anything
-assignReg_IntCode pk reg src = do
+assignReg_IntCode _ reg src = do
   code <- getAnyReg src
   return (code (getRegisterReg False{-no sse2-} reg))
 
@@ -1418,7 +1409,7 @@ assignMem_FltCode pk addr src = do
   return code
 
 -- Floating point assignment to a register/temporary
-assignReg_FltCode pk reg src = do
+assignReg_FltCode _ reg src = do
   use_sse2 <- sse2Enabled
   src_code <- getAnyReg src
   return (src_code (getRegisterReg use_sse2 reg))
@@ -1426,7 +1417,7 @@ assignReg_FltCode pk reg src = do
 
 genJump :: CmmExpr{-the branch target-} -> NatM InstrBlock
 
-genJump (CmmLoad mem pk) = do
+genJump (CmmLoad mem _) = do
   Amode target code <- getAmode mem
   return (code `snocOL` JMP (OpAddr target))
 
@@ -1519,14 +1510,18 @@ genCCall (CmmPrim MO_WriteBarrier) _ _ = return nilOL
        -- write barrier compiles to no code on x86/x86-64; 
        -- we keep it this long in order to prevent earlier optimisations.
 
+-- void return type prim op
+genCCall (CmmPrim op) [] args =
+    outOfLineCmmOp op Nothing args
+
 -- we only cope with a single result for foreign calls
-genCCall (CmmPrim op) [CmmHinted r _] args = do
+genCCall (CmmPrim op) [r_hinted@(CmmHinted r _)] args = do
   l1 <- getNewLabelNat
   l2 <- getNewLabelNat
   sse2 <- sse2Enabled
   if sse2
     then
-      outOfLineFloatOp op r args
+      outOfLineCmmOp op (Just r_hinted) args
     else case op of
        MO_F32_Sqrt -> actuallyInlineFloatOp GSQRT FF32 args
        MO_F64_Sqrt -> actuallyInlineFloatOp GSQRT FF64 args
@@ -1540,14 +1535,18 @@ genCCall (CmmPrim op) [CmmHinted r _] args = do
        MO_F32_Tan  -> actuallyInlineFloatOp (\s -> GTAN s l1 l2) FF32 args
        MO_F64_Tan  -> actuallyInlineFloatOp (\s -> GTAN s l1 l2) FF64 args
        
-       other_op    -> outOfLineFloatOp op r args
+       _other_op   -> outOfLineCmmOp op (Just r_hinted) args
 
  where
   actuallyInlineFloatOp instr size [CmmHinted x _]
-       = do res <- trivialUFCode size (instr size) x
+        = do res <- trivialUFCode size (instr size) x
             any <- anyReg res
             return (any (getRegisterReg False (CmmLocal r)))
 
+  actuallyInlineFloatOp _ _ args
+        = panic $ "genCCall.actuallyInlineFloatOp: bad number of arguments! ("
+                ++ show (length args) ++ ")"
+
 genCCall target dest_regs args = do
     let
         sizes               = map (arg_size . cmmExprType . hintlessCmm) (reverse args)
@@ -1569,7 +1568,6 @@ genCCall target dest_regs args = do
     -- deal with static vs dynamic call targets
     (callinsns,cconv) <-
       case target of
-       -- CmmPrim -> ...
         CmmCallee (CmmLit (CmmLabel lbl)) conv
            -> -- ToDo: stdcall arg sizes
              return (unitOL (CALL (Left fn_imm) []), conv)
@@ -1578,6 +1576,9 @@ genCCall target dest_regs args = do
            -> do { (dyn_r, dyn_c) <- getSomeReg expr
                  ; ASSERT( isWord32 (cmmExprType expr) )
                    return (dyn_c `snocOL` CALL (Right dyn_r) [], conv) }
+        CmmPrim _
+            -> panic $ "genCCall: Can't handle CmmPrim call type here, error "
+                        ++ "probably because too many return values."
 
     let        push_code
 #if darwin_TARGET_OS
@@ -1646,9 +1647,10 @@ genCCall target dest_regs args = do
     arg_size :: CmmType -> Int -- Width in bytes
     arg_size ty = widthInBytes (typeWidth ty)
 
+#if darwin_TARGET_OS        
     roundTo a x | x `mod` a == 0 = x
                 | otherwise = x + a - (x `mod` a)
-
+#endif
 
     push_arg :: Bool -> HintedCmmActual {-current argument-}
                     -> NatM InstrBlock  -- code
@@ -1703,9 +1705,13 @@ genCCall (CmmPrim MO_WriteBarrier) _ _ = return nilOL
        -- write barrier compiles to no code on x86/x86-64; 
        -- we keep it this long in order to prevent earlier optimisations.
 
+-- void return type prim op
+genCCall (CmmPrim op) [] args =
+  outOfLineCmmOp op Nothing args
 
-genCCall (CmmPrim op) [CmmHinted r _] args = 
-  outOfLineFloatOp op r args
+-- we only cope with a single result for foreign calls
+genCCall (CmmPrim op) [res] args =
+  outOfLineCmmOp op (Just res) args
 
 genCCall target dest_regs args = do
 
@@ -1749,7 +1755,6 @@ genCCall target dest_regs args = do
     -- deal with static vs dynamic call targets
     (callinsns,cconv) <-
       case target of
-       -- CmmPrim -> ...
         CmmCallee (CmmLit (CmmLabel lbl)) conv
            -> -- ToDo: stdcall arg sizes
              return (unitOL (CALL (Left fn_imm) arg_regs), conv)
@@ -1757,6 +1762,9 @@ genCCall target dest_regs args = do
         CmmCallee expr conv
            -> do (dyn_r, dyn_c) <- getSomeReg expr
                 return (dyn_c `snocOL` CALL (Right dyn_r) arg_regs, conv)
+        CmmPrim _
+            -> panic $ "genCCall: Can't handle CmmPrim call type here, error "
+                        ++ "probably because too many return values."
 
     let
        -- The x86_64 ABI requires us to set %al to the number of SSE2
@@ -1792,7 +1800,7 @@ genCCall target dest_regs args = do
          where 
                rep = localRegType dest
                r_dest = getRegisterReg True (CmmLocal dest)
-       assign_code many = panic "genCCall.assign_code many"
+       assign_code _many = panic "genCCall.assign_code many"
 
     return (load_args_code     `appOL` 
            adjust_rsp          `appOL`
@@ -1834,7 +1842,7 @@ genCCall target dest_regs args = do
            return ((CmmHinted arg hint):args', ars, frs, code')
 
     push_args [] code = return code
-    push_args ((CmmHinted arg hint):rest) code
+    push_args ((CmmHinted arg _):rest) code
        | isFloatType arg_rep = do
         (arg_reg, arg_code) <- getSomeReg arg
          delta <- getDeltaNat
@@ -1867,22 +1875,26 @@ genCCall        = panic "X86.genCCAll: not defined"
 #endif /* x86_64_TARGET_ARCH */
 
 
-
-
-outOfLineFloatOp :: CallishMachOp -> CmmFormal -> HintedCmmActuals -> NatM InstrBlock
-outOfLineFloatOp mop res args
+outOfLineCmmOp :: CallishMachOp -> Maybe HintedCmmFormal -> HintedCmmActuals -> NatM InstrBlock
+outOfLineCmmOp mop res args
   = do
       dflags <- getDynFlagsNat
       targetExpr <- cmmMakeDynamicReference dflags addImportNat CallReference lbl
       let target = CmmCallee targetExpr CCallConv
      
-      stmtToInstrs (CmmCall target [CmmHinted res NoHint] args CmmUnsafe CmmMayReturn)
+      stmtToInstrs (CmmCall target (catMaybes [res]) args' CmmUnsafe CmmMayReturn)
   where
        -- Assume we can call these functions directly, and that they're not in a dynamic library.
        -- TODO: Why is this ok? Under linux this code will be in libm.so
        --       Is is because they're really implemented as a primitive instruction by the assembler??  -- BL 2009/12/31 
        lbl = mkForeignLabel fn Nothing ForeignLabelInThisPackage IsFunction
 
+        args' = case mop of
+                    MO_Memcpy    -> init args
+                    MO_Memset    -> init args
+                    MO_Memmove   -> init args
+                    _            -> args
+
        fn = case mop of
              MO_F32_Sqrt  -> fsLit "sqrtf"
              MO_F32_Sin   -> fsLit "sinf"
@@ -1916,8 +1928,11 @@ outOfLineFloatOp mop res args
              MO_F64_Tanh  -> fsLit "tanh"
              MO_F64_Pwr   -> fsLit "pow"
 
+             MO_Memcpy    -> fsLit "memcpy"
+             MO_Memset    -> fsLit "memset"
+             MO_Memmove   -> fsLit "memmove"
 
-
+              other -> panic $ "outOfLineCmmOp: unmatched op! (" ++ show other ++ ")"
 
 
 -- -----------------------------------------------------------------------------
@@ -1956,10 +1971,7 @@ genSwitch expr ids
     -- conjunction with the hack in PprMach.hs/pprDataItem once
     -- binutils 2.17 is standard.
             code = e_code `appOL` t_code `appOL` toOL [
-                           MOVSxL II32
-                                  (OpAddr (AddrBaseIndex (EABaseReg tableReg)
-                                                         (EAIndex reg wORD_SIZE) (ImmInt 0)))
-                                  (OpReg reg),
+                           MOVSxL II32 op (OpReg reg),
                            ADD (intSize wordWidth) (OpReg reg) (OpReg tableReg),
                            JMP_TBL (OpReg tableReg) ids ReadOnlyData lbl
                   ]
@@ -1975,8 +1987,7 @@ genSwitch expr ids
   = do
         (reg,e_code) <- getSomeReg expr
         lbl <- getNewLabelNat
-        let
-            op = OpAddr (AddrBaseIndex EABaseNone (EAIndex reg wORD_SIZE) (ImmCLbl lbl))
+        let op = OpAddr (AddrBaseIndex EABaseNone (EAIndex reg wORD_SIZE) (ImmCLbl lbl))
             code = e_code `appOL` toOL [
                     JMP_TBL op ids ReadOnlyData lbl
                  ]
@@ -1987,6 +1998,7 @@ generateJumpTableForInstr :: Instr -> Maybe (NatCmmTop Instr)
 generateJumpTableForInstr (JMP_TBL _ ids section lbl) = Just (createJumpTable ids section lbl)
 generateJumpTableForInstr _ = Nothing
 
+createJumpTable :: [Maybe BlockId] -> Section -> CLabel -> GenCmmTop CmmStatic h g
 createJumpTable ids section lbl
     = let jumpTable
             | opt_PIC =
@@ -2142,7 +2154,10 @@ SDM's version of The Rules:
   register happens to be the destination register.
 -}
 
-trivialCode width instr (Just revinstr) (CmmLit lit_a) b
+trivialCode :: Width -> (Operand -> Operand -> Instr)
+            -> Maybe (Operand -> Operand -> Instr)
+            -> CmmExpr -> CmmExpr -> NatM Register
+trivialCode width _ (Just revinstr) (CmmLit lit_a) b
   | is32BitLit lit_a = do
   b_code <- getAnyReg b
   let
@@ -2152,10 +2167,12 @@ trivialCode width instr (Just revinstr) (CmmLit lit_a) b
   -- in
   return (Any (intSize width) code)
 
-trivialCode width instr maybe_revinstr a b
+trivialCode width instr _ a b
   = genTrivialCode (intSize width) instr a b
 
 -- This is re-used for floating pt instructions too.
+genTrivialCode :: Size -> (Operand -> Operand -> Instr)
+               -> CmmExpr -> CmmExpr -> NatM Register
 genTrivialCode rep instr a b = do
   (b_op, b_code) <- getNonClobberedOperand b
   a_code <- getAnyReg a
@@ -2180,12 +2197,15 @@ genTrivialCode rep instr a b = do
   -- in
   return (Any rep code)
 
+regClashesWithOp :: Reg -> Operand -> Bool
 reg `regClashesWithOp` OpReg reg2   = reg == reg2
 reg `regClashesWithOp` OpAddr amode = any (==reg) (addrModeRegs amode)
-reg `regClashesWithOp` _            = False
+_   `regClashesWithOp` _            = False
 
 -----------
 
+trivialUCode :: Size -> (Operand -> Instr)
+             -> CmmExpr -> NatM Register
 trivialUCode rep instr x = do
   x_code <- getAnyReg x
   let
@@ -2196,7 +2216,9 @@ trivialUCode rep instr x = do
 
 -----------
 
-trivialFCode_x87 width instr x y = do
+trivialFCode_x87 :: (Size -> Reg -> Reg -> Reg -> Instr)
+                 -> CmmExpr -> CmmExpr -> NatM Register
+trivialFCode_x87 instr x y = do
   (x_reg, x_code) <- getNonClobberedReg x -- these work for float regs too
   (y_reg, y_code) <- getSomeReg y
   let
@@ -2207,11 +2229,14 @@ trivialFCode_x87 width instr x y = do
        instr size x_reg y_reg dst
   return (Any size code)
 
+trivialFCode_sse2 :: Width -> (Size -> Operand -> Operand -> Instr)
+                  -> CmmExpr -> CmmExpr -> NatM Register
 trivialFCode_sse2 pk instr x y
     = genTrivialCode size (instr size) x y
     where size = floatSize pk
 
 
+trivialUFCode :: Size -> (Reg -> Reg -> Instr) -> CmmExpr -> NatM Register
 trivialUFCode size instr x = do
   (x_reg, x_code) <- getSomeReg x
   let
@@ -2229,7 +2254,9 @@ coerceInt2FP from to x = if_sse2 coerce_sse2 coerce_x87
    coerce_x87 = do
      (x_reg, x_code) <- getSomeReg x
      let
-           opc  = case to of W32 -> GITOF; W64 -> GITOD
+           opc  = case to of W32 -> GITOF; W64 -> GITOD;
+                             n -> panic $ "coerceInt2FP.x87: unhandled width ("
+                                         ++ show n ++ ")"
            code dst = x_code `snocOL` opc x_reg dst
        -- ToDo: works for non-II32 reps?
      return (Any FF80 code)
@@ -2238,6 +2265,8 @@ coerceInt2FP from to x = if_sse2 coerce_sse2 coerce_x87
      (x_op, x_code) <- getOperand x  -- ToDo: could be a safe operand
      let
            opc  = case to of W32 -> CVTSI2SS; W64 -> CVTSI2SD
+                             n -> panic $ "coerceInt2FP.sse: unhandled width ("
+                                         ++ show n ++ ")"
            code dst = x_code `snocOL` opc (intSize from) x_op dst
      -- in
      return (Any (floatSize to) code)
@@ -2251,6 +2280,8 @@ coerceFP2Int from to x = if_sse2 coerceFP2Int_sse2 coerceFP2Int_x87
      (x_reg, x_code) <- getSomeReg x
      let
            opc  = case from of W32 -> GFTOI; W64 -> GDTOI
+                               n -> panic $ "coerceFP2Int.x87: unhandled width ("
+                                           ++ show n ++ ")"
            code dst = x_code `snocOL` opc x_reg dst
        -- ToDo: works for non-II32 reps?
      -- in
@@ -2259,7 +2290,9 @@ coerceFP2Int from to x = if_sse2 coerceFP2Int_sse2 coerceFP2Int_x87
    coerceFP2Int_sse2 = do
      (x_op, x_code) <- getOperand x  -- ToDo: could be a safe operand
      let
-           opc  = case from of W32 -> CVTTSS2SIQ; W64 -> CVTTSD2SIQ
+           opc  = case from of W32 -> CVTTSS2SIQ; W64 -> CVTTSD2SIQ;
+                               n -> panic $ "coerceFP2Init.sse: unhandled width ("
+                                           ++ show n ++ ")"
            code dst = x_code `snocOL` opc (intSize to) x_op dst
      -- in
      return (Any (intSize to) code)
@@ -2272,7 +2305,9 @@ coerceFP2FP to x = do
   use_sse2 <- sse2Enabled
   (x_reg, x_code) <- getSomeReg x
   let
-        opc | use_sse2  = case to of W32 -> CVTSD2SS; W64 -> CVTSS2SD
+        opc | use_sse2  = case to of W32 -> CVTSD2SS; W64 -> CVTSS2SD;
+                                     n -> panic $ "coerceFP2FP: unhandled width ("
+                                                 ++ show n ++ ")"
             | otherwise = GDTOF
         code dst = x_code `snocOL` opc x_reg dst
   -- in
index 92655d1..b9c851a 100644 (file)
@@ -781,6 +781,9 @@ is_G_instr instr
 
 data JumpDest = DestBlockId BlockId | DestImm Imm
 
+getJumpDestBlockId :: JumpDest -> Maybe BlockId
+getJumpDestBlockId (DestBlockId bid) = Just bid
+getJumpDestBlockId _                 = Nothing
 
 canShortcut :: Instr -> Maybe JumpDest
 canShortcut (JXX ALWAYS id)    = Just (DestBlockId id)
index 38b6344..769057a 100644 (file)
@@ -118,9 +118,7 @@ pprData (CmmStaticLit lit)       = pprDataItem lit
 pprGloblDecl :: CLabel -> Doc
 pprGloblDecl lbl
   | not (externallyVisibleCLabel lbl) = empty
-  | otherwise = ptext IF_ARCH_sparc((sLit ".global "),
-                                    (sLit ".globl ")) <>
-                pprCLabel_asm lbl
+  | otherwise = ptext (sLit ".globl ") <> pprCLabel_asm lbl
 
 pprTypeAndSizeDecl :: CLabel -> Doc
 #if elf_OBJ_FORMAT
@@ -492,15 +490,7 @@ pprInstr :: Instr -> Doc
 
 pprInstr (COMMENT _) = empty -- nuke 'em
 {-
-pprInstr (COMMENT s)
-   =  IF_ARCH_alpha( ((<>) (ptext (sLit "\t# ")) (ftext s))
-     ,IF_ARCH_sparc( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_i386( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_x86_64( ((<>) (ptext (sLit "# "))   (ftext s))
-     ,IF_ARCH_powerpc( IF_OS_linux(
-        ((<>) (ptext (sLit "# ")) (ftext s)),
-        ((<>) (ptext (sLit "; ")) (ftext s)))
-     ,)))))
+pprInstr (COMMENT s) = ptext (sLit "# ") <> ftext s
 -}
 pprInstr (DELTA d)
    = pprInstr (COMMENT (mkFastString ("\tdelta = " ++ show d)))
index 21b594e..140ff57 100644 (file)
@@ -13,12 +13,11 @@ import Size
 import Reg
 
 import Outputable
+import Platform
 import Unique
 
-#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
 import UniqFM
 import X86.Regs
-#endif
 
 
 mkVirtualReg :: Unique -> Size -> VirtualReg
@@ -29,52 +28,41 @@ mkVirtualReg u size
         FF80   -> VirtualRegD   u
         _other  -> VirtualRegI   u
 
-
--- reg colors for x86
-#if i386_TARGET_ARCH
 regDotColor :: RealReg -> SDoc
 regDotColor reg
  = let Just    str     = lookupUFM regColors reg
    in  text str
 
 regColors :: UniqFM [Char]
-regColors
- = listToUFM
- $     [ (eax, "#00ff00")
-       , (ebx, "#0000ff")
-       , (ecx, "#00ffff")
-       , (edx, "#0080ff") ]
-        ++ fpRegColors
+regColors = listToUFM (normalRegColors ++ fpRegColors)
 
--- reg colors for x86_64
-#elif x86_64_TARGET_ARCH
-regDotColor :: RealReg -> SDoc
-regDotColor reg
- = let Just    str     = lookupUFM regColors reg
-   in  text str
+-- TODO: We shouldn't be using defaultTargetPlatform here.
+--       We should be passing DynFlags in instead, and looking at
+--       its targetPlatform.
 
-regColors :: UniqFM [Char]
-regColors
- = listToUFM
- $     [ (rax, "#00ff00"), (eax, "#00ff00")
-       , (rbx, "#0000ff"), (ebx, "#0000ff")
-       , (rcx, "#00ffff"), (ecx, "#00ffff")
-       , (rdx, "#0080ff"), (edx, "#00ffff")
-       , (r8,  "#00ff80")
-       , (r9,  "#008080")
-       , (r10, "#0040ff")
-       , (r11, "#00ff40")
-       , (r12, "#008040")
-       , (r13, "#004080")
-       , (r14, "#004040")
-       , (r15, "#002080") ]
-       ++ fpRegColors
-#else
-regDotColor :: Reg -> SDoc
-regDotColor    = panic "not defined"
-#endif
+normalRegColors :: [(Reg,String)]
+normalRegColors = case platformArch defaultTargetPlatform of
+                  ArchX86 -> [ (eax, "#00ff00")
+                             , (ebx, "#0000ff")
+                             , (ecx, "#00ffff")
+                             , (edx, "#0080ff") ]
+                  ArchX86_64 -> [ (rax, "#00ff00"), (eax, "#00ff00")
+                                , (rbx, "#0000ff"), (ebx, "#0000ff")
+                                , (rcx, "#00ffff"), (ecx, "#00ffff")
+                                , (rdx, "#0080ff"), (edx, "#00ffff")
+                                , (r8,  "#00ff80")
+                                , (r9,  "#008080")
+                                , (r10, "#0040ff")
+                                , (r11, "#00ff40")
+                                , (r12, "#008040")
+                                , (r13, "#004080")
+                                , (r14, "#004040")
+                                , (r15, "#002080") ]
+                  ArchPPC     -> panic "X86 normalRegColors ArchPPC"
+                  ArchPPC_64  -> panic "X86 normalRegColors ArchPPC_64"
+                  ArchSPARC   -> panic "X86 normalRegColors ArchSPARC"
+                  ArchUnknown -> panic "X86 normalRegColors ArchUnknown"
 
-#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
 fpRegColors :: [(Reg,String)]
 fpRegColors =
         [ (fake0, "#ff00ff")
@@ -85,4 +73,4 @@ fpRegColors =
        , (fake5, "#5500ff") ]
 
        ++ zip (map regSingle [24..39]) (repeat "red")
-#endif
+
index 101780d..d226cbe 100644 (file)
@@ -277,8 +277,8 @@ gHC_PRIM, gHC_TYPES, gHC_UNIT, gHC_ORDERING, gHC_GENERICS,
     gHC_CLASSES, gHC_BASE, gHC_ENUM, gHC_CSTRING,
     gHC_SHOW, gHC_READ, gHC_NUM, gHC_INTEGER, gHC_INTEGER_TYPE, gHC_LIST,
     gHC_TUPLE, dATA_TUPLE, dATA_EITHER, dATA_STRING, dATA_FOLDABLE, dATA_TRAVERSABLE,
-    gHC_PACK, gHC_CONC, gHC_IO, gHC_IO_Exception,
-    gHC_ST, gHC_ARR, gHC_STABLE, gHC_ADDR, gHC_PTR, gHC_ERR, gHC_REAL,
+    gHC_CONC, gHC_IO, gHC_IO_Exception,
+    gHC_ST, gHC_ARR, gHC_STABLE, gHC_PTR, gHC_ERR, gHC_REAL,
     gHC_FLOAT, gHC_TOP_HANDLER, sYSTEM_IO, dYNAMIC, tYPEABLE, gENERICS,
     dOTNET, rEAD_PREC, lEX, gHC_INT, gHC_WORD, mONAD, mONAD_FIX, mONAD_GROUP, mONAD_ZIP,
     aRROW, cONTROL_APPLICATIVE, gHC_DESUGAR, rANDOM, gHC_EXTS,
@@ -307,14 +307,12 @@ dATA_EITHER       = mkBaseModule (fsLit "Data.Either")
 dATA_STRING    = mkBaseModule (fsLit "Data.String")
 dATA_FOLDABLE  = mkBaseModule (fsLit "Data.Foldable")
 dATA_TRAVERSABLE= mkBaseModule (fsLit "Data.Traversable")
-gHC_PACK       = mkBaseModule (fsLit "GHC.Pack")
 gHC_CONC       = mkBaseModule (fsLit "GHC.Conc")
 gHC_IO         = mkBaseModule (fsLit "GHC.IO")
 gHC_IO_Exception = mkBaseModule (fsLit "GHC.IO.Exception")
 gHC_ST         = mkBaseModule (fsLit "GHC.ST")
 gHC_ARR                = mkBaseModule (fsLit "GHC.Arr")
 gHC_STABLE     = mkBaseModule (fsLit "GHC.Stable")
-gHC_ADDR       = mkBaseModule (fsLit "GHC.Addr")
 gHC_PTR                = mkBaseModule (fsLit "GHC.Ptr")
 gHC_ERR                = mkBaseModule (fsLit "GHC.Err")
 gHC_REAL       = mkBaseModule (fsLit "GHC.Real")
index 7b2502d..e4f97bd 100644 (file)
@@ -31,7 +31,8 @@ data Platform
 --     about what instruction set extensions an architecture might support.
 --
 data Arch
-       = ArchX86
+       = ArchUnknown
+       | ArchX86
        | ArchX86_64
        | ArchPPC
        | ArchPPC_64
@@ -80,7 +81,7 @@ defaultTargetArch     = ArchPPC_64
 #elif sparc_TARGET_ARCH
 defaultTargetArch      = ArchSPARC
 #else
-#error "Platform.buildArch: undefined"
+defaultTargetArch      = ArchUnknown
 #endif
 
 
index 5014fd6..780a07f 100644 (file)
@@ -1,24 +1,24 @@
 
 module Vectorise.Env (
-       Scope(..),
-
-       -- * Local Environments
-       LocalEnv(..),
-       emptyLocalEnv,
-       
-       -- * Global Environments
-       GlobalEnv(..),
-       initGlobalEnv,
-       extendImportedVarsEnv,
-       extendScalars,
-       setFamEnv,
-        extendFamEnv,
-       extendTyConsEnv,
-       extendDataConsEnv,
-       extendPAFunsEnv,
-       setPRFunsEnv,
-       setBoxedTyConsEnv,
-       updVectInfo
+  Scope(..),
+
+  -- * Local Environments
+  LocalEnv(..),
+  emptyLocalEnv,
+
+  -- * Global Environments
+  GlobalEnv(..),
+  initGlobalEnv,
+  extendImportedVarsEnv,
+  extendScalars,
+  setFamEnv,
+  extendFamEnv,
+  extendTyConsEnv,
+  extendDataConsEnv,
+  extendPAFunsEnv,
+  setPRFunsEnv,
+  setBoxedTyConsEnv,
+  modVectInfo
 ) where
 
 import HscTypes
@@ -31,6 +31,7 @@ import DataCon
 import VarEnv
 import VarSet
 import Var
+import NameSet
 import Name
 import NameEnv
 import FastString
@@ -38,8 +39,8 @@ import FastString
 
 -- | Indicates what scope something (a variable) is in.
 data Scope a b 
-       = Global a 
-       | Local  b
+        = Global a 
+        | Local  b
 
 
 -- LocalEnv -------------------------------------------------------------------
@@ -71,61 +72,68 @@ emptyLocalEnv = LocalEnv {
 
 
 -- GlobalEnv ------------------------------------------------------------------
--- | The global environment.
---      These are things the exist at top-level.
+
+-- |The global environment: entities that exist at top-level.
+--
 data GlobalEnv 
-        = GlobalEnv {
-        -- | Mapping from global variables to their vectorised versions â€” aka the /vectorisation
-        --   map/.
-          global_vars           :: VarEnv Var
-
-        -- | Mapping from global variables that have a vectorisation declaration to the right-hand
-        --   side of that declaration and its type.  This mapping only applies to non-scalar
-        --   vectorisation declarations.  All variables with a scalar vectorisation declaration are
-        --   mentioned in 'global_scalars'.
+        = GlobalEnv
+        { global_vars           :: VarEnv Var
+          -- ^Mapping from global variables to their vectorised versions â€” aka the /vectorisation
+          -- map/.
+
         , global_vect_decls     :: VarEnv (Type, CoreExpr)
+          -- ^Mapping from global variables that have a vectorisation declaration to the right-hand
+          -- side of that declaration and its type.  This mapping only applies to non-scalar
+          -- vectorisation declarations.  All variables with a scalar vectorisation declaration are
+          -- mentioned in 'global_scalars_vars'.
+
+        , global_scalar_vars    :: VarSet
+          -- ^Purely scalar variables. Code which mentions only these variables doesn't have to be
+          -- lifted.  This includes variables from the current module that have a scalar
+          -- vectorisation declaration and those that the vectoriser determines to be scalar.
 
-        -- | Purely scalar variables. Code which mentions only these variables doesn't have to be
-        --   lifted.  This includes variables from the current module that have a scalar
-        --   vectorisation declaration and those that the vectoriser determines to be scalar.
-        , global_scalars        :: VarSet
+        , global_scalar_tycons  :: NameSet
+          -- ^Type constructors whose values can only contain scalar data.  Scalar code may only
+          -- operate on such data.
 
-        -- | Exported variables which have a vectorised version.
-        , global_exported_vars :: VarEnv (Var, Var)
+        , global_exported_vars  :: VarEnv (Var, Var)
+          -- ^Exported variables which have a vectorised version.
 
-        -- | Mapping from TyCons to their vectorised versions.
-        --   TyCons which do not have to be vectorised are mapped to themselves.
-        , global_tycons                :: NameEnv TyCon
+        , global_tycons         :: NameEnv TyCon
+          -- ^Mapping from TyCons to their vectorised versions.
+          -- TyCons which do not have to be vectorised are mapped to themselves.
 
-        -- | Mapping from DataCons to their vectorised versions.
         , global_datacons       :: NameEnv DataCon
+          -- ^Mapping from DataCons to their vectorised versions.
 
-        -- | Mapping from TyCons to their PA dfuns.
         , global_pa_funs        :: NameEnv Var
+          -- ^Mapping from TyCons to their PA dfuns.
 
-        -- | Mapping from TyCons to their PR dfuns.
-        , global_pr_funs       :: NameEnv Var
+        , global_pr_funs        :: NameEnv Var
+          -- ^Mapping from TyCons to their PR dfuns.
 
-        -- | Mapping from unboxed TyCons to their boxed versions.
-        , global_boxed_tycons  :: NameEnv TyCon
+        , global_boxed_tycons   :: NameEnv TyCon
+          -- ^Mapping from unboxed TyCons to their boxed versions.
 
-        -- | External package inst-env & home-package inst-env for class instances.
-        , global_inst_env      :: (InstEnv, InstEnv)
+        , global_inst_env       :: (InstEnv, InstEnv)
+          -- ^External package inst-env & home-package inst-env for class instances.
 
-        -- | External package inst-env & home-package inst-env for family instances.
-        , global_fam_inst_env  :: FamInstEnvs
+        , global_fam_inst_env   :: FamInstEnvs
+          -- ^External package inst-env & home-package inst-env for family instances.
 
-        -- | Hoisted bindings.
-        , global_bindings      :: [(Var, CoreExpr)]
+        , global_bindings       :: [(Var, CoreExpr)]
+          -- ^Hoisted bindings.
         }
 
--- | Create an initial global environment
+-- |Create an initial global environment.
+--
 initGlobalEnv :: VectInfo -> [CoreVect] -> (InstEnv, InstEnv) -> FamInstEnvs -> GlobalEnv
 initGlobalEnv info vectDecls instEnvs famInstEnvs
   = GlobalEnv 
   { global_vars          = mapVarEnv snd $ vectInfoVar info
   , global_vect_decls    = mkVarEnv vects
-  , global_scalars       = mkVarSet scalars
+  , global_scalar_vars   = vectInfoScalarVars   info `extendVarSetList` scalars
+  , global_scalar_tycons = vectInfoScalarTyCons info
   , global_exported_vars = emptyVarEnv
   , global_tycons        = mapNameEnv snd $ vectInfoTyCon info
   , global_datacons      = mapNameEnv snd $ vectInfoDataCon info
@@ -142,71 +150,80 @@ initGlobalEnv info vectDecls instEnvs famInstEnvs
 
 
 -- Operators on Global Environments -------------------------------------------
--- | Extend the list of global variables in an environment.
+
+-- |Extend the list of global variables in an environment.
+--
 extendImportedVarsEnv :: [(Var, Var)] -> GlobalEnv -> GlobalEnv
 extendImportedVarsEnv ps genv
-  = genv { global_vars  = extendVarEnvList (global_vars genv) ps }
+  = genv { global_vars = extendVarEnvList (global_vars genv) ps }
 
--- | Extend the set of scalar variables in an environment.
+-- |Extend the set of scalar variables in an environment.
+--
 extendScalars :: [Var] -> GlobalEnv -> GlobalEnv
 extendScalars vs genv
-  = genv { global_scalars = extendVarSetList (global_scalars genv) vs }
+  = genv { global_scalar_vars = extendVarSetList (global_scalar_vars genv) vs }
 
--- | Set the list of type family instances in an environment.
+-- |Set the list of type family instances in an environment.
+--
 setFamEnv :: FamInstEnv -> GlobalEnv -> GlobalEnv
 setFamEnv l_fam_inst genv
   = genv { global_fam_inst_env = (g_fam_inst, l_fam_inst) }
   where (g_fam_inst, _) = global_fam_inst_env genv
 
+-- |Extend the list of type family instances.
+--
 extendFamEnv :: [FamInst] -> GlobalEnv -> GlobalEnv
 extendFamEnv new genv
   = genv { global_fam_inst_env = (g_fam_inst, extendFamInstEnvList l_fam_inst new) }
   where (g_fam_inst, l_fam_inst) = global_fam_inst_env genv
 
-
--- | Extend the list of type constructors in an environment.
+-- |Extend the list of type constructors in an environment.
+--
 extendTyConsEnv :: [(Name, TyCon)] -> GlobalEnv -> GlobalEnv
 extendTyConsEnv ps genv
   = genv { global_tycons = extendNameEnvList (global_tycons genv) ps }
 
-
--- | Extend the list of data constructors in an environment.
+-- |Extend the list of data constructors in an environment.
+--
 extendDataConsEnv :: [(Name, DataCon)] -> GlobalEnv -> GlobalEnv
 extendDataConsEnv ps genv
   = genv { global_datacons = extendNameEnvList (global_datacons genv) ps }
 
-
--- | Extend the list of PA functions in an environment.
+-- |Extend the list of PA functions in an environment.
+--
 extendPAFunsEnv :: [(Name, Var)] -> GlobalEnv -> GlobalEnv
 extendPAFunsEnv ps genv
   = genv { global_pa_funs = extendNameEnvList (global_pa_funs genv) ps }
 
-
--- | Set the list of PR functions in an environment.
+-- |Set the list of PR functions in an environment.
+--
 setPRFunsEnv :: [(Name, Var)] -> GlobalEnv -> GlobalEnv
 setPRFunsEnv ps genv
   = genv { global_pr_funs = mkNameEnv ps }
 
-
--- | Set the list of boxed type constructor in an environment.
+-- |Set the list of boxed type constructor in an environment.
+--
 setBoxedTyConsEnv :: [(Name, TyCon)] -> GlobalEnv -> GlobalEnv
 setBoxedTyConsEnv ps genv
   = genv { global_boxed_tycons = mkNameEnv ps }
 
-
--- | TODO: What is this for?
-updVectInfo :: GlobalEnv -> TypeEnv -> VectInfo -> VectInfo
-updVectInfo env tyenv info
+-- |Compute vectorisation information that goes into 'ModGuts' (and is stored in interface files).
+-- The incoming 'vectInfo' is that from the 'HscEnv' and 'EPS'.  The outgoing one contains only the
+-- definitions for the currently compiled module.
+--
+modVectInfo :: GlobalEnv -> TypeEnv -> VectInfo -> VectInfo
+modVectInfo env tyenv info
   = info 
-    { vectInfoVar     = global_exported_vars env
-    , vectInfoTyCon   = mk_env typeEnvTyCons global_tycons
-    , vectInfoDataCon = mk_env typeEnvDataCons global_datacons
-    , vectInfoPADFun  = mk_env typeEnvTyCons global_pa_funs
+    { vectInfoVar          = global_exported_vars env
+    , vectInfoTyCon        = mk_env typeEnvTyCons global_tycons
+    , vectInfoDataCon      = mk_env typeEnvDataCons global_datacons
+    , vectInfoPADFun       = mk_env typeEnvTyCons global_pa_funs
+    , vectInfoScalarVars   = global_scalar_vars   env `minusVarSet`  vectInfoScalarVars   info
+    , vectInfoScalarTyCons = global_scalar_tycons env `minusNameSet` vectInfoScalarTyCons info
     }
   where
     mk_env from_tyenv from_env 
-       = mkNameEnv [(name, (from,to))
-                        | from     <- from_tyenv tyenv
-                        , let name =  getName from
-                        , Just to  <- [lookupNameEnv (from_env env) name]]
-
+      = mkNameEnv [(name, (from,to))
+                  | from     <- from_tyenv tyenv
+                  , let name =  getName from
+                  , Just to  <- [lookupNameEnv (from_env env) name]]
index 5fcd2ac..e2933cd 100644 (file)
@@ -1,27 +1,26 @@
 
 module Vectorise.Monad (
-       module Vectorise.Monad.Base,
-       module Vectorise.Monad.Naming,
-       module Vectorise.Monad.Local,
-       module Vectorise.Monad.Global,
-       module Vectorise.Monad.InstEnv,
-       initV,
-
-       -- * Builtins
-       liftBuiltinDs,
-       builtin,
-       builtins,
-       
-       -- * Variables
-       lookupVar,
-       maybeCantVectoriseVarM,
-       dumpVar,
-       addGlobalScalar, 
-    deleteGlobalScalar,
+  module Vectorise.Monad.Base,
+  module Vectorise.Monad.Naming,
+  module Vectorise.Monad.Local,
+  module Vectorise.Monad.Global,
+  module Vectorise.Monad.InstEnv,
+  initV,
+
+  -- * Builtins
+  liftBuiltinDs,
+  builtin,
+  builtins,
+  
+  -- * Variables
+  lookupVar,
+  maybeCantVectoriseVarM,
+  dumpVar,
+  addGlobalScalar, 
     
-       -- * Primitives
-       lookupPrimPArray,
-       lookupPrimMethod
+  -- * Primitives
+  lookupPrimPArray,
+  lookupPrimMethod
 ) where
 
 import Vectorise.Monad.Base
@@ -98,7 +97,7 @@ initV hsc_env guts info thing_inside
                No           -> return Nothing
            } }
 
-    new_info genv = updVectInfo genv (mg_types guts) info
+    new_info genv = modVectInfo genv (mg_types guts) info
 
     selectBackendErr = sLit "To use -fvectorise select a DPH backend with -fdph-par or -fdph-seq"
 
@@ -120,7 +119,7 @@ builtins f = VM $ \bi genv lenv -> return (Yes genv lenv (`f` bi))
 
 -- Var ------------------------------------------------------------------------
 -- | Lookup the vectorised and\/or lifted versions of this variable.
---     If it's in the global environment we get the vectorised version.
+--  If it's in the global environment we get the vectorised version.
 --      If it's in the local environment we get both the vectorised and lifted version.
 lookupVar :: Var -> VM (Scope Var (Var, Var))
 lookupVar v
@@ -140,29 +139,24 @@ maybeCantVectoriseVarM v p
 
 dumpVar :: Var -> a
 dumpVar var
-       | Just _                <- isClassOpId_maybe var
-       = cantVectorise "ClassOpId not vectorised:" (ppr var)
+  | Just _    <- isClassOpId_maybe var
+  = cantVectorise "ClassOpId not vectorised:" (ppr var)
 
-       | otherwise
-       = cantVectorise "Variable not vectorised:" (ppr var)
+  | otherwise
+  = cantVectorise "Variable not vectorised:" (ppr var)
 
 
--- local scalars --------------------------------------------------------------
+-- Global scalars --------------------------------------------------------------
 
 addGlobalScalar :: Var -> VM ()
 addGlobalScalar var 
   = do { traceVt "addGlobalScalar" (ppr var)
-       ; updGEnv $ \env -> env{global_scalars = extendVarSet (global_scalars env) var}
-     }
-     
-deleteGlobalScalar :: Var -> VM ()
-deleteGlobalScalar var 
-  = do { traceVt "deleteGlobalScalar" (ppr var)
-       ; updGEnv $ \env -> env{global_scalars = delVarSet (global_scalars env) var}
-     }
+       ; updGEnv $ \env -> env{global_scalar_vars = extendVarSet (global_scalar_vars env) var}
+       }
      
      
 -- Primitives -----------------------------------------------------------------
+
 lookupPrimPArray :: TyCon -> VM (Maybe TyCon)
 lookupPrimPArray = liftBuiltinDs . primPArray
 
index ae68ffb..632845f 100644 (file)
@@ -73,19 +73,24 @@ defGlobalVar v v' = updGEnv $ \env ->
 
 
 -- Vectorisation declarations -------------------------------------------------
--- | Check whether a variable has a (non-scalar) vectorisation declaration.
+
+-- |Check whether a variable has a (non-scalar) vectorisation declaration.
+--
 lookupVectDecl :: Var -> VM (Maybe (Type, CoreExpr))
 lookupVectDecl var = readGEnv $ \env -> lookupVarEnv (global_vect_decls env) var
 
 
 -- Scalars --------------------------------------------------------------------
--- | Get the set of global scalar variables.
+
+-- |Get the set of global scalar variables.
+--
 globalScalars :: VM VarSet
-globalScalars = readGEnv global_scalars
+globalScalars = readGEnv global_scalar_vars
 
--- | Check whether a given variable is in the set of global scalar variables.
+-- |Check whether a given variable is in the set of global scalar variables.
+--
 isGlobalScalar :: Var -> VM Bool
-isGlobalScalar var = readGEnv $ \env -> elemVarSet var (global_scalars env)
+isGlobalScalar var = readGEnv $ \env -> elemVarSet var (global_scalar_vars env)
 
 
 -- TyCons ---------------------------------------------------------------------
index 2de4d8a..b634bbf 100644 (file)
@@ -782,7 +782,7 @@ fi
 dnl ** check whether this machine has BFD and liberty installed (used for debugging)
 dnl    the order of these tests matters: bfd needs liberty
 AC_CHECK_LIB(iberty, xmalloc)
-AC_CHECK_LIB(bfd,    bfd_init)
+AC_CHECK_LIB(bfd,    bfd_uncompress_section_contents)
 
 dnl ################################################################
 dnl Check for libraries
index 0e6ffb4..4d3e299 100644 (file)
@@ -300,7 +300,7 @@ import SpecConstr
         <para>
           The RTS now exports a function <literal>setKeepCAFs</literal>
           which is important when loading Haskell DLLs dynamically, as
-          a DLL may refer to CAFs that hae already been GCed.
+          a DLL may refer to CAFs that have already been GCed.
         </para>
       </listitem>
 
index 803f9a8..9b167cc 100644 (file)
@@ -5,7 +5,7 @@
   <sect1 id="vs-Haskell-defn">
     <title>Haskell&nbsp;98 vs.&nbsp;Glasgow Haskell: language non-compliance
 </title>
-    
+
     <indexterm><primary>GHC vs the Haskell 98 language</primary></indexterm>
     <indexterm><primary>Haskell 98 language vs GHC</primary></indexterm>
 
 
   <sect2 id="haskell98-divergence">
     <title>Divergence from Haskell&nbsp;98</title>
-    
-      
+
+
     <sect3 id="infelicities-lexical">
       <title>Lexical syntax</title>
-      
+
       <itemizedlist>
        <listitem>
          <para>Certain lexical rules regarding qualified identifiers
        </listitem>
       </itemizedlist>
     </sect3>
-      
+
       <sect3 id="infelicities-syntax">
        <title>Context-free syntax</title>
-       
+
        <itemizedlist>
          <listitem>
            <para>GHC is a little less strict about the layout rule when used
@@ -101,14 +101,14 @@ main = do args &lt;- getArgs
       <option>-XNoMonoPatBinds</option>.  See <xref
       linkend="options-language" />.</para>
     </sect3>
-      
+
       <sect3 id="infelicities-Modules">
        <title>Module system and interface files</title>
-       
+
        <para>GHC requires the use of <literal>hs-boot</literal>
          files to cut the recursive loops among mutually recursive modules
          as described in <xref linkend="mutual-recursion"/>.  This more of an infelicity
-           than a bug: the Haskell Report says 
+           than a bug: the Haskell Report says
          (<ulink url="http://haskell.org/onlinereport/modules.html#sect5.7">Section 5.7</ulink>) "Depending on the Haskell
        implementation used, separate compilation of mutually
        recursive modules may require that imported modules contain
@@ -141,7 +141,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
          </listitem>
        </varlistentry>
       </variablelist>
-      
+
     </sect3>
 
       <sect3 id="infelicities-Prelude">
@@ -251,7 +251,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
          the <literal>Int</literal> type.</para>
 
          <para>The <literal>fromInteger</literal><indexterm><primary><literal>fromInteger</literal></primary>
-           </indexterm>function (and hence
+           </indexterm> function (and hence
          also <literal>fromIntegral</literal><indexterm><primary><literal>fromIntegral</literal></primary>
            </indexterm>) is a special case when
          converting to <literal>Int</literal>.  The value of
@@ -265,7 +265,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
 
 
           <para>Negative literals, such as <literal>-3</literal>, are
-             specified by (a careful reading of) the Haskell Report as 
+             specified by (a careful reading of) the Haskell Report as
              meaning <literal>Prelude.negate (Prelude.fromInteger 3)</literal>.
             So <literal>-2147483648</literal> means <literal>negate (fromInteger 2147483648)</literal>.
             Since <literal>fromInteger</literal> takes the lower 32 bits of the representation,
@@ -302,12 +302,12 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
        </listitem>
       </varlistentry>
     </variablelist>
-      
+
     </sect2>
 
   <sect2 id="ffi-divergence">
     <title>Divergence from the FFI specification</title>
-    
+
     <variablelist>
       <varlistentry>
         <term><literal>hs_init()</literal> not allowed
@@ -321,7 +321,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
       </varlistentry>
     </variablelist>
   </sect2>
-    
+
   </sect1>
 
 
@@ -348,7 +348,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
       </listitem>
 
       <listitem>
-       <para>GHC does not allow you to have a data type with a context 
+       <para>GHC does not allow you to have a data type with a context
           that mentions type variables that are not data type parameters.
          For example:
 <programlisting>
@@ -369,10 +369,10 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
         using the standard way to encode recursion via a data type:</para>
 <programlisting>
   data U = MkU (U -> Bool)
-       
+
   russel :: U -> Bool
   russel u@(MkU p) = not $ p u
-  
+
   x :: Bool
   x = russel (MkU russel)
 </programlisting>
@@ -414,7 +414,7 @@ checking for duplicates.  The reason for this is efficiency, pure and simple.
         module (whatever that is).</para>
       </listitem>
 
-      <listitem> 
+      <listitem>
       <para>On Windows, there's a GNU ld/BFD bug
       whereby it emits bogus PE object files that have more than
       0xffff relocations. When GHCi tries to load a package affected by this
index 9c48f7d..fe98537 100644 (file)
@@ -8,10 +8,10 @@
 
   <sect2 id="dumping-output">
     <title>Dumping out compiler intermediate structures</title>
-    
+
     <indexterm><primary>dumping GHC intermediates</primary></indexterm>
     <indexterm><primary>intermediate passes, output</primary></indexterm>
-    
+
     <variablelist>
       <varlistentry>
        <term>
                 <indexterm><primary><option>-ddump-rules</option></primary></indexterm>
              </term>
              <listitem>
-               <para>dumps all rewrite rules specified in this module; 
+               <para>dumps all rewrite rules specified in this module;
                       see <xref linkend="controlling-rules"/>.
                 </para>
              </listitem>
          </variablelist>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>
           <option>-ddump-simpl-phases</option>:
         </term>
        <listitem>
          <para>Make the interface loader be *real* chatty about what it is
-       upto.</para>
+       up to.</para>
        </listitem>
       </varlistentry>
 
         </term>
   <listitem>
     <para>Make the type checker be *real* chatty about what it is
-  upto.</para>
+  up to.</para>
   </listitem>
       </varlistentry>
 
         </term>
   <listitem>
     <para>Make the vectoriser be *real* chatty about what it is
-  upto.</para>
+  up to.</para>
   </listitem>
       </varlistentry>
 
         </term>
        <listitem>
          <para>Make the renamer be *real* chatty about what it is
-       upto.</para>
+       up to.</para>
        </listitem>
       </varlistentry>
 
 
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>
           <option>-dshow-passes</option>
           <indexterm><primary><option>-dppr-case-as-let</option></primary></indexterm>
         </term>
        <listitem>
-         <para>Print single alternative case expressions as though they were strict 
+         <para>Print single alternative case expressions as though they were strict
                let expressions. This is helpful when your code does a lot of unboxing.</para>
        </listitem>
       </varlistentry>
           <indexterm><primary><option>-dsuppress-all</option></primary></indexterm>
         </term>
        <listitem>
-         <para>Suppress everything that can be suppressed, except for unique ids as this often 
+         <para>Suppress everything that can be suppressed, except for unique ids as this often
                makes the printout ambiguous. If you just want to see the overall structure of
                the code, then start here.</para>
        </listitem>
           <indexterm><primary><option>-dsuppress-uniques</option></primary></indexterm>
         </term>
        <listitem>
-         <para>Suppress the printing of uniques. This may make 
+         <para>Suppress the printing of uniques. This may make
          the printout ambiguous (e.g. unclear where an occurrence of 'x' is bound), but
          it makes the output of two compiler runs have many fewer gratuitous differences,
            so you can realistically apply <command>diff</command>.  Once <command>diff</command>
         </term>
        <listitem>
          <para>Suppress extended information about identifiers where they are bound. This includes
-               strictness information and inliner templates. Using this flag can cut the size 
+               strictness information and inliner templates. Using this flag can cut the size
                of the core dump in half, due to the lack of inliner templates</para>
        </listitem>
       </varlistentry>
index 97a2378..2fef135 100644 (file)
@@ -51,7 +51,7 @@ Foreign function interface (FFI)
        calling arbitrary IO procedures in some part of the program.)
 </para>
 <para>The Haskell FFI already specifies that arguments and results of
-foreign imports and exports will be automatically unwrapped if they are 
+foreign imports and exports will be automatically unwrapped if they are
 newtypes (Section 3.2 of the FFI addendum).  GHC extends the FFI by automatically unwrapping any newtypes that
 wrap the IO monad itself.
 More precisely, wherever the FFI specification requires an IO type, GHC will
@@ -96,7 +96,7 @@ OK:
           the time, then the program will not respond to the user
           interrupt.
         </para>
-        
+
         <para>
           The problem is that it is not possible in general to
           interrupt a foreign call safely.  However, GHC does provide
@@ -106,11 +106,11 @@ OK:
           of <literal>safe</literal> or <literal>unsafe</literal>:
 
 <programlisting>
-foreign import ccall interruptible 
+foreign import ccall interruptible
    "sleep" :: CUint -> IO CUint
 </programlisting>
 
-          <literal>interruptble</literal> behaves exactly as
+          <literal>interruptible</literal> behaves exactly as
           <literal>safe</literal>, except that when
           a <literal>throwTo</literal> is directed at a thread in an
           interruptible foreign call, an OS-specific mechanism will be
@@ -174,7 +174,7 @@ foreign import ccall interruptible
       </indexterm>
 
       <para>When GHC compiles a module (say <filename>M.hs</filename>)
-      which uses <literal>foreign export</literal> or 
+      which uses <literal>foreign export</literal> or
       <literal>foreign import "wrapper"</literal>, it generates two
       additional files, <filename>M_stub.c</filename> and
       <filename>M_stub.h</filename>.  GHC will automatically compile
@@ -223,7 +223,7 @@ extern HsInt foo(HsInt a0);</programlisting>
         &ndash;&ndash;make</literal>, as GHC will automatically link in the
         correct bits).</para>
 
-      <sect3 id="using-own-main"> 
+      <sect3 id="using-own-main">
        <title>Using your own <literal>main()</literal></title>
 
        <para>Normally, GHC's runtime system provides a
@@ -371,7 +371,7 @@ int main(int argc, char *argv[])
       </sect3>
 
     </sect2>
-    
+
     <sect2 id="glasgow-foreign-headers">
       <title>Using header files</title>
 
@@ -396,7 +396,7 @@ int main(int argc, char *argv[])
         available when compiling an inlined version of a foreign call,
         so the compiler is free to inline foreign calls in any
         context.</para>
-        
+
       <para>The <literal>-&num;include</literal> option is now
         deprecated, and the <literal>include-files</literal> field
         in a Cabal package specification is ignored.</para>
@@ -481,17 +481,17 @@ int main(int argc, char *argv[])
        </varlistentry>
       </variablelist>
     </sect2>
-    
+
     <sect2 id="ffi-threads">
       <title>Multi-threading and the FFI</title>
-      
+
       <para>In order to use the FFI in a multi-threaded setting, you must
         use the <option>-threaded</option> option
         (see <xref linkend="options-linker" />).</para>
-        
+
       <sect3>
         <title>Foreign imports and multi-threading</title>
-        
+
         <para>When you call a <literal>foreign import</literal>ed
           function that is annotated as <literal>safe</literal> (the
           default), and the program was linked
@@ -500,7 +500,7 @@ int main(int argc, char *argv[])
           program was linked without <option>-threaded</option>,
           then the other Haskell threads will be blocked until the
           call returns.</para>
-        
+
         <para>This means that if you need to make a foreign call to
           a function that takes a long time or blocks indefinitely,
           then you should mark it <literal>safe</literal> and
@@ -540,7 +540,7 @@ int main(int argc, char *argv[])
       <sect3 id="haskell-threads-and-os-threads">
         <title>The relationship between Haskell threads and OS
           threads</title>
-        
+
         <para>Normally there is no fixed relationship between Haskell
           threads and OS threads.  This means that when you make a
           foreign call, that call may take place in an unspecified OS
@@ -560,10 +560,10 @@ int main(int argc, char *argv[])
           for the <ulink url="&libraryBaseLocation;/Control-Concurrent.html"><literal>Control.Concurrent</literal></ulink>
           module.</para>
       </sect3>
-      
+
       <sect3>
         <title>Foreign exports and multi-threading</title>
-        
+
         <para>When the program is linked
           with <option>-threaded</option>, then you may
           invoke <literal>foreign export</literal>ed functions from
@@ -612,7 +612,7 @@ int main(int argc, char *argv[])
           isn't necessary to ensure that the threads have exited first.
           (Unofficially, if you want to use this fast and loose version of
           <literal>hs_exit()</literal>, then call
-          <literal>shutdownHaskellAndExit()</literal> instead).</para> 
+          <literal>shutdownHaskellAndExit()</literal> instead).</para>
       </sect3>
     </sect2>
 
index bfc28d8..3e70be9 100644 (file)
     </sect2>
     <sect2>
       <title>Which phases to run</title>
-      
+
       <para><xref linkend="options-order"/></para>
 
       <informaltable>
 
      <sect2>
       <title>Alternative modes of operation</title>
-      
+
       <para><xref linkend="modes"/></para>
 
       <informaltable>
 
     <sect2>
       <title>Redirecting output</title>
-      
+
       <para><xref linkend="options-output"/></para>
 
       <informaltable>
 
     <sect2>
       <title>Keeping intermediate files</title>
-      
+
       <para><xref linkend="keeping-intermediates"/></para>
-      
+
       <informaltable>
        <tgroup cols="4" align="left" colsep="1" rowsep="1">
          <thead>
 
     <sect2>
       <title>Temporary files</title>
-      
+
       <para><xref linkend="temp-files"/></para>
 
       <informaltable>
        </tgroup>
       </informaltable>
     </sect2>
-    
+
     <sect2>
       <title>Recompilation checking</title>
 
 
     <sect2 id="interactive-mode-options">
       <title>Interactive-mode options</title>
-      
+
       <para><xref linkend="ghci-dot-files"/></para>
 
       <informaltable>
              <entry><link linkend="breakpoints">Enable usage of Show instances in <literal>:print</literal></link></entry>
              <entry>dynamic</entry>
              <entry><option>-fno-print-evld-with-show</option></entry>
-           </row>          
+           </row>
            <row>
              <entry><option>-fprint-bind-result</option></entry>
              <entry><link linkend="ghci-stmts">Turn on printing of binding results in GHCi</link></entry>
     <sect2>
       <title>Language options</title>
 
-      <para>Language options can be enabled either by a command-line option 
+      <para>Language options can be enabled either by a command-line option
       <option>-Xblah</option>, or by a <literal>{-# LANGUAGE blah #-}</literal>
       pragma in the file itself.  See <xref linkend="options-language"/></para>
 
            </row>
            <row>
              <entry><option>-XIncoherentInstances</option></entry>
-             <entry>Enable <link linkend="instance-overlap">incoherent instances</link>.  
+             <entry>Enable <link linkend="instance-overlap">incoherent instances</link>.
              Implies <option>-XOverlappingInstances</option> </entry>
              <entry>dynamic</entry>
              <entry><option>-XNoIncoherentInstances</option></entry>
            </row>
            <row>
              <entry><option>-XDisambiguateRecordFields</option></entry>
-             <entry>Enable <link linkend="disambiguate-fields">record 
+             <entry>Enable <link linkend="disambiguate-fields">record
              field disambiguation</link></entry>
              <entry>dynamic</entry>
              <entry><option>-XNoDisambiguateRecordFields</option></entry>
            </row>
            <row>
              <entry><option>-XTemplateHaskell</option></entry>
-             <entry>Enable <link linkend="template-haskell">Template Haskell</link>. 
+             <entry>Enable <link linkend="template-haskell">Template Haskell</link>.
                No longer implied by <option>-fglasgow-exts</option>.</entry>
              <entry>dynamic</entry>
              <entry><option>-XNoTemplateHaskell</option></entry>
              <entry><option>-XNoMagicHash</option></entry>
            </row>
            <row>
-             <entry><option>-XExplicitForALl</option></entry>
+             <entry><option>-XExplicitForAll</option></entry>
              <entry>Enable <link linkend="explicit-foralls">explicit universal quantification</link>.
               Implied by <option>-XScopedTypeVariables</option>,
            <option>-XLiberalTypeSynonyms</option>,
 
     <sect2>
       <title>Warnings</title>
-      
+
       <para><xref linkend="options-sanity"/></para>
 
     <informaltable>
 
          <row>
            <entry><option>-fwarn-missing-import-lists</option></entry>
-           <entry>warn when an import declaration does not explicitly 
+           <entry>warn when an import declaration does not explicitly
                    list all the names brought into scope</entry>
            <entry>dynamic</entry>
            <entry><option>-fnowarn-missing-import-lists</option></entry>
          </tbody>
        </tgroup>
       </informaltable>
-             
+
     </sect2>
     <sect2>
       <title>Individual optimisations</title>
@@ -1494,7 +1494,7 @@ phase <replaceable>n</replaceable></entry>
 
            <row>
              <entry><option>-fspec-constr-count</option>=<replaceable>n</replaceable></entry>
-             <entry>Set to <replaceable>n</replaceable> (default: 3) the maximum number of 
+             <entry>Set to <replaceable>n</replaceable> (default: 3) the maximum number of
                specialisations that will be created for any one function
                by the SpecConstr transformation</entry>
              <entry>static</entry>
@@ -1584,7 +1584,7 @@ phase <replaceable>n</replaceable></entry>
 
     <sect2>
       <title>Profiling options</title>
-      
+
       <para><xref linkend="profiling"/></para>
 
       <informaltable>
@@ -1637,7 +1637,7 @@ phase <replaceable>n</replaceable></entry>
 
     <sect2>
       <title>Program coverage options</title>
-      
+
       <para><xref linkend="hpc"/></para>
 
       <informaltable>
@@ -2156,7 +2156,7 @@ phase <replaceable>n</replaceable></entry>
 
     <sect2>
       <title>Platform-specific options</title>
-      
+
       <para><xref linkend="options-platform"/></para>
 
       <informaltable>
@@ -2189,7 +2189,7 @@ phase <replaceable>n</replaceable></entry>
       </informaltable>
     </sect2>
 
-         
+
     <sect2>
       <title>External core file options</title>
 
@@ -2605,7 +2605,7 @@ phase <replaceable>n</replaceable></entry>
        </tgroup>
       </informaltable>
     </sect2>
-      
+
     <sect2>
       <title>Misc compiler options</title>
 
@@ -2646,7 +2646,7 @@ phase <replaceable>n</replaceable></entry>
            </row>
            <row>
              <entry><option>-fno-ghci-sandbox</option></entry>
-             <entry>Turn off the GHCi sandbox. Means computations are run in teh main thread, rather than a forked thread.</entry>
+             <entry>Turn off the GHCi sandbox. Means computations are run in the main thread, rather than a forked thread.</entry>
              <entry>dynamic</entry>
              <entry>-</entry>
            </row>
index 7c3fed2..72481eb 100644 (file)
@@ -4,7 +4,7 @@
   <indexterm><primary>GHCi</primary></indexterm>
   <indexterm><primary>interpreter</primary><see>GHCi</see></indexterm>
   <indexterm><primary>interactive</primary><see>GHCi</see></indexterm>
-  
+
   <para>GHCi<footnote>
       <para>The &lsquo;i&rsquo; stands for &ldquo;Interactive&rdquo;</para>
     </footnote>
@@ -33,7 +33,7 @@ Loading package ghc-prim ... linking ... done.
 Loading package integer-gmp ... linking ... done.
 Loading package base ... linking ... done.
 Loading package ffi-1.0 ... linking ... done.
-Prelude> 
+Prelude>
 </screen>
 
     <para>There may be a short pause while GHCi loads the prelude and
@@ -54,33 +54,33 @@ Prelude> 1+2
 3
 Prelude> let x = 42 in x / 9
 4.666666666666667
-Prelude> 
+Prelude>
 </screen>
 
     <para>GHCi interprets the whole line as an expression to evaluate.
-    The expression may not span several lines - as soon as you press enter, 
+    The expression may not span several lines - as soon as you press enter,
     GHCi will attempt to evaluate it.</para>
 
-    <para>GHCi also has a multiline mode, 
+    <para>GHCi also has a multiline mode,
     <indexterm><primary><literal>:set +m</literal></primary></indexterm>,
     which is terminated by an empty line:</para>
 
 <screen>
 Prelude> :set +m
 Prelude> let x = 42 in x / 9
-Prelude| 
+Prelude|
 4.666666666666667
-Prelude> 
+Prelude>
 </screen>
-    
+
     <para>In Haskell, a <literal>let</literal> expression is followed
-    by <literal>in</literal>.  However, in GHCi, since the expression 
-    can also be interpreted in the <literal>IO</literal> monad, 
-    a <literal>let</literal> binding with no accompanying 
-    <literal>in</literal> statement can be signalled by an empty line, 
+    by <literal>in</literal>.  However, in GHCi, since the expression
+    can also be interpreted in the <literal>IO</literal> monad,
+    a <literal>let</literal> binding with no accompanying
+    <literal>in</literal> statement can be signalled by an empty line,
     as in the above example.</para>
 
-    <para>Multiline mode is useful when entering monadic 
+    <para>Multiline mode is useful when entering monadic
     <literal>do</literal> statements:</para>
 
 <screen>
@@ -94,7 +94,7 @@ Control.Monad.State|
 0
 Control.Monad.State>
 </screen>
-  
+
    <para>During a multiline interaction, the user can interrupt and
    return to the top-level prompt.</para>
 
@@ -174,7 +174,7 @@ Ok, modules loaded: Main.
       <title>Modules vs. filenames</title>
       <indexterm><primary>modules</primary><secondary>and filenames</secondary></indexterm>
       <indexterm><primary>filenames</primary><secondary>of modules</secondary></indexterm>
-      
+
       <para>Question: How does GHC find the filename which contains
       module <replaceable>M</replaceable>?  Answer: it looks for the
       file <literal><replaceable>M</replaceable>.hs</literal>, or
@@ -279,7 +279,7 @@ Ok, modules loaded: A, B, C, D.
     because the source and everything it depends on
     is unchanged since the last compilation.</para>
 
-    <para>At any time you can use the command 
+    <para>At any time you can use the command
     <literal>:show modules</literal>
     to get a list of the modules currently loaded
     into GHCi:</para>
@@ -302,7 +302,7 @@ A                ( A.hs, interpreted )
 *Main> :reload
 Compiling D                ( D.hs, interpreted )
 Ok, modules loaded: A, B, C, D.
-*Main> 
+*Main>
 </screen>
 
     <para>Note that module D was compiled, but in this instance
@@ -429,7 +429,7 @@ hello
       <title>Using <literal>do-</literal>notation at the prompt</title>
       <indexterm><primary>do-notation</primary><secondary>in GHCi</secondary></indexterm>
       <indexterm><primary>statements</primary><secondary>in GHCi</secondary></indexterm>
-      
+
       <para>GHCi actually accepts <firstterm>statements</firstterm>
       rather than just expressions at the prompt.  This means you can
       bind values and functions to names, and use them in future
@@ -454,10 +454,10 @@ Prelude>
       it as we did above.</para>
 
       <para>If <option>-fprint-bind-result</option> is set then
-      GHCi will print the result of a statement if and only if: 
+      GHCi will print the result of a statement if and only if:
        <itemizedlist>
          <listitem>
-           <para>The statement is not a binding, or it is a monadic binding 
+           <para>The statement is not a binding, or it is a monadic binding
              (<literal>p &lt;- e</literal>) that binds exactly one
              variable.</para>
          </listitem>
@@ -501,9 +501,9 @@ Prelude> add 1 2
 3
 Prelude>
 </screen>
-        <para>However, this quickly gets tedious when defining functions 
+        <para>However, this quickly gets tedious when defining functions
         with multiple clauses, or groups of mutually recursive functions,
-        because the complete definition has to be given on a single line, 
+        because the complete definition has to be given on a single line,
         using explicit braces and semicolons instead of layout:</para>
 <screen>
 Prelude> let { f op n [] = n ; f op n (h:t) = h `op` f op n t }
@@ -525,9 +525,9 @@ Prelude> g (*) 1 [1..3]
 </screen>
       <para>Such multiline commands can be used with any GHCi command,
       and the lines between <literal>:{</literal> and
-      <literal>:}</literal> are simply merged into a single line for 
+      <literal>:}</literal> are simply merged into a single line for
       interpretation. That implies that each such group must form a single
-      valid command when merged, and that no layout rule is used. 
+      valid command when merged, and that no layout rule is used.
       The main purpose of multiline commands is not to replace module
       loading but to make definitions in .ghci-files (see <xref
       linkend="ghci-dot-files"/>) more readable and maintainable.</para>
@@ -571,7 +571,7 @@ xs :: [Integer]
     </sect2>
 
     <sect2 id="ghci-scope">
-      <title>What's really in scope at the prompt?</title> 
+      <title>What's really in scope at the prompt?</title>
 
       <para>When you type an expression at the prompt, what
       identifiers and types are in scope?  GHCi provides a flexible
@@ -637,7 +637,7 @@ Prelude IO>
       haskell <literal>import</literal> syntax as
       well, but this does not support
       <literal>*</literal> forms).
-      <literal>:module</literal> can also be shortened to 
+      <literal>:module</literal> can also be shortened to
       <literal>:m</literal>. The full syntax of the
       <literal>:module</literal> command is:</para>
 
@@ -785,13 +785,13 @@ bar
 
       </sect3>
     </sect2>
-  
+
 
     <sect2>
       <title>The <literal>it</literal> variable</title>
       <indexterm><primary><literal>it</literal></primary>
       </indexterm>
-      
+
       <para>Whenever an expression (or a non-binding statement, to be
       precise) is typed at the prompt, GHCi implicitly binds its value
       to the variable <literal>it</literal>.  For example:</para>
@@ -804,7 +804,7 @@ Prelude> it * 2
     <para>What actually happens is that GHCi typechecks the
     expression, and if it doesn't have an <literal>IO</literal> type,
     then it transforms it as follows: an expression
-    <replaceable>e</replaceable> turns into 
+    <replaceable>e</replaceable> turns into
 <screen>
 let it = <replaceable>e</replaceable>;
 print it
@@ -875,7 +875,7 @@ it &lt;- <replaceable>e</replaceable>
     rules (Section 4.3.4 of the Haskell 2010 Report) as follows.  The
     standard rules take each group of constraints <literal>(C1 a, C2 a, ..., Cn
     a)</literal> for each type variable <literal>a</literal>, and defaults the
-    type variable if 
+    type variable if
     <orderedlist>
         <listitem>
             <para>
@@ -973,7 +973,7 @@ def = toEnum 0
         <listitem>
           <para>The ability to set a <firstterm>breakpoint</firstterm> on a
             function definition or expression in the program.  When the function
-            is called, or the expression evaluated, GHCi suspends 
+            is called, or the expression evaluated, GHCi suspends
             execution and returns to the prompt, where you can inspect the
             values of local variables before continuing with the
             execution.</para>
@@ -999,7 +999,7 @@ def = toEnum 0
         </listitem>
       </itemizedlist>
     </para>
-      
+
     <para>There is currently no support for obtaining a &ldquo;stack
     trace&rdquo;, but the tracing and history features provide a
     useful second-best, which will often be enough to establish the
@@ -1007,14 +1007,14 @@ def = toEnum 0
     automatically when an exception is thrown, even if it is thrown
     from within compiled code (see <xref
     linkend="ghci-debugger-exceptions" />).</para>
-      
+
     <sect2 id="breakpoints">
       <title>Breakpoints and inspecting variables</title>
-      
+
       <para>Let's use quicksort as a running example.  Here's the code:</para>
 
 <programlisting>
-qsort [] = [] 
+qsort [] = []
 qsort (a:as) = qsort left ++ [a] ++ qsort right
   where (left,right) = (filter (&lt;=a) as, filter (&gt;a) as)
 
@@ -1028,7 +1028,7 @@ Prelude> :l qsort.hs
 [1 of 1] Compiling Main             ( qsort.hs, interpreted )
 Ok, modules loaded: Main.
 *Main>
-      </screen>       
+      </screen>
 
       <para>Now, let's set a breakpoint on the right-hand-side of the second
         equation of qsort:</para>
@@ -1038,12 +1038,12 @@ Ok, modules loaded: Main.
 Breakpoint 0 activated at qsort.hs:2:15-46
 *Main>
 </programlisting>
-      
+
       <para>The command <literal>:break 2</literal> sets a breakpoint on line
         2 of the most recently-loaded module, in this case
         <literal>qsort.hs</literal>.   Specifically, it picks the
         leftmost complete subexpression on that line on which to set the
-        breakpoint, which in this case is the expression 
+        breakpoint, which in this case is the expression
         <literal>(qsort left ++ [a] ++ qsort right)</literal>.</para>
 
       <para>Now, we run the program:</para>
@@ -1064,8 +1064,8 @@ right :: [a]
         location, we can use the <literal>:list</literal> command:</para>
 
 <programlisting>
-[qsort.hs:2:15-46] *Main> :list 
-1  qsort [] = [] 
+[qsort.hs:2:15-46] *Main> :list
+1  qsort [] = []
 2  qsort (a:as) = qsort left ++ [a] ++ qsort right
 3    where (left,right) = (filter (&lt;=a) as, filter (&gt;a) as)
 </programlisting>
@@ -1138,7 +1138,7 @@ left = (_t1::[a])
       <para>The flag <literal>-fprint-evld-with-show</literal> instructs
       <literal>:print</literal> to reuse
       available <literal>Show</literal> instances when possible. This happens
-      only when the contents of the variable being inspected 
+      only when the contents of the variable being inspected
       are completely evaluated.</para>
 
 
@@ -1174,7 +1174,7 @@ _t1 :: [Integer]
 [qsort.hs:2:15-46] *Main> a
 8
 </screen>
-      
+
       <para>You might find it useful to use Haskell's
         <literal>seq</literal> function to evaluate individual thunks rather
         than evaluating the whole expression with <literal>:force</literal>.
@@ -1205,7 +1205,7 @@ _result :: [a]
 a :: a
 left :: [a]
 right :: [a]
-[qsort.hs:2:15-46] *Main> 
+[qsort.hs:2:15-46] *Main>
 </screen>
 
       <para>The execution continued at the point it previously stopped, and has
@@ -1235,13 +1235,13 @@ right :: [a]
    :break <replaceable>line</replaceable>
    :break <replaceable>line</replaceable> <replaceable>column</replaceable>
    :break <replaceable>module</replaceable> <replaceable>line</replaceable>
-   :break <replaceable>module</replaceable> <replaceable>line</replaceable> <replaceable>column</replaceable> 
+   :break <replaceable>module</replaceable> <replaceable>line</replaceable> <replaceable>column</replaceable>
 </screen>
 
       <para>When a breakpoint is set on a particular line, GHCi sets the
         breakpoint on the
         leftmost subexpression that begins and ends on that line.  If two
-        complete subexpressions start at the same 
+        complete subexpressions start at the same
         column, the longest one is picked.  If there is no complete
         subexpression on the line, then the leftmost expression starting on
         the line is picked, and failing that the rightmost expression that
@@ -1255,7 +1255,7 @@ right :: [a]
           and doesn't match others.  The best advice is to avoid tab
           characters in your source code altogether (see
           <option>-fwarn-tabs</option> in <xref linkend="options-sanity"
-            />).</para> 
+            />).</para>
 
       <para>If the module is omitted, then the most recently-loaded module is
         used.</para>
@@ -1289,7 +1289,7 @@ right :: [a]
 *Main> :delete 0
 *Main> :show breaks
 [1] Main qsort.hs:2:15-46
-</screen>        
+</screen>
 
         <para>To delete all breakpoints at once, use <literal>:delete *</literal>.</para>
 
@@ -1301,7 +1301,7 @@ right :: [a]
 
       <para>Single-stepping is a great way to visualise the execution of your
         program, and it is also a useful tool for identifying the source of a
-        bug. GHCi offers two variants of stepping. Use 
+        bug. GHCi offers two variants of stepping. Use
        <literal>:step</literal>  to enable all the
         breakpoints in the program, and execute until the next breakpoint is
         reached. Use <literal>:steplocal</literal> to limit the set
@@ -1320,7 +1320,7 @@ _result :: IO ()
         <replaceable>expr</replaceable></literal> begins the evaluation of
         <replaceable>expr</replaceable> in single-stepping mode.  If
         <replaceable>expr</replaceable> is omitted, then it single-steps from
-        the current breakpoint. <literal>:stepover</literal> 
+        the current breakpoint. <literal>:stepover</literal>
         works similarly.</para>
 
       <para>The <literal>:list</literal> command is particularly useful when
@@ -1328,9 +1328,9 @@ _result :: IO ()
 
 <screen>
 [qsort.hs:5:7-47] *Main> :list
-4  
+4
 5  main = print (qsort [8, 4, 0, 3, 1, 23, 11, 18])
-6  
+6
 [qsort.hs:5:7-47] *Main>
 </screen>
 
@@ -1343,9 +1343,9 @@ _result :: IO ()
 [qsort.hs:5:7-47] *Main> :step
 Stopped at qsort.hs:5:14-46
 _result :: [Integer]
-4  
+4
 5  main = print (qsort [8, 4, 0, 3, 1, 23, 11, 18])
-6  
+6
 [qsort.hs:5:14-46] *Main>
 </screen>
     </sect2>
@@ -1439,13 +1439,13 @@ _result :: [a]
 
 <screen>
 *Main&gt; :list qsort
-1  qsort [] = [] 
+1  qsort [] = []
 2  qsort (a:as) = qsort left ++ [a] ++ qsort right
 3    where (left,right) = (filter (&lt;=a) as, filter (&gt;a) as)
-4  
+4
 *Main&gt; :b 1
 Breakpoint 1 activated at qsort.hs:1:11-12
-*Main&gt; 
+*Main&gt;
 </screen>
 
       <para>and then run a small <literal>qsort</literal> with
@@ -1490,7 +1490,7 @@ Logged breakpoint at qsort.hs:3:24-38
 _result :: [a]
 as :: [a]
 a :: a
-[-1: qsort.hs:3:24-38] *Main> 
+[-1: qsort.hs:3:24-38] *Main>
 </screen>
 
       <para>Note that the local variables at each step in the history have been
@@ -1532,10 +1532,10 @@ a :: a
         we can't set a breakpoint on it directly.  For this reason, GHCi
         provides the flags <literal>-fbreak-on-exception</literal> which causes
         the evaluator to stop when an exception is thrown, and <literal>
-       -fbreak-on-error</literal>, which works similarly but stops only on 
-       uncaught exceptions. When stopping at an exception, GHCi will act 
+       -fbreak-on-error</literal>, which works similarly but stops only on
+       uncaught exceptions. When stopping at an exception, GHCi will act
        just as it does when a breakpoint is hit, with the deviation that it
-       will not show you any source code location. Due to this, these 
+       will not show you any source code location. Due to this, these
        commands are only really useful in conjunction with
         <literal>:trace</literal>, in order to log the steps leading up to the
         exception.  For example:</para>
@@ -1575,15 +1575,15 @@ as = 'b' : 'c' : (_t1::[Char])
 
     <sect2><title>Example: inspecting functions</title>
       <para>
-        It is possible to use the debugger to examine function values. 
+        It is possible to use the debugger to examine function values.
         When we are at a breakpoint and a function is in scope, the debugger
-        cannot show 
-        you the source code for it; however, it is possible to get some 
-        information by applying it to some arguments and  observing the result. 
+        cannot show
+        you the source code for it; however, it is possible to get some
+        information by applying it to some arguments and  observing the result.
       </para>
 
       <para>
-        The process is slightly complicated when the binding is polymorphic. 
+        The process is slightly complicated when the binding is polymorphic.
         We show the process by means of an example.
         To keep things simple, we will use the well known <literal>map</literal> function:
 <programlisting>
@@ -1607,9 +1607,9 @@ x :: a
 f :: a -> b
 xs :: [a]
 </screen>
-      GHCi tells us that, among other bindings, <literal>f</literal> is in scope. 
-      However, its type is not fully known yet,  
-      and thus it is not possible to apply it to any 
+      GHCi tells us that, among other bindings, <literal>f</literal> is in scope.
+      However, its type is not fully known yet,
+      and thus it is not possible to apply it to any
       arguments. Nevertheless, observe that the type of its first argument is the
       same as the type of <literal>x</literal>, and its result type is shared
         with <literal>_result</literal>.
@@ -1617,12 +1617,12 @@ xs :: [a]
 
       <para>
         As we demonstrated earlier (<xref linkend="breakpoints" />),  the
-        debugger has some intelligence built-in to update the type of 
-        <literal>f</literal> whenever the types of <literal>x</literal> or 
+        debugger has some intelligence built-in to update the type of
+        <literal>f</literal> whenever the types of <literal>x</literal> or
         <literal>_result</literal> are discovered.  So what we do in this
         scenario is
-        force <literal>x</literal> a bit, in order to recover both its type 
-      and the argument part of <literal>f</literal>.  
+        force <literal>x</literal> a bit, in order to recover both its type
+      and the argument part of <literal>f</literal>.
 <screen>
 *Main> seq x ()
 *Main> :print x
@@ -1631,7 +1631,7 @@ x = 1
       </para>
       <para>
         We can check now that as expected, the type of <literal>x</literal>
-        has been reconstructed, and with it the 
+        has been reconstructed, and with it the
         type of <literal>f</literal> has been too:</para>
 <screen>
 *Main> :t x
@@ -1641,7 +1641,7 @@ f :: Integer -> b
 </screen>
       <para>
         From here, we can apply f to any argument of type Integer and observe
-        the results. 
+        the results.
 <screen><![CDATA[
 *Main> let b = f 10
 *Main> :t b
@@ -1667,10 +1667,10 @@ Just 20
 *Main> map f [1..5]
 [Just 1, Just 2, Just 3, Just 4, Just 5]
 ]]></screen>
-      In the first application of <literal>f</literal>, we had to do 
+      In the first application of <literal>f</literal>, we had to do
       some more type reconstruction
-      in order to recover the result type of <literal>f</literal>. 
-      But after that, we are free to use 
+      in order to recover the result type of <literal>f</literal>.
+      But after that, we are free to use
       <literal>f</literal> normally.
      </para>
     </sect2>
@@ -1691,7 +1691,7 @@ Just 20
             CAF at the prompt again.</para>
         </listitem>
        <listitem><para>
-         Implicit parameters (see <xref linkend="implicit-parameters"/>) are only available 
+         Implicit parameters (see <xref linkend="implicit-parameters"/>) are only available
          at the scope of a breakpoint if there is an explicit type signature.
        </para>
         </listitem>
@@ -1739,7 +1739,7 @@ $ ghci -package readline
 GHCi, version 6.8.1: http://www.haskell.org/ghc/  :? for help
 Loading package base ... linking ... done.
 Loading package readline-1.0 ... linking ... done.
-Prelude> 
+Prelude>
 </screen>
 
       <para>The following command works to load new packages into a
@@ -1757,7 +1757,7 @@ Prelude> :set -package <replaceable>name</replaceable>
     <sect2>
       <title>Extra libraries</title>
       <indexterm><primary>libraries</primary><secondary>with GHCi</secondary></indexterm>
-      
+
       <para>Extra libraries may be specified on the command line using
       the normal <literal>-l<replaceable>lib</replaceable></literal>
       option.  (The term <emphasis>library</emphasis> here refers to
@@ -1889,11 +1889,11 @@ $ ghci -lm
          modules from packages) only the non-<literal>*</literal>
     form of <literal>:browse</literal> is available.
     If the <literal>!</literal> symbol is appended to the
-    command, data constructors and class methods will be 
+    command, data constructors and class methods will be
     listed individually, otherwise, they will only be listed
-    in the context of their data type or class declaration. 
-    The <literal>!</literal>-form also annotates the listing 
-    with comments giving possible imports for each group of 
+    in the context of their data type or class declaration.
+    The <literal>!</literal>-form also annotates the listing
+    with comments giving possible imports for each group of
     entries.</para>
 <screen>
 Prelude> :browse! Data.Maybe
@@ -1961,7 +1961,7 @@ maybe :: b -> (a -> b) -> Maybe a -> b
 
       <varlistentry>
        <term>
-          <literal>:continue</literal> 
+          <literal>:continue</literal>
           <indexterm><primary><literal>:continue</literal></primary></indexterm>
         </term>
        <listitem><para>Continue the current evaluation, when stopped at a
@@ -2067,7 +2067,7 @@ Prelude> :. cmds.ghci
 
       <varlistentry>
        <term>
-          <literal>:delete * | <replaceable>num</replaceable> ...</literal> 
+          <literal>:delete * | <replaceable>num</replaceable> ...</literal>
           <indexterm><primary><literal>:delete</literal></primary></indexterm>
         </term>
        <listitem>
@@ -2095,7 +2095,7 @@ Prelude> :. cmds.ghci
 
       <varlistentry>
        <term>
-          <literal>:etags</literal> 
+          <literal>:etags</literal>
         </term>
        <listitem>
          <para>See <literal>:ctags</literal>.</para>
@@ -2185,9 +2185,9 @@ Prelude> :. cmds.ghci
          the location of its definition in the source.</para>
          <para>For types and classes, GHCi also summarises instances that
          mention them.  To avoid showing irrelevant information, an instance
-         is shown only if (a) its head mentions <replaceable>name</replaceable>, 
+         is shown only if (a) its head mentions <replaceable>name</replaceable>,
          and (b) all the other things mentioned in the instance
-         are in scope (either qualified or otherwise) as a result of 
+         are in scope (either qualified or otherwise) as a result of
          a <literal>:load</literal> or <literal>:module</literal> commands. </para>
        </listitem>
       </varlistentry>
@@ -2389,7 +2389,7 @@ bar
 
       <varlistentry>
        <term>
-          <literal>:script</literal> <optional><replaceable>n</replaceable></optional> 
+          <literal>:script</literal> <optional><replaceable>n</replaceable></optional>
          <literal>filename</literal>
           <indexterm><primary><literal>:script</literal></primary></indexterm>
         </term>
@@ -2581,7 +2581,7 @@ bar
 
       <varlistentry>
        <term>
-          <literal>:step [<replaceable>expr</replaceable>]</literal> 
+          <literal>:step [<replaceable>expr</replaceable>]</literal>
           <indexterm><primary><literal>:step</literal></primary></indexterm>
         </term>
        <listitem>
@@ -2709,7 +2709,7 @@ bar
            top-level expressions to be discarded after each
            evaluation (they are still retained
            <emphasis>during</emphasis> a single evaluation).</para>
-         
+
            <para>This option may help if the evaluated top-level
            expressions are consuming large amounts of space, or if
            you need repeatable performance measurements.</para>
@@ -2757,7 +2757,7 @@ bar
 <screen>
 Prelude> :set -fglasgow-exts
 </screen>
-      
+
       <para>Any GHC command-line option that is designated as
       <firstterm>dynamic</firstterm> (see the table in <xref
       linkend="flag-reference"/>), may be set using
@@ -2812,7 +2812,7 @@ Prelude> :set -fno-glasgow-exts
     defining useful macros.  Placing a <filename>.ghci</filename> file
     in a directory with a Haskell project is a useful way to set
     certain project-wide options so you don't have to type them
-    everytime you start GHCi: eg. if your project uses GHC extensions
+    every time you start GHCi: eg. if your project uses GHC extensions
     and CPP, and has source files in three subdirectories A, B and C,
     you might put the following lines in
     <filename>.ghci</filename>:</para>
@@ -2836,7 +2836,7 @@ Prelude> :set -fno-glasgow-exts
 :def source readFile
 </screen>
 
-    <para>With this macro defined in your <filename>.ghci</filename> 
+    <para>With this macro defined in your <filename>.ghci</filename>
     file, you can use <literal>:source file</literal> to read GHCi
     commands from <literal>file</literal>. You can find (and contribute!-)
     other suggestions for <filename>.ghci</filename> files on this Haskell
@@ -2902,7 +2902,7 @@ Prelude> :set -fno-glasgow-exts
 
   <sect1 id="ghci-faq">
     <title>FAQ and Things To Watch Out For</title>
-    
+
     <variablelist>
       <varlistentry>
        <term>The interpreter can't load modules with foreign export
@@ -2991,8 +2991,8 @@ Prelude> :set -fno-glasgow-exts
             because this is normally what you want in an interpreter:
             output appears as it is generated.
           </para>
-          <para> 
-            If you want line-buffered behaviour, as in GHC, you can 
+          <para>
+            If you want line-buffered behaviour, as in GHC, you can
             start your program thus:
             <programlisting>
                main = do { hSetBuffering stdout LineBuffering; ... }
index 0f37953..e1795f2 100644 (file)
@@ -44,8 +44,8 @@ documentation</ulink> describes all the libraries that come with GHC.
 
     <para>Language options can be controlled in two ways:
     <itemizedlist>
-      <listitem><para>Every language option can switched on by a command-line flag "<option>-X...</option>" 
-        (e.g. <option>-XTemplateHaskell</option>), and switched off by the flag "<option>-XNo...</option>"; 
+      <listitem><para>Every language option can switched on by a command-line flag "<option>-X...</option>"
+        (e.g. <option>-XTemplateHaskell</option>), and switched off by the flag "<option>-XNo...</option>";
         (e.g. <option>-XNoTemplateHaskell</option>).</para></listitem>
       <listitem><para>
           Language options recognised by Cabal can also be enabled using the <literal>LANGUAGE</literal> pragma,
@@ -55,11 +55,11 @@ documentation</ulink> describes all the libraries that come with GHC.
 
     <para>The flag <option>-fglasgow-exts</option>
           <indexterm><primary><option>-fglasgow-exts</option></primary></indexterm>
-         is equivalent to enabling the following extensions: 
+         is equivalent to enabling the following extensions:
           &what_glasgow_exts_does;
-           Enabling these options is the <emphasis>only</emphasis> 
+           Enabling these options is the <emphasis>only</emphasis>
            effect of <option>-fglasgow-exts</option>.
-          We are trying to move away from this portmanteau flag, 
+          We are trying to move away from this portmanteau flag,
          and towards enabling features individually.</para>
 
   </sect1>
@@ -77,8 +77,8 @@ While you really can use this stuff to write fast code,
   unboxed version in any case.  And if it isn't, we'd like to know
   about it.</para>
 
-<para>All these primitive data types and operations are exported by the 
-library <literal>GHC.Prim</literal>, for which there is 
+<para>All these primitive data types and operations are exported by the
+library <literal>GHC.Prim</literal>, for which there is
 <ulink url="&libraryGhcPrimLocation;/GHC-Prim.html">detailed online documentation</ulink>.
 (This documentation is generated from the file <filename>compiler/prelude/primops.txt.pp</filename>.)
 </para>
@@ -89,10 +89,10 @@ into scope.  Many of them have names ending in "&num;", and to mention such
 names you need the <option>-XMagicHash</option> extension (<xref linkend="magic-hash"/>).
 </para>
 
-<para>The primops make extensive use of <link linkend="glasgow-unboxed">unboxed types</link> 
+<para>The primops make extensive use of <link linkend="glasgow-unboxed">unboxed types</link>
 and <link linkend="unboxed-tuples">unboxed tuples</link>, which
 we briefly summarise here. </para>
-  
+
 <sect2 id="glasgow-unboxed">
 <title>Unboxed types
 </title>
@@ -124,7 +124,7 @@ know and love&mdash;usually one instruction.
 Primitive (unboxed) types cannot be defined in Haskell, and are
 therefore built into the language and compiler.  Primitive types are
 always unlifted; that is, a value of a primitive type cannot be
-bottom.  We use the convention (but it is only a convention) 
+bottom.  We use the convention (but it is only a convention)
 that primitive types, values, and
 operations have a <literal>&num;</literal> suffix (see <xref linkend="magic-hash"/>).
 For some primitive types we have special syntax for literals, also
@@ -283,7 +283,7 @@ You can have an unboxed tuple in a pattern binding, thus
   f x = let (# p,q #) = h x in ..body..
 </programlisting>
 If the types of <literal>p</literal> and <literal>q</literal> are not unboxed,
-the resulting binding is lazy like any other Haskell pattern binding.  The 
+the resulting binding is lazy like any other Haskell pattern binding.  The
 above example desugars like this:
 <programlisting>
   f x = let t = case h x o f{ (# p,q #) -> (p,q)
@@ -302,7 +302,7 @@ Indeed, the bindings can even be recursive.
 
 <sect1 id="syntax-extns">
 <title>Syntactic extensions</title>
+
     <sect2 id="unicode-syntax">
       <title>Unicode syntax</title>
       <para>The language
@@ -425,17 +425,17 @@ Indeed, the bindings can even be recursive.
        postfix modifier to identifiers.  Thus, "x&num;" is a valid variable, and "T&num;" is
        a valid type constructor or data constructor.</para>
 
-      <para>The hash sign does not change sematics at all.  We tend to use variable
-       names ending in "&num;" for unboxed values or types (e.g. <literal>Int&num;</literal>), 
-       but there is no requirement to do so; they are just plain ordinary variables.
+      <para>The hash sign does not change semantics at all.  We tend to use variable
+       names ending in "&num;" for unboxed values or types (e.g. <literal>Int&num;</literal>),
+        but there is no requirement to do so; they are just plain ordinary variables.
        Nor does the <option>-XMagicHash</option> extension bring anything into scope.
-       For example, to bring <literal>Int&num;</literal> into scope you must 
-       import <literal>GHC.Prim</literal> (see <xref linkend="primitives"/>); 
+       For example, to bring <literal>Int&num;</literal> into scope you must
+       import <literal>GHC.Prim</literal> (see <xref linkend="primitives"/>);
        the <option>-XMagicHash</option> extension
        then allows you to <emphasis>refer</emphasis> to the <literal>Int&num;</literal>
        that is now in scope.</para>
       <para> The <option>-XMagicHash</option> also enables some new forms of literals (see <xref linkend="glasgow-unboxed"/>):
-       <itemizedlist> 
+       <itemizedlist>
          <listitem><para> <literal>'x'&num;</literal> has type <literal>Char&num;</literal></para> </listitem>
          <listitem><para> <literal>&quot;foo&quot;&num;</literal> has type <literal>Addr&num;</literal></para> </listitem>
          <listitem><para> <literal>3&num;</literal> has type <literal>Int&num;</literal>. In general,
@@ -530,7 +530,7 @@ where
 </programlisting>
 
 <para>
-The auxiliary functions are 
+The auxiliary functions are
 </para>
 
 <programlisting>
@@ -575,10 +575,10 @@ This is a bit shorter, but hardly better.  Of course, we can rewrite any set
 of pattern-matching, guarded equations as case expressions; that is
 precisely what the compiler does when compiling equations! The reason that
 Haskell provides guarded equations is because they allow us to write down
-the cases we want to consider, one at a time, independently of each other. 
+the cases we want to consider, one at a time, independently of each other.
 This structure is hidden in the case version.  Two of the right-hand sides
 are really the same (<function>fail</function>), and the whole expression
-tends to become more and more indented. 
+tends to become more and more indented.
 </para>
 
 <para>
@@ -594,9 +594,9 @@ clunky env var1 var2
 </programlisting>
 
 <para>
-The semantics should be clear enough.  The qualifiers are matched in order. 
+The semantics should be clear enough.  The qualifiers are matched in order.
 For a <literal>&lt;-</literal> qualifier, which I call a pattern guard, the
-right hand side is evaluated and matched against the pattern on the left. 
+right hand side is evaluated and matched against the pattern on the left.
 If the match fails then the whole guard fails and the next equation is
 tried.  If it succeeds, then the appropriate binding takes place, and the
 next qualifier is matched, in the augmented environment.  Unlike list
@@ -646,7 +646,7 @@ language as follows:
 
 <programlisting>
 type Typ
+
 data TypView = Unit
              | Arrow Typ Typ
 
@@ -658,7 +658,7 @@ view :: Type -> TypeView
 The representation of Typ is held abstract, permitting implementations
 to use a fancy representation (e.g., hash-consing to manage sharing).
 
-Without view patterns, using this signature a little inconvenient: 
+Without view patterns, using this signature a little inconvenient:
 <programlisting>
 size :: Typ -> Integer
 size t = case view t of
@@ -673,7 +673,7 @@ against <literal>t</literal> is buried deep inside another pattern.
 
 <para>
 View patterns permit calling the view function inside the pattern and
-matching against the result: 
+matching against the result:
 <programlisting>
 size (view -> Unit) = 1
 size (view -> Arrow t1 t2) = size t1 + size t2
@@ -716,7 +716,7 @@ clunky env (lookup env -> Just val1) (lookup env -> Just val2) = val1 + val2
 </para>
 
 <para>
-More precisely, the scoping rules are: 
+More precisely, the scoping rules are:
 <itemizedlist>
 <listitem>
 <para>
@@ -734,7 +734,7 @@ example :: (String -> Integer) -> String -> Bool
 example f (f -> 4) = True
 </programlisting>
 That is, the scoping is the same as it would be if the curried arguments
-were collected into a tuple.  
+were collected into a tuple.
 </para>
 </listitem>
 
@@ -750,7 +750,7 @@ let {(x -> y) = e1 ;
      (y -> x) = e2 } in x
 </programlisting>
 
-(For some amplification on this design choice see 
+(For some amplification on this design choice see
 <ulink url="http://hackage.haskell.org/trac/ghc/ticket/4061">Trac #4061</ulink>.)
 
 </para>
@@ -771,8 +771,8 @@ a <replaceable>T2</replaceable>, then the whole view pattern matches a
 <ulink url="http://www.haskell.org/onlinereport/">Haskell 98
 Report</ulink>, add the following:
 <programlisting>
-case v of { (e -> p) -> e1 ; _ -> e2 } 
- = 
+case v of { (e -> p) -> e1 ; _ -> e2 }
+ =
 case (e v) of { p -> e1 ; _ -> e2 }
 </programlisting>
 That is, to match a variable <replaceable>v</replaceable> against a pattern
@@ -781,7 +781,7 @@ That is, to match a variable <replaceable>v</replaceable> against a pattern
 <literal>)</literal>, evaluate <literal>(</literal>
 <replaceable>exp</replaceable> <replaceable> v</replaceable>
 <literal>)</literal> and match the result against
-<replaceable>pat</replaceable>.  
+<replaceable>pat</replaceable>.
 </para></listitem>
 
 <listitem><para> Efficiency: When the same view function is applied in
@@ -839,7 +839,7 @@ it, you can use the <option>-XNoNPlusKPatterns</option> flag.
 
 <para>
 The do-notation of Haskell 98 does not allow <emphasis>recursive bindings</emphasis>,
-that is, the variables bound in a do-expression are visible only in the textually following 
+that is, the variables bound in a do-expression are visible only in the textually following
 code block. Compare this to a let-expression, where bound variables are visible in the entire binding
 group. It turns out that several applications can benefit from recursive bindings in
 the do-notation.  The <option>-XDoRec</option> flag provides the necessary syntactic support.
@@ -857,7 +857,7 @@ As you can guess <literal>justOnes</literal> will evaluate to <literal>Just [-1,
 The background and motivation for recursive do-notation is described in
 <ulink url="http://sites.google.com/site/leventerkok/">A recursive do for Haskell</ulink>,
 by Levent Erkok, John Launchbury,
-Haskell Workshop 2002, pages: 29-37. Pittsburgh, Pennsylvania. 
+Haskell Workshop 2002, pages: 29-37. Pittsburgh, Pennsylvania.
 The theory behind monadic value recursion is explained further in Erkok's thesis
 <ulink url="http://sites.google.com/site/leventerkok/erkok-thesis.pdf">Value Recursion in Monadic Computations</ulink>.
 However, note that GHC uses a different syntax than the one described in these documents.
@@ -872,38 +872,38 @@ which wraps a mutually-recursive group of monadic statements,
 producing a single statement.
 </para>
 <para>Similar to a <literal>let</literal>
-statement, the variables bound in the <literal>rec</literal> are 
+statement, the variables bound in the <literal>rec</literal> are
 visible throughout the <literal>rec</literal> group, and below it.
 For example, compare
 <programlisting>
-do { a &lt;- getChar              do { a &lt;- getChar                    
-   ; let { r1 = f a r2            ; rec { r1 &lt;- f a r2      
-         ; r2 = g r1 }                  ; r2 &lt;- g r1 }      
+do { a &lt;- getChar              do { a &lt;- getChar
+   ; let { r1 = f a r2            ; rec { r1 &lt;- f a r2
+         ; r2 = g r1 }                  ; r2 &lt;- g r1 }
    ; return (r1 ++ r2) }          ; return (r1 ++ r2) }
 </programlisting>
-In both cases, <literal>r1</literal> and <literal>r2</literal> are 
+In both cases, <literal>r1</literal> and <literal>r2</literal> are
 available both throughout the <literal>let</literal> or <literal>rec</literal> block, and
 in the statements that follow it.  The difference is that <literal>let</literal> is non-monadic,
-while <literal>rec</literal> is monadic.  (In Haskell <literal>let</literal> is 
+while <literal>rec</literal> is monadic.  (In Haskell <literal>let</literal> is
 really <literal>letrec</literal>, of course.)
 </para>
 <para>
-The static and dynamic semantics of <literal>rec</literal> can be described as follows:  
+The static and dynamic semantics of <literal>rec</literal> can be described as follows:
 <itemizedlist>
 <listitem><para>
 First,
-similar to let-bindings, the <literal>rec</literal> is broken into 
+similar to let-bindings, the <literal>rec</literal> is broken into
 minimal recursive groups, a process known as <emphasis>segmentation</emphasis>.
 For example:
 <programlisting>
 rec { a &lt;- getChar      ===>     a &lt;- getChar
     ; b &lt;- f a c                 rec { b &lt;- f a c
     ; c &lt;- f b a                     ; c &lt;- f b a }
-    ; putChar c }                putChar c 
+    ; putChar c }                putChar c
 </programlisting>
 The details of segmentation are described in Section 3.2 of
 <ulink url="http://sites.google.com/site/leventerkok/">A recursive do for Haskell</ulink>.
-Segmentation improves polymorphism, reduces the size of the recursive "knot", and, as the paper 
+Segmentation improves polymorphism, reduces the size of the recursive "knot", and, as the paper
 describes, also has a semantic effect (unless the monad satisfies the right-shrinking law).
 </para></listitem>
 <listitem><para>
@@ -921,13 +921,13 @@ is desugared to the statement
 </programlisting>
 where <replaceable>vs</replaceable> is a tuple of the variables bound by <replaceable>ss</replaceable>.
 </para><para>
-The original <literal>rec</literal> typechecks exactly 
-when the above desugared version would do so.  For example, this means that 
+The original <literal>rec</literal> typechecks exactly
+when the above desugared version would do so.  For example, this means that
 the variables <replaceable>vs</replaceable> are all monomorphic in the statements
 following the <literal>rec</literal>, because they are bound by a lambda.
 </para>
 <para>
-The <literal>mfix</literal> function is defined in the <literal>MonadFix</literal> 
+The <literal>mfix</literal> function is defined in the <literal>MonadFix</literal>
 class, in <literal>Control.Monad.Fix</literal>, thus:
 <programlisting>
 class Monad m => MonadFix m where
@@ -951,14 +951,14 @@ then that monad must be declared an instance of the <literal>MonadFix</literal>
 </para></listitem>
 
 <listitem><para>
-The following instances of <literal>MonadFix</literal> are automatically provided: List, Maybe, IO. 
-Furthermore, the Control.Monad.ST and Control.Monad.ST.Lazy modules provide the instances of the MonadFix class 
+The following instances of <literal>MonadFix</literal> are automatically provided: List, Maybe, IO.
+Furthermore, the Control.Monad.ST and Control.Monad.ST.Lazy modules provide the instances of the MonadFix class
 for Haskell's internal state monad (strict and lazy, respectively).
 </para></listitem>
 
 <listitem><para>
 Like <literal>let</literal> and <literal>where</literal> bindings,
-name shadowing is not allowed within a <literal>rec</literal>; 
+name shadowing is not allowed within a <literal>rec</literal>;
 that is, all the names bound in a single <literal>rec</literal> must
 be distinct (Section 3.3 of the paper).
 </para></listitem>
@@ -1007,7 +1007,7 @@ This name is not supported by GHC.
     example, the following zips together two lists:</para>
 
 <programlisting>
-   [ (x, y) | x &lt;- xs | y &lt;- ys ] 
+   [ (x, y) | x &lt;- xs | y &lt;- ys ]
 </programlisting>
 
     <para>The behavior of parallel list comprehensions follows that of
@@ -1020,26 +1020,26 @@ This name is not supported by GHC.
     <para>Given a parallel comprehension of the form: </para>
 
 <programlisting>
-   [ e | p1 &lt;- e11, p2 &lt;- e12, ... 
-       | q1 &lt;- e21, q2 &lt;- e22, ... 
-       ... 
-   ] 
+   [ e | p1 &lt;- e11, p2 &lt;- e12, ...
+       | q1 &lt;- e21, q2 &lt;- e22, ...
+       ...
+   ]
 </programlisting>
 
     <para>This will be translated to: </para>
 
 <programlisting>
-   [ e | ((p1,p2), (q1,q2), ...) &lt;- zipN [(p1,p2) | p1 &lt;- e11, p2 &lt;- e12, ...] 
-                                         [(q1,q2) | q1 &lt;- e21, q2 &lt;- e22, ...] 
-                                         ... 
-   ] 
+   [ e | ((p1,p2), (q1,q2), ...) &lt;- zipN [(p1,p2) | p1 &lt;- e11, p2 &lt;- e12, ...]
+                                         [(q1,q2) | q1 &lt;- e21, q2 &lt;- e22, ...]
+                                         ...
+   ]
 </programlisting>
 
     <para>where `zipN' is the appropriate zip for the given number of
     branches.</para>
 
   </sect2>
-  
+
   <!-- ===================== TRANSFORM LIST COMPREHENSIONS ===================  -->
 
   <sect2 id="generalised-list-comprehensions">
@@ -1059,7 +1059,7 @@ This name is not supported by GHC.
          Comprehensive comprehensions: comprehensions with "order by" and "group by"</ulink>,
     except that the syntax we use differs slightly from the paper.</para>
 <para>The extension is enabled with the flag <option>-XTransformListComp</option>.</para>
-<para>Here is an example: 
+<para>Here is an example:
 <programlisting>
 employees = [ ("Simon", "MS", 80)
 , ("Erik", "MS", 100)
@@ -1073,9 +1073,9 @@ output = [ (the dept, sum salary)
 , then sortWith by (sum salary)
 , then take 5 ]
 </programlisting>
-In this example, the list <literal>output</literal> would take on 
+In this example, the list <literal>output</literal> would take on
     the value:
-    
+
 <programlisting>
 [("Yale", 60), ("Ed", 85), ("MS", 180)]
 </programlisting>
@@ -1088,7 +1088,7 @@ function that is exported by <literal>GHC.Exts</literal>.)</para>
 all introduced by the (existing) keyword <literal>then</literal>:
     <itemizedlist>
     <listitem>
-    
+
 <programlisting>
 then f
 </programlisting>
@@ -1096,10 +1096,10 @@ then f
     This statement requires that <literal>f</literal> have the type <literal>
     forall a. [a] -> [a]</literal>. You can see an example of its use in the
     motivating example, as this form is used to apply <literal>take 5</literal>.
-    
+
     </listitem>
-    
-    
+
+
     <listitem>
 <para>
 <programlisting>
@@ -1107,13 +1107,13 @@ then f by e
 </programlisting>
 
     This form is similar to the previous one, but allows you to create a function
-    which will be passed as the first argument to f. As a consequence f must have 
+    which will be passed as the first argument to f. As a consequence f must have
     the type <literal>forall a. (a -> t) -> [a] -> [a]</literal>. As you can see
-    from the type, this function lets f &quot;project out&quot; some information 
+    from the type, this function lets f &quot;project out&quot; some information
     from the elements of the list it is transforming.</para>
 
-    <para>An example is shown in the opening example, where <literal>sortWith</literal> 
-    is supplied with a function that lets it find out the <literal>sum salary</literal> 
+    <para>An example is shown in the opening example, where <literal>sortWith</literal>
+    is supplied with a function that lets it find out the <literal>sum salary</literal>
     for any item in the list comprehension it transforms.</para>
 
     </listitem>
@@ -1134,7 +1134,7 @@ then group by e using f
     at every point after this statement, binders occurring before it in the comprehension
     refer to <emphasis>lists</emphasis> of possible values, not single values. To help understand
     this, let's look at an example:</para>
-    
+
 <programlisting>
 -- This works similarly to groupWith in GHC.Exts, but doesn't sort its input first
 groupRuns :: Eq b => (a -> b) -> [a] -> [[a]]
@@ -1152,8 +1152,8 @@ output = [ (the x, y)
 [(1, [4, 5, 6]), (2, [4, 5, 6]), (3, [4, 5, 6]), (1, [4, 5, 6]), (2, [4, 5, 6])]
 </programlisting>
 
-    <para>Note that we have used the <literal>the</literal> function to change the type 
-    of x from a list to its original numeric type. The variable y, in contrast, is left 
+    <para>Note that we have used the <literal>the</literal> function to change the type
+    of x from a list to its original numeric type. The variable y, in contrast, is left
     unchanged from the list form introduced by the grouping.</para>
 
     </listitem>
@@ -1166,13 +1166,13 @@ then group by e
 
     <para>This form of grouping is essentially the same as the one described above. However,
     since no function to use for the grouping has been supplied it will fall back on the
-    <literal>groupWith</literal> function defined in 
+    <literal>groupWith</literal> function defined in
     <ulink url="&libraryBaseLocation;/GHC-Exts.html"><literal>GHC.Exts</literal></ulink>. This
     is the form of the group statement that we made use of in the opening example.</para>
 
     </listitem>
-    
-    
+
+
     <listitem>
 
 <programlisting>
@@ -1182,7 +1182,7 @@ then group using f
     <para>With this form of the group statement, f is required to simply have the type
     <literal>forall a. [a] -> [[a]]</literal>, which will be used to group up the
     comprehension so far directly. An example of this form is as follows:</para>
-    
+
 <programlisting>
 output = [ x
 | y &lt;- [1..5]
@@ -1208,10 +1208,10 @@ output = [ x
     <indexterm><primary>monad comprehensions</primary></indexterm>
 
     <para>
-        Monad comprehesions generalise the list comprehension notation,
-        including parallel comprehensions 
-        (<xref linkend="parallel-list-comprehensions"/>) and 
-        transform comprenensions (<xref linkend="generalised-list-comprehensions"/>) 
+        Monad comprehensions generalise the list comprehension notation,
+        including parallel comprehensions
+        (<xref linkend="parallel-list-comprehensions"/>) and
+        transform comprehensions (<xref linkend="generalised-list-comprehensions"/>)
         to work for any monad.
     </para>
 
@@ -1364,11 +1364,11 @@ do (x,y) &lt;- mzip (do x &lt;- [1..10]
         compatible to built-in, transform and parallel list comprehensions.
     </para>
 <para> More formally, the desugaring is as follows.  We write <literal>D[ e | Q]</literal>
-to mean the desugaring of the monad comprehension <literal>[ e | Q]</literal>: 
+to mean the desugaring of the monad comprehension <literal>[ e | Q]</literal>:
 <programlisting>
 Expressions: e
 Declarations: d
-Lists of qualifiers: Q,R,S  
+Lists of qualifiers: Q,R,S
 
 -- Basic forms
 D[ e | ]               = return e
@@ -1384,11 +1384,11 @@ D[ e | Q then f, R ]                  = f D[ Qv | Q ] &gt;&gt;= \Qv -&gt; D[ e |
 
 D[ e | Q then f by b, R ]             = f b D[ Qv | Q ] &gt;&gt;= \Qv -&gt; D[ e | R ]
 
-D[ e | Q then group using f, R ]      = f D[ Qv | Q ] &gt;&gt;= \ys -&gt; 
+D[ e | Q then group using f, R ]      = f D[ Qv | Q ] &gt;&gt;= \ys -&gt;
                                         case (fmap selQv1 ys, ..., fmap selQvn ys) of
                                             Qv -&gt; D[ e | R ]
 
-D[ e | Q then group by b using f, R ] = f b D[ Qv | Q ] &gt;&gt;= \ys -&gt; 
+D[ e | Q then group by b using f, R ] = f b D[ Qv | Q ] &gt;&gt;= \ys -&gt;
                                         case (fmap selQv1 ys, ..., fmap selQvn ys) of
                                            Qv -&gt; D[ e | R ]
 
@@ -1404,11 +1404,11 @@ guard        Control.Monad          t1 -&gt; m t2
 fmap         GHC.Base               forall a b. (a-&gt;b) -&gt; n a -&gt; n b
 mgroupWith   Control.Monad.Group    forall a. (a -&gt; t) -&gt; m1 a -&gt; m2 (n a)
 mzip         Control.Monad.Zip      forall a b. m a -&gt; m b -&gt; m (a,b)
-</programlisting>                                          
-The comprehension should typecheck when its desugaring would typecheck. 
+</programlisting>
+The comprehension should typecheck when its desugaring would typecheck.
 </para>
 <para>
-Monad comprehensions support rebindable syntax (<xref linkend="rebindable-syntax"/>).  
+Monad comprehensions support rebindable syntax (<xref linkend="rebindable-syntax"/>).
 Without rebindable
 syntax, the operators from the "standard binding" module are used; with
 rebindable syntax, the operators are looked up in the current lexical scope.
@@ -1416,7 +1416,7 @@ For example, parallel comprehensions will be typechecked and desugared
 using whatever "<literal>mzip</literal>" is in scope.
 </para>
 <para>
-The rebindable operators must have the "Expected type" given in the 
+The rebindable operators must have the "Expected type" given in the
 table above.  These types are surprisingly general.  For example, you can
 use a bind operator with the type
 <programlisting>
@@ -1449,7 +1449,7 @@ the comprehension being over an arbitrary monad.
             hierarchy.  It completely defeats that purpose if the
             literal "1" means "<literal>Prelude.fromInteger
             1</literal>", which is what the Haskell Report specifies.
-            So the <option>-XRebindableSyntax</option> 
+            So the <option>-XRebindableSyntax</option>
              flag causes
             the following pieces of built-in syntax to refer to
             <emphasis>whatever is in scope</emphasis>, not the Prelude
@@ -1459,16 +1459,16 @@ the comprehension being over an arbitrary monad.
                <para>An integer literal <literal>368</literal> means
                 "<literal>fromInteger (368::Integer)</literal>", rather than
                 "<literal>Prelude.fromInteger (368::Integer)</literal>".
-</para> </listitem>        
+</para> </listitem>
 
       <listitem><para>Fractional literals are handed in just the same way,
-         except that the translation is 
+         except that the translation is
              <literal>fromRational (3.68::Rational)</literal>.
-</para> </listitem>        
+</para> </listitem>
 
          <listitem><para>The equality test in an overloaded numeric pattern
              uses whatever <literal>(==)</literal> is in scope.
-</para> </listitem>        
+</para> </listitem>
 
          <listitem><para>The subtraction operation, and the
          greater-than-or-equal test, in <literal>n+k</literal> patterns
@@ -1510,7 +1510,7 @@ the comprehension being over an arbitrary monad.
 </para>
 <para>
 In all cases (apart from arrow notation), the static semantics should be that of the desugared form,
-even if that is a little unexpected. For example, the 
+even if that is a little unexpected. For example, the
 static semantics of the literal <literal>368</literal>
 is exactly that of <literal>fromInteger (368::Integer)</literal>; it's fine for
 <literal>fromInteger</literal> to have any of the types:
@@ -1521,7 +1521,7 @@ fromInteger :: Num a => a -> Integer
 fromInteger :: Integer -> Bool -> Bool
 </programlisting>
 </para>
-               
+
             <para>Be warned: this is an experimental facility, with
             fewer checks than usual.  Use <literal>-dcore-lint</literal>
             to typecheck the desugared program.  If Core Lint is happy
@@ -1609,7 +1609,7 @@ module Foo where
   import M
 
   data T = MkT { x :: Int }
-  
+
   ok1 (MkS { x = n }) = n+1   -- Unambiguous
   ok2 n = MkT { x = n+1 }     -- Unambiguous
 
@@ -1628,7 +1628,7 @@ it is not clear which of the two types is intended.
 Haskell 98 regards all four as ambiguous, but with the
 <option>-XDisambiguateRecordFields</option> flag, GHC will accept
 the former two.  The rules are precisely the same as those for instance
-declarations in Haskell 98, where the method names on the left-hand side 
+declarations in Haskell 98, where the method names on the left-hand side
 of the method bindings in an instance declaration refer unambiguously
 to the method of that class (provided they are in scope at all), even
 if there are other variables in scope with the same name.
@@ -1639,7 +1639,7 @@ records from different modules that use the same field name.
 Some details:
 <itemizedlist>
 <listitem><para>
-Field disambiguation can be combined with punning (see <xref linkend="record-puns"/>). For exampe:
+Field disambiguation can be combined with punning (see <xref linkend="record-puns"/>). For example:
 <programlisting>
 module Foo where
   import M
@@ -1649,8 +1649,8 @@ module Foo where
 </para></listitem>
 
 <listitem><para>
-With <option>-XDisambiguateRecordFields</option> you can use <emphasis>unqualifed</emphasis>
-field names even if the correponding selector is only in scope <emphasis>qualified</emphasis>
+With <option>-XDisambiguateRecordFields</option> you can use <emphasis>unqualified</emphasis>
+field names even if the corresponding selector is only in scope <emphasis>qualified</emphasis>
 For example, assuming the same module <literal>M</literal> as in our earlier example, this is legal:
 <programlisting>
 module Foo where
@@ -1658,7 +1658,7 @@ module Foo where
 
   ok4 (M.MkS { x = n }) = n+1   -- Unambiguous
 </programlisting>
-Since the constructore <literal>MkS</literal> is only in scope qualified, you must
+Since the constructor <literal>MkS</literal> is only in scope qualified, you must
 name it <literal>M.MkS</literal>, but the field <literal>x</literal> does not need
 to be qualified even though <literal>M.x</literal> is in scope but <literal>x</literal>
 is not.  (In effect, it is qualified by the constructor.)
@@ -1698,7 +1698,7 @@ f (C {a}) = a
 
 to mean the same pattern as above.  That is, in a record pattern, the
 pattern <literal>a</literal> expands into the pattern <literal>a =
-a</literal> for the same name <literal>a</literal>.  
+a</literal> for the same name <literal>a</literal>.
 </para>
 
 <para>
@@ -1709,7 +1709,7 @@ Record punning can also be used in an expression, writing, for example,
 <programlisting>
 let a = 1 in C {a}
 </programlisting>
-instead of 
+instead of
 <programlisting>
 let a = 1 in C {a = a}
 </programlisting>
@@ -1728,7 +1728,7 @@ f (C {a, b = 4}) = a
 
 <listitem><para>
 Puns can be used wherever record patterns occur (e.g. in
-<literal>let</literal> bindings or at the top-level).  
+<literal>let</literal> bindings or at the top-level).
 </para></listitem>
 
 <listitem><para>
@@ -1811,9 +1811,9 @@ the same as the omitted field names.
 </para></listitem>
 
 <listitem><para>
-The "<literal>..</literal>" expands to the missing 
+The "<literal>..</literal>" expands to the missing
 <emphasis>in-scope</emphasis> record fields, where "in scope"
-includes both unqualified and qualified-only.  
+includes both unqualified and qualified-only.
 Any fields that are not in scope are not filled in.  For example
 <programlisting>
 module M where
@@ -1848,7 +1848,7 @@ the semantics of such bindings very precisely.
 <programlisting>
 let f = ...
     infixr 3 `f`
-in 
+in
     ...
 </programlisting>
 and the fixity declaration applies wherever the binding is in scope.
@@ -1883,7 +1883,7 @@ necessary to enable them.
 <programlisting>
 import "network" Network.Socket
 </programlisting>
-  
+
   <para>would import the module <literal>Network.Socket</literal> from
     the package <literal>network</literal> (any version).  This may
     be used to disambiguate an import when the same module is
@@ -1907,7 +1907,7 @@ import "network" Network.Socket
     "stolen" by language extensions.
      We use
     notation and nonterminal names from the Haskell 98 lexical syntax
-    (see the Haskell 98 Report).  
+    (see the Haskell 98 Report).
     We only list syntax changes here that might affect
     existing working programs (i.e. "stolen" syntax).  Many of these
     extensions will also enable new context-free syntax, but in all
@@ -1929,7 +1929,7 @@ import "network" Network.Socket
        on.</para>
       </listitem>
     </itemizedlist>
-    
+
 The following syntax is stolen:
 
     <variablelist>
@@ -2021,12 +2021,12 @@ The following syntax is stolen:
       <varlistentry>
        <term>
              <replaceable>varid</replaceable>{<literal>&num;</literal>},
-             <replaceable>char</replaceable><literal>&num;</literal>,      
-             <replaceable>string</replaceable><literal>&num;</literal>,    
-             <replaceable>integer</replaceable><literal>&num;</literal>,    
-             <replaceable>float</replaceable><literal>&num;</literal>,    
-             <replaceable>float</replaceable><literal>&num;&num;</literal>,    
-             <literal>(&num;</literal>, <literal>&num;)</literal>,         
+             <replaceable>char</replaceable><literal>&num;</literal>,
+             <replaceable>string</replaceable><literal>&num;</literal>,
+             <replaceable>integer</replaceable><literal>&num;</literal>,
+             <replaceable>float</replaceable><literal>&num;</literal>,
+             <replaceable>float</replaceable><literal>&num;&num;</literal>,
+             <literal>(&num;</literal>, <literal>&num;)</literal>,
        </term>
        <listitem><para>
        Stolen by: <option>-XMagicHash</option>,
@@ -2053,7 +2053,7 @@ a data type with no constructors.  For example:</para>
   data T a    -- T :: * -> *
 </programlisting>
 
-<para>Syntactically, the declaration lacks the "= constrs" part.  The 
+<para>Syntactically, the declaration lacks the "= constrs" part.  The
 type can be parameterised over types of any kind, but if the kind is
 not <literal>*</literal> then an explicit kind annotation must be used
 (see <xref linkend="kinding"/>).</para>
@@ -2121,7 +2121,7 @@ to be written infix, very much like expressions.  More specifically:
    type T (+) = Int + Int
    f :: T Either
    f = Left 3
+
    liftA2 :: Arrow (~>)
          => (a -> b -> c) -> (e ~> a) -> (e ~> b) -> (e ~> c)
    liftA2 = ...
@@ -2159,7 +2159,7 @@ Type synonyms are like macros at the type level, but Haskell 98 imposes many rul
 on individual synonym declarations.
 With the <option>-XLiberalTypeSynonyms</option> extension,
 GHC does validity checking on types <emphasis>only after expanding type synonyms</emphasis>.
-That means that GHC can be very much more liberal about type synonyms than Haskell 98. 
+That means that GHC can be very much more liberal about type synonyms than Haskell 98.
 
 <itemizedlist>
 <listitem> <para>You can write a <literal>forall</literal> (including overloading)
@@ -2177,7 +2177,7 @@ in a type synonym, thus:
 </listitem>
 
 <listitem><para>
-If you also use <option>-XUnboxedTuples</option>, 
+If you also use <option>-XUnboxedTuples</option>,
 you can write an unboxed tuple in a type synonym:
 <programlisting>
   type Pr = (# Int, Int #)
@@ -2191,7 +2191,7 @@ you can write an unboxed tuple in a type synonym:
 You can apply a type synonym to a forall type:
 <programlisting>
   type Foo a = a -> a -> Bool
+
   f :: Foo (forall b. b->b)
 </programlisting>
 After expanding the synonym, <literal>f</literal> has the legal (in GHC) type:
@@ -2205,7 +2205,7 @@ You can apply a type synonym to a partially applied type synonym:
 <programlisting>
   type Generic i o = forall x. i x -> o x
   type Id x = x
-  
+
   foo :: Generic Id []
 </programlisting>
 After expanding the synonym, <literal>foo</literal> has the legal (in GHC) type:
@@ -2454,7 +2454,7 @@ To make use of these hidden fields, we need to create some helper functions:
 <programlisting>
 inc :: Counter a -> Counter a
 inc (NewCounter x i d t) = NewCounter
-    { _this = i x, _inc = i, _display = d, tag = t } 
+    { _this = i x, _inc = i, _display = d, tag = t }
 
 display :: Counter a -> IO ()
 display NewCounter{ _this = x, _display = d } = d x
@@ -2463,11 +2463,11 @@ display NewCounter{ _this = x, _display = d } = d x
 Now we can define counters with different underlying implementations:
 
 <programlisting>
-counterA :: Counter String 
+counterA :: Counter String
 counterA = NewCounter
     { _this = 0, _inc = (1+), _display = print, tag = "A" }
 
-counterB :: Counter String 
+counterB :: Counter String
 counterB = NewCounter
     { _this = "", _inc = ('#':), _display = putStrLn, tag = "B" }
 
@@ -2671,16 +2671,16 @@ giving the type signatures of constructors explicitly.  For example:
       Just    :: a -> Maybe a
 </programlisting>
 The form is called a "GADT-style declaration"
-because Generalised Algebraic Data Types, described in <xref linkend="gadt"/>, 
+because Generalised Algebraic Data Types, described in <xref linkend="gadt"/>,
 can only be declared using this form.</para>
-<para>Notice that GADT-style syntax generalises existential types (<xref linkend="existential-quantification"/>).  
+<para>Notice that GADT-style syntax generalises existential types (<xref linkend="existential-quantification"/>).
 For example, these two declarations are equivalent:
 <programlisting>
   data Foo = forall a. MkFoo a (a -> Bool)
   data Foo' where { MKFoo :: a -> (a->Bool) -> Foo' }
 </programlisting>
 </para>
-<para>Any data type that can be declared in standard Haskell-98 syntax 
+<para>Any data type that can be declared in standard Haskell-98 syntax
 can also be declared using GADT-style syntax.
 The choice is largely stylistic, but GADT-style declarations differ in one important respect:
 they treat class constraints on the data constructors differently.
@@ -2697,14 +2697,14 @@ context is made available by pattern matching.  For example:
   insert a (MkSet as) | a `elem` as = MkSet as
                       | otherwise   = MkSet (a:as)
 </programlisting>
-A use of <literal>MkSet</literal> as a constructor (e.g. in the definition of <literal>makeSet</literal>) 
+A use of <literal>MkSet</literal> as a constructor (e.g. in the definition of <literal>makeSet</literal>)
 gives rise to a <literal>(Eq a)</literal>
 constraint, as you would expect.  The new feature is that pattern-matching on <literal>MkSet</literal>
 (as in the definition of <literal>insert</literal>) makes <emphasis>available</emphasis> an <literal>(Eq a)</literal>
 context.  In implementation terms, the <literal>MkSet</literal> constructor has a hidden field that stores
 the <literal>(Eq a)</literal> dictionary that is passed to <literal>MkSet</literal>; so
 when pattern-matching that dictionary becomes available for the right-hand side of the match.
-In the example, the equality dictionary is used to satisfy the equality constraint 
+In the example, the equality dictionary is used to satisfy the equality constraint
 generated by the call to <literal>elem</literal>, so that the type of
 <literal>insert</literal> itself has no <literal>Eq</literal> constraint.
 </para>
@@ -2720,36 +2720,36 @@ For example, one possible application is to reify dictionaries:
    plus :: NumInst a -> a -> a -> a
    plus MkNumInst p q = p + q
 </programlisting>
-Here, a value of type <literal>NumInst a</literal> is equivalent 
+Here, a value of type <literal>NumInst a</literal> is equivalent
 to an explicit <literal>(Num a)</literal> dictionary.
 </para>
 <para>
 All this applies to constructors declared using the syntax of <xref linkend="existential-with-context"/>.
-For example, the <literal>NumInst</literal> data type above could equivalently be declared 
+For example, the <literal>NumInst</literal> data type above could equivalently be declared
 like this:
 <programlisting>
-   data NumInst a 
+   data NumInst a
       = Num a => MkNumInst (NumInst a)
 </programlisting>
-Notice that, unlike the situation when declaring an existential, there is 
+Notice that, unlike the situation when declaring an existential, there is
 no <literal>forall</literal>, because the <literal>Num</literal> constrains the
-data type's universally quantified type variable <literal>a</literal>.  
+data type's universally quantified type variable <literal>a</literal>.
 A constructor may have both universal and existential type variables: for example,
 the following two declarations are equivalent:
 <programlisting>
-   data T1 a 
+   data T1 a
        = forall b. (Num a, Eq b) => MkT1 a b
    data T2 a where
        MkT2 :: (Num a, Eq b) => a -> b -> T2 a
 </programlisting>
 </para>
-<para>All this behaviour contrasts with Haskell 98's peculiar treatment of 
+<para>All this behaviour contrasts with Haskell 98's peculiar treatment of
 contexts on a data type declaration (Section 4.2.1 of the Haskell 98 Report).
 In Haskell 98 the definition
 <programlisting>
   data Eq a => Set' a = MkSet' [a]
 </programlisting>
-gives <literal>MkSet'</literal> the same type as <literal>MkSet</literal> above.  But instead of 
+gives <literal>MkSet'</literal> the same type as <literal>MkSet</literal> above.  But instead of
 <emphasis>making available</emphasis> an <literal>(Eq a)</literal> constraint, pattern-matching
 on <literal>MkSet'</literal> <emphasis>requires</emphasis> an <literal>(Eq a)</literal> constraint!
 GHC faithfully implements this behaviour, odd though it is.  But for GADT-style declarations,
@@ -2763,7 +2763,7 @@ type declarations.
 <itemizedlist>
 <listitem><para>
 The result type of each data constructor must begin with the type constructor being defined.
-If the result type of all constructors 
+If the result type of all constructors
 has the form <literal>T a1 ... an</literal>, where <literal>a1 ... an</literal>
 are distinct type variables, then the data type is <emphasis>ordinary</emphasis>;
 otherwise is a <emphasis>generalised</emphasis> data type (<xref linkend="gadt"/>).
@@ -2781,8 +2781,8 @@ In this example we give a single signature for <literal>T1</literal> and <litera
 
 <listitem><para>
 The type signature of
-each constructor is independent, and is implicitly universally quantified as usual. 
-In particular, the type variable(s) in the "<literal>data T a where</literal>" header 
+each constructor is independent, and is implicitly universally quantified as usual.
+In particular, the type variable(s) in the "<literal>data T a where</literal>" header
 have no scope, and different constructors may have different universally-quantified type variables:
 <programlisting>
   data T a where        -- The 'a' has no scope
@@ -2799,7 +2799,7 @@ different constructors.  For example, this is fine:
     T1 :: Eq b => b -> b -> T b
     T2 :: (Show c, Ix c) => c -> [c] -> T c
 </programlisting>
-When patten matching, these constraints are made available to discharge constraints
+When pattern matching, these constraints are made available to discharge constraints
 in the body of the match. For example:
 <programlisting>
   f :: T a -> String
@@ -2813,8 +2813,8 @@ and similarly the <literal>Show</literal> constraint arising from the use of <li
 </para></listitem>
 
 <listitem><para>
-Unlike a Haskell-98-style 
-data type declaration, the type variable(s) in the "<literal>data Set a where</literal>" header 
+Unlike a Haskell-98-style
+data type declaration, the type variable(s) in the "<literal>data Set a where</literal>" header
 have no scope.  Indeed, one can write a kind signature instead:
 <programlisting>
   data Set :: * -> * where ...
@@ -2851,7 +2851,7 @@ declaration.   For example, these two declarations are equivalent
       Just1    :: a -> Maybe1 a
     } deriving( Eq, Ord )
 
-  data Maybe2 a = Nothing2 | Just2 a 
+  data Maybe2 a = Nothing2 | Just2 a
        deriving( Eq, Ord )
 </programlisting>
 </para></listitem>
@@ -2865,10 +2865,10 @@ in the result type:
      Nil   :: Foo
 </programlisting>
 Here the type variable <literal>a</literal> does not appear in the result type
-of either constructor.  
+of either constructor.
 Although it is universally quantified in the type of the constructor, such
-a type variable is often called "existential".  
-Indeed, the above declaration declares precisely the same type as 
+a type variable is often called "existential".
+Indeed, the above declaration declares precisely the same type as
 the <literal>data Foo</literal> in <xref linkend="existential-quantification"/>.
 </para><para>
 The type may contain a class context too, of course:
@@ -2889,23 +2889,23 @@ You can use record syntax on a GADT-style data type declaration:
 As usual, for every constructor that has a field <literal>f</literal>, the type of
 field <literal>f</literal> must be the same (modulo alpha conversion).
 The <literal>Child</literal> constructor above shows that the signature
-may have a context, existentially-quantified variables, and strictness annotations, 
+may have a context, existentially-quantified variables, and strictness annotations,
 just as in the non-record case.  (NB: the "type" that follows the double-colon
 is not really a type, because of the record syntax and strictness annotations.
 A "type" of this form can appear only in a constructor signature.)
 </para></listitem>
 
-<listitem><para> 
-Record updates are allowed with GADT-style declarations, 
+<listitem><para>
+Record updates are allowed with GADT-style declarations,
 only fields that have the following property: the type of the field
 mentions no existential type variables.
 </para></listitem>
 
-<listitem><para> 
-As in the case of existentials declared using the Haskell-98-like record syntax 
+<listitem><para>
+As in the case of existentials declared using the Haskell-98-like record syntax
 (<xref linkend="existential-records"/>),
 record-selector functions are generated only for those fields that have well-typed
-selectors.  
+selectors.
 Here is the example of that section, in GADT-style syntax:
 <programlisting>
 data Counter a where
@@ -2925,18 +2925,18 @@ Nevertheless, you can still use all the field names in pattern matching and reco
 <sect2 id="gadt">
 <title>Generalised Algebraic Data Types (GADTs)</title>
 
-<para>Generalised Algebraic Data Types generalise ordinary algebraic data types 
+<para>Generalised Algebraic Data Types generalise ordinary algebraic data types
 by allowing constructors to have richer return types.  Here is an example:
 <programlisting>
   data Term a where
       Lit    :: Int -> Term Int
       Succ   :: Term Int -> Term Int
-      IsZero :: Term Int -> Term Bool  
+      IsZero :: Term Int -> Term Bool
       If     :: Term Bool -> Term a -> Term a -> Term a
       Pair   :: Term a -> Term b -> Term (a,b)
 </programlisting>
 Notice that the return type of the constructors is not always <literal>Term a</literal>, as is the
-case with ordinary data types.  This generality allows us to 
+case with ordinary data types.  This generality allows us to
 write a well-typed <literal>eval</literal> function
 for these <literal>Terms</literal>:
 <programlisting>
@@ -2947,22 +2947,22 @@ for these <literal>Terms</literal>:
   eval (If b e1 e2) = if eval b then eval e1 else eval e2
   eval (Pair e1 e2) = (eval e1, eval e2)
 </programlisting>
-The key point about GADTs is that <emphasis>pattern matching causes type refinement</emphasis>.  
+The key point about GADTs is that <emphasis>pattern matching causes type refinement</emphasis>.
 For example, in the right hand side of the equation
 <programlisting>
   eval :: Term a -> a
   eval (Lit i) =  ...
 </programlisting>
 the type <literal>a</literal> is refined to <literal>Int</literal>.  That's the whole point!
-A precise specification of the type rules is beyond what this user manual aspires to, 
+A precise specification of the type rules is beyond what this user manual aspires to,
 but the design closely follows that described in
 the paper <ulink
 url="http://research.microsoft.com/%7Esimonpj/papers/gadt/">Simple
 unification-based type inference for GADTs</ulink>,
 (ICFP 2006).
-The general principle is this: <emphasis>type refinement is only carried out 
+The general principle is this: <emphasis>type refinement is only carried out
 based on user-supplied type annotations</emphasis>.
-So if no type signature is supplied for <literal>eval</literal>, no type refinement happens, 
+So if no type signature is supplied for <literal>eval</literal>, no type refinement happens,
 and lots of obscure error messages will
 occur.  However, the refinement is quite general.  For example, if we had:
 <programlisting>
@@ -2982,14 +2982,14 @@ and Ralf Hinze's
 may use different notation to that implemented in GHC.
 </para>
 <para>
-The rest of this section outlines the extensions to GHC that support GADTs.   The extension is enabled with 
+The rest of this section outlines the extensions to GHC that support GADTs.   The extension is enabled with
 <option>-XGADTs</option>.  The <option>-XGADTs</option> flag also sets <option>-XRelaxedPolyRec</option>.
 <itemizedlist>
 <listitem><para>
-A GADT can only be declared using GADT-style syntax (<xref linkend="gadt-style"/>); 
+A GADT can only be declared using GADT-style syntax (<xref linkend="gadt-style"/>);
 the old Haskell-98 syntax for data declarations always declares an ordinary data type.
 The result type of each constructor must begin with the type constructor being defined,
-but for a GADT the arguments to the type constructor can be arbitrary monotypes.  
+but for a GADT the arguments to the type constructor can be arbitrary monotypes.
 For example, in the <literal>Term</literal> data
 type above, the type of each constructor must end with <literal>Term ty</literal>, but
 the <literal>ty</literal> need not be a type variable (e.g. the <literal>Lit</literal>
@@ -3015,7 +3015,7 @@ For example:
       Lit    { val  :: Int }      :: Term Int
       Succ   { num  :: Term Int } :: Term Int
       Pred   { num  :: Term Int } :: Term Int
-      IsZero { arg  :: Term Int } :: Term Bool 
+      IsZero { arg  :: Term Int } :: Term Bool
       Pair   { arg1 :: Term a
              , arg2 :: Term b
              }                    :: Term (a,b)
@@ -3024,11 +3024,11 @@ For example:
              , fls  :: Term a
              }                    :: Term a
 </programlisting>
-However, for GADTs there is the following additional constraint: 
+However, for GADTs there is the following additional constraint:
 every constructor that has a field <literal>f</literal> must have
 the same result type (modulo alpha conversion)
-Hence, in the above example, we cannot merge the <literal>num</literal> 
-and <literal>arg</literal> fields above into a 
+Hence, in the above example, we cannot merge the <literal>num</literal>
+and <literal>arg</literal> fields above into a
 single name.  Although their field types are both <literal>Term Int</literal>,
 their selector functions actually have different types:
 
@@ -3039,7 +3039,7 @@ their selector functions actually have different types:
 </para></listitem>
 
 <listitem><para>
-When pattern-matching against data constructors drawn from a GADT, 
+When pattern-matching against data constructors drawn from a GADT,
 for example in a <literal>case</literal> expression, the following rules apply:
 <itemizedlist>
 <listitem><para>The type of the scrutinee must be rigid.</para></listitem>
@@ -3083,12 +3083,12 @@ The natural generated <literal>Eq</literal> code would result in these instance
   instance Eq (f a)     => Eq (T1 f a) where ...
   instance Eq (f (f a)) => Eq (T2 f a) where ...
 </programlisting>
-The first of these is obviously fine. The second is still fine, although less obviously. 
+The first of these is obviously fine. The second is still fine, although less obviously.
 The third is not Haskell 98, and risks losing termination of instances.
 </para>
 <para>
 GHC takes a conservative position: it accepts the first two, but not the third.  The  rule is this:
-each constraint in the inferred instance context must consist only of type variables, 
+each constraint in the inferred instance context must consist only of type variables,
 with no repetitions.
 </para>
 <para>
@@ -3112,10 +3112,10 @@ The syntax is identical to that of an ordinary instance declaration apart from (
 Note the following points:
 <itemizedlist>
 <listitem><para>
-You must supply an explicit context (in the example the context is <literal>(Eq a)</literal>), 
+You must supply an explicit context (in the example the context is <literal>(Eq a)</literal>),
 exactly as you would in an ordinary instance declaration.
-(In contrast, in a <literal>deriving</literal> clause 
-attached to a data type declaration, the context is inferred.) 
+(In contrast, in a <literal>deriving</literal> clause
+attached to a data type declaration, the context is inferred.)
 </para></listitem>
 
 <listitem><para>
@@ -3127,7 +3127,7 @@ controlled by the same flags; see <xref linkend="instance-decls"/>.
 <listitem><para>
 Unlike a <literal>deriving</literal>
 declaration attached to a <literal>data</literal> declaration, the instance can be more specific
-than the data type (assuming you also use 
+than the data type (assuming you also use
 <literal>-XFlexibleInstances</literal>, <xref linkend="instance-rules"/>).  Consider
 for example
 <programlisting>
@@ -3142,10 +3142,10 @@ but other types such as <literal>(Foo (Int,Bool))</literal> will not be an insta
 
 <listitem><para>
 Unlike a <literal>deriving</literal>
-declaration attached to a <literal>data</literal> declaration, 
+declaration attached to a <literal>data</literal> declaration,
 GHC does not restrict the form of the data type.  Instead, GHC simply generates the appropriate
 boilerplate code for the specified class, and typechecks it. If there is a type error, it is
-your problem. (GHC will show you the offending code if it has a type error.) 
+your problem. (GHC will show you the offending code if it has a type error.)
 The merit of this is that you can derive instances for GADTs and other exotic
 data types, providing only that the boilerplate code does indeed typecheck.  For example:
 <programlisting>
@@ -3155,8 +3155,8 @@ data types, providing only that the boilerplate code does indeed typecheck.  For
 
   deriving instance Show (T a)
 </programlisting>
-In this example, you cannot say <literal>... deriving( Show )</literal> on the 
-data type declaration for <literal>T</literal>, 
+In this example, you cannot say <literal>... deriving( Show )</literal> on the
+data type declaration for <literal>T</literal>,
 because <literal>T</literal> is a GADT, but you <emphasis>can</emphasis> generate
 the instance declaration using stand-alone deriving.
 </para>
@@ -3183,10 +3183,10 @@ GHC always treats the <emphasis>last</emphasis> parameter of the instance
 <title>Deriving clause for extra classes (<literal>Typeable</literal>, <literal>Data</literal>, etc)</title>
 
 <para>
-Haskell 98 allows the programmer to add "<literal>deriving( Eq, Ord )</literal>" to a data type 
-declaration, to generate a standard instance declaration for classes specified in the <literal>deriving</literal> clause.  
+Haskell 98 allows the programmer to add "<literal>deriving( Eq, Ord )</literal>" to a data type
+declaration, to generate a standard instance declaration for classes specified in the <literal>deriving</literal> clause.
 In Haskell 98, the only classes that may appear in the <literal>deriving</literal> clause are the standard
-classes <literal>Eq</literal>, <literal>Ord</literal>, 
+classes <literal>Eq</literal>, <literal>Ord</literal>,
 <literal>Enum</literal>, <literal>Ix</literal>, <literal>Bounded</literal>, <literal>Read</literal>, and <literal>Show</literal>.
 </para>
 <para>
@@ -3206,7 +3206,7 @@ Scrap More Boilerplate: Reflection, Zips, and Generalised Casts
 (Section 7.4 of the paper describes the multiple <literal>Typeable</literal> classes that
 are used, and only <literal>Typeable1</literal> up to
 <literal>Typeable7</literal> are provided in the library.)
-In other cases, there is nothing to stop the programmer writing a <literal>TypableX</literal>
+In other cases, there is nothing to stop the programmer writing a <literal>TypeableX</literal>
 class, whose kind suits that of the data type constructor, and
 then writing the data type instance by hand.
 </para>
@@ -3218,22 +3218,22 @@ instances of  the class <literal>Generic</literal>, defined in
 as described in <xref linkend="generic-programming"/>.
 </para></listitem>
 
-<listitem><para> With <option>-XDeriveFunctor</option>, you can derive instances of 
+<listitem><para> With <option>-XDeriveFunctor</option>, you can derive instances of
 the class <literal>Functor</literal>,
 defined in <literal>GHC.Base</literal>.
 </para></listitem>
 
-<listitem><para> With <option>-XDeriveFoldable</option>, you can derive instances of 
+<listitem><para> With <option>-XDeriveFoldable</option>, you can derive instances of
 the class <literal>Foldable</literal>,
 defined in <literal>Data.Foldable</literal>.
 </para></listitem>
 
-<listitem><para> With <option>-XDeriveTraversable</option>, you can derive instances of 
+<listitem><para> With <option>-XDeriveTraversable</option>, you can derive instances of
 the class <literal>Traversable</literal>,
 defined in <literal>Data.Traversable</literal>.
 </para></listitem>
 </itemizedlist>
-In each case the appropriate class must be in scope before it 
+In each case the appropriate class must be in scope before it
 can be mentioned in the <literal>deriving</literal> clause.
 </para>
 </sect2>
@@ -3250,7 +3250,7 @@ other classes you have to write an explicit instance declaration. For
 example, if you define
 
 <programlisting>
-  newtype Dollars = Dollars Int 
+  newtype Dollars = Dollars Int
 </programlisting>
 
 and you want to use arithmetic on <literal>Dollars</literal>, you have to
@@ -3271,9 +3271,9 @@ dictionary, only slower!
 
 <sect3> <title> Generalising the deriving clause </title>
 <para>
-GHC now permits such instances to be derived instead, 
+GHC now permits such instances to be derived instead,
 using the flag <option>-XGeneralizedNewtypeDeriving</option>,
-so one can write 
+so one can write
 <programlisting>
   newtype Dollars = Dollars Int deriving (Eq,Show,Num)
 </programlisting>
@@ -3295,10 +3295,10 @@ way. For example, suppose we have implemented state and failure monad
 transformers, such that
 
 <programlisting>
-  instance Monad m => Monad (State s m) 
+  instance Monad m => Monad (State s m)
   instance Monad m => Monad (Failure m)
 </programlisting>
-In Haskell 98, we can define a parsing monad by 
+In Haskell 98, we can define a parsing monad by
 <programlisting>
   type Parser tok m a = State [tok] (Failure m) a
 </programlisting>
@@ -3311,9 +3311,9 @@ without needing to write an instance of class <literal>Monad</literal>, via
   newtype Parser tok m a = Parser (State [tok] (Failure m) a)
                          deriving Monad
 </programlisting>
-In this case the derived instance declaration is of the form 
+In this case the derived instance declaration is of the form
 <programlisting>
-  instance Monad (State [tok] (Failure m)) => Monad (Parser tok m) 
+  instance Monad (State [tok] (Failure m)) => Monad (Parser tok m)
 </programlisting>
 
 Notice that, since <literal>Monad</literal> is a constructor class, the
@@ -3330,10 +3330,10 @@ application'' of the class appears in the <literal>deriving</literal>
 clause. For example, given the class
 
 <programlisting>
-  class StateMonad s m | m -> s where ... 
-  instance Monad m => StateMonad s (State s m) where ... 
+  class StateMonad s m | m -> s where ...
+  instance Monad m => StateMonad s (State s m) where ...
 </programlisting>
-then we can derive an instance of <literal>StateMonad</literal> for <literal>Parser</literal>s by 
+then we can derive an instance of <literal>StateMonad</literal> for <literal>Parser</literal>s by
 <programlisting>
   newtype Parser tok m a = Parser (State [tok] (Failure m) a)
                          deriving (Monad, StateMonad [tok])
@@ -3363,10 +3363,10 @@ Derived instance declarations are constructed as follows. Consider the
 declaration (after expansion of any type synonyms)
 
 <programlisting>
-  newtype T v1...vn = T' (t vk+1...vn) deriving (c1...cm) 
+  newtype T v1...vn = T' (t vk+1...vn) deriving (c1...cm)
 </programlisting>
 
-where 
+where
  <itemizedlist>
 <listitem><para>
   The <literal>ci</literal> are partial applications of
@@ -3380,15 +3380,15 @@ where
   The type <literal>t</literal> is an arbitrary type.
 </para></listitem>
 <listitem><para>
-  The type variables <literal>vk+1...vn</literal> do not occur in <literal>t</literal>, 
+  The type variables <literal>vk+1...vn</literal> do not occur in <literal>t</literal>,
   nor in the <literal>ci</literal>, and
 </para></listitem>
 <listitem><para>
-  None of the <literal>ci</literal> is <literal>Read</literal>, <literal>Show</literal>, 
+  None of the <literal>ci</literal> is <literal>Read</literal>, <literal>Show</literal>,
                <literal>Typeable</literal>, or <literal>Data</literal>.  These classes
                should not "look through" the type or its constructor.  You can still
-               derive these classes for a newtype, but it happens in the usual way, not 
-               via this new mechanism.  
+               derive these classes for a newtype, but it happens in the usual way, not
+               via this new mechanism.
 </para></listitem>
 </itemizedlist>
 Then, for each <literal>ci</literal>, the derived instance
@@ -3396,13 +3396,13 @@ declaration is:
 <programlisting>
   instance ci t => ci (T v1...vk)
 </programlisting>
-As an example which does <emphasis>not</emphasis> work, consider 
+As an example which does <emphasis>not</emphasis> work, consider
 <programlisting>
-  newtype NonMonad m s = NonMonad (State s m s) deriving Monad 
+  newtype NonMonad m s = NonMonad (State s m s) deriving Monad
 </programlisting>
-Here we cannot derive the instance 
+Here we cannot derive the instance
 <programlisting>
-  instance Monad (State s m) => Monad (NonMonad m) 
+  instance Monad (State s m) => Monad (NonMonad m)
 </programlisting>
 
 because the type variable <literal>s</literal> occurs in <literal>State s m</literal>,
@@ -3418,7 +3418,7 @@ important, since we can only derive instances for the last one. If the
 <literal>StateMonad</literal> class above were instead defined as
 
 <programlisting>
-  class StateMonad m s | m -> s where ... 
+  class StateMonad m s | m -> s where ...
 </programlisting>
 
 then we would not have been able to derive an instance for the
@@ -3427,7 +3427,7 @@ classes usually have one "main" parameter for which deriving new
 instances is most interesting.
 </para>
 <para>Lastly, all of this applies only for classes other than
-<literal>Read</literal>, <literal>Show</literal>, <literal>Typeable</literal>, 
+<literal>Read</literal>, <literal>Show</literal>, <literal>Typeable</literal>,
 and <literal>Data</literal>, for which the built-in derivation applies (section
 4.3.3. of the Haskell Report).
 (For the standard classes <literal>Eq</literal>, <literal>Ord</literal>,
@@ -3460,7 +3460,7 @@ All the extensions are enabled by the <option>-fglasgow-exts</option> flag.
 <sect3>
 <title>Multi-parameter type classes</title>
 <para>
-Multi-parameter type classes are permitted, with flag <option>-XMultiParamTypeClasses</option>. 
+Multi-parameter type classes are permitted, with flag <option>-XMultiParamTypeClasses</option>.
 For example:
 
 
@@ -3478,11 +3478,11 @@ For example:
 
 <para>
 In Haskell 98 the context of a class declaration (which introduces superclasses)
-must be simple; that is, each predicate must consist of a class applied to 
-type variables.  The flag <option>-XFlexibleContexts</option> 
+must be simple; that is, each predicate must consist of a class applied to
+type variables.  The flag <option>-XFlexibleContexts</option>
 (<xref linkend="flexible-contexts"/>)
 lifts this restriction,
-so that the only restriction on the context in a class declaration is 
+so that the only restriction on the context in a class declaration is
 that the class hierarchy must be acyclic.  So these class declarations are OK:
 
 
@@ -3532,7 +3532,7 @@ class type variable, thus:
     elem     :: Eq a => a -> s a -> Bool
 </programlisting>
 The type of <literal>elem</literal> is illegal in Haskell 98, because it
-contains the constraint <literal>Eq a</literal>, constrains only the 
+contains the constraint <literal>Eq a</literal>, constrains only the
 class type variable (in this case <literal>a</literal>).
 GHC lifts this restriction (flag <option>-XConstrainedClassMethods</option>).
 </para>
@@ -3555,7 +3555,7 @@ The type of the <literal>enum</literal> method is <literal>[a]</literal>, and
 this is also the type of the default method. You can lift this restriction
 and give another type to the default method using the flag
 <option>-XDefaultSignatures</option>. For instance, if you have written a
-generic implementation of enumeration in a class <literal>GEnum</literal> 
+generic implementation of enumeration in a class <literal>GEnum</literal>
 with method <literal>genum</literal> in terms of <literal>GHC.Generics</literal>,
 you can specify a default method that uses that generic implementation:
 <programlisting>
@@ -3574,7 +3574,7 @@ and type-checked with the type
 </para>
 
 <para>
-We use default signatures to simplify generic programming in GHC 
+We use default signatures to simplify generic programming in GHC
 (<xref linkend="generic-programming"/>).
 </para>
 
@@ -3587,14 +3587,14 @@ We use default signatures to simplify generic programming in GHC
 </title>
 
 <para> Functional dependencies are implemented as described by Mark Jones
-in &ldquo;<ulink url="http://citeseer.ist.psu.edu/jones00type.html">Type Classes with Functional Dependencies</ulink>&rdquo;, Mark P. Jones, 
-In Proceedings of the 9th European Symposium on Programming, 
+in &ldquo;<ulink url="http://citeseer.ist.psu.edu/jones00type.html">Type Classes with Functional Dependencies</ulink>&rdquo;, Mark P. Jones,
+In Proceedings of the 9th European Symposium on Programming,
 ESOP 2000, Berlin, Germany, March 2000, Springer-Verlag LNCS 1782,
 .
 </para>
 <para>
-Functional dependencies are introduced by a vertical bar in the syntax of a 
-class declaration;  e.g. 
+Functional dependencies are introduced by a vertical bar in the syntax of a
+class declaration;  e.g.
 <programlisting>
   class (Monad m) => MonadState s m | m -> s where ...
 
@@ -3605,7 +3605,7 @@ There should be more documentation, but there isn't (yet).  Yell if you need it.
 
 <sect3><title>Rules for functional dependencies </title>
 <para>
-In a class declaration, all of the class type variables must be reachable (in the sense 
+In a class declaration, all of the class type variables must be reachable (in the sense
 mentioned in <xref linkend="flexible-contexts"/>)
 from the free variables of each method type.
 For example:
@@ -3658,7 +3658,7 @@ class like this:
 from the Hugs user manual, reproduced here (with minor changes) by kind
 permission of Mark Jones.
 </para>
-<para> 
+<para>
 Consider the following class, intended as part of a
 library for collection types:
 <programlisting>
@@ -3673,7 +3673,7 @@ instances of this class for lists or characteristic functions (both of which
 can be used to represent collections of any equality type), bit sets (which can
 be used to represent collections of characters), or hash tables (which can be
 used to represent any collection whose elements have a hash function). Omitting
-standard implementation details, this would lead to the following declarations: 
+standard implementation details, this would lead to the following declarations:
 <programlisting>
    instance Eq e => Collects e [e] where ...
    instance Eq e => Collects e (e -> Bool) where ...
@@ -3683,7 +3683,7 @@ standard implementation details, this would lead to the following declarations:
 </programlisting>
 All this looks quite promising; we have a class and a range of interesting
 implementations. Unfortunately, there are some serious problems with the class
-declaration. First, the empty function has an ambiguous type: 
+declaration. First, the empty function has an ambiguous type:
 <programlisting>
    empty :: Collects e ce => ce
 </programlisting>
@@ -3697,12 +3697,12 @@ type.
 We can sidestep this specific problem by removing the empty member from the
 class declaration. However, although the remaining members, insert and member,
 do not have ambiguous types, we still run into problems when we try to use
-them. For example, consider the following two functions: 
+them. For example, consider the following two functions:
 <programlisting>
    f x y = insert x . insert y
    g     = f True 'a'
 </programlisting>
-for which GHC infers the following types: 
+for which GHC infers the following types:
 <programlisting>
    f :: (Collects a c, Collects b c) => a -> b -> c -> c
    g :: (Collects Bool c, Collects Char c) => c -> c
@@ -3721,7 +3721,7 @@ might even be in a different module.
 
 <para>
 Faced with the problems described above, some Haskell programmers might be
-tempted to use something like the following version of the class declaration: 
+tempted to use something like the following version of the class declaration:
 <programlisting>
    class Collects e c where
       empty  :: c e
@@ -3732,16 +3732,16 @@ The key difference here is that we abstract over the type constructor c that is
 used to form the collection type c e, and not over that collection type itself,
 represented by ce in the original class declaration. This avoids the immediate
 problems that we mentioned above: empty has type <literal>Collects e c => c
-e</literal>, which is not ambiguous. 
+e</literal>, which is not ambiguous.
 </para>
 <para>
-The function f from the previous section has a more accurate type: 
+The function f from the previous section has a more accurate type:
 <programlisting>
    f :: (Collects e c) => e -> e -> c e -> c e
 </programlisting>
 The function g from the previous section is now rejected with a type error as
 we would hope because the type of f does not allow the two arguments to have
-different types. 
+different types.
 This, then, is an example of a multiple parameter class that does actually work
 quite well in practice, without ambiguity problems.
 There is, however, a catch. This version of the Collects class is nowhere near
@@ -3767,14 +3767,14 @@ underlying ideas are also discussed in a more theoretical and abstract setting
 in a manuscript [implparam], where they are identified as one point in a
 general design space for systems of implicit parameterization.).
 
-To start with an abstract example, consider a declaration such as: 
+To start with an abstract example, consider a declaration such as:
 <programlisting>
    class C a b where ...
 </programlisting>
 which tells us simply that C can be thought of as a binary relation on types
 (or type constructors, depending on the kinds of a and b). Extra clauses can be
 included in the definition of classes to add information about dependencies
-between parameters, as in the following examples: 
+between parameters, as in the following examples:
 <programlisting>
    class D a b | a -> b where ...
    class E a b | a -> b, b -> a where ...
@@ -3797,11 +3797,11 @@ annotated with multiple dependencies using commas as separators, as in the
 definition of E above. Some dependencies that we can write in this notation are
 redundant, and will be rejected because they don't serve any useful
 purpose, and may instead indicate an error in the program. Examples of
-dependencies like this include  <literal>a -&gt; a </literal>,  
-<literal>a -&gt; a a </literal>,  
+dependencies like this include  <literal>a -&gt; a </literal>,
+<literal>a -&gt; a a </literal>,
 <literal>a -&gt; </literal>, etc. There can also be
-some redundancy if multiple dependencies are given, as in  
-<literal>a-&gt;b</literal>, 
+some redundancy if multiple dependencies are given, as in
+<literal>a-&gt;b</literal>,
  <literal>b-&gt;c </literal>,  <literal>a-&gt;c </literal>, and
 in which some subset implies the remaining dependencies. Examples like this are
 not treated as errors. Note that dependencies appear only in class
@@ -3816,19 +3816,19 @@ compiler, on the other hand, is responsible for ensuring that the set of
 instances that are in scope at any given point in the program is consistent
 with any declared dependencies. For example, the following pair of instance
 declarations cannot appear together in the same scope because they violate the
-dependency for D, even though either one on its own would be acceptable: 
+dependency for D, even though either one on its own would be acceptable:
 <programlisting>
    instance D Bool Int where ...
    instance D Bool Char where ...
 </programlisting>
-Note also that the following declaration is not allowed, even by itself: 
+Note also that the following declaration is not allowed, even by itself:
 <programlisting>
    instance D [a] b where ...
 </programlisting>
 The problem here is that this instance would allow one particular choice of [a]
 to be associated with more than one choice for b, which contradicts the
 dependency specified in the definition of D. More generally, this means that,
-in any instance of the form: 
+in any instance of the form:
 <programlisting>
    instance D t s where ...
 </programlisting>
@@ -3841,7 +3841,7 @@ The benefit of including dependency information is that it allows us to define
 more general multiple parameter classes, without ambiguity problems, and with
 the benefit of more accurate types. To illustrate this, we return to the
 collection class example, and annotate the original definition of <literal>Collects</literal>
-with a simple dependency: 
+with a simple dependency:
 <programlisting>
    class Collects e ce | ce -> e where
       empty  :: ce
@@ -3870,18 +3870,18 @@ contains a variable on the left of the => that is not uniquely determined
 Dependencies also help to produce more accurate types for user defined
 functions, and hence to provide earlier detection of errors, and less cluttered
 types for programmers to work with. Recall the previous definition for a
-function f: 
+function f:
 <programlisting>
    f x y = insert x y = insert x . insert y
 </programlisting>
-for which we originally obtained a type: 
+for which we originally obtained a type:
 <programlisting>
    f :: (Collects a c, Collects b c) => a -> b -> c -> c
 </programlisting>
 Given the dependency information that we have for Collects, however, we can
 deduce that a and b must be equal because they both appear as the second
 parameter in a Collects constraint with the same first parameter c. Hence we
-can infer a shorter and more accurate type for f: 
+can infer a shorter and more accurate type for f:
 <programlisting>
    f :: (Collects a c) => a -> a -> c -> c
 </programlisting>
@@ -3992,7 +3992,7 @@ The Paterson Conditions: for each assertion in the context
 <replaceable>tvs</replaceable><subscript>left</subscript> <literal>-&gt;</literal>
 <replaceable>tvs</replaceable><subscript>right</subscript>,  of the class,
 every type variable in
-S(<replaceable>tvs</replaceable><subscript>right</subscript>) must appear in 
+S(<replaceable>tvs</replaceable><subscript>right</subscript>) must appear in
 S(<replaceable>tvs</replaceable><subscript>left</subscript>), where S is the
 substitution mapping each type variable in the class declaration to the
 corresponding type in the instance declaration.
@@ -4000,8 +4000,8 @@ corresponding type in the instance declaration.
 </orderedlist>
 These restrictions ensure that context reduction terminates: each reduction
 step makes the problem smaller by at least one
-constructor.  Both the Paterson Conditions and the Coverage Condition are lifted 
-if you give the <option>-XUndecidableInstances</option> 
+constructor.  Both the Paterson Conditions and the Coverage Condition are lifted
+if you give the <option>-XUndecidableInstances</option>
 flag (<xref linkend="undecidable-instances"/>).
 You can find lots of background material about the reason for these
 restrictions in the paper <ulink
@@ -4015,7 +4015,7 @@ For example, these are OK:
   instance Eq (S [a])         -- Structured type in head
 
       -- Repeated type variable in head
-  instance C4 a a => C4 [a] [a] 
+  instance C4 a a => C4 [a] [a]
   instance Stateful (ST s) (MutVar s)
 
       -- Head can consist of type variables only
@@ -4031,7 +4031,7 @@ But these are not:
 <programlisting>
       -- Context assertion no smaller than head
   instance C a => C a where ...
-      -- (C b b) has more more occurrences of b than the head
+      -- (C b b) has more occurrences of b than the head
   instance C b b => Foo [b] where ...
 </programlisting>
 </para>
@@ -4089,7 +4089,7 @@ the head, something that is excluded by the normal rules. For example:
 <programlisting>
   class HasConverter a b | a -> b where
      convert :: a -> b
-   
+
   data Foo a = MkFoo a
 
   instance (HasConverter a b,Show b) => Show (Foo a) where
@@ -4123,7 +4123,7 @@ makes instance inference go into a loop, because it requires the constraint
 <para>
 Nevertheless, GHC allows you to experiment with more liberal rules.  If you use
 the experimental flag <option>-XUndecidableInstances</option>
-<indexterm><primary>-XUndecidableInstances</primary></indexterm>, 
+<indexterm><primary>-XUndecidableInstances</primary></indexterm>,
 both the Paterson Conditions and the Coverage Condition
 (described in <xref linkend="instance-rules"/>) are lifted.  Termination is ensured by having a
 fixed-depth recursion stack.  If you exceed the stack depth you get a
@@ -4142,11 +4142,11 @@ declaration
 should be used to resolve a type-class constraint</emphasis>. This behaviour
 can be modified by two flags: <option>-XOverlappingInstances</option>
 <indexterm><primary>-XOverlappingInstances
-</primary></indexterm> 
+</primary></indexterm>
 and <option>-XIncoherentInstances</option>
 <indexterm><primary>-XIncoherentInstances
 </primary></indexterm>, as this section discusses.  Both these
-flags are dynamic flags, and can be set on a per-module basis, using 
+flags are dynamic flags, and can be set on a per-module basis, using
 an <literal>OPTIONS_GHC</literal> pragma if desired (<xref linkend="source-file-options"/>).</para>
 <para>
 When GHC tries to resolve, say, the constraint <literal>C Int Bool</literal>,
@@ -4160,14 +4160,14 @@ these declarations:
   instance context3 => C Int [a]   where ...  -- (C)
   instance context4 => C Int [Int] where ...  -- (D)
 </programlisting>
-The instances (A) and (B) match the constraint <literal>C Int Bool</literal>, 
+The instances (A) and (B) match the constraint <literal>C Int Bool</literal>,
 but (C) and (D) do not.  When matching, GHC takes
 no account of the context of the instance declaration
 (<literal>context1</literal> etc).
 GHC's default behaviour is that <emphasis>exactly one instance must match the
-constraint it is trying to resolve</emphasis>.  
+constraint it is trying to resolve</emphasis>.
 It is fine for there to be a <emphasis>potential</emphasis> of overlap (by
-including both declarations (A) and (B), say); an error is only reported if a 
+including both declarations (A) and (B), say); an error is only reported if a
 particular constraint matches more than one.
 </para>
 
@@ -4187,16 +4187,16 @@ However, GHC is conservative about committing to an overlapping instance.  For e
 Suppose that from the RHS of <literal>f</literal> we get the constraint
 <literal>C Int [b]</literal>.  But
 GHC does not commit to instance (C), because in a particular
-call of <literal>f</literal>, <literal>b</literal> might be instantiate 
+call of <literal>f</literal>, <literal>b</literal> might be instantiate
 to <literal>Int</literal>, in which case instance (D) would be more specific still.
-So GHC rejects the program.  
+So GHC rejects the program.
 (If you add the flag <option>-XIncoherentInstances</option>,
-GHC will instead pick (C), without complaining about 
+GHC will instead pick (C), without complaining about
 the problem of subsequent instantiations.)
 </para>
 <para>
 Notice that we gave a type signature to <literal>f</literal>, so GHC had to
-<emphasis>check</emphasis> that <literal>f</literal> has the specified type.  
+<emphasis>check</emphasis> that <literal>f</literal> has the specified type.
 Suppose instead we do not give a type signature, asking GHC to <emphasis>infer</emphasis>
 it instead.  In this case, GHC will refrain from
 simplifying the constraint <literal>C Int [b]</literal> (for the same reason
@@ -4204,10 +4204,10 @@ as before) but, rather than rejecting the program, it will infer the type
 <programlisting>
   f :: C Int [b] => [b] -> [b]
 </programlisting>
-That postpones the question of which instance to pick to the 
+That postpones the question of which instance to pick to the
 call site for <literal>f</literal>
 by which time more is known about the type <literal>b</literal>.
-You can write this type signature yourself if you use the 
+You can write this type signature yourself if you use the
 <link linkend="flexible-contexts"><option>-XFlexibleContexts</option></link>
 flag.
 </para>
@@ -4231,7 +4231,7 @@ of the instance declaration, thus:
 (You need <link linkend="instance-rules"><option>-XFlexibleInstances</option></link> to do this.)
 </para>
 <para>
-Warning: overlapping instances must be used with care.  They 
+Warning: overlapping instances must be used with care.  They
 can give rise to incoherence (ie different instance choices are made
 in different parts of the program) even without <option>-XIncoherentInstances</option>. Consider:
 <programlisting>
@@ -4265,20 +4265,20 @@ In function <literal>showHelp</literal> GHC sees no overlapping
 instances, and so uses the <literal>MyShow [a]</literal> instance
 without complaint.  In the call to <literal>myshow</literal> in <literal>main</literal>,
 GHC resolves the <literal>MyShow [T]</literal> constraint using the overlapping
-instance declaration in module <literal>Main</literal>. As a result, 
+instance declaration in module <literal>Main</literal>. As a result,
 the program prints
 <programlisting>
   "Used more specific instance"
   "Used generic instance"
 </programlisting>
-(An alternative possible behaviour, not currently implemented, 
+(An alternative possible behaviour, not currently implemented,
 would be to reject module <literal>Help</literal>
 on the grounds that a later instance declaration might overlap the local one.)
 </para>
 <para>
-The willingness to be overlapped or incoherent is a property of 
+The willingness to be overlapped or incoherent is a property of
 the <emphasis>instance declaration</emphasis> itself, controlled by the
-presence or otherwise of the <option>-XOverlappingInstances</option> 
+presence or otherwise of the <option>-XOverlappingInstances</option>
 and <option>-XIncoherentInstances</option> flags when that module is
 being defined.  Specifically, during the lookup process:
 <itemizedlist>
@@ -4297,12 +4297,12 @@ Suppose an instance declaration does not match the constraint being looked up, b
 does <emphasis>unify</emphasis> with it, so that it might match when the constraint is further
 instantiated.  Usually GHC will regard this as a reason for not committing to
 some other constraint.  But if the instance declaration was compiled with
-<option>-XIncoherentInstances</option>, GHC will skip the "does-it-unify?" 
+<option>-XIncoherentInstances</option>, GHC will skip the "does-it-unify?"
 check for that declaration.
 </para></listitem>
 </itemizedlist>
-These rules make it possible for a library author to design a library that relies on 
-overlapping instances without the library client having to know.  
+These rules make it possible for a library author to design a library that relies on
+overlapping instances without the library client having to know.
 </para>
 <para>The <option>-XIncoherentInstances</option> flag implies the
 <option>-XOverlappingInstances</option> flag, but not vice versa.
@@ -4350,7 +4350,7 @@ Haskell's defaulting mechanism is extended to cover string literals, when <optio
 Specifically:
 <itemizedlist>
 <listitem><para>
-Each type in a default declaration must be an 
+Each type in a default declaration must be an
 instance of <literal>Num</literal> <emphasis>or</emphasis> of <literal>IsString</literal>.
 </para></listitem>
 
@@ -4395,23 +4395,23 @@ to work since it gets translated into an equality comparison.
 
 <para>
   <firstterm>Indexed type families</firstterm> are a new GHC extension to
-  facilitate type-level 
+  facilitate type-level
   programming. Type families are a generalisation of <firstterm>associated
-  data types</firstterm> 
-  (&ldquo;<ulink url="http://www.cse.unsw.edu.au/~chak/papers/CKPM05.html">Associated 
+  data types</firstterm>
+  (&ldquo;<ulink url="http://www.cse.unsw.edu.au/~chak/papers/CKPM05.html">Associated
   Types with Class</ulink>&rdquo;, M. Chakravarty, G. Keller, S. Peyton Jones,
   and S. Marlow. In Proceedings of &ldquo;The 32nd Annual ACM SIGPLAN-SIGACT
      Symposium on Principles of Programming Languages (POPL'05)&rdquo;, pages
   1-13, ACM Press, 2005) and <firstterm>associated type synonyms</firstterm>
-  (&ldquo;<ulink url="http://www.cse.unsw.edu.au/~chak/papers/CKP05.html">Type  
+  (&ldquo;<ulink url="http://www.cse.unsw.edu.au/~chak/papers/CKP05.html">Type
   Associated Type Synonyms</ulink>&rdquo;. M. Chakravarty, G. Keller, and
-  S. Peyton Jones. 
+  S. Peyton Jones.
   In Proceedings of &ldquo;The Tenth ACM SIGPLAN International Conference on
   Functional Programming&rdquo;, ACM Press, pages 241-253, 2005).  Type families
-  themselves are described in the paper &ldquo;<ulink 
+  themselves are described in the paper &ldquo;<ulink
   url="http://www.cse.unsw.edu.au/~chak/papers/SPCS08.html">Type
   Checking with Open Type Functions</ulink>&rdquo;, T. Schrijvers,
-  S. Peyton-Jones, 
+  S. Peyton-Jones,
   M. Chakravarty, and M. Sulzmann, in Proceedings of &ldquo;ICFP 2008: The
   13th ACM SIGPLAN International Conference on Functional
   Programming&rdquo;, ACM Press, pages 51-62, 2008. Type families
@@ -4420,13 +4420,13 @@ to work since it gets translated into an equality comparison.
   interfaces as well as interfaces with enhanced static information, much like
   dependent types. They might also be regarded as an alternative to functional
   dependencies, but provide a more functional style of type-level programming
-  than the relational style of functional dependencies. 
+  than the relational style of functional dependencies.
 </para>
 <para>
   Indexed type families, or type families for short, are type constructors that
   represent sets of types. Set members are denoted by supplying the type family
   constructor with type parameters, which are called <firstterm>type
-  indices</firstterm>. The 
+  indices</firstterm>. The
   difference between vanilla parametrised type constructors and family
   constructors is much like between parametrically polymorphic functions and
   (ad-hoc polymorphic) methods of type classes. Parametric polymorphic functions
@@ -4434,14 +4434,14 @@ to work since it gets translated into an equality comparison.
   behaviour in dependence on the class type parameters. Similarly, vanilla type
   constructors imply the same data representation for all type instances, but
   family constructors can have varying representation types for varying type
-  indices. 
+  indices.
 </para>
 <para>
   Indexed type families come in two flavours: <firstterm>data
-    families</firstterm> and <firstterm>type synonym 
+    families</firstterm> and <firstterm>type synonym
     families</firstterm>. They are the indexed family variants of algebraic
   data types and type synonyms, respectively. The instances of data families
-  can be data types and newtypes. 
+  can be data types and newtypes.
 </para>
 <para>
   Type families are enabled by the flag <option>-XTypeFamilies</option>.
@@ -4455,7 +4455,7 @@ to work since it gets translated into an equality comparison.
 
   <para>
     Data families appear in two flavours: (1) they can be defined on the
-    toplevel 
+    toplevel
     or (2) they can appear inside type classes (in which case they are known as
     associated types). The former is the more general variant, as it lacks the
     requirement for the type-indexes to coincide with the class
@@ -4465,11 +4465,11 @@ to work since it gets translated into an equality comparison.
     and then cover the additional constraints placed on associated types.
   </para>
 
-  <sect3 id="data-family-declarations"> 
+  <sect3 id="data-family-declarations">
     <title>Data family declarations</title>
 
     <para>
-      Indexed data families are introduced by a signature, such as 
+      Indexed data families are introduced by a signature, such as
 <programlisting>
 data family GMap k :: * -> *
 </programlisting>
@@ -4483,7 +4483,7 @@ data family Array e
       Just as with
       [http://www.haskell.org/ghc/docs/latest/html/users_guide/gadt.html GADT
       declarations] named arguments are entirely optional, so that we can
-      declare <literal>Array</literal> alternatively with 
+      declare <literal>Array</literal> alternatively with
 <programlisting>
 data family Array :: * -> *
 </programlisting>
@@ -4494,7 +4494,7 @@ data family Array :: * -> *
       <para>
        When a data family is declared as part of a type class, we drop
        the <literal>family</literal> special.  The <literal>GMap</literal>
-       declaration takes the following form 
+       declaration takes the following form
 <programlisting>
 class GMapKey k where
   data GMap k :: * -> *
@@ -4505,7 +4505,7 @@ class GMapKey k where
        the argument names must be class parameters.  Each class parameter may
        only be used at most once per associated type, but some may be omitted
        and they may be in an order other than in the class head.  Hence, the
-       following contrived example is admissible: 
+       following contrived example is admissible:
 <programlisting>
   class C a b c where
   data T c a :: *
@@ -4514,7 +4514,7 @@ class GMapKey k where
     </sect4>
   </sect3>
 
-  <sect3 id="data-instance-declarations"> 
+  <sect3 id="data-instance-declarations">
     <title>Data instance declarations</title>
 
     <para>
@@ -4528,7 +4528,7 @@ class GMapKey k where
       they are fully applied and expand to a type that is itself admissible -
       exactly as this is required for occurrences of type synonyms in class
       instance parameters.  For example, the <literal>Either</literal>
-      instance for <literal>GMap</literal> is 
+      instance for <literal>GMap</literal> is
 <programlisting>
 data instance GMap (Either a b) v = GMapEither (GMap a v) (GMap b v)
 </programlisting>
@@ -4537,18 +4537,18 @@ data instance GMap (Either a b) v = GMapEither (GMap a v) (GMap b v)
     </para>
     <para>
       Data and newtype instance declarations are only permitted when an
-      appropriate family declaration is in scope - just as a class instance declaratoin
+      appropriate family declaration is in scope - just as a class instance declaration
       requires the class declaration to be visible.  Moreover, each instance
       declaration has to conform to the kind determined by its family
       declaration.  This implies that the number of parameters of an instance
       declaration matches the arity determined by the kind of the family.
     </para>
     <para>
-      A data family instance declaration can use the full exprssiveness of
+      A data family instance declaration can use the full expressiveness of
       ordinary <literal>data</literal> or <literal>newtype</literal> declarations:
       <itemizedlist>
       <listitem><para> Although, a data family is <emphasis>introduced</emphasis> with
-      the keyword "<literal>data</literal>", a data family <emphasis>instance</emphasis> can 
+      the keyword "<literal>data</literal>", a data family <emphasis>instance</emphasis> can
       use either <literal>data</literal> or <literal>newtype</literal>. For example:
 <programlisting>
 data family T a
@@ -4576,7 +4576,7 @@ data instance G [a] b where
       Even if type families are defined as toplevel declarations, functions
       that perform different computations for different family instances may still
       need to be defined as methods of type classes.  In particular, the
-      following is not possible: 
+      following is not possible:
 <programlisting>
 data family T a
 data instance T Int  = A
@@ -4587,7 +4587,7 @@ foo B = 2             -- ...will produce a type error.
 </programlisting>
 Instead, you would have to write <literal>foo</literal> as a class operation, thus:
 <programlisting>
-class C a where 
+class C a where
   foo :: T a -> Int
 instance Foo Int where
   foo A = 1
@@ -4598,7 +4598,7 @@ instance Foo Char where
       Types), it might seem as if a definition, such as the above, should be
       feasible.  However, type families are - in contrast to GADTs - are
       <emphasis>open;</emphasis> i.e., new instances can always be added,
-      possibly in other 
+      possibly in other
       modules.  Supporting pattern matching across different data instances
       would require a form of extensible case construct.)
     </para>
@@ -4609,7 +4609,7 @@ instance Foo Char where
        When an associated data family instance is declared within a type
        class instance, we drop the <literal>instance</literal> keyword in the
        family instance.  So, the <literal>Either</literal> instance
-       for <literal>GMap</literal> becomes: 
+       for <literal>GMap</literal> becomes:
 <programlisting>
 instance (GMapKey a, GMapKey b) => GMapKey (Either a b) where
   data GMap (Either a b) v = GMapEither (GMap a v) (GMap b v)
@@ -4622,7 +4622,7 @@ instance (GMapKey a, GMapKey b) => GMapKey (Either a b) where
         which coincides with the only class parameter.  Any parameters to the
         family constructor that do not correspond to class parameters, need to
         be variables in every instance; here this is the
-        variable <literal>v</literal>. 
+        variable <literal>v</literal>.
       </para>
       <para>
        Instances for an associated family can only appear as part of
@@ -4632,7 +4632,7 @@ instance (GMapKey a, GMapKey b) => GMapKey (Either a b) where
        types can be omitted in class instances.  If an associated family
        instance is omitted, the corresponding instance type is not inhabited;
        i.e., only diverging expressions, such
-       as <literal>undefined</literal>, can assume the type. 
+       as <literal>undefined</literal>, can assume the type.
       </para>
     </sect4>
 
@@ -4642,13 +4642,13 @@ instance (GMapKey a, GMapKey b) => GMapKey (Either a b) where
        In the case of multi-parameter type classes, the visibility of class
        parameters in the right-hand side of associated family instances
        depends <emphasis>solely</emphasis> on the parameters of the data
-       family.  As an example, consider the simple class declaration 
+       family.  As an example, consider the simple class declaration
 <programlisting>
 class C a b where
   data T a
 </programlisting>
         Only one of the two class parameters is a parameter to the data
-        family.  Hence, the following instance declaration is invalid: 
+        family.  Hence, the following instance declaration is invalid:
 <programlisting>
 instance C [c] d where
   data T [c] = MkT (c, d)    -- WRONG!!  'd' is not in scope
@@ -4656,7 +4656,7 @@ instance C [c] d where
         Here, the right-hand side of the data instance mentions the type
         variable <literal>d</literal> that does not occur in its left-hand
         side.  We cannot admit such data instances as they would compromise
-        type safety. 
+        type safety.
       </para>
     </sect4>
 
@@ -4665,7 +4665,7 @@ instance C [c] d where
       <para>
        Type class instances of instances of data families can be defined as
        usual, and in particular data instance declarations can
-       have <literal>deriving</literal> clauses.  For example, we can write 
+       have <literal>deriving</literal> clauses.  For example, we can write
 <programlisting>
 data GMap () v = GMapUnit (Maybe v)
                deriving Show
@@ -4682,7 +4682,7 @@ instance Show v => Show (GMap () v) where ...
        reasons that we cannot define a toplevel function that performs
        pattern matching on the data constructors
        of <emphasis>different</emphasis> instances of a single type family.
-       It would require a form of extensible case construct. 
+       It would require a form of extensible case construct.
       </para>
     </sect4>
 
@@ -4692,7 +4692,7 @@ instance Show v => Show (GMap () v) where ...
        The instance declarations of a data family used in a single program
        may not overlap at all, independent of whether they are associated or
        not.  In contrast to type class instances, this is not only a matter
-       of consistency, but one of type safety. 
+       of consistency, but one of type safety.
       </para>
     </sect4>
 
@@ -4716,7 +4716,7 @@ instance Show v => Show (GMap () v) where ...
       an export item, these may be either imported or defined in the current
       module.  The treatment of import and export items that explicitly list
       data constructors, such as <literal>GMap(GMapEither)</literal>, is
-      analogous. 
+      analogous.
     </para>
 
     <sect4 id="data-family-impexp-assoc">
@@ -4731,7 +4731,7 @@ instance Show v => Show (GMap () v) where ...
        type name needs to be prefixed by the keyword <literal>type</literal>.
        So for example, when explicitly listing the components of
        the <literal>GMapKey</literal> class, we write <literal>GMapKey(type
-       GMap, empty, lookup, insert)</literal>. 
+       GMap, empty, lookup, insert)</literal>.
       </para>
     </sect4>
 
@@ -4739,7 +4739,7 @@ instance Show v => Show (GMap () v) where ...
       <title>Examples</title>
       <para>
        Assuming our running <literal>GMapKey</literal> class example, let us
-       look at some export lists and their meaning: 
+       look at some export lists and their meaning:
        <itemizedlist>
          <listitem>
            <para><literal>module GMap (GMapKey) where...</literal>: Exports
@@ -4750,14 +4750,14 @@ instance Show v => Show (GMap () v) where ...
              Exports the class, the associated type <literal>GMap</literal>
              and the member
              functions <literal>empty</literal>, <literal>lookup</literal>,
-             and <literal>insert</literal>.  None of the data constructors is 
+             and <literal>insert</literal>.  None of the data constructors is
              exported.</para>
-         </listitem> 
+         </listitem>
          <listitem>
            <para><literal>module GMap (GMapKey(..), GMap(..))
                where...</literal>: As before, but also exports all the data
-             constructors <literal>GMapInt</literal>, 
-             <literal>GMapChar</literal>,  
+             constructors <literal>GMapInt</literal>,
+             <literal>GMapChar</literal>,
              <literal>GMapUnit</literal>, <literal>GMapPair</literal>,
              and <literal>GMapUnit</literal>.</para>
          </listitem>
@@ -4778,7 +4778,7 @@ instance Show v => Show (GMap () v) where ...
        write <literal>GMapKey(type GMap(..))</literal> &mdash; i.e.,
        sub-component specifications cannot be nested.  To
        specify <literal>GMap</literal>'s data constructors, you have to list
-       it separately. 
+       it separately.
       </para>
     </sect4>
 
@@ -4787,7 +4787,7 @@ instance Show v => Show (GMap () v) where ...
       <para>
        Family instances are implicitly exported, just like class instances.
        However, this applies only to the heads of instances, not to the data
-       constructors an instance defines. 
+       constructors an instance defines.
       </para>
     </sect4>
 
@@ -4814,13 +4814,13 @@ instance Show v => Show (GMap () v) where ...
     <title>Type family declarations</title>
 
     <para>
-      Indexed type families are introduced by a signature, such as 
+      Indexed type families are introduced by a signature, such as
 <programlisting>
 type family Elem c :: *
 </programlisting>
       The special <literal>family</literal> distinguishes family from standard
       type declarations.  The result kind annotation is optional and, as
-      usual, defaults to <literal>*</literal> if omitted.  An example is 
+      usual, defaults to <literal>*</literal> if omitted.  An example is
 <programlisting>
 type family Elem c
 </programlisting>
@@ -4831,13 +4831,13 @@ type family Elem c
       and it implies that the kind of a type family is not sufficient to
       determine a family's arity, and hence in general, also insufficient to
       determine whether a type family application is well formed.  As an
-      example, consider the following declaration: 
+      example, consider the following declaration:
 <programlisting>
-type family F a b :: * -> *   -- F's arity is 2, 
+type family F a b :: * -> *   -- F's arity is 2,
                               -- although its overall kind is * -> * -> * -> *
 </programlisting>
       Given this declaration the following are examples of well-formed and
-      malformed types: 
+      malformed types:
 <programlisting>
 F Char [Int]       -- OK!  Kind: * -> *
 F Char [Int] Bool  -- OK!  Kind: *
@@ -4851,7 +4851,7 @@ F Bool             -- WRONG: unsaturated application
       <para>
        When a type family is declared as part of a type class, we drop
        the <literal>family</literal> special.  The <literal>Elem</literal>
-       declaration takes the following form 
+       declaration takes the following form
 <programlisting>
 class Collects ce where
   type Elem ce :: *
@@ -4860,7 +4860,7 @@ class Collects ce where
         The argument names of the type family must be class parameters.  Each
         class parameter may only be used at most once per associated type, but
         some may be omitted and they may be in an order other than in the
-        class head.  Hence, the following contrived example is admissible: 
+        class head.  Hence, the following contrived example is admissible:
 <programlisting>
 class C a b c where
   type T c a :: *
@@ -4882,7 +4882,7 @@ class C a b c where
       type synonyms are allowed as long as they are fully applied and expand
       to a type that is admissible - these are the exact same requirements as
       for data instances.  For example, the <literal>[e]</literal> instance
-      for <literal>Elem</literal> is 
+      for <literal>Elem</literal> is
 <programlisting>
 type instance Elem [e] = e
 </programlisting>
@@ -4898,7 +4898,7 @@ type instance Elem [e] = e
       monotype (i.e., it may not include foralls) and after the expansion of
       all saturated vanilla type synonyms, no synonyms, except family synonyms
       may remain.  Here are some examples of admissible and illegal type
-      instances: 
+      instances:
 <programlisting>
 type family F a :: *
 type instance F [Int]              = Int         -- OK!
@@ -4919,7 +4919,7 @@ type instance G Int Char Float = Double  -- WRONG: must be two type parameters
        When an associated family instance is declared within a type class
        instance, we drop the <literal>instance</literal> keyword in the family
        instance.  So, the <literal>[e]</literal> instance
-       for <literal>Elem</literal> becomes: 
+       for <literal>Elem</literal> becomes:
 <programlisting>
 instance (Eq (Elem [e])) => Collects ([e]) where
   type Elem [e] = e
@@ -4928,7 +4928,7 @@ instance (Eq (Elem [e])) => Collects ([e]) where
         The most important point about associated family instances is that the
        type indexes corresponding to class parameters must be identical to the
         type given in the instance head; here this is <literal>[e]</literal>,
-        which coincides with the only class parameter. 
+        which coincides with the only class parameter.
       </para>
       <para>
         Instances for an associated family can only appear as part of  instances
@@ -4937,7 +4937,7 @@ instance (Eq (Elem [e])) => Collects ([e]) where
        how methods are handled, declarations of associated types can be omitted
        in class instances.  If an associated family instance is omitted, the
        corresponding instance type is not inhabited; i.e., only diverging
-       expressions, such as <literal>undefined</literal>, can assume the type. 
+       expressions, such as <literal>undefined</literal>, can assume the type.
       </para>
     </sect4>
 
@@ -4952,11 +4952,11 @@ instance (Eq (Elem [e])) => Collects ([e]) where
        that is the case, the right-hand sides of the instances must also be
        syntactically equal under the same substitution.  This condition is
        independent of whether the type family is associated or not, and it is
-       not only a matter of consistency, but one of type safety. 
+       not only a matter of consistency, but one of type safety.
       </para>
       <para>
        Here are two example to illustrate the condition under which overlap
-       is permitted. 
+       is permitted.
 <programlisting>
 type instance F (a, Int) = [a]
 type instance F (Int, b) = [b]   -- overlap permitted
@@ -4973,15 +4973,15 @@ type instance G (Char, a) = [a]  -- ILLEGAL overlap, as [Char] /= [Int]
        In order to guarantee that type inference in the presence of type
        families decidable, we need to place a number of additional
        restrictions on the formation of type instance declarations (c.f.,
-       Definition 5 (Relaxed Conditions) of &ldquo;<ulink 
+       Definition 5 (Relaxed Conditions) of &ldquo;<ulink
         url="http://www.cse.unsw.edu.au/~chak/papers/SPCS08.html">Type
          Checking with Open Type Functions</ulink>&rdquo;).  Instance
-         declarations have the general form 
+         declarations have the general form
 <programlisting>
 type instance F t1 .. tn = t
 </programlisting>
         where we require that for every type family application <literal>(G s1
-        .. sm)</literal> in <literal>t</literal>,  
+        .. sm)</literal> in <literal>t</literal>,
        <orderedlist>
          <listitem>
            <para><literal>s1 .. sm</literal> do not contain any type family
@@ -4990,7 +4990,7 @@ type instance F t1 .. tn = t
          <listitem>
            <para>the total number of symbols (data type constructors and type
            variables) in <literal>s1 .. sm</literal> is strictly smaller than
-           in <literal>t1 .. tn</literal>, and</para> 
+           in <literal>t1 .. tn</literal>, and</para>
          </listitem>
          <listitem>
            <para>for every type
@@ -5004,13 +5004,13 @@ type instance F t1 .. tn = t
        of type inference in the presence of, so called, ''loopy equalities'',
        such as <literal>a ~ [F a]</literal>, where a recursive occurrence of
        a type variable is underneath a family application and data
-       constructor application - see the above mentioned paper for details.   
+       constructor application - see the above mentioned paper for details.
       </para>
       <para>
        If the option <option>-XUndecidableInstances</option> is passed to the
        compiler, the above restrictions are not enforced and it is on the
        programmer to ensure termination of the normalisation of type families
-       during type inference. 
+       during type inference.
       </para>
     </sect4>
   </sect3>
@@ -5023,7 +5023,7 @@ type instance F t1 .. tn = t
       and <literal>t2</literal> need to be the same.  In the presence of type
       families, whether two types are equal cannot generally be decided
       locally.  Hence, the contexts of function signatures may include
-      equality constraints, as in the following example: 
+      equality constraints, as in the following example:
 <programlisting>
 sumCollects :: (Collects c1, Collects c2, Elem c1 ~ Elem c2) => c1 -> c2 -> c2
 </programlisting>
@@ -5032,13 +5032,13 @@ sumCollects :: (Collects c1, Collects c2, Elem c1 ~ Elem c2) => c1 -> c2 -> c2
       types <literal>t1</literal> and <literal>t2</literal> of an equality
       constraint may be arbitrary monotypes; i.e., they may not contain any
       quantifiers, independent of whether higher-rank types are otherwise
-      enabled. 
+      enabled.
     </para>
     <para>
       Equality constraints can also appear in class and instance contexts.
       The former enable a simple translation of programs using functional
       dependencies into programs using family synonyms instead.  The general
-      idea is to rewrite a class declaration of the form 
+      idea is to rewrite a class declaration of the form
 <programlisting>
 class C a b | a -> b
 </programlisting>
@@ -5053,18 +5053,18 @@ class (F a ~ b) => C a b where
       essentially giving a name to the functional dependency.  In class
       instances, we define the type instances of FD families in accordance
       with the class head.  Method signatures are not affected by that
-      process. 
+      process.
     </para>
     <para>
       NB: Equalities in superclass contexts are not fully implemented in
-      GHC 6.10. 
+      GHC 6.10.
     </para>
   </sect3>
 
   <sect3 id-="ty-fams-in-instances">
     <title>Type families and instance declarations</title>
-    <para>Type families require us to extend the rules for 
-      the form of instance heads, which are given 
+    <para>Type families require us to extend the rules for
+      the form of instance heads, which are given
       in <xref linkend="flexible-instance-head"/>.
       Specifically:
 <itemizedlist>
@@ -5119,9 +5119,9 @@ a type variable any more!
 <sect2 id="flexible-contexts"><title>The context of a type signature</title>
 <para>
 The <option>-XFlexibleContexts</option> flag lifts the Haskell 98 restriction
-that the type-class constraints in a type signature must have the 
+that the type-class constraints in a type signature must have the
 form <emphasis>(class type-variable)</emphasis> or
-<emphasis>(class (type-variable type-variable ...))</emphasis>. 
+<emphasis>(class (type-variable type-variable ...))</emphasis>.
 With <option>-XFlexibleContexts</option>
 these type signatures are perfectly OK
 <programlisting>
@@ -5159,8 +5159,8 @@ in GHC, you can give the foralls if you want.  See <xref linkend="explicit-foral
 
 A type variable <literal>a</literal> is "reachable" if it appears
 in the same constraint as either a type variable free in
-<literal>type</literal>, or another reachable type variable.  
-A value with a type that does not obey 
+<literal>type</literal>, or another reachable type variable.
+A value with a type that does not obey
 this reachability restriction cannot be used without introducing
 ambiguity; that is why the type is rejected.
 Here, for example, is an illegal type:
@@ -5239,8 +5239,8 @@ territory free in case we need it later.
 <sect2 id="implicit-parameters">
 <title>Implicit parameters</title>
 
-<para> Implicit parameters are implemented as described in 
-"Implicit parameters: dynamic scoping with static types", 
+<para> Implicit parameters are implemented as described in
+"Implicit parameters: dynamic scoping with static types",
 J Lewis, MB Shields, E Meijer, J Launchbury,
 27th ACM Symposium on Principles of Programming Languages (POPL'00),
 Boston, Jan 2000.
@@ -5267,7 +5267,7 @@ However, by a simple extension to the type class system of Haskell, we
 can support dynamic binding. Basically, we express the use of a
 dynamically bound variable as a constraint on the type. These
 constraints lead to types of the form <literal>(?x::t') => t</literal>, which says "this
-function uses a dynamically-bound variable <literal>?x</literal> 
+function uses a dynamically-bound variable <literal>?x</literal>
 of type <literal>t'</literal>". For
 example, the following expresses the type of a sort function,
 implicitly parameterized by a comparison function named <literal>cmp</literal>.
@@ -5277,11 +5277,11 @@ implicitly parameterized by a comparison function named <literal>cmp</literal>.
 The dynamic binding constraints are just a new form of predicate in the type class system.
 </para>
 <para>
-An implicit parameter occurs in an expression using the special form <literal>?x</literal>, 
+An implicit parameter occurs in an expression using the special form <literal>?x</literal>,
 where <literal>x</literal> is
-any valid identifier (e.g. <literal>ord ?x</literal> is a valid expression). 
+any valid identifier (e.g. <literal>ord ?x</literal> is a valid expression).
 Use of this construct also introduces a new
-dynamic-binding constraint in the type of the expression. 
+dynamic-binding constraint in the type of the expression.
 For example, the following definition
 shows how we can define an implicitly parameterized sort function in
 terms of an explicitly parameterized <literal>sortBy</literal> function:
@@ -5314,8 +5314,8 @@ propagate them.
 <para>
 An implicit-parameter type constraint differs from other type class constraints in the
 following way: All uses of a particular implicit parameter must have
-the same type. This means that the type of <literal>(?x, ?x)</literal> 
-is <literal>(?x::a) => (a,a)</literal>, and not 
+the same type. This means that the type of <literal>(?x, ?x)</literal>
+is <literal>(?x::a) => (a,a)</literal>, and not
 <literal>(?x::a, ?x::b) => (a, b)</literal>, as would be the case for type
 class constraints.
 </para>
@@ -5340,7 +5340,7 @@ Implicit-parameter constraints do not cause ambiguity.  For example, consider:
    g s = show (read s)
 </programlisting>
 Here, <literal>g</literal> has an ambiguous type, and is rejected, but <literal>f</literal>
-is fine.  The binding for <literal>?x</literal> at <literal>f</literal>'s call site is 
+is fine.  The binding for <literal>?x</literal> at <literal>f</literal>'s call site is
 quite unambiguous, and fixes the type <literal>a</literal>.
 </para>
 </sect3>
@@ -5360,8 +5360,8 @@ For example, we define the <literal>min</literal> function by binding
 </para>
 <para>
 A group of implicit-parameter bindings may occur anywhere a normal group of Haskell
-bindings can occur, except at top level.  That is, they can occur in a <literal>let</literal> 
-(including in a list comprehension, or do-notation, or pattern guards), 
+bindings can occur, except at top level.  That is, they can occur in a <literal>let</literal>
+(including in a list comprehension, or do-notation, or pattern guards),
 or a <literal>where</literal> clause.
 Note the following points:
 <itemizedlist>
@@ -5369,10 +5369,10 @@ Note the following points:
 An implicit-parameter binding group must be a
 collection of simple bindings to implicit-style variables (no
 function-style bindings, and no type signatures); these bindings are
-neither polymorphic or recursive.  
+neither polymorphic or recursive.
 </para></listitem>
 <listitem><para>
-You may not mix implicit-parameter bindings with ordinary bindings in a 
+You may not mix implicit-parameter bindings with ordinary bindings in a
 single <literal>let</literal>
 expression; use two nested <literal>let</literal>s instead.
 (In the case of <literal>where</literal> you are stuck, since you can't nest <literal>where</literal> clauses.)
@@ -5485,7 +5485,7 @@ problem that monads seem over-kill for certain sorts of problem, notably:
 Linear implicit parameters are just like ordinary implicit parameters,
 except that they are "linear"; that is, they cannot be copied, and
 must be explicitly "split" instead.  Linear implicit parameters are
-written '<literal>%x</literal>' instead of '<literal>?x</literal>'.  
+written '<literal>%x</literal>' instead of '<literal>?x</literal>'.
 (The '/' in the '%' suggests the split!)
 </para>
 <para>
@@ -5494,7 +5494,7 @@ For example:
     import GHC.Exts( Splittable )
 
     data NameSupply = ...
-    
+
     splitNS :: NameSupply -> (NameSupply, NameSupply)
     newName :: NameSupply -> Name
 
@@ -5509,7 +5509,7 @@ For example:
                      env' = extend env x x'
     ...more equations for f...
 </programlisting>
-Notice that the implicit parameter %ns is consumed 
+Notice that the implicit parameter %ns is consumed
 <itemizedlist>
 <listitem> <para> once by the call to <literal>newName</literal> </para> </listitem>
 <listitem> <para> once by the recursive call to <literal>f</literal> </para></listitem>
@@ -5543,14 +5543,14 @@ and GHC will infer
 <programlisting>
        g :: (Splittable a, %ns :: a) => b -> (b,a,a)
 </programlisting>
-The <literal>Splittable</literal> class is built into GHC.  It's exported by module 
+The <literal>Splittable</literal> class is built into GHC.  It's exported by module
 <literal>GHC.Exts</literal>.
 </para>
 <para>
 Other points:
 <itemizedlist>
-<listitem> <para> '<literal>?x</literal>' and '<literal>%x</literal>' 
-are entirely distinct implicit parameters: you 
+<listitem> <para> '<literal>?x</literal>' and '<literal>%x</literal>'
+are entirely distinct implicit parameters: you
   can use them together and they won't interfere with each other. </para>
 </listitem>
 
@@ -5583,7 +5583,7 @@ usually a harmless thing to do, we get:
 </programlisting>
 But now the name supply is consumed in <emphasis>three</emphasis> places
 (the two calls to newName,and the recursive call to f), so
-the result is utterly different.  Urk!  We don't even have 
+the result is utterly different.  Urk!  We don't even have
 the beta rule.
 </para>
 <para>
@@ -5632,7 +5632,7 @@ semantics of the program depends on whether or not foo has a type signature.
 Yikes!
 </para><para>
 You may say that this is a good reason to dislike linear implicit parameters
-and you'd be right.  That is why they are an experimental feature. 
+and you'd be right.  That is why they are an experimental feature.
 </para>
 </sect3>
 
@@ -5645,7 +5645,7 @@ and you'd be right.  That is why they are an experimental feature.
 
 <para>
 Haskell infers the kind of each type variable.  Sometimes it is nice to be able
-to give the kind explicitly as (machine-checked) documentation, 
+to give the kind explicitly as (machine-checked) documentation,
 just as it is nice to give a type signature for a function.  On some occasions,
 it is essential to do so.  For example, in his paper "Restricted Data Types in Haskell" (Haskell Workshop 1999)
 John Hughes had to define the data type:
@@ -5710,9 +5710,9 @@ The parentheses are required.
 </title>
 
 <para>
-GHC's type system supports <emphasis>arbitrary-rank</emphasis> 
+GHC's type system supports <emphasis>arbitrary-rank</emphasis>
 explicit universal quantification in
-types. 
+types.
 For example, all the following types are legal:
 <programlisting>
     f1 :: forall a b. a -> b -> a
@@ -5846,11 +5846,11 @@ the constructor to suitable values, just as usual.  For example,
 <programlisting>
     a1 :: T Int
     a1 = T1 (\xy->x) 3
-    
+
     a2, a3 :: Swizzle
     a2 = MkSwizzle sort
     a3 = MkSwizzle reverse
-    
+
     a4 :: MonadT Maybe
     a4 = let r x = Just x
             b m k = case m of
@@ -5917,7 +5917,7 @@ provides an explicit polymorphic type for x, or GHC's type inference will assume
 that x's type has no foralls in it</emphasis>.
 </para>
 <para>
-What does it mean to "provide" an explicit type for x?  You can do that by 
+What does it mean to "provide" an explicit type for x?  You can do that by
 giving a type signature for x directly, using a pattern type signature
 (<xref linkend="scoped-type-variables"/>), thus:
 <programlisting>
@@ -5953,10 +5953,10 @@ it needs to know.
 <title>Implicit quantification</title>
 
 <para>
-GHC performs implicit quantification as follows.  <emphasis>At the top level (only) of 
+GHC performs implicit quantification as follows.  <emphasis>At the top level (only) of
 user-written types, if and only if there is no explicit <literal>forall</literal>,
 GHC finds all the type variables mentioned in the type that are not already
-in scope, and universally quantifies them.</emphasis>  For example, the following pairs are 
+in scope, and universally quantifies them.</emphasis>  For example, the following pairs are
 equivalent:
 <programlisting>
   f :: a -> a
@@ -6001,8 +6001,8 @@ for rank-2 types.
 <sect2 id="impredicative-polymorphism">
 <title>Impredicative polymorphism
 </title>
-<para>GHC supports <emphasis>impredicative polymorphism</emphasis>, 
-enabled with <option>-XImpredicativeTypes</option>.  
+<para>GHC supports <emphasis>impredicative polymorphism</emphasis>,
+enabled with <option>-XImpredicativeTypes</option>.
 This means
 that you can call a polymorphic function at a polymorphic type, and
 parameterise data structures over polymorphic types.  For example:
@@ -6018,7 +6018,7 @@ Notice here that the <literal>Maybe</literal> type is parameterised by the
 <para>The technical details of this extension are described in the paper
 <ulink url="http://research.microsoft.com/%7Esimonpj/papers/boxy/">Boxy types:
 type inference for higher-rank types and impredicativity</ulink>,
-which appeared at ICFP 2006.  
+which appeared at ICFP 2006.
 </para>
 </sect2>
 
@@ -6040,9 +6040,9 @@ The type signature for <literal>f</literal> brings the type variable <literal>a<
 because of the explicit <literal>forall</literal> (<xref linkend="decl-type-sigs"/>).
 The type variables bound by a <literal>forall</literal> scope over
 the entire definition of the accompanying value declaration.
-In this example, the type variable <literal>a</literal> scopes over the whole 
+In this example, the type variable <literal>a</literal> scopes over the whole
 definition of <literal>f</literal>, including over
-the type signature for <varname>ys</varname>. 
+the type signature for <varname>ys</varname>.
 In Haskell 98 it is not possible to declare
 a type for <varname>ys</varname>; a major benefit of scoped type variables is that
 it becomes possible to do so.
@@ -6084,7 +6084,7 @@ A <emphasis>lexically scoped type variable</emphasis> can be bound by:
 In Haskell, a programmer-written type signature is implicitly quantified over
 its free type variables (<ulink
 url="http://www.haskell.org/onlinereport/decls.html#sect4.1.2">Section
-4.1.2</ulink> 
+4.1.2</ulink>
 of the Haskell Report).
 Lexically scoped type variables affect this implicit quantification rules
 as follows: any type variable that is in scope is <emphasis>not</emphasis> universally
@@ -6127,7 +6127,7 @@ over the definition of "<literal>g</literal>", so "<literal>x::a</literal>"
 means "<literal>x::forall a. a</literal>" by Haskell's usual implicit
 quantification rules.
 </para></listitem>
-<listitem><para> The signature gives a type for a function binding or a bare variable binding, 
+<listitem><para> The signature gives a type for a function binding or a bare variable binding,
 not a pattern binding.
 For example:
 <programlisting>
@@ -6137,7 +6137,7 @@ For example:
   f2 :: forall a. [a] -> [a]
   f2 = \(x:xs) -> xs ++ [ x :: a ]   -- OK
 
-  f3 :: forall a. [a] -> [a] 
+  f3 :: forall a. [a] -> [a]
   Just f3 = Just (\(x:xs) -> xs ++ [ x :: a ])   -- Not OK!
 </programlisting>
 The binding for <literal>f3</literal> is a pattern binding, and so its type signature
@@ -6159,8 +6159,8 @@ type variables, in the annotated expression.  For example:
 <programlisting>
   f = runST ( (op >>= \(x :: STRef s Int) -> g x) :: forall s. ST s Bool )
 </programlisting>
-Here, the type signature <literal>forall s. ST s Bool</literal> brings the 
-type variable <literal>s</literal> into scope, in the annotated expression 
+Here, the type signature <literal>forall s. ST s Bool</literal> brings the
+type variable <literal>s</literal> into scope, in the annotated expression
 <literal>(op >>= \(x :: STRef s Int) -> g x)</literal>.
 </para>
 
@@ -6170,7 +6170,7 @@ type variable <literal>s</literal> into scope, in the annotated expression
 <title>Pattern type signatures</title>
 <para>
 A type signature may occur in any pattern; this is a <emphasis>pattern type
-signature</emphasis>. 
+signature</emphasis>.
 For example:
 <programlisting>
   -- f and g assume that 'a' is already in scope
@@ -6197,7 +6197,7 @@ that are already in scope.  For example:
 </programlisting>
 Here, the pattern signatures for <literal>ys</literal> and <literal>zs</literal>
 are fine, but the one for <literal>v</literal> is not because <literal>b</literal> is
-not in scope. 
+not in scope.
 </para>
 <para>
 However, in all patterns <emphasis>other</emphasis> than pattern bindings, a pattern
@@ -6220,7 +6220,7 @@ not already in scope; the effect is to bring it into scope, standing for the
 existentially-bound type variable.
 </para>
 <para>
-When a pattern type signature binds a type variable in this way, GHC insists that the 
+When a pattern type signature binds a type variable in this way, GHC insists that the
 type variable is bound to a <emphasis>rigid</emphasis>, or fully-known, type variable.
 This means that any user-written type signature always stands for a completely known type.
 </para>
@@ -6230,7 +6230,7 @@ If all this seems a little odd, we think so too.  But we must have
 could not name existentially-bound type variables in subsequent type signatures.
 </para>
 <para>
-This is (now) the <emphasis>only</emphasis> situation in which a pattern type 
+This is (now) the <emphasis>only</emphasis> situation in which a pattern type
 signature is allowed to mention a lexical variable that is not already in
 scope.
 For example, both <literal>f</literal> and <literal>g</literal> would be
@@ -6240,7 +6240,7 @@ illegal if <literal>a</literal> was not already in scope.
 
 </sect3>
 
-<!-- ==================== Commented out part about result type signatures 
+<!-- ==================== Commented out part about result type signatures
 
 <sect3 id="result-type-sigs">
 <title>Result type signatures</title>
@@ -6258,7 +6258,7 @@ The result type of a function, lambda, or case expression alternative can be giv
   h xs = case xs of
            (y:ys) :: a -> y
 </programlisting>
-The final <literal>:: [a]</literal> after the patterns of <literal>f</literal> gives the type of 
+The final <literal>:: [a]</literal> after the patterns of <literal>f</literal> gives the type of
 the result of the function.  Similarly, the body of the lambda in the RHS of
 <literal>g</literal> is <literal>[Int]</literal>, and the RHS of the case
 alternative in <literal>h</literal> is <literal>a</literal>.
@@ -6324,12 +6324,12 @@ The Haskell Report specifies that a group of bindings (at top level, or in a
 <literal>let</literal> or <literal>where</literal>) should be sorted into
 strongly-connected components, and then type-checked in dependency order
 (<ulink url="http://www.haskell.org/onlinereport/decls.html#sect4.5.1">Haskell
-Report, Section 4.5.1</ulink>).  
+Report, Section 4.5.1</ulink>).
 As each group is type-checked, any binders of the group that
 have
 an explicit type signature are put in the type environment with the specified
 polymorphic type,
-and all others are monomorphic until the group is generalised 
+and all others are monomorphic until the group is generalised
 (<ulink url="http://www.haskell.org/onlinereport/decls.html#sect4.5.2">Haskell Report, Section 4.5.2</ulink>).
 </para>
 
@@ -6345,7 +6345,7 @@ typecheck.  For example, consider:
 <programlisting>
   f :: Eq a =&gt; a -> Bool
   f x = (x == x) || g True || g "Yes"
-  
+
   g y = (y &lt;= y) || f True
 </programlisting>
 This is rejected by Haskell 98, but under Jones's scheme the definition for
@@ -6362,7 +6362,7 @@ Now, the definition for <literal>f</literal> is typechecked, with this type for
 </para>
 
 <para>
-The same refined dependency analysis also allows the type signatures of 
+The same refined dependency analysis also allows the type signatures of
 mutually-recursive functions to have different contexts, something that is illegal in
 Haskell 98 (Section 4.5.2, last sentence).  With
 <option>-XRelaxedPolyRec</option>
@@ -6372,7 +6372,7 @@ pattern binding must have the same context.  For example, this is fine:
 <programlisting>
   f :: Eq a =&gt; a -> Bool
   f x = (x == x) || g True
-  
+
   g :: Ord a =&gt; a -> Bool
   g y = (y &lt;= y) || f True
 </programlisting>
@@ -6383,7 +6383,7 @@ pattern binding must have the same context.  For example, this is fine:
 <title>Monomorphic local bindings</title>
 <para>
 We are actively thinking of simplifying GHC's type system, by <emphasis>not generalising local bindings</emphasis>.
-The rationale is described in the paper 
+The rationale is described in the paper
 <ulink url="http://research.microsoft.com/~simonpj/papers/constraints/index.htm">Let should not be generalised</ulink>.
 </para>
 <para>
@@ -6396,14 +6396,14 @@ If you supply a type signature, then the flag has no effect.
 
 </sect1>
 <!-- ==================== End of type system extensions =================  -->
-  
+
 <!-- ====================== TEMPLATE HASKELL =======================  -->
 
 <sect1 id="template-haskell">
 <title>Template Haskell</title>
 
 <para>Template Haskell allows you to do compile-time meta-programming in
-Haskell.  
+Haskell.
 The background to
 the main technical innovations is discussed in "<ulink
 url="http://research.microsoft.com/~simonpj/papers/meta-haskell/">
@@ -6414,23 +6414,23 @@ There is a Wiki page about
 Template Haskell at <ulink url="http://www.haskell.org/haskellwiki/Template_Haskell">
 http://www.haskell.org/haskellwiki/Template_Haskell</ulink>, and that is the best place to look for
 further details.
-You may also 
+You may also
 consult the <ulink
 url="http://www.haskell.org/ghc/docs/latest/html/libraries/index.html">online
-Haskell library reference material</ulink> 
+Haskell library reference material</ulink>
 (look for module <literal>Language.Haskell.TH</literal>).
-Many changes to the original design are described in 
+Many changes to the original design are described in
       <ulink url="http://research.microsoft.com/~simonpj/papers/meta-haskell/notes2.ps">
 Notes on Template Haskell version 2</ulink>.
 Not all of these changes are in GHC, however.
 </para>
 
-<para> The first example from that paper is set out below (<xref linkend="th-example"/>) 
-as a worked example to help get you started. 
+<para> The first example from that paper is set out below (<xref linkend="th-example"/>)
+as a worked example to help get you started.
 </para>
 
 <para>
-The documentation here describes the realisation of Template Haskell in GHC.  It is not detailed enough to 
+The documentation here describes the realisation of Template Haskell in GHC.  It is not detailed enough to
 understand Template Haskell; see the <ulink url="http://haskell.org/haskellwiki/Template_Haskell">
 Wiki page</ulink>.
 </para>
@@ -6454,24 +6454,24 @@ Wiki page</ulink>.
                  of "$" overrides its meaning as an infix operator, just as "M.x" overrides the meaning
                  of "." as an infix operator.  If you want the infix operator, put spaces around it.
                  </para>
-             <para> A splice can occur in place of 
+             <para> A splice can occur in place of
                  <itemizedlist>
                    <listitem><para> an expression; the spliced expression must
                    have type <literal>Q Exp</literal></para></listitem>
                    <listitem><para> an type; the spliced expression must
                    have type <literal>Q Typ</literal></para></listitem>
-                   <listitem><para> a list of top-level declarations; the spliced expression 
+                   <listitem><para> a list of top-level declarations; the spliced expression
                     must have type <literal>Q [Dec]</literal></para></listitem>
                    </itemizedlist>
             Note that pattern splices are not supported.
-           Inside a splice you can can only call functions defined in imported modules,
+            Inside a splice you can only call functions defined in imported modules,
            not functions defined elsewhere in the same module.</para></listitem>
 
              <listitem><para>
                  A expression quotation is written in Oxford brackets, thus:
                  <itemizedlist>
-                   <listitem><para> <literal>[| ... |]</literal>, or <literal>[e| ... |]</literal>, 
-                             where the "..." is an expression; 
+                   <listitem><para> <literal>[| ... |]</literal>, or <literal>[e| ... |]</literal>,
+                             where the "..." is an expression;
                              the quotation has type <literal>Q Exp</literal>.</para></listitem>
                    <listitem><para> <literal>[d| ... |]</literal>, where the "..." is a list of top-level declarations;
                              the quotation has type <literal>Q [Dec]</literal>.</para></listitem>
@@ -6496,17 +6496,17 @@ Wiki page</ulink>.
                    <listitem><para> <literal>'f</literal> has type <literal>Name</literal>, and names the function <literal>f</literal>.
                  Similarly <literal>'C</literal> has type <literal>Name</literal> and names the data constructor <literal>C</literal>.
                  In general <literal>'</literal><replaceable>thing</replaceable> interprets <replaceable>thing</replaceable> in an expression context.
-                    </para></listitem> 
+                    </para></listitem>
                    <listitem><para> <literal>''T</literal> has type <literal>Name</literal>, and names the type constructor  <literal>T</literal>.
                  That is, <literal>''</literal><replaceable>thing</replaceable> interprets <replaceable>thing</replaceable> in a type context.
-                    </para></listitem> 
+                    </para></listitem>
                  </itemizedlist>
                  These <literal>Names</literal> can be used to construct Template Haskell expressions, patterns, declarations etc.  They
                  may also be given as an argument to the <literal>reify</literal> function.
                 </para>
                </listitem>
 
-             <listitem><para> You may omit the <literal>$(...)</literal> in a top-level declaration splice. 
+             <listitem><para> You may omit the <literal>$(...)</literal> in a top-level declaration splice.
               Simply writing an expression (rather than a declaration) implies a splice.  For example, you can write
 <programlisting>
 module Foo where
@@ -6525,7 +6525,7 @@ h z = z-1
             This abbreviation makes top-level declaration slices quieter and less intimidating.
            </para></listitem>
 
-                 
+
        </itemizedlist>
 (Compared to the original paper, there are many differences of detail.
 The syntax for a declaration splice uses "<literal>$</literal>" not "<literal>splice</literal>".
@@ -6551,7 +6551,7 @@ Pattern splices and quotations are not implemented.)
    <listitem><para>
    You can only run a function at compile time if it is imported
    from another module <emphasis>that is not part of a mutually-recursive group of modules
-   that includes the module currently being compiled</emphasis>.  Furthermore, all of the modules of 
+   that includes the module currently being compiled</emphasis>.  Furthermore, all of the modules of
    the mutually-recursive group must be reachable by non-SOURCE imports from the module where the
    splice is to be run.</para>
    <para>
@@ -6573,11 +6573,11 @@ Pattern splices and quotations are not implemented.)
 </itemizedlist>
 </para>
 <para> Template Haskell works in any mode (<literal>--make</literal>, <literal>--interactive</literal>,
-       or file-at-a-time).  There used to be a restriction to the former two, but that restriction 
+       or file-at-a-time).  There used to be a restriction to the former two, but that restriction
        has been lifted.
 </para>
 </sect2>
+
 <sect2 id="th-example">  <title> A Template Haskell Worked Example </title>
 <para>To help you get over the confidence barrier, try out this skeletal worked example.
   First cut and paste the two modules below into "Main.hs" and "Printf.hs":</para>
@@ -6647,7 +6647,7 @@ Hello
 <sect2>
 <title>Using Template Haskell with Profiling</title>
 <indexterm><primary>profiling</primary><secondary>with Template Haskell</secondary></indexterm>
+
 <para>Template Haskell relies on GHC's built-in bytecode compiler and
 interpreter to run the splice expressions.  The bytecode interpreter
 runs the compiled expression on top of the same runtime on which GHC
@@ -6699,11 +6699,11 @@ A quasi-quote has the form
 <literal>[<replaceable>quoter</replaceable>| <replaceable>string</replaceable> |]</literal>.
 <itemizedlist>
 <listitem><para>
-The <replaceable>quoter</replaceable> must be the (unqualified) name of an imported 
-quoter; it cannot be an arbitrary expression.  
+The <replaceable>quoter</replaceable> must be the (unqualified) name of an imported
+quoter; it cannot be an arbitrary expression.
 </para></listitem>
 <listitem><para>
-The <replaceable>quoter</replaceable> cannot be "<literal>e</literal>", 
+The <replaceable>quoter</replaceable> cannot be "<literal>e</literal>",
 "<literal>t</literal>", "<literal>d</literal>", or "<literal>p</literal>", since
 those overlap with Template Haskell quotations.
 </para></listitem>
@@ -6712,7 +6712,7 @@ There must be no spaces in the token
 <literal>[<replaceable>quoter</replaceable>|</literal>.
 </para></listitem>
 <listitem><para>
-The quoted <replaceable>string</replaceable> 
+The quoted <replaceable>string</replaceable>
 can be arbitrary, and may contain newlines.
 </para></listitem>
 </itemizedlist>
@@ -6730,7 +6730,7 @@ A quasiquote may appear in place of
 </para></listitem>
 
 <listitem><para>
-A quoter is a value of type <literal>Language.Haskell.TH.Quote.QuasiQuoter</literal>, 
+A quoter is a value of type <literal>Language.Haskell.TH.Quote.QuasiQuoter</literal>,
 which is defined thus:
 <programlisting>
 data QuasiQuoter = QuasiQuoter { quoteExp  :: String -> Q Exp,
@@ -6923,7 +6923,7 @@ it won't make much sense unless you've read Hughes's paper.
        |  proc <replaceable>apat</replaceable> -> <replaceable>cmd</replaceable>
 </screen>
 where <literal>proc</literal> is a new keyword.
-The variables of the pattern are bound in the body of the 
+The variables of the pattern are bound in the body of the
 <literal>proc</literal>-expression,
 which is a new sort of thing called a <firstterm>command</firstterm>.
 The syntax of commands is as follows:
@@ -7326,7 +7326,7 @@ a new <literal>form</literal> keyword.
 <para>
 Although only GHC implements arrow notation directly,
 there is also a preprocessor
-(available from the 
+(available from the
 <ulink url="http://www.haskell.org/arrows/">arrows web page</ulink>)
 that translates arrow notation into Haskell 98
 for use with other Haskell systems.
@@ -7371,7 +7371,7 @@ Because the preprocessor targets Haskell (rather than Core),
 <indexterm><primary>Bang patterns</primary></indexterm>
 </title>
 <para>GHC supports an extension of pattern matching called <emphasis>bang
-patterns</emphasis>, written <literal>!<replaceable>pat</replaceable></literal>.   
+patterns</emphasis>, written <literal>!<replaceable>pat</replaceable></literal>.
 Bang patterns are under consideration for Haskell Prime.
 The <ulink
 url="http://hackage.haskell.org/trac/haskell-prime/wiki/BangPatterns">Haskell
@@ -7379,9 +7379,9 @@ prime feature description</ulink> contains more discussion and examples
 than the material below.
 </para>
 <para>
-The key change is the addition of a new rule to the 
+The key change is the addition of a new rule to the
 <ulink url="http://haskell.org/onlinereport/exps.html#sect3.17.2">semantics of pattern matching in the Haskell 98 report</ulink>.
-Add new bullet 10, saying: Matching the pattern <literal>!</literal><replaceable>pat</replaceable> 
+Add new bullet 10, saying: Matching the pattern <literal>!</literal><replaceable>pat</replaceable>
 against a value <replaceable>v</replaceable> behaves as follows:
 <itemizedlist>
 <listitem><para>if <replaceable>v</replaceable> is bottom, the match diverges</para></listitem>
@@ -7413,13 +7413,13 @@ Bang patterns can be nested of course:
 f2 (!x, y) = [x,y]
 </programlisting>
 Here, <literal>f2</literal> is strict in <literal>x</literal> but not in
-<literal>y</literal>.  
+<literal>y</literal>.
 A bang only really has an effect if it precedes a variable or wild-card pattern:
 <programlisting>
 f3 !(x,y) = [x,y]
 f4 (x,y)  = [x,y]
 </programlisting>
-Here, <literal>f3</literal> and <literal>f4</literal> are identical; 
+Here, <literal>f3</literal> and <literal>f4</literal> are identical;
 putting a bang before a pattern that
 forces evaluation anyway does nothing.
 </para>
@@ -7466,7 +7466,7 @@ g5 x = let y = f x in body
 g6 x = case f x of { y -&gt; body }
 g7 x = case f x of { !y -&gt; body }
 </programlisting>
-The functions <literal>g5</literal> and <literal>g6</literal> mean exactly the same thing.  
+The functions <literal>g5</literal> and <literal>g6</literal> mean exactly the same thing.
 But <literal>g7</literal> evaluates <literal>(f x)</literal>, binds <literal>y</literal> to the
 result, and then evaluates <literal>body</literal>.
 </para>
@@ -7496,7 +7496,7 @@ prefix notation:
 </programlisting>
 The semantics of Haskell pattern matching is described in <ulink
 url="http://www.haskell.org/onlinereport/exps.html#sect3.17.2">
-Section 3.17.2</ulink> of the Haskell Report.  To this description add 
+Section 3.17.2</ulink> of the Haskell Report.  To this description add
 one extra item 10, saying:
 <itemizedlist><listitem><para>Matching
 the pattern <literal>!pat</literal> against a value <literal>v</literal> behaves as follows:
@@ -7512,13 +7512,13 @@ case v of { !pat -> e; _ -> e' }
    = v `seq` case v of { pat -> e; _ -> e' }
 </programlisting>
 </para><para>
-That leaves let expressions, whose translation is given in 
+That leaves let expressions, whose translation is given in
 <ulink url="http://www.haskell.org/onlinereport/exps.html#sect3.12">Section
 3.12</ulink>
 of the Haskell Report.
-In the translation box, first apply 
-the following transformation:  for each pattern <literal>pi</literal> that is of 
-form <literal>!qi = ei</literal>, transform it to <literal>(xi,!qi) = ((),ei)</literal>, and and replace <literal>e0</literal> 
+In the translation box, first apply
+the following transformation:  for each pattern <literal>pi</literal> that is of
+form <literal>!qi = ei</literal>, transform it to <literal>(xi,!qi) = ((),ei)</literal>, and replace <literal>e0</literal>
 by <literal>(xi `seq` e0)</literal>.  Then, when none of the left-hand-side patterns
 have a bang at the top, apply the rules in the existing box.
 </para>
@@ -7646,7 +7646,7 @@ Assertion failures can be caught, see the documentation for the
 
     <para>Pragmas all take the form
 
-<literal>{-# <replaceable>word</replaceable> ... #-}</literal>  
+<literal>{-# <replaceable>word</replaceable> ... #-}</literal>
 
     where <replaceable>word</replaceable> indicates the type of
     pragma, and is followed optionally by information specific to that
@@ -7656,7 +7656,7 @@ Assertion failures can be caught, see the documentation for the
     in the following sections; any pragma encountered with an
     unrecognised <replaceable>word</replaceable> is
     ignored. The layout rule applies in pragmas, so the closing <literal>#-}</literal>
-    should start in a column to the right of the opening <literal>{-#</literal>. </para> 
+    should start in a column to the right of the opening <literal>{-#</literal>. </para>
 
     <para>Certain pragmas are <emphasis>file-header pragmas</emphasis>:
       <itemizedlist>
@@ -7666,7 +7666,7 @@ Assertion failures can be caught, see the documentation for the
          </para></listitem>
       <listitem><para>
       There can be as many file-header pragmas as you please, and they can be
-      preceded or followed by comments.  
+      preceded or followed by comments.
          </para></listitem>
       <listitem><para>
       File-header pragmas are read once only, before
@@ -7686,7 +7686,7 @@ Assertion failures can be caught, see the documentation for the
       <indexterm><primary>LANGUAGE</primary><secondary>pragma</secondary></indexterm>
       <indexterm><primary>pragma</primary><secondary>LANGUAGE</secondary></indexterm>
 
-      <para>The <literal>LANGUAGE</literal> pragma allows language extensions to be enabled 
+      <para>The <literal>LANGUAGE</literal> pragma allows language extensions to be enabled
        in a portable way.
        It is the intention that all Haskell compilers support the
        <literal>LANGUAGE</literal> pragma with the same syntax, although not
@@ -7795,7 +7795,7 @@ Assertion failures can be caught, see the documentation for the
       (a) uses within the defining module, and
       (b) uses in an export list.
       The latter reduces spurious complaints within a library
-      in which one module gathers together and re-exports 
+      in which one module gathers together and re-exports
       the exports of several others.
       </para>
       <para>You can suppress the warnings with the flag
@@ -7832,7 +7832,7 @@ key_function :: Int -> String -> (Bool, Double)
         <para>The major effect of an <literal>INLINE</literal> pragma
         is to declare a function's &ldquo;cost&rdquo; to be very low.
         The normal unfolding machinery will then be very keen to
-        inline it.  However, an <literal>INLINE</literal> pragma for a 
+        inline it.  However, an <literal>INLINE</literal> pragma for a
        function "<literal>f</literal>" has a number of other effects:
 <itemizedlist>
 <listitem><para>
@@ -7846,13 +7846,13 @@ there really isn't any point in inlining <literal>key_function</literal> to get
 map (\x -> <replaceable>body</replaceable>) xs
 </programlisting>
 In general, GHC only inlines the function if there is some reason (no matter
-how slight) to supose that it is useful to do so.
+how slight) to suppose that it is useful to do so.
 </para></listitem>
 
 <listitem><para>
-Moreover, GHC will only inline the function if it is <emphasis>fully applied</emphasis>, 
+Moreover, GHC will only inline the function if it is <emphasis>fully applied</emphasis>,
 where "fully applied"
-means applied to as many arguments as appear (syntactically) 
+means applied to as many arguments as appear (syntactically)
 on the LHS of the function
 definition.  For example:
 <programlisting>
@@ -7864,7 +7864,7 @@ comp2 :: (b -> c) -> (a -> b) -> a -> c
 {-# INLINE comp2 #-}
 comp2 f g x = f (g x)
 </programlisting>
-The two functions <literal>comp1</literal> and <literal>comp2</literal> have the 
+The two functions <literal>comp1</literal> and <literal>comp2</literal> have the
 same semantics, but <literal>comp1</literal> will be inlined when applied
 to <emphasis>two</emphasis> arguments, while <literal>comp2</literal> requires
 <emphasis>three</emphasis>.  This might make a big difference if you say
@@ -7874,14 +7874,14 @@ map (not `comp1` not) xs
 which will optimise better than the corresponding use of `comp2`.
 </para></listitem>
 
-<listitem><para> 
+<listitem><para>
 It is useful for GHC to optimise the definition of an
-INLINE function <literal>f</literal> just like any other non-INLINE function, 
+INLINE function <literal>f</literal> just like any other non-INLINE function,
 in case the non-inlined version of <literal>f</literal> is
-ultimately called.  But we don't want to inline 
+ultimately called.  But we don't want to inline
 the <emphasis>optimised</emphasis> version
 of <literal>f</literal>;
-a major reason for INLINE pragmas is to expose functions 
+a major reason for INLINE pragmas is to expose functions
 in <literal>f</literal>'s RHS that have
 rewrite rules, and it's no good if those functions have been optimised
 away.
@@ -7890,7 +7890,7 @@ away.
 So <emphasis>GHC guarantees to inline precisely the code that you wrote</emphasis>, no more
 and no less.  It does this by capturing a copy of the definition of the function to use
 for inlining (we call this the "inline-RHS"), which it leaves untouched,
-while optimising the ordinarly RHS as usual.  For externally-visible functions
+while optimising the ordinarily RHS as usual.  For externally-visible functions
 the inline-RHS (not the optimised RHS) is recorded in the interface file.
 </para></listitem>
 <listitem><para>
@@ -7925,13 +7925,13 @@ itself, so an INLINE pragma is always ignored.</para>
 {-# INLINE returnUs #-}
 </programlisting>
 
-       <para>See also the <literal>NOINLINE</literal> (<xref linkend="inlinable-pragma"/>) 
-        and <literal>INLINABLE</literal> (<xref linkend="noinline-pragma"/>) 
+       <para>See also the <literal>NOINLINE</literal> (<xref linkend="inlinable-pragma"/>)
+        and <literal>INLINABLE</literal> (<xref linkend="noinline-pragma"/>)
         pragmas.</para>
 
        <para>Note: the HBC compiler doesn't like <literal>INLINE</literal> pragmas,
          so if you want your code to be HBC-compatible you'll have to surround
-         the pragma with C pre-processor directives 
+         the pragma with C pre-processor directives
          <literal>#ifdef __GLASGOW_HASKELL__</literal>...<literal>#endif</literal>.</para>
 
       </sect3>
@@ -7989,7 +7989,7 @@ The principal reason do to so to allow later use of <literal>SPECIALISE</literal
 
       <sect3 id="noinline-pragma">
        <title>NOINLINE pragma</title>
-       
+
        <indexterm><primary>NOINLINE</primary></indexterm>
        <indexterm><primary>NOTINLINE</primary></indexterm>
 
@@ -8008,7 +8008,7 @@ The principal reason do to so to allow later use of <literal>SPECIALISE</literal
       <sect3 id="conlike-pragma">
        <title>CONLIKE modifier</title>
        <indexterm><primary>CONLIKE</primary></indexterm>
-        <para>An INLINE or NOINLINE pragma may have a CONLIKE modifier, 
+        <para>An INLINE or NOINLINE pragma may have a CONLIKE modifier,
         which affects matching in RULEs (only).  See <xref linkend="conlike"/>.
         </para>
       </sect3>
@@ -8082,27 +8082,27 @@ happen.
 
     <sect2 id="annotation-pragmas">
       <title>ANN pragmas</title>
-      
+
       <para>GHC offers the ability to annotate various code constructs with additional
       data by using three pragmas.  This data can then be inspected at a later date by
       using GHC-as-a-library.</para>
-            
+
       <sect3 id="ann-pragma">
         <title>Annotating values</title>
-        
+
         <indexterm><primary>ANN</primary></indexterm>
-        
+
         <para>Any expression that has both <literal>Typeable</literal> and <literal>Data</literal> instances may be attached to a top-level value
         binding using an <literal>ANN</literal> pragma. In particular, this means you can use <literal>ANN</literal>
         to annotate data constructors (e.g. <literal>Just</literal>) as well as normal values (e.g. <literal>take</literal>).
         By way of example, to annotate the function <literal>foo</literal> with the annotation <literal>Just "Hello"</literal>
         you would do this:</para>
-        
+
 <programlisting>
 {-# ANN foo (Just "Hello") #-}
 foo = ...
 </programlisting>
-        
+
         <para>
           A number of restrictions apply to use of annotations:
           <itemizedlist>
@@ -8111,46 +8111,46 @@ foo = ...
             <listitem><para>The expression you are annotating with must have a type with <literal>Typeable</literal> and <literal>Data</literal> instances</para></listitem>
             <listitem><para>The <ulink linkend="using-template-haskell">Template Haskell staging restrictions</ulink> apply to the
             expression being annotated with, so for example you cannot run a function from the module being compiled.</para>
-            
-            <para>To be precise, the annotation <literal>{-# ANN x e #-}</literal> is well staged if and only if <literal>$(e)</literal> would be 
+
+            <para>To be precise, the annotation <literal>{-# ANN x e #-}</literal> is well staged if and only if <literal>$(e)</literal> would be
             (disregarding the usual type restrictions of the splice syntax, and the usual restriction on splicing inside a splice - <literal>$([|1|])</literal> is fine as an annotation, albeit redundant).</para></listitem>
           </itemizedlist>
-          
+
           If you feel strongly that any of these restrictions are too onerous, <ulink url="http://hackage.haskell.org/trac/ghc/wiki/MailingListsAndIRC">
           please give the GHC team a shout</ulink>.
         </para>
-        
+
         <para>However, apart from these restrictions, many things are allowed, including expressions which are not fully evaluated!
         Annotation expressions will be evaluated by the compiler just like Template Haskell splices are. So, this annotation is fine:</para>
-        
+
 <programlisting>
 {-# ANN f SillyAnnotation { foo = (id 10) + $([| 20 |]), bar = 'f } #-}
 f = ...
 </programlisting>
       </sect3>
-      
+
       <sect3 id="typeann-pragma">
         <title>Annotating types</title>
-        
+
         <indexterm><primary>ANN type</primary></indexterm>
         <indexterm><primary>ANN</primary></indexterm>
-        
+
         <para>You can annotate types with the <literal>ANN</literal> pragma by using the <literal>type</literal> keyword. For example:</para>
-        
+
 <programlisting>
 {-# ANN type Foo (Just "A `Maybe String' annotation") #-}
 data Foo = ...
 </programlisting>
       </sect3>
-      
+
       <sect3 id="modann-pragma">
         <title>Annotating modules</title>
-        
+
         <indexterm><primary>ANN module</primary></indexterm>
         <indexterm><primary>ANN</primary></indexterm>
-        
+
         <para>You can annotate modules with the <literal>ANN</literal> pragma by using the <literal>module</literal> keyword. For example:</para>
-        
+
 <programlisting>
 {-# ANN module (Just "A `Maybe String' annotation") #-}
 </programlisting>
@@ -8238,7 +8238,7 @@ data Foo = ...
   h :: Eq a => a -> a -> a
   {-# SPECIALISE h :: (Eq a) => [a] -> [a] -> [a] #-}
 </programlisting>
-The last of these examples will generate a 
+The last of these examples will generate a
 RULE with a somewhat-complex left-hand side (try it yourself), so it might not fire very
 well.  If you use this kind of specialisation, let us know how well it works.
 </para>
@@ -8247,7 +8247,7 @@ well.  If you use this kind of specialisation, let us know how well it works.
       <title>SPECIALIZE INLINE</title>
 
 <para>A <literal>SPECIALIZE</literal> pragma can optionally be followed with a
-<literal>INLINE</literal> or <literal>NOINLINE</literal> pragma, optionally 
+<literal>INLINE</literal> or <literal>NOINLINE</literal> pragma, optionally
 followed by a phase, as described in <xref linkend="inline-noinline-pragma"/>.
 The <literal>INLINE</literal> pragma affects the specialised version of the
 function (only), and applies even if the function is recursive.  The motivating
@@ -8282,7 +8282,7 @@ on an ordinarily-recursive function.</para>
 Generally, you can only give a <literal>SPECIALIZE</literal> pragma
 for a function defined in the same module.
 However if a function <literal>f</literal> is given an <literal>INLINABLE</literal>
-pragma at its definition site, then it can subequently be specialised by
+pragma at its definition site, then it can subsequently be specialised by
 importing modules (see <xref linkend="inlinable-pragma"/>).
 For example
 <programlisting>
@@ -8333,7 +8333,7 @@ pragma can be useful.
 </para>
 </sect3>
 
-<sect3><title>Obselete SPECIALIZE syntax</title>
+<sect3><title>Obsolete SPECIALIZE syntax</title>
 
       <para>Note: In earlier versions of GHC, it was possible to provide your own
       specialised function for a given type:
@@ -8358,7 +8358,7 @@ pragma can be useful.
 Same idea, except for instance declarations.  For example:
 
 <programlisting>
-instance (Eq a) => Eq (Foo a) where { 
+instance (Eq a) => Eq (Foo a) where {
    {-# SPECIALIZE instance Eq (Foo [(Int, Bar)]) #-}
    ... usual stuff ...
  }
@@ -8377,7 +8377,7 @@ of the pragma.
       <title>UNPACK pragma</title>
 
       <indexterm><primary>UNPACK</primary></indexterm>
-      
+
       <para>The <literal>UNPACK</literal> indicates to the compiler
       that it should unpack the contents of a constructor field into
       the constructor itself, removing a level of indirection.  For
@@ -8457,7 +8457,7 @@ data S = S {-# UNPACK #-} !Int {-# UNPACK #-} !Int
 
 <para>
 The programmer can specify rewrite rules as part of the source program
-(in a pragma).  
+(in a pragma).
 Here is an example:
 
 <programlisting>
@@ -8590,7 +8590,7 @@ declarations.
 <para>
 Inside a RULE "<literal>forall</literal>" is treated as a keyword, regardless of
 any other flag settings.  Furthermore, inside a RULE, the language extension
-<option>-XScopedTypeVariables</option> is automatically enabled; see 
+<option>-XScopedTypeVariables</option> is automatically enabled; see
 <xref linkend="scoped-type-variables"/>.
 </para>
 </listitem>
@@ -8598,9 +8598,9 @@ any other flag settings.  Furthermore, inside a RULE, the language extension
 
 <para>
 Like other pragmas, RULE pragmas are always checked for scope errors, and
-are typechecked. Typechecking means that the LHS and RHS of a rule are typechecked, 
+are typechecked. Typechecking means that the LHS and RHS of a rule are typechecked,
 and must have the same type.  However, rules are only <emphasis>enabled</emphasis>
-if the <option>-fenable-rewrite-rules</option> flag is 
+if the <option>-fenable-rewrite-rules</option> flag is
 on (see <xref linkend="rule-semantics"/>).
 </para>
 </listitem>
@@ -8623,8 +8623,8 @@ Rules are enabled (that is, used during optimisation)
 by the <option>-fenable-rewrite-rules</option> flag.
 This flag is implied by <option>-O</option>, and may be switched
 off (as usual) by <option>-fno-enable-rewrite-rules</option>.
-(NB: enabling <option>-fenable-rewrite-rules</option> without <option>-O</option> 
-may not do what you expect, though, because without <option>-O</option> GHC 
+(NB: enabling <option>-fenable-rewrite-rules</option> without <option>-O</option>
+may not do what you expect, though, because without <option>-O</option> GHC
 ignores all optimisation information in interface files;
 see <option>-fignore-interface-pragmas</option>, <xref linkend="options-f"/>.)
 Note that <option>-fenable-rewrite-rules</option> is an <emphasis>optimisation</emphasis> flag, and
@@ -8733,12 +8733,12 @@ to give
 g y = y
 </programlisting>
 Now <literal>g</literal> is inlined into <literal>h</literal>, but <literal>f</literal>'s RULE has
-no chance to fire.  
+no chance to fire.
 If instead GHC had first inlined <literal>g</literal> into <literal>h</literal> then there
-would have been a better chance that <literal>f</literal>'s RULE might fire.  
+would have been a better chance that <literal>f</literal>'s RULE might fire.
 </para>
 <para>
-The way to get predictable behaviour is to use a NOINLINE 
+The way to get predictable behaviour is to use a NOINLINE
 pragma, or an INLINE[<replaceable>phase</replaceable>] pragma, on <literal>f</literal>, to ensure
 that it is not inlined until its RULEs have had a chance to fire.
 </para>
@@ -8761,12 +8761,12 @@ when this is a good idea, so we provide the CONLIKE pragma to declare it, thus:
 {-# INLINE[1] CONLIKE f #-}
 f x = <replaceable>blah</replaceable>
 </programlisting>
-CONLIKE is a modifier to an INLINE or NOINLINE pragam.  It specifies that an application
+CONLIKE is a modifier to an INLINE or NOINLINE pragma.  It specifies that an application
 of f to one argument (in general, the number of arguments to the left of the '=' sign)
 should be considered cheap enough to duplicate, if such a duplication would make rule
 fire.  (The name "CONLIKE" is short for "constructor-like", because constructors certainly
 have such a property.)
-The CONLIKE pragam is a modifier to INLINE/NOINLINE because it really only makes sense to match 
+The CONLIKE pragma is a modifier to INLINE/NOINLINE because it really only makes sense to match
 <literal>f</literal> on the LHS of a rule if you are sure that <literal>f</literal> is
 not going to be inlined before the rule has a chance to fire.
 </para>
@@ -9041,7 +9041,7 @@ comparison.
 Use <option>-ddump-rules</option> to see the rules that are defined
 <emphasis>in this module</emphasis>.
 This includes rules generated by the specialisation pass, but excludes
-rules imported from other modules. 
+rules imported from other modules.
 </para>
 </listitem>
 
@@ -9174,7 +9174,7 @@ allows control over inlining on a per-call-site basis.
 restrains the strictness analyser.
 </para></listitem>
 <listitem><para>
-<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html#v%3AunsafeCoerce%23"><literal>unsafeCoerce#</literal></ulink> 
+<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html#v%3AunsafeCoerce%23"><literal>unsafeCoerce#</literal></ulink>
 allows you to fool the type checker.
 </para></listitem>
 </itemizedlist>
@@ -9212,7 +9212,7 @@ or the original paper:
 <itemizedlist>
 <listitem>
 <para>
-José Pedro Magalhães, Atze Dijkstra, Johan Jeuring, and Andres Löh.
+Jos� Pedro Magalh�es, Atze Dijkstra, Johan Jeuring, and Andres L�h.
 <ulink url="http://dreixel.net/research/pdf/gdmh.pdf">
   A generic deriving mechanism for Haskell</ulink>.
 <citetitle>Proceedings of the third ACM Haskell symposium on Haskell</citetitle>
@@ -9240,17 +9240,17 @@ that can be used to represent most Haskell datatypes:
 <programlisting>
 -- | Unit: used for constructors without arguments
 data U1 p = U1
+
 -- | Constants, additional parameters and recursion of kind *
 newtype K1 i c p = K1 { unK1 :: c }
+
 -- | Meta-information (constructor names, etc.)
 newtype M1 i c f p = M1 { unM1 :: f p }
+
 -- | Sums: encode choice between constructors
 infixr 5 :+:
 data (:+:) f g p = L1 (f p) | R1 (g p)
+
 -- | Products: encode multiple arguments to constructors
 infixr 6 :*:
 data (:*:) f g p = f p :*: g p
@@ -9262,7 +9262,7 @@ For example, a user-defined datatype of trees <literal>data UserTree a = Node a
 <programlisting>
 instance Generic (UserTree a) where
   -- Representation type
-  type Rep (UserTree a) = 
+  type Rep (UserTree a) =
     M1 D D1UserTree (
           M1 C C1_0UserTree (
                 M1 S NoSelector (K1 P a)
@@ -9284,10 +9284,10 @@ data C1_1UserTree
 instance Datatype D1UserTree where
   datatypeName _ = "UserTree"
   moduleName _   = "Main"
-  
+
 instance Constructor C1_0UserTree where
   conName _ = "Node"
-  
+
 instance Constructor C1_1UserTree where
   conName _ = "Leaf"
 </programlisting>
@@ -9343,7 +9343,7 @@ exposed to the user:
 <programlisting>
 class Serialize a where
   put :: a -> [Bin]
-  
+
   default put :: (Generic a, GSerialize (Rep a)) => a -> [Bit]
   put = gput . from
 </programlisting>
@@ -9376,7 +9376,7 @@ carried out at let and where bindings.
 <title>Switching off the dreaded Monomorphism Restriction</title>
           <indexterm><primary><option>-XNoMonomorphismRestriction</option></primary></indexterm>
 
-<para>Haskell's monomorphism restriction (see 
+<para>Haskell's monomorphism restriction (see
 <ulink url="http://www.haskell.org/onlinereport/decls.html#sect4.5.5">Section
 4.5.5</ulink>
 of the Haskell Report)
@@ -9391,7 +9391,7 @@ can be completely switched off by
           <indexterm><primary><option>-XMonoPatBinds</option></primary></indexterm>
 
          <para> As an experimental change, we are exploring the possibility of
-         making pattern bindings monomorphic; that is, not generalised at all.  
+         making pattern bindings monomorphic; that is, not generalised at all.
            A pattern binding is a binding whose LHS has no function arguments,
            and is not a simple variable.  For example:
 <programlisting>
index 4d4849f..e219f90 100644 (file)
@@ -35,7 +35,7 @@
   possible while not making too much effort to optimise the generated
   code (although GHC probably isn't what you'd describe as a fast
   compiler :-).</para>
-  
+
   <para>GHC's profiling system supports &ldquo;cost centre
   stacks&rdquo;: a way of seeing the profile of a Haskell program in a
   call-graph like structure.  See <xref linkend="profiling"/> for more
            </varlistentry>
 
            <varlistentry>
-             <term>subscribe at:</term> 
+             <term>subscribe at:</term>
              <listitem>
                <para><ulink
              url="http://www.haskell.org/mailman/listinfo/glasgow-haskell-users"><literal>http://www.haskell.org/mailman/listinfo/glasgow-haskell-users</literal></ulink>.</para>
            </varlistentry>
 
            <varlistentry>
-             <term>subscribe at:</term> 
+             <term>subscribe at:</term>
              <listitem>
                <para><ulink
              url="http://www.haskell.org/mailman/listinfo/glasgow-haskell-bugs"><literal>http://www.haskell.org/mailman/listinfo/glasgow-haskell-bugs</literal></ulink>.</para>
          </variablelist>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>cvs-ghc:</term>
        <listitem>
          other lists for other darcs
          repositories (most notably <literal>cvs-libraries</literal>).
          </para>
-         
+
          <variablelist>
            <varlistentry>
              <term>list email address:</term>
            </varlistentry>
 
            <varlistentry>
-             <term>subscribe at:</term> 
+             <term>subscribe at:</term>
              <listitem>
                <para><ulink
              url="http://www.haskell.org/mailman/listinfo/cvs-ghc"><literal>http://www.haskell.org/mailman/listinfo/cvs-ghc</literal></ulink>.</para>
          </indexterm>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>Stable snapshots</term>
        <listitem>
        </listitem>
       </varlistentry>
     </variablelist>
-    
+
     <para>The version number of your copy of GHC can be found by
     invoking <literal>ghc</literal> with the
     <literal>&ndash;&ndash;version</literal> flag (see <xref
index 27db02d..19f928d 100644 (file)
@@ -23,7 +23,7 @@ this list of conditions and the following disclaimer.
 </listitem>
 
 <listitem>
-<para> 
+<para>
 Redistributions in binary form must reproduce the above copyright notice,
 this list of conditions and the following disclaimer in the documentation
 and/or other materials provided with the distribution.
@@ -31,7 +31,7 @@ and/or other materials provided with the distribution.
 </listitem>
 
 <listitem>
-<para> 
+<para>
 Neither name of the University nor the names of its contributors may be
 used to endorse or promote products derived from this software without
 specific prior written permission.
index 86df594..0a8412b 100644 (file)
@@ -462,7 +462,7 @@ depends: array-0.2.0.1-9cbf76a576b6ee9c1f880cf171a0928d
       The purpose of the package ID is to detect problems caused by
       re-installing a package without also recompiling the packages
       that depend on it.  Recompiling dependencies is necessary,
-      because the newly compiled package may have a differnt ABI
+      because the newly compiled package may have a different ABI
       (Application Binary Interface) than the previous version, even
       if both packages were built from the same source code using the
       same compiler.  With package IDs, a recompiled
@@ -985,7 +985,7 @@ ghc-pkg dot | tred | dot -Tpdf >pkgs.pdf
       </listitem>
       <listitem>
         <para>Versions of the Haskell libraries for use with GHCi may also
-          abe included: GHCi cannot load <literal>.a</literal> files
+          be included: GHCi cannot load <literal>.a</literal> files
           directly, instead it will look for an object file
           called <filename>HSfoo.o</filename> and load that.  On some
           systems, the <literal>ghc-pkg</literal> tool can automatically
@@ -1221,7 +1221,7 @@ haddock-html: /usr/share/doc/ghc/html/libraries/unix
             <indexterm><primary><literal>maintainer</literal></primary><secondary>package specification</secondary></indexterm>
           </term>
           <listitem>
-            <para>(optinoal freeform) The email address of the package's maintainer.</para>
+            <para>(optional freeform) The email address of the package's maintainer.</para>
           </listitem>
         </varlistentry>
 
@@ -1273,7 +1273,7 @@ haddock-html: /usr/share/doc/ghc/html/libraries/unix
             <indexterm><primary><literal>category</literal></primary><secondary>package specification</secondary></indexterm>
           </term>
           <listitem>
-            <para>(optinoal freeform) Which category the package belongs to.  This field
+            <para>(optional freeform) Which category the package belongs to.  This field
             is for use in conjunction with a future centralised package
             distribution framework, tentatively titled Hackage.</para>
           </listitem>
index 92bad19..b8e7316 100644 (file)
@@ -4,7 +4,7 @@
   <indexterm><primary>parallelism</primary>
   </indexterm>
 
-  <para>GHC implements some major extensions to Haskell to support 
+  <para>GHC implements some major extensions to Haskell to support
   concurrent and parallel programming.  Let us first establish terminology:
   <itemizedlist>
        <listitem><para><emphasis>Parallelism</emphasis> means running
          performance.  Ideally, this should be done invisibly, and with no
          semantic changes.
            </para></listitem>
-       <listitem><para><emphasis>Concurrency</emphasis> means implementing 
+       <listitem><para><emphasis>Concurrency</emphasis> means implementing
          a program by using multiple I/O-performing threads.  While a
-         concurrent Haskell program <emphasis>can</emphasis> run on a 
+         concurrent Haskell program <emphasis>can</emphasis> run on a
          parallel machine, the primary goal of using concurrency is not to gain
          performance, but rather because that is the simplest and most
          direct way to write the program.  Since the threads perform I/O,
          the semantics of the program is necessarily non-deterministic.
            </para></listitem>
   </itemizedlist>
-  GHC supports both concurrency and parallelism. 
+  GHC supports both concurrency and parallelism.
   </para>
 
   <sect2 id="concurrent-haskell">
@@ -55,7 +55,7 @@ the FFI with concurrency</ulink>.</para></listitem>
    <sect2><title>Software Transactional Memory</title>
 
     <para>GHC now supports a new way to coordinate the activities of Concurrent
-    Haskell threads, called Software Transactional Memory (STM).  The 
+    Haskell threads, called Software Transactional Memory (STM).  The
     <ulink
     url="http://research.microsoft.com/%7Esimonpj/papers/stm/index.htm">STM
     papers</ulink> are an excellent introduction to what STM is, and how to use
@@ -78,7 +78,7 @@ All these features are described in the papers mentioned earlier.
 <sect2><title>Parallel Haskell</title>
 
   <para>GHC includes support for running Haskell programs in parallel
-  on symmetric, shared-memory multi-processor 
+  on symmetric, shared-memory multi-processor
       (SMP)<indexterm><primary>SMP</primary></indexterm>.
   By default GHC runs your program on one processor; if you
      want it to run in parallel you must link your program
index dfa10a5..863838c 100644 (file)
@@ -5,7 +5,7 @@
   <sect2 id="replacing-phases">
     <title>Replacing the program for one or more phases</title>
     <indexterm><primary>phases, changing</primary></indexterm>
-    
+
     <para>You may specify that a different program be used for one
     of the phases of the compilation system, in place of whatever
     the <command>ghc</command> has wired into it.  For example, you
@@ -409,7 +409,7 @@ $ cat foo.hspp</screen>
           for Windows, <literal>solaris</literal>, etc.).</para>
         </listitem>
       </varlistentry>
-        
+
       <varlistentry>
         <term>
           <constant><replaceable>arch</replaceable>_HOST_ARCH=1</constant>
@@ -437,7 +437,7 @@ $ cat foo.hspp</screen>
 <programlisting>strmod = "\
 \ p \
 \ "</programlisting>
-      
+
       <para>don't work with <option>-cpp</option>;
       <filename>/usr/bin/cpp</filename> elides the backslash-newline
       pairs.</para>
@@ -452,7 +452,7 @@ $ cat foo.hspp</screen>
 
   <sect2 id="pre-processor">
     <title>Options affecting a Haskell pre-processor</title>
-    
+
     <indexterm><primary>pre-processing: custom</primary></indexterm>
     <indexterm><primary>Pre-processor options</primary></indexterm>
 
@@ -855,11 +855,11 @@ $ cat foo.hspp</screen>
             However, if all the modules are otherwise up to date, you may need to force
             recompilation both of the module where the new "main" is, and of the
             module where the "main" function used to be;
-            <literal>ghc</literal> is not clever 
+            <literal>ghc</literal> is not clever
             enough to figure out that they both need recompiling.  You can
             force recompilation by removing the object file, or by using the
             <option>-fforce-recomp</option> flag.
-            </para> 
+            </para>
         </listitem>
       </varlistentry>
 
@@ -928,7 +928,7 @@ $ cat foo.hspp</screen>
           <para>The threaded runtime system provides the following
           benefits:</para>
 
-          <itemizedlist> 
+          <itemizedlist>
             <listitem>
               <para>Parallelism<indexterm><primary>parallelism</primary></indexterm> on a multiprocessor<indexterm><primary>multiprocessor</primary></indexterm><indexterm><primary>SMP</primary></indexterm> or multicore<indexterm><primary>multicore</primary></indexterm>
               machine.  See <xref linkend="using-smp" />.</para>
@@ -1038,7 +1038,7 @@ $ cat foo.hspp</screen>
             <option>-with-rtsopts="-H128m"</option> sets the default heap size to 128MB.
             This will always be the default heap size for this program, unless the user overrides it.
             (Depending on the setting of the <option>-rtsopts</option> option, the user might
-            not have the ability to change RTS options at run-time, in which case 
+            not have the ability to change RTS options at run-time, in which case
             <option>-with-rtsopts</option> would be the <emphasis>only</emphasis> way to set
             them.)
           </para>
@@ -1054,7 +1054,7 @@ $ cat foo.hspp</screen>
         <listitem>
           <para>On Windows, GHC normally generates a
             <firstterm>manifest</firstterm><indexterm><primary>manifest</primary>
-            </indexterm>file when linking a binary.  The
+            </indexterm> file when linking a binary.  The
             manifest is placed in the file
             <literal><replaceable>prog</replaceable>.exe.manifest</literal>
             where <replaceable>prog.exe</replaceable> is the name of the
@@ -1074,7 +1074,7 @@ $ cat foo.hspp</screen>
             system using the security control panel, but GHC by default
             generates binaries that don't depend on the user having disabled
             installer detection.</para>
-          
+
           <para>The <option>-fno-gen-manifest</option> disables generation of
             the manifest file.  One reason to do this would be if you had
             a manifest file of your own, for example.</para>
@@ -1086,7 +1086,7 @@ $ cat foo.hspp</screen>
             <option>-fno-embed-manifest</option>, see below.</para>
         </listitem>
       </varlistentry>
-          
+
       <varlistentry>
         <term>
           <option>-fno-embed-manifest</option>
@@ -1102,15 +1102,15 @@ $ cat foo.hspp</screen>
             </indexterm>; to see exactly what GHC does to embed the manifest,
             use the <option>-v</option> flag.  A GHC installation comes with
             its own copy of <literal>windres</literal> for this reason.</para>
-          
+
           <para>See also <option>-pgmwindres</option> (<xref
-              linkend="replacing-phases" />) and 
+              linkend="replacing-phases" />) and
             <option>-optwindres</option> (<xref
                                             linkend="forcing-options-through"
               />).</para>
         </listitem>
       </varlistentry>
-          
+
       <varlistentry>
         <term>
           <option>-fno-shared-implib</option>
@@ -1125,7 +1125,7 @@ $ cat foo.hspp</screen>
             disk-space cost of creating this import library, which can be substantial - it
             might require as much space as the code itself, as Haskell DLLs tend to export
             lots of symbols.</para>
-            
+
           <para>As long as you are happy to only be able to link to the DLL using
             <literal>GetProcAddress</literal> and friends, you can supply the
             <option>-fno-shared-implib</option> flag to disable the creation of the import
index 00bbcdb..01c7576 100644 (file)
@@ -8,7 +8,7 @@
   <para> Glasgow Haskell comes with a time and space profiling
   system. Its purpose is to help you improve your understanding of
   your program's execution behaviour, so you can improve it.</para>
-  
+
   <para> Any comments, suggestions and/or improvements you have are
   welcome.  Recommended &ldquo;profiling tricks&rdquo; would be
   especially cool! </para>
       <indexterm><primary><option>-p</option></primary><secondary>RTS
       option</secondary></indexterm>
     </listitem>
-      
+
     <listitem>
       <para> Examine the generated profiling information, using one of
       GHC's profiling tools.  The tool to use will depend on the kind
       of profiling information generated.</para>
     </listitem>
-    
+
   </orderedlist>
-  
+
   <sect1 id="cost-centres">
     <title>Cost centres and cost-centre stacks</title>
-    
+
     <para>GHC's profiling system assigns <firstterm>costs</firstterm>
     to <firstterm>cost centres</firstterm>.  A cost is simply the time
     or space required to evaluate an expression.  Cost centres are
@@ -385,7 +385,7 @@ x = nfib 25
        </listitem>
       </varlistentry>
     </variablelist>
-      
+
     <para>There are a few other profiling-related compilation options.
     Use them <emphasis>in addition to</emphasis>
     <option>-prof</option>.  These do not have to be used consistently
@@ -406,7 +406,7 @@ x = nfib 25
           it manually.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>
           <option>-auto-all</option>:
@@ -509,7 +509,7 @@ x = nfib 25
       </varlistentry>
 
     </variablelist>
-    
+
   </sect1>
 
   <sect1 id="prof-heap">
@@ -541,7 +541,7 @@ x = nfib 25
        file,
        <filename><replaceable>prog</replaceable>.ps</filename>.  The
        <command>hp2ps</command> utility is described in detail in
-       <xref linkend="hp2ps"/>.</para> 
+       <xref linkend="hp2ps"/>.</para>
       </listitem>
       <listitem>
        <para>Display the heap profile using a postscript viewer such
@@ -612,7 +612,7 @@ x = nfib 25
            represent an approximation to the actual type.</para>
          </listitem>
        </varlistentry>
-       
+
        <varlistentry>
          <term>
             <option>-hr</option>
@@ -644,7 +644,7 @@ x = nfib 25
       to display a profile by type but only for data produced by a
       certain module, or a profile by retainer for a certain type of
       data.  Restrictions are specified as follows:</para>
-      
+
       <variablelist>
        <varlistentry>
          <term>
@@ -702,7 +702,7 @@ x = nfib 25
            types.</para>
          </listitem>
        </varlistentry>
-       
+
        <varlistentry>
          <term>
             <option>-hr</option><replaceable>cc</replaceable>,...
@@ -776,7 +776,7 @@ x = nfib 25
            state in addition to the space allocated for its stack
            (stacks normally start small and then grow as
            necessary).</para>
-           
+
            <para>This includes the main thread, so using
            <option>-xt</option> is a good way to see how much stack
            space the program is using.</para>
@@ -802,7 +802,7 @@ x = nfib 25
       </variablelist>
 
     </sect2>
-    
+
     <sect2 id="retainer-prof">
       <title>Retainer Profiling</title>
 
@@ -843,7 +843,7 @@ x = nfib 25
       set <literal>MANY</literal>.  The maximum set size defaults to 8
       and can be altered with the <option>-R</option> RTS
       option:</para>
-      
+
       <variablelist>
        <varlistentry>
          <term><option>-R</option><replaceable>size</replaceable></term>
@@ -883,7 +883,7 @@ x = nfib 25
 <screen>
 <replaceable>prog</replaceable> +RTS -hr -hcB
 </screen>
-       
+
        <para>This trick isn't foolproof, because there might be other
         B closures in the heap which aren't the retainers we are
         interested in, but we've found this to be a useful technique
@@ -1004,9 +1004,9 @@ x = nfib 25
     <indexterm><primary>heap profiles</primary></indexterm>
     <indexterm><primary>postscript, from heap profiles</primary></indexterm>
     <indexterm><primary><option>-h&lt;break-down&gt;</option></primary></indexterm>
-    
+
     <para>Usage:</para>
-    
+
 <screen>
 hp2ps [flags] [&lt;file&gt;[.hp]]
 </screen>
@@ -1030,7 +1030,7 @@ hp2ps [flags] [&lt;file&gt;[.hp]]
     <para>The flags are:</para>
 
     <variablelist>
-      
+
       <varlistentry>
        <term><option>-d</option></term>
        <listitem>
@@ -1136,7 +1136,7 @@ hp2ps [flags] [&lt;file&gt;[.hp]]
          <para>Use a small box for the title.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term><option>-t&lt;float&gt;</option></term>
        <listitem>
@@ -1157,14 +1157,14 @@ hp2ps [flags] [&lt;file&gt;[.hp]]
          <para>Generate colour output.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term><option>-y</option></term>
        <listitem>
          <para>Ignore marks.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term><option>-?</option></term>
        <listitem>
@@ -1177,7 +1177,7 @@ hp2ps [flags] [&lt;file&gt;[.hp]]
     <sect2 id="manipulating-hp">
       <title>Manipulating the hp file</title>
 
-<para>(Notes kindly offered by Jan-Willhem Maessen.)</para>
+<para>(Notes kindly offered by Jan-Willem Maessen.)</para>
 
 <para>
 The <filename>FOO.hp</filename> file produced when you ask for the
@@ -1256,7 +1256,7 @@ profile of your program as it runs.  Simply generate an incremental
 heap profile as described in the previous section.  Run <command>gv</command> on your
 profile:
 <screen>
-  gv -watch -seascape FOO.ps 
+  gv -watch -seascape FOO.ps
 </screen>
 If you forget the <literal>-watch</literal> flag you can still select
 "Watch file" from the "State" menu.  Now each time you generate a new
@@ -1292,7 +1292,7 @@ to re-read its input file:
     head -`fgrep -n END_SAMPLE FOO.hp | tail -1 | cut -d : -f 1` FOO.hp \
       | hp2ps > FOO.ps
     kill -HUP $gvpsnum
-  done    
+  done
 </screen>
 </para>
 </sect2>
@@ -1335,7 +1335,7 @@ to re-read its input file:
       a yellow background indicates a part of the program that was
       never evaluated; a green background indicates an always-True
       expression and a red background indicates an always-False one.
-    </para> 
+    </para>
 
    <sect2><title>A small example: Reciprocation</title>
 
@@ -1381,10 +1381,10 @@ main = do
     </para>
 
 <screen>
-$ ghc -fhpc Recip.hs --make 
+$ ghc -fhpc Recip.hs --make
 </screen>
-    <para>HPC index (.mix) files are placed placed in .hpc subdirectory. These can be considered like
-    the .hi files for HPC. 
+    <para>HPC index (.mix) files are placed in .hpc subdirectory. These can be considered like
+    the .hi files for HPC.
    </para>
 <screen>
 $ ./Recip
@@ -1396,8 +1396,8 @@ $ ./Recip
 $ hpc report Recip
  80% expressions used (81/101)
  12% boolean coverage (1/8)
-      14% guards (1/7), 3 always True, 
-                        1 always False, 
+      14% guards (1/7), 3 always True,
+                        1 always False,
                         2 unevaluated
        0% 'if' conditions (0/1), 1 always False
      100% qualifiers (0/0)
@@ -1415,11 +1415,11 @@ writing Recip.hs.html
                hpc_index.html, hpc_index_alt.html, hpc_index_exp.html,
                hpc_index_fun.html.
        </para>
-     </sect2> 
+     </sect2>
 
      <sect2><title>Options for instrumenting code for coverage</title>
        <para>
-               Turning on code coverage is easy, use the -fhpc flag. 
+               Turning on code coverage is easy, use the -fhpc flag.
                Instrumented and non-instrumented can be freely mixed.
                When compiling the Main module GHC automatically detects when there
                is an hpc compiled file, and adds the correct initialization code.
@@ -1431,9 +1431,9 @@ writing Recip.hs.html
 
       <para>
       The hpc toolkit uses a cvs/svn/darcs-like interface, where a
-      single binary contains many function units.</para> 
+      single binary contains many function units.</para>
 <screen>
-$ hpc 
+$ hpc
 Usage: hpc COMMAND ...
 
 Commands:
@@ -1456,9 +1456,9 @@ Others:
      <para>In general, these options act on .tix file after an
      instrumented binary has generated it, which hpc acting as a
      conduit between the raw .tix file, and the more detailed reports
-     produced. 
+     produced.
        </para>
-         
+
        <para>
                The hpc tool assumes you are in the top-level directory of
                the location where you built your application, and the .tix
@@ -1467,7 +1467,7 @@ Others:
                --srcdir multiple times to analyse programs compiled from
                difference locations, as is typical for packages.
        </para>
-         
+
        <para>
        We now explain in more details the major modes of hpc.
      </para>
@@ -1477,8 +1477,8 @@ Others:
                        all modules and packages are considered in generating report,
                        unless include or exclude are used. The report is a summary
                        unless the --per-module flag is used. The --xml-output option
-                       allows for tools to use hpc to glean coverage. 
-               </para> 
+                       allows for tools to use hpc to glean coverage.
+               </para>
 <screen>
 $ hpc help report
 Usage: hpc report [OPTION] .. &lt;TIX_FILE&gt; [&lt;MODULE&gt; [&lt;MODULE&gt; ..]]
@@ -1518,8 +1518,8 @@ Options:
 
        </sect3>
        <sect3><title>hpc sum</title>
-               <para>hpc sum adds together any number of .tix files into a single 
-               .tix file. hpc sum does not change the original .tix file; it generates a new .tix file. 
+               <para>hpc sum adds together any number of .tix files into a single
+               .tix file. hpc sum does not change the original .tix file; it generates a new .tix file.
                </para>
 <screen>
 $ hpc help sum
@@ -1535,10 +1535,10 @@ Options:
 </screen>
        </sect3>
        <sect3><title>hpc combine</title>
-               <para>hpc combine is the swiss army knife of hpc. It can be 
+               <para>hpc combine is the swiss army knife of hpc. It can be
                 used to take the difference between .tix files, to subtract one
                .tix file from another, or to add two .tix files. hpc combine does not
-               change the original .tix file; it generates a new .tix file. 
+               change the original .tix file; it generates a new .tix file.
                </para>
 <screen>
 $ hpc help combine
@@ -1557,11 +1557,11 @@ Options:
        </sect3>
        <sect3><title>hpc map</title>
                <para>hpc map inverts or zeros a .tix file. hpc map does not
-               change the original .tix file; it generates a new .tix file. 
+               change the original .tix file; it generates a new .tix file.
                </para>
 <screen>
 $ hpc help map
-Usage: hpc map [OPTION] .. &lt;TIX_FILE&gt; 
+Usage: hpc map [OPTION] .. &lt;TIX_FILE&gt;
 Map a function over a single .tix file
 
 Options:
@@ -1591,7 +1591,7 @@ Options:
     --hpcdir=DIR   sub-directory that contains .mix files
                    default .hpc [rarely used]
     --output=FILE  output FILE
-% hpc help draft  
+% hpc help draft
 Usage: hpc draft [OPTION] .. &lt;TIX_FILE&gt;
 
 Options:
@@ -1660,7 +1660,7 @@ Options:
             for <option>-debug</option> at link-time).  This links in
             the debug version of the RTS, which includes the code for
             aggregating and reporting the results of ticky-ticky
-            profilng.
+            profiling.
           </para>
         </listitem>
         <listitem>
@@ -1678,7 +1678,7 @@ Options:
       the invocation
       <command>foo +RTS -rfoo.ticky</command>.
       </para>
-    
+
 <screen>
  foo +RTS -rfoo.ticky
 
index be341b2..defae22 100644 (file)
@@ -329,7 +329,7 @@ char *ghc_rts_opts = "-H128m -K1m";
            with a message like &ldquo;<literal>failed to mmap() memory below 2Gb</literal>&rdquo;.  If you need to use this option to get GHCi working
            on your machine, please file a bug.
          </para>
-         
+
          <para>
            On 64-bit machines, the RTS needs to allocate memory in the
            low 2Gb of the address space.  Support for this across
@@ -495,7 +495,7 @@ char *ghc_rts_opts = "-H128m -K1m";
             generation <replaceable>gen</replaceable> and higher.
             Omitting <replaceable>gen</replaceable> turns off the
             parallel GC completely, reverting to sequential GC.</para>
-          
+
           <para>The default parallel GC settings are usually suitable
             for parallel programs (i.e. those
             using <literal>par</literal>, Strategies, or with multiple
@@ -509,7 +509,7 @@ char *ghc_rts_opts = "-H128m -K1m";
             restrict parallel GC to the old generation
             with <literal>-qg1</literal>.</para>
         </listitem>
-      </varlistentry>        
+      </varlistentry>
 
       <varlistentry>
         <term>
@@ -524,7 +524,7 @@ char *ghc_rts_opts = "-H128m -K1m";
             generation <replaceable>gen</replaceable> and higher.
             Omitting <replaceable>gen</replaceable> disables
             load-balancing entirely.</para>
-          
+
           <para>
             Load-balancing shares out the work of GC between the
             available cores.  This is a good idea when the heap is
@@ -817,7 +817,7 @@ char *ghc_rts_opts = "-H128m -K1m";
       </listitem>
       <listitem>
         <para>
-          The peak memory the RTS has allocated from the OS. 
+          The peak memory the RTS has allocated from the OS.
         </para>
       </listitem>
       <listitem>
@@ -1012,12 +1012,12 @@ char *ghc_rts_opts = "-H128m -K1m";
       </listitem>
       <listitem>
         <para>
-          How many page faults occured this garbage collection.
+          How many page faults occurred this garbage collection.
         </para>
       </listitem>
       <listitem>
         <para>
-          How many page faults occured since the end of the last garbage
+          How many page faults occurred since the end of the last garbage
           collection.
         </para>
       </listitem>
@@ -1209,7 +1209,7 @@ char *ghc_rts_opts = "-H128m -K1m";
         </term>
        <listitem>
          <para>
-            An RTS debugging flag; only availble if the program was
+            An RTS debugging flag; only available if the program was
            linked with the <option>-debug</option> option.  Various
            values of <replaceable>x</replaceable> are provided to
            enable debug messages and additional runtime sanity checks
index 099a91f..e2c9c33 100644 (file)
          has been specified, then the object filename is
          <replaceable>dir</replaceable>/<replaceable>mod</replaceable>.<replaceable>osuf</replaceable>,
          where <replaceable>mod</replaceable> is the module name with
-         dots replaced by slashes.  GHC will silently create the necessary directory 
+         dots replaced by slashes.  GHC will silently create the necessary directory
           structure underneath <replaceable>dir</replaceable>, if it does not
-          already exist.</para> 
+          already exist.</para>
        </listitem>
       </itemizedlist>
 
           <para>If you use <command>ghc --make</command> and you don't
           use the <option>-o</option>, the name GHC will choose
           for the executable will be based on the name of the file
-          containing the module <literal>Main</literal>. 
+          containing the module <literal>Main</literal>.
           Note that with GHC the <literal>Main</literal> module doesn't
           have to be put in file <filename>Main.hs</filename>.
           Thus both
@@ -433,7 +433,7 @@ $ ghc -c parse/Foo.hs parse/Bar.hs gurgle/Bumble.hs -odir `uname -m`
        </varlistentry>
       </variablelist>
     </sect2>
-  
+
     <sect2 id="keeping-intermediates">
       <title>Keeping Intermediate Files</title>
       <indexterm><primary>intermediate files, saving</primary>
@@ -693,22 +693,22 @@ $ ghc -c parse/Foo.hs parse/Bar.hs gurgle/Bumble.hs -odir `uname -m`
       This section explains how.</para>
 
       <para>Every cycle in the module import graph must be broken by a <filename>hs-boot</filename> file.
-      Suppose that modules <filename>A.hs</filename> and <filename>B.hs</filename> are Haskell source files, 
+      Suppose that modules <filename>A.hs</filename> and <filename>B.hs</filename> are Haskell source files,
       thus:
 <programlisting>
 module A where
     import B( TB(..) )
-    
+
     newtype TA = MkTA Int
-    
+
     f :: TB -&#62; TA
     f (MkTB x) = MkTA x
 
 module B where
     import {-# SOURCE #-} A( TA(..) )
-    
+
     data TB = MkTB !Int
-    
+
     g :: TA -&#62; TB
     g (MkTA x) = MkTB x
 </programlisting>
@@ -750,12 +750,12 @@ module A where
 <programlisting>
   ghc -c A.hs-boot
 </programlisting>
-When a hs-boot file <filename>A.hs-boot</filename> 
+When a hs-boot file <filename>A.hs-boot</filename>
    is compiled, it is checked for scope and type errors.
    When its parent module <filename>A.hs</filename> is compiled, the two are compared, and
    an error is reported if the two are inconsistent.
    </para></listitem>
-   
+
        <listitem>
          <para> Just as compiling <filename>A.hs</filename> produces an
            interface file <filename>A.hi</filename>, and an object file
@@ -793,7 +793,7 @@ When a hs-boot file <filename>A.hs-boot</filename>
    <command>ghc -M</command> will report an error if a cycle is found.
    </para></listitem>
 
-   <listitem><para> A module <literal>M</literal> that is 
+   <listitem><para> A module <literal>M</literal> that is
    <literal>{-# SOURCE #-}</literal>-imported in a program will usually also be
    ordinarily imported elsewhere.  If not, <command>ghc --make</command>
    automatically adds <literal>M</literal> to the set of modules it tries to
@@ -812,9 +812,9 @@ A hs-boot file need only contain the bare
 <para>A hs-boot file is written in a subset of Haskell:
 <itemizedlist>
 <listitem><para> The module header (including the export list), and import statements, are exactly as in
-Haskell, and so are the scoping rules.  
+Haskell, and so are the scoping rules.
    Hence, to mention a non-Prelude type or class, you must import it.</para></listitem>
-   
+
 <listitem><para> There must be no value declarations, but there can be type signatures for
 values.  For example:
 <programlisting>
@@ -823,7 +823,7 @@ values.  For example:
 </para></listitem>
 <listitem><para> Fixity declarations are exactly as in Haskell.</para></listitem>
 <listitem><para> Type synonym declarations are exactly as in Haskell.</para></listitem>
-<listitem><para> A data type declaration can either be given in full, exactly as in Haskell, or it 
+<listitem><para> A data type declaration can either be given in full, exactly as in Haskell, or it
 can be given abstractly, by omitting the '=' sign and everything that follows.  For example:
 <programlisting>
   data T a b
@@ -835,7 +835,7 @@ can be given abstractly, by omitting the '=' sign and everything that follows.
          You <emphasis>can</emphasis> also write out the constructors but, if you do so, you must write
          it out precisely as in its real definition.</para>
          <para>
-           If you do not write out the constructors, you may need to give a kind 
+           If you do not write out the constructors, you may need to give a kind
            annotation (<xref linkend="kinding"/>), to tell
            GHC the kind of the type variable, if it is not "*".  (In source files, this is worked out
            from the way the type variable is used in the constructors.)  For example:
@@ -938,7 +938,7 @@ Foo.o Foo.hc Foo.s    : Baz.hi          # Foo imports Baz
       brought up to date.  To bring it up to date,
       <literal>make</literal> looks for a rule to do so; one of the
       preceding suffix rules does the job nicely.  These dependencies
-      can be generated automatically by <command>ghc</command>; see 
+      can be generated automatically by <command>ghc</command>; see
       <xref linkend="makefile-dependencies"/></para>
 
  </sect2>
@@ -967,7 +967,7 @@ depend :
         <filename>Makefile</filename>.</para>
 
        <para>In general, <command>ghc -M Foo</command> does the following.
-       For each module <literal>M</literal> in the set 
+       For each module <literal>M</literal> in the set
        <literal>Foo</literal> plus all its imports (transitively),
        it adds to the Makefile:
        <itemizedlist>
@@ -990,7 +990,7 @@ M.o : X.hi-boot
        (See <xref linkend="mutual-recursion"/> for details of
        <literal>hi-boot</literal> style interface files.)
       </para></listitem>
-        </itemizedlist> 
+        </itemizedlist>
        If <literal>M</literal> imports multiple modules, then there will
        be multiple lines with <filename>M.o</filename> as the
        target.</para>
@@ -1127,7 +1127,7 @@ just in case they contain an instance declaration that matters to M.  This would
 be a disaster in practice, so GHC tries to be clever. </para>
 
 <para>In particular, if an instance declaration is in the same module as the definition
-of any type or class mentioned in the <emphasis>head</emphasis> of the instance declaration 
+of any type or class mentioned in the <emphasis>head</emphasis> of the instance declaration
 (the part after the &ldquo;<literal>=&gt;</literal>&rdquo;; see <xref linkend="instance-rules"/>), then
 GHC has to visit that interface file anyway.  Example:</para>
 <programlisting>
@@ -1178,8 +1178,8 @@ These considerations lead to the following definition of an orphan module:
   least one <emphasis>orphan rule</emphasis>.</para> </listitem>
 
   <listitem><para> An instance declaration in a module M is an <emphasis>orphan instance</emphasis> if
-  <indexterm><primary>orphan instance</primary></indexterm> 
-<itemizedlist> 
+  <indexterm><primary>orphan instance</primary></indexterm>
+<itemizedlist>
 <listitem><para>
   The class of the instance declaration is not declared in M, and
 </para></listitem>
@@ -1191,7 +1191,7 @@ These considerations lead to the following definition of an orphan module:
        </para></listitem>
   </itemizedlist>
   </para>
-  <para> Only the instance head 
+  <para> Only the instance head
   counts.  In the example above, it is not good enough for C's declaration
   to be in module A; it must be the declaration of D or T.</para>
   </listitem>
@@ -1205,9 +1205,9 @@ These considerations lead to the following definition of an orphan module:
 
 
 
-<para>If you use the flag <option>-fwarn-orphans</option>, GHC will warn you 
+<para>If you use the flag <option>-fwarn-orphans</option>, GHC will warn you
 if you are creating an orphan module.
-Like any warning, you can switch the warning off with <option>-fno-warn-orphans</option>, 
+Like any warning, you can switch the warning off with <option>-fno-warn-orphans</option>,
 and <option>-Werror</option>
 will make the compilation fail if the warning is issued.
 </para>
index 29dcb37..5c258d4 100644 (file)
@@ -113,8 +113,8 @@ ghc --make -dynamic Main.hs
       Building Haskell code into a shared library is a good way to include
       Haskell code in a larger mixed-language project. While with static
       linking it is recommended to use GHC to perform the final link step,
-      with shared libaries a Haskell library can be treated just like any
-      other shared libary. The linking can be done using the normal system C
+      with shared libraries a Haskell library can be treated just like any
+      other shared library. The linking can be done using the normal system C
       compiler or linker.
     </para>
     <para>
@@ -138,7 +138,7 @@ ghc --make -dynamic -shared -fPIC Foo.hs -o libfoo.so
       package. The <literal>-fPIC</literal> flag is required for all code
       that will end up in a shared library. The <literal>-shared</literal>
       flag specifies to make a shared library rather than a program. To make
-      this clearer we can break this down into separate compliation and link
+      this clearer we can break this down into separate compilation and link
       steps:
 <programlisting>
 ghc -dynamic -fPIC -c Foo.hs
@@ -179,7 +179,7 @@ ghc -dynamic -shared Foo.o -o libfoo.so
       is to use a "runtime path" or "rpath" embedded into programs and
       libraries themselves. These paths can either be absolute paths or on at
       least Linux and Solaris they can be paths relative to the program or
-      libary itself. In principle this makes it possible to construct fully
+      library itself. In principle this makes it possible to construct fully
       relocatable sets of programs and libraries.
     </para>
     <para>
index df01521..2828c6a 100644 (file)
@@ -78,7 +78,7 @@ Hello World!</screen>
 
   <sect1>
     <title>Options overview</title>
-    
+
     <para>GHC's behaviour is controlled by
     <firstterm>options</firstterm>, which for historical reasons are
     also sometimes referred to as command-line flags or arguments.
@@ -86,11 +86,11 @@ Hello World!</screen>
 
     <sect2>
       <title>Command-line arguments</title>
-      
+
       <indexterm><primary>structure, command-line</primary></indexterm>
       <indexterm><primary>command-line</primary><secondary>arguments</secondary></indexterm>
       <indexterm><primary>arguments</primary><secondary>command-line</secondary></indexterm>
-      
+
       <para>An invocation of GHC takes the following form:</para>
 
 <screen>
@@ -112,7 +112,7 @@ ghc [argument...]
 
     <sect2 id="source-file-options">
       <title>Command line options in source files</title>
-    
+
       <indexterm><primary>source-file options</primary></indexterm>
 
       <para>Sometimes it is useful to make the connection between a
@@ -130,7 +130,7 @@ ghc [argument...]
 module X where
 ...
 </programlisting>
-      
+
       <para><literal>OPTIONS_GHC</literal> is a <emphasis>file-header pragma</emphasis>
       (see <xref linkend="pragmas"/>).</para>
 
@@ -163,7 +163,7 @@ module X where
       for more details.</para>
     </sect2>
   </sect1>
-    
+
   <sect1 id="static-dynamic-flags">
     <title>Static, Dynamic, and Mode options</title>
     <indexterm><primary>static</primary><secondary>options</secondary>
@@ -204,14 +204,14 @@ module X where
        </listitem>
       </varlistentry>
     </variablelist>
-    
+
     <para>The flag reference tables (<xref
     linkend="flag-reference"/>) lists the status of each flag.</para>
 
     <para>There are a few flags that are static except that they can
     also be used with GHCi's <literal>:set</literal> command; these
     are listed as &ldquo;static/<literal>:set</literal>&rdquo; in the
-    table.</para> 
+    table.</para>
   </sect1>
 
   <sect1 id="file-suffixes">
@@ -266,7 +266,7 @@ module X where
          compiler.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term><filename>.ll</filename></term>
        <listitem>
@@ -336,7 +336,7 @@ module X where
          more detail in <xref linkend="ghci"/>.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>
          <cmdsynopsis><command>ghc &ndash;&ndash;make</command>
@@ -375,7 +375,7 @@ module X where
          more details.</para>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term>
           <cmdsynopsis>
@@ -531,7 +531,7 @@ module X where
       <title>Using <command>ghc</command> <option>&ndash;&ndash;make</option></title>
       <indexterm><primary><option>&ndash;&ndash;make</option></primary></indexterm>
       <indexterm><primary>separate compilation</primary></indexterm>
-      
+
       <para>In this mode, GHC will build a multi-module Haskell program by following
       dependencies from one or more root modules (usually just
       <literal>Main</literal>).  For example, if your
@@ -583,7 +583,7 @@ ghc Main.hs
          source.</para>
        </listitem>
       </itemizedlist>
-      
+
       <para>Any of the command-line options described in the rest of
       this chapter can be used with
       <option>&ndash;&ndash;make</option>, but note that any options
@@ -596,7 +596,7 @@ ghc Main.hs
       (say, some auxiliary C code), then the object files can be
       given on the command line and GHC will include them when linking
       the executable.</para>
-      
+
       <para>Note that GHC can only follow dependencies if it has the
       source file available, so if your program includes a module for
       which there is no source file, even if you have an object and an
@@ -609,7 +609,7 @@ ghc Main.hs
       to add directories to the search path (see <xref
       linkend="search-path"/>).</para>
     </sect2>
-  
+
     <sect2 id="eval-mode">
       <title>Expression evaluation mode</title>
 
@@ -633,7 +633,7 @@ ghc -e <replaceable>expr</replaceable>
 <screen>
 ghc -e Main.main Main.hs
 </screen>
-      
+
       <para>or we can just use this mode to evaluate expressions in
       the context of the <literal>Prelude</literal>:</para>
 
@@ -646,22 +646,22 @@ olleh
 
     <sect2 id="options-order">
       <title>Batch compiler mode</title>
-      
+
       <para>In <emphasis>batch mode</emphasis>, GHC will compile one or more source files
       given on the command line.</para>
-      
+
       <para>The first phase to run is determined by each input-file
       suffix, and the last phase is determined by a flag.  If no
       relevant flag is present, then go all the way through to linking.
       This table summarises:</para>
-      
+
       <informaltable>
        <tgroup cols="4">
          <colspec align="left"/>
          <colspec align="left"/>
          <colspec align="left"/>
          <colspec align="left"/>
-         
+
          <thead>
            <row>
              <entry>Phase of the compilation system</entry>
@@ -677,7 +677,7 @@ olleh
              <entry>-</entry>
              <entry><literal>.hs</literal></entry>
            </row>
-           
+
            <row>
              <entry>C pre-processor (opt.) </entry>
              <entry><literal>.hs</literal> (with
@@ -685,28 +685,28 @@ olleh
              <entry><option>-E</option></entry>
              <entry><literal>.hspp</literal></entry>
            </row>
-           
+
            <row>
              <entry>Haskell compiler</entry>
              <entry><literal>.hs</literal></entry>
              <entry><option>-C</option>, <option>-S</option></entry>
              <entry><literal>.hc</literal>, <literal>.s</literal></entry>
            </row>
-           
+
            <row>
              <entry>C compiler (opt.)</entry>
              <entry><literal>.hc</literal> or <literal>.c</literal></entry>
              <entry><option>-S</option></entry>
              <entry><literal>.s</literal></entry>
            </row>
-           
+
            <row>
              <entry>assembler</entry>
              <entry><literal>.s</literal></entry>
              <entry><option>-c</option></entry>
              <entry><literal>.o</literal></entry>
            </row>
-           
+
            <row>
              <entry>linker</entry>
              <entry><replaceable>other</replaceable></entry>
@@ -716,17 +716,17 @@ olleh
          </tbody>
        </tgroup>
       </informaltable>
-      
+
       <indexterm><primary><option>-C</option></primary></indexterm>
       <indexterm><primary><option>-E</option></primary></indexterm>
       <indexterm><primary><option>-S</option></primary></indexterm>
       <indexterm><primary><option>-c</option></primary></indexterm>
-      
+
       <para>Thus, a common invocation would be: </para>
 
 <screen>
 ghc -c Foo.hs</screen>
-      
+
       <para>to compile the Haskell source file
       <filename>Foo.hs</filename> to an object file
       <filename>Foo.o</filename>.</para>
@@ -741,7 +741,7 @@ ghc -c Foo.hs</screen>
       <option>-cpp</option><indexterm><primary><option>-cpp</option></primary></indexterm>
       flag turns it on.  See <xref linkend="c-pre-processor"/> for more
       details.</para>
-      
+
       <para>Note: The option <option>-E</option><indexterm><primary>-E
       option</primary></indexterm> runs just the pre-processing passes
       of the compiler, dumping the result in a file.</para>
@@ -800,7 +800,7 @@ ghc -c Foo.hs</screen>
           verify.</para>
        </listitem>
       </varlistentry>
-       
+
       <varlistentry>
        <term>
           <option>-v</option><replaceable>n</replaceable>
@@ -812,7 +812,7 @@ ghc -c Foo.hs</screen>
          argument.  Specifying <option>-v</option> on its own is
          equivalent to <option>-v3</option>, and the other levels
          have the following meanings:</para>
-         
+
          <variablelist>
            <varlistentry>
              <term><option>-v0</option></term>
@@ -862,7 +862,7 @@ ghc -c Foo.hs</screen>
          </variablelist>
        </listitem>
       </varlistentry>
-      
+
       <varlistentry>
        <term><option>-ferror-spans</option>
           <indexterm><primary><option>-ferror-spans</option></primary>
@@ -1000,7 +1000,7 @@ ghc -c Foo.hs</screen>
        <term><option>-Werror</option>:</term>
        <listitem>
          <indexterm><primary><option>-Werror</option></primary></indexterm>
-         <para>Makes any warning into a fatal error. Useful so that you don't 
+         <para>Makes any warning into a fatal error. Useful so that you don't
            miss warnings when doing batch compilation. </para>
        </listitem>
       </varlistentry>
@@ -1205,18 +1205,18 @@ foreign import "&amp;f" f :: FunPtr t
       </varlistentry>
 
       <varlistentry>
-       <term><option>-fwarn-incomplete-patterns</option>, 
+       <term><option>-fwarn-incomplete-patterns</option>,
               <option>-fwarn-incomplete-uni-patterns</option>:
-        </term> 
+        </term>
        <listitem>
          <indexterm><primary><option>-fwarn-incomplete-patterns</option></primary></indexterm>
          <indexterm><primary><option>-fwarn-incomplete-uni-patterns</option></primary></indexterm>
          <indexterm><primary>incomplete patterns, warning</primary></indexterm>
          <indexterm><primary>patterns, incomplete</primary></indexterm>
 
-          <para>The option <option>-fwarn-incomplete-patterns</option> warns 
+          <para>The option <option>-fwarn-incomplete-patterns</option> warns
             about places where
-           a pattern-match might fail at runtime.  
+           a pattern-match might fail at runtime.
           The function
           <function>g</function> below will fail when applied to
           non-empty lists, so the compiler will emit a warning about
@@ -1228,7 +1228,7 @@ g [] = 2
          This option isn't enabled by default because it can be
           a bit noisy, and it doesn't always indicate a bug in the
           program.  However, it's generally considered good practice
-          to cover all the cases in your functions, and it is switched 
+          to cover all the cases in your functions, and it is switched
           on by <option>-W</option>.</para>
 
           <para>The flag <option>-fwarn-incomplete-uni-patterns</option> is
@@ -1296,9 +1296,9 @@ f foo = foo { x = 6 }
         </term>
        <listitem>
 
-         <para>This flag warns if you use an unqualified 
+         <para>This flag warns if you use an unqualified
             <literal>import</literal> declaration
-           that does not explicitly list the entities brought into scope. For 
+           that does not explicitly list the entities brought into scope. For
            example
       </para>
 <programlisting>
@@ -1339,7 +1339,7 @@ module M where
                complexFn :: a -> a -> String
                complexFn x y = ... _simpleFn ...
              </programlisting>
-           The idea is that: (a) users of the class will only call <literal>complexFn</literal>; 
+           The idea is that: (a) users of the class will only call <literal>complexFn</literal>;
            never <literal>_simpleFn</literal>; and (b)
            instance declarations can define either <literal>complexFn</literal> or <literal>_simpleFn</literal>.
            </para>
@@ -1379,7 +1379,7 @@ module M where
        <listitem>
          <indexterm><primary><option>-fwarn-name-shadowing</option></primary></indexterm>
          <indexterm><primary>shadowing, warning</primary></indexterm>
-         
+
          <para>This option causes a warning to be emitted whenever an
           inner-scope value has the same name as an outer-scope value,
           i.e. the inner value shadows the outer one.  This can catch
@@ -1400,8 +1400,8 @@ module M where
          <indexterm><primary><option>-fwarn-orphans</option></primary></indexterm>
          <indexterm><primary>orphan instances, warning</primary></indexterm>
          <indexterm><primary>orphan rules, warning</primary></indexterm>
-         
-         <para>This option causes a warning to be emitted whenever the 
+
+         <para>This option causes a warning to be emitted whenever the
            module contains an "orphan" instance declaration or rewrite rule.
            An instance declaration is an orphan if it appears in a module in
            which neither the class nor the type being instanced are declared
@@ -1410,7 +1410,7 @@ module M where
          orphans is called an orphan module.</para>
          <para>The trouble with orphans is that GHC must pro-actively read the interface
            files for all orphan modules, just in case their instances or rules
-           play a role, whether or not the module's interface would otherwise 
+           play a role, whether or not the module's interface would otherwise
            be of any use.  See <xref linkend="orphan-modules"/> for details.
             </para>
        </listitem>
@@ -1498,8 +1498,8 @@ f "2"    = 2
           which are unused.  For top-level functions, the warning is
           only given if the binding is not exported.</para>
          <para>A definition is regarded as "used" if (a) it is exported, or (b) it is
-           mentioned in the right hand side of another definition that is used, or (c) the 
-           function it defines begins with an underscore.  The last case provides a 
+           mentioned in the right hand side of another definition that is used, or (c) the
+           function it defines begins with an underscore.  The last case provides a
            way to suppress unused-binding warnings selectively.  </para>
          <para> Notice that a variable
            is reported as unused even if it appears in the right-hand side of another
@@ -1547,7 +1547,7 @@ f "2"    = 2
          <indexterm><primary>unused do binding, warning</primary></indexterm>
          <indexterm><primary>do binding, unused</primary></indexterm>
 
-         <para>Report expressions occuring in <literal>do</literal> and <literal>mdo</literal> blocks
+         <para>Report expressions occurring in <literal>do</literal> and <literal>mdo</literal> blocks
          that appear to silently throw information away.
           For instance <literal>do { mapM popInt xs ; return 10 }</literal> would report
           the first statement in the <literal>do</literal> block as suspicious,
@@ -1572,7 +1572,7 @@ f "2"    = 2
          <indexterm><primary>apparently erroneous do binding, warning</primary></indexterm>
          <indexterm><primary>do binding, apparently erroneous</primary></indexterm>
 
-         <para>Report expressions occuring in <literal>do</literal> and <literal>mdo</literal> blocks
+         <para>Report expressions occurring in <literal>do</literal> and <literal>mdo</literal> blocks
          that appear to lack a binding.
           For instance <literal>do { return (popInt 10) ; return 10 }</literal> would report
           the first statement in the <literal>do</literal> block as suspicious,
@@ -1858,7 +1858,7 @@ f "2"    = 2
              <literal>State#</literal> token as argument is considered to be
              single-entry, hence it is considered OK to inline things inside
              it.  This can improve performance of IO and ST monad code, but it
-           runs the risk of reducing sharing.</para> 
+           runs the risk of reducing sharing.</para>
          </listitem>
        </varlistentry>
 
@@ -1922,10 +1922,10 @@ f "2"    = 2
            <indexterm><primary>unfolding, controlling</primary></indexterm>
           </term>
          <listitem>
-           <para>(Default: 45) Governs the maximum size that GHC will 
+           <para>(Default: 45) Governs the maximum size that GHC will
             allow a function unfolding to be.   (An unfolding has a
             &ldquo;size&rdquo; that reflects the cost in terms of
-            &ldquo;code bloat&rdquo; of expanding that unfolding at
+            &ldquo;code bloat&rdquo; of expanding that unfolding
             at a call site. A bigger function would be assigned a
             bigger cost.) </para>
 
@@ -1959,10 +1959,10 @@ f "2"    = 2
       </variablelist>
 
     </sect2>
-    
+
   </sect1>
-  
-  &phases;  
+
+  &phases;
 
   &shared_libs;
 
@@ -2022,7 +2022,7 @@ f "2"    = 2
       use GHC to compile and run parallel programs, in <xref
        linkend="lang-parallel" /> we describe the language features that affect
     parallelism.</para>
-    
+
     <sect2 id="parallel-compile-options">
       <title>Compile-time options for SMP parallelism</title>
 
@@ -2030,7 +2030,7 @@ f "2"    = 2
        linked with the <option>-threaded</option> option (see <xref
          linkend="options-linker" />).  Additionally, the following
        compiler options affect parallelism:</para>
-      
+
       <variablelist>
         <varlistentry>
           <term><option>-feager-blackholing</option></term>
@@ -2087,7 +2087,7 @@ f "2"    = 2
                  results you find.</para></footnote>.  For example,
              on a dual-core machine we would probably use
              <literal>+RTS -N2 -RTS</literal>.</para>
-           
+
             <para>Omitting <replaceable>x</replaceable>,
               i.e. <literal>+RTS -N -RTS</literal>, lets the runtime
               choose the value of <replaceable>x</replaceable> itself
@@ -2149,7 +2149,7 @@ f "2"    = 2
         </varlistentry>
        </variablelist>
     </sect2>
-      
+
     <sect2>
       <title>Hints for using SMP parallelism</title>
 
@@ -2216,14 +2216,14 @@ f "2"    = 2
 
   <indexterm><primary>intermediate code generation</primary></indexterm>
 
-  <para>GHC can dump its optimized intermediate code (said to be in &ldquo;Core&rdquo; format) 
+  <para>GHC can dump its optimized intermediate code (said to be in &ldquo;Core&rdquo; format)
   to a file as a side-effect of compilation. Non-GHC back-end tools can read and process Core files; these files have the suffix
   <filename>.hcr</filename>. The Core format is described in <ulink url="../../core.pdf">
-  <citetitle>An External Representation for the GHC Core Language</citetitle></ulink>, 
+  <citetitle>An External Representation for the GHC Core Language</citetitle></ulink>,
   and sample tools
   for manipulating Core files (in Haskell) are available in the
   <ulink url="http://hackage.haskell.org/package/extcore">extcore package on Hackage</ulink>.  Note that the format of <literal>.hcr</literal>
-  files is <emphasis>different</emphasis> from the Core output format that GHC generates 
+  files is <emphasis>different</emphasis> from the Core output format that GHC generates
   for debugging purposes (<xref linkend="options-debugging"/>), though the two formats appear somewhat similar.</para>
 
   <para>The Core format natively supports notes which you can add to
index 44f589a..ad1c788 100644 (file)
@@ -23,7 +23,7 @@ interpret the filename as two, "c:\\Program" and "Files\\Haskell\\Project.hs".
 <!-- not clear whether there are current editions of Win32 OSes that
      doesn't do this by default.
 
-<para> Solution: don't use "Open With...", avoid spaces in file names, 
+<para> Solution: don't use "Open With...", avoid spaces in file names,
 or fiddle with the appropriate registry setting:
 <programlisting>
   HKEY_CLASSES_ROOT\Unknown\shell\openas\command
@@ -152,7 +152,7 @@ cygwin's bash), but what matters here is that - just like any other
 normal windows program - neither GHC nor the executables it produces
 are aware of cygwin's pretended unix hierarchy. GHC will happily
 accept either '/' or '\' as path separators, but it won't know where
-to find <filename>/home/joe/Main.hs</filename> or <filename>/bin/bash</filename> 
+to find <filename>/home/joe/Main.hs</filename> or <filename>/bin/bash</filename>
 or the like. This causes all
 kinds of fun when GHC is used from within cygwin's bash, or in
 make-sessions running under cygwin.
@@ -162,9 +162,9 @@ make-sessions running under cygwin.
 <sect2><title>Things to do</title>
 <itemizedlist>
 <listitem>
-<para> Don't use absolute paths in make, configure &amp; co if there is any chance 
+<para> Don't use absolute paths in make, configure &amp; co if there is any chance
   that those might be passed to GHC (or to GHC-compiled programs). Relative
-  paths are fine because cygwin tools are happy with them and GHC accepts 
+  paths are fine because cygwin tools are happy with them and GHC accepts
   '/' as path-separator. And relative paths don't depend on where cygwin's
   root directory is located, or on which partition or network drive your source
   tree happens to reside, as long as you 'cd' there first.
@@ -175,25 +175,25 @@ make-sessions running under cygwin.
   <literal>ROOT=`pwd`</literal> in makefile hierarchies or configure scripts), cygwin provides
   a tool called <command>cygpath</command> that can convert cygwin's unix-style paths to their
   actual windows-style counterparts. Many cygwin tools actually accept
-  absolute windows-style paths (remember, though, that you either need 
-  to escape '\' or convert '\' to '/'), so you should be fine just using those 
-  everywhere. If you need to use tools that do some kind of path-mangling 
-  that depends on unix-style paths (one fun example is trying to interpret ':' 
-  as a separator in path lists..), you can still try to convert paths using 
+  absolute windows-style paths (remember, though, that you either need
+  to escape '\' or convert '\' to '/'), so you should be fine just using those
+  everywhere. If you need to use tools that do some kind of path-mangling
+  that depends on unix-style paths (one fun example is trying to interpret ':'
+  as a separator in path lists..), you can still try to convert paths using
   <command>cygpath</command> just before they are passed to GHC and friends.
 </para></listitem>
-  
+
 <listitem>
 <para> If you don't have <command>cygpath</command>, you probably don't have cygwin and hence
   no problems with it... unless you want to write one build process for several
   platforms. Again, relative paths are your friend, but if you have to use
   absolute paths, and don't want to use different tools on different platforms,
   you can simply write a short Haskell program to print the current directory
-   (thanks to George Russell for this idea): compiled with GHC, this will give 
-  you the view of the file system that GHC depends on (which will differ 
+   (thanks to George Russell for this idea): compiled with GHC, this will give
+  you the view of the file system that GHC depends on (which will differ
   depending on whether GHC is compiled with cygwin's gcc or mingw's
-  gcc or on a real unix system..) - that little program can also deal with 
-  escaping '\' in paths. Apart from the banner and the startup time, 
+  gcc or on a real unix system..) - that little program can also deal with
+  escaping '\' in paths. Apart from the banner and the startup time,
   something like this would also do:
 <programlisting>
   $ echo "Directory.getCurrentDirectory >>= putStrLn . init . tail . show " | ghci
@@ -258,7 +258,7 @@ cured the problem (it was supposedly fixed some years ago).
 The default on Win32 platforms is to link applications in such a way
 that the executables will use the Prelude and system libraries DLLs,
 rather than contain (large chunks of) them. This is transparent at the
-command-line, so 
+command-line, so
 </para>
 
 <para>
@@ -273,7 +273,7 @@ sh$ ls -l main.exe
 -rwxr-xr-x   1 544      everyone     4608 May  3 17:11 main.exe*
 sh$ ./main
 hello, world!
-sh$ 
+sh$
 </screen>
 </para>
 
index 9c0ec9e..24181d3 100644 (file)
@@ -1585,8 +1585,6 @@ void freeWin32ProgArgv (void);
 void
 freeWin32ProgArgv (void)
 {
-    freeArgv(win32_prog_argc, win32_prog_argv);
-
     int i;
 
     if (win32_prog_argv != NULL) {
index aeae1d4..a35a962 100644 (file)
@@ -230,8 +230,40 @@ threadPaused(Capability *cap, StgTSO *tso)
 #ifdef THREADED_RTS
         retry:
 #endif
-           if (bh_info == &stg_BLACKHOLE_info ||
-                bh_info == &stg_WHITEHOLE_info)
+            // If the info table is a WHITEHOLE or a BLACKHOLE, then
+            // another thread has claimed it (via the SET_INFO()
+            // below), or is in the process of doing so.  In that case
+            // we want to suspend the work that the current thread has
+            // done on this thunk and wait until the other thread has
+            // finished.
+            //
+            // If eager blackholing is taking place, it could be the
+            // case that the blackhole points to the current
+            // TSO. e.g.:
+            //
+            //    this thread                   other thread
+            //    --------------------------------------------------------
+            //                                  c->indirectee = other_tso;
+            //                                  c->header.info = EAGER_BH
+            //                                  threadPaused():
+            //                                    c->header.info = WHITEHOLE
+            //                                    c->indirectee = other_tso
+            //    c->indirectee = this_tso;
+            //    c->header.info = EAGER_BH
+            //                                    c->header.info = BLACKHOLE
+            //    threadPaused()
+            //    *** c->header.info is now BLACKHOLE,
+            //        c->indirectee  points to this_tso
+            //
+            // So in this case do *not* suspend the work of the
+            // current thread, because the current thread will become
+            // deadlocked on itself.  See #5226 for an instance of
+            // this bug.
+            //
+            if ((bh_info == &stg_WHITEHOLE_info ||
+                 bh_info == &stg_BLACKHOLE_info)
+                &&
+                ((StgInd*)bh)->indirectee != (StgClosure*)tso)
             {
                debugTrace(DEBUG_squeeze,
                           "suspending duplicate work: %ld words of stack",
index e472c5a..70f4a39 100644 (file)
@@ -267,16 +267,18 @@ void traceCapsetModify_ (EventTypeNum tag,
         tracePreface();
         switch (tag) {
         case EVENT_CAPSET_CREATE:   // (capset, capset_type)
-            debugBelch("created capset %d of type %d\n", capset, other);
+            debugBelch("created capset %lu of type %d\n", (lnat)capset, (int)other);
             break;
         case EVENT_CAPSET_DELETE:   // (capset)
-            debugBelch("deleted capset %d\n", capset);
+            debugBelch("deleted capset %lu\n", (lnat)capset);
             break;
         case EVENT_CAPSET_ASSIGN_CAP:  // (capset, capno)
-            debugBelch("assigned cap %d to capset %d\n", other, capset);
+            debugBelch("assigned cap %lu to capset %lu\n",
+                       (lnat)other, (lnat)capset);
             break;
         case EVENT_CAPSET_REMOVE_CAP:  // (capset, capno)
-            debugBelch("removed cap %d from capset %d\n", other, capset);
+            debugBelch("removed cap %lu from capset %lu\n",
+                       (lnat)other, (lnat)capset);
             break;
         }
         RELEASE_LOCK(&trace_utx);
index abfb4eb..cea313e 100644 (file)
@@ -528,7 +528,7 @@ void postCapsetStrEvent (EventTypeNum tag,
                          char *msg)
 {
     int strsize = strlen(msg);
-    int size = strsize + sizeof(EventCapsetID)
+    int size = strsize + sizeof(EventCapsetID);
 
     ACQUIRE_LOCK(&eventBufMutex);
 
index b8a4395..c472096 100644 (file)
@@ -7,6 +7,7 @@
  * ---------------------------------------------------------------------------*/
 
 #include "Rts.h"
+#include "RtsUtils.h"
 #include "GetEnv.h"
 
 #include <windows.h>
@@ -40,10 +41,10 @@ void getProgEnvv(int *out_envc, char **out_envv[]) {
         envc++;
     }
 
-    envv = stgMallocBytes(sizeof(char*) * (envc+1));
+    envv = stgMallocBytes(sizeof(char*) * (envc+1), "getProgEnvv");
 
     i = 0;
-    for (envp = env; *envp != NULL; envp += strlen(envp) + 1) {
+    for (envp = env; *envp != 0; envp += strlen(envp) + 1) {
         envv[i] = envp;
         i++;
     }