[commit: ghc] ghc-7.6: Be lazier when typechecking data type contexts (Trac #7321) (e7be164)

Ian Lynagh <[email protected]>
Newsgroups gmane.comp.lang.haskell.cvs.ghc
Message-ID <[email protected]>
Repository : ssh://darcs.haskell.org//srv/darcs/ghc

On branch  : ghc-7.6

http://hackage.haskell.org/trac/ghc/changeset/e7be164fcd44821af9ffd9b8ec0ff2a0529fa6aa

>---------------------------------------------------------------

commit e7be164fcd44821af9ffd9b8ec0ff2a0529fa6aa
Author: Simon Peyton Jones <[email protected]>
Date:   Fri Oct 12 08:15:44 2012 +0100

    Be lazier when typechecking data type contexts (Trac #7321)
    
    We should be lazy when type-checking the equality-contraint
    part of a data constructor's type, to make the knot-tying
    work out right.  The fact that it's always worked before
    is a fluke: no one else wrote a GADT whose type index mentions
    itself
      data T a wher
        MkT :: T (T Int)

>---------------------------------------------------------------

 compiler/iface/TcIface.lhs |   25 +++++++++++--------------
 1 files changed, 11 insertions(+), 14 deletions(-)

diff --git a/compiler/iface/TcIface.lhs b/compiler/iface/TcIface.lhs
index 80c2029..55b9978 100644
--- a/compiler/iface/TcIface.lhs
+++ b/compiler/iface/TcIface.lhs
@@ -570,20 +570,17 @@ tcIfaceDataCons tycon_name tycon _ if_cons
      = bindIfaceTyVars univ_tvs $ \ univ_tyvars -> do
        bindIfaceTyVars ex_tvs    $ \ ex_tyvars -> do
         { name  <- lookupIfaceTop occ
-        ; eq_spec <- tcIfaceEqSpec spec
-        ; theta <- tcIfaceCtxt ctxt     -- Laziness seems not worth the bother here
-                -- At one stage I thought that this context checking *had*
-                -- to be lazy, because of possible mutual recursion between the
-                -- type and the classe: 
-                -- E.g. 
-                --      class Real a where { toRat :: a -> Ratio Integer }
-                --      data (Real a) => Ratio a = ...
-                -- But now I think that the laziness in checking class ops breaks 
-                -- the loop, so no laziness needed
-
-        -- Read the argument types, but lazily to avoid faulting in
-        -- the component types unless they are really needed
-        ; arg_tys <- forkM (mk_doc name) (mapM tcIfaceType args)
+
+        -- Read the context and argument types, but lazily for two reasons
+        -- (a) to avoid looking tugging on a recursive use of 
+        --     the type itself, which is knot-tied
+        -- (b) to avoid faulting in the component types unless 
+        --     they are really needed
+        ; ~(eq_spec, theta, arg_tys) <- forkM (mk_doc name) $
+             do { eq_spec <- tcIfaceEqSpec spec
+                ; theta   <- tcIfaceCtxt ctxt
+                ; arg_tys <- mapM tcIfaceType args
+                ; return (eq_spec, theta, arg_tys) }
         ; lbl_names <- mapM lookupIfaceTop field_lbls
 
         -- Remember, tycon is the representation tycon
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.