GHC API: How to determine Type.Type equality when using type operators?

Manuel M T Chakravarty chak at
Thu Jul 9 08:27:20 EDT 2009

Christiaan Baaij:
>> I believe that you are asking about type functions.  Specifically,  
>> I think what you are asking is this:
>> How can I normalise a type, by rewriting it exhaustively using
>> the top-level type-function definitions
> That is indeed a better formulation of my original question
>> I think the function TcTyFuns.tcNormaliseFamInst (rather an odd  
>> name!) does this.  But it's not very helpful to you because it's in  
>> the main typechecker monad.
> At the moment it is not such a big problem that it is in the  
> typechecker
> monad, as we run some parts of our compiler in a GHC Monad, and can  
> thus
> initialize a typechecker monad with the function TcRnMonad.initTc.
> However, at the moment I can't get to normalise the types as far as I
> had hoped. Here is an example of my debug output:
> Before normalisation:
> Types.Data.Num.Decimal.Literals.D4
> Types.Data.Num.Ops.:*: Types.Data.Num.Decimal.Literals.D3
> After normalisation:
> Types.Data.Num.Decimal.Digits.Dec
>  (Types.Data.Num.Decimal.Digits.DecN
>   Types.Data.Num.Ops.:. Types.Data.Num.Decimal.Digits.Dec4)
> Types.Data.Num.Ops.:*: Types.Data.Num.Decimal.Digits.Dec
>                         (Types.Data.Num.Decimal.Digits.DecN
>                          Types.Data.Num.Ops.:.  
> Types.Data.Num.Decimal.Digits.Dec3)
> So, currently I can normalize the synonyms D4 and D3, but I can't
> normalize the type function :*:. Maybe it has something to do with  
> how I
> load the module and its dependencies.

Yes, it has something to do with module loading and the type-checker  
monad.  It's not enough to load the modules, you also need to  
initialise those components of the type-checker monad that contain the  
environment of visible type instance declarations.  The component is  
called tcg_fam_inst_env and you can see in the function  
TcRnDriver.tcRnImports how to extend it.  You did well in remembering  
to load the orphan modules, but you also ought to call  
FamInst.checkFamInstConsistency to check for overlapping instances in  
the modules that you are loading (it's used right at the end of  

Hope that helps a bit.


More information about the Glasgow-haskell-users mailing list